From 72244f8b857cc19cad88ed03fa83b6d355f615af Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Tue, 3 Dec 2024 10:57:15 +0100 Subject: [PATCH 001/144] Added new branch with collisionless TC from develop --- src/fluid/braginskii/bragThermalDiffusion.cpp | 2 +- src/fluid/braginskii/bragThermalDiffusion.hpp | 80 ++++++++++++++++--- src/fluid/fluid_defs.hpp | 4 + 3 files changed, 76 insertions(+), 10 deletions(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index 82d5dac94..2d340adb0 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -46,7 +46,7 @@ void BragThermalDiffusion::ShowConfig() { } } -void BragThermalDiffusion::EnrollBragThermalDiffusivity(BragDiffusivityFunc myFunc) { +void BragThermalDiffusion::EnrollBragThermalDiffusivity(FourArrayDiffusivityFunc myFunc) { if(this->status.status != UserDefFunction) { IDEFIX_WARNING("Braginskii thermal diffusivity enrollment requires Hydro/BragThermalDiffusion " "to be set to userdef in .ini file"); diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 1fe774a41..217039994 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -35,11 +35,13 @@ class BragThermalDiffusion { void AddBragDiffusiveFluxLim(int, const real, const IdefixArray4D &); // Enroll user-defined thermal conductivity - void EnrollBragThermalDiffusivity(BragDiffusivityFunc); + void EnrollBragThermalDiffusivity(FourArrayDiffusivityFunc); IdefixArray3D heatSrc; // Source terms of the thermal operator IdefixArray3D knorArr; IdefixArray3D kparArr; + IdefixArray3D alpha; // Transition from Brag to collisionless tc + IdefixArray3D clessQ; // Collisionless tc flux coefficient // pre-computed geometrical factors in non-cartesian geometry IdefixArray1D one_dmu; @@ -50,7 +52,7 @@ class BragThermalDiffusion { // status of the module ParabolicModuleStatus &status; - BragDiffusivityFunc diffusivityFunc; + FourArrayDiffusivityFunc diffusivityFunc; bool haveSlopeLimiter{false}; @@ -110,6 +112,12 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], data->np_tot[JDIR], data->np_tot[IDIR]); + this->alpha = IdefixArray3D("ClessThermalDiffusionAlphaArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->clessQ = IdefixArray3D("ClessThermalDiffusionClessQ",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); } else { IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " "Can only be constant or userdef."); @@ -256,7 +264,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, if(haveThermalDiffusion == UserDefFunction && dir == IDIR) { if(diffusivityFunc) { idfx::pushRegion("UserDef::BragThermalDiffusivityFunction"); - diffusivityFunc(*this->data, t, kparArr, knorArr); + diffusivityFunc(*this->data, t, kparArr, knorArr, alpha, clessQ); idfx::popRegion(); } else { IDEFIX_ERROR("No user-defined thermal diffusion function has been enrolled"); @@ -274,6 +282,8 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, [[maybe_unused]] real dTi, dTj, dTk, dTn; dTi = dTj = dTk = dTn = ZERO_F; + [[maybe_unused]] real dvp, dvm, dpp, dpm, Pn, Vn; /* For the collisionless / saturated flux */ + real locdmax = 0; /////////////////////////////////////////// // IDIR sweep // @@ -292,9 +302,9 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, kpar = kparConstant; } - EXPAND( Bi = BX_I; , - Bj = BY_I; , - Bk = BZ_I; ) + D_EXPAND( Bi = BX_I; , + Bj = BY_I; , + Bk = BZ_I; ) Bn = BX_I; #if GEOMETRY == CARTESIAN @@ -370,7 +380,9 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, } dTi = D_DX_I_T(Vc)/dx1(i); + #if DIMENSIONS >= 2 + if (haveSlopeLimiter) { dTj = 1./x1(i-1)*SL::PLMLim(SL_DY_T(Vc,k,j,i-1)/dx2(j), SL_DY_T(Vc,k,j+1,i-1)/dx2(j+1)); @@ -399,6 +411,22 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, locdmax = FMAX(kpar,knor)/(0.5*(Vc(RHO,k,j,i) + Vc(RHO,k,j,i - 1)))*gamma_m1; dTn = dTi; + + /* For collisionless / saturated heat flux */ + + dvp = Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i); + dvm = Vc(VX1,k,j,i) - Vc(VX1,k,j,i-1); + + dpp = Vc(PRS,k,j,i+1) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); + + if(haveSlopeLimiter) { + Vn = Vc(VX1,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX1,k, j, i) + Vc(VX1,k,j,i+1)); + Pn = 0.5*(Vc(PRS,k, j, i) + Vc(PRS,k,j,i+1)); + } } else if(dir == JDIR) { ////////////// // JDIR @@ -533,6 +561,22 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, locdmax = FMAX(kpar,knor)/(0.5*(Vc(RHO,k,j,i) + Vc(RHO,k,j - 1,i)))*gamma_m1; dTn = dTj; + + /* For the collisionless / saturated flux */ + + dvp = Vc(VX2,k,j+1,i) - Vc(VX2,k,j,i); + dvm = Vc(VX2,k,j,i) - Vc(VX2,k,j-1,i); + + dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); + + if(haveSlopeLimiter) { + Vn = Vc(VX2,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX2,k,j, i) + Vc(VX2,k,j+1,i)); + Pn = 0.5*(Vc(PRS,k,j, i) + Vc(PRS,k,j+1,i)); + } } else if(dir == KDIR) { ////////////// // KDIR @@ -625,11 +669,28 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, locdmax = FMAX(kpar,knor)/(0.5*(Vc(RHO,k,j,i) + Vc(RHO,k-1,j,i)))*gamma_m1; dTn = dTk; + + /* For the collisionless / saturated flux */ + dvp = Vc(VX3,k+1,j,i) - Vc(VX3,k,j,i); + dvm = Vc(VX3,k,j,i) - Vc(VX3,k-1,j,i); + + dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); + + if(haveSlopeLimiter) { + Vn = Vc(VX3,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX3,k,j,i) + Vc(VX3,k+1,j,i)); + Pn = 0.5*(Vc(PRS,k,j,i) + Vc(PRS,k+1,j,i)); + } } // From here, gradients and normal have been computed, so we just need to get the fluxes - bgradT = EXPAND( Bi*dTi , + Bj*dTj, +Bk*dTk); - Bmag = EXPAND( Bi*Bi , + Bj*Bj, + Bk*Bk); + bgradT = D_EXPAND( Bi*dTi , + Bj*dTj, +Bk*dTk); + Bmag = D_EXPAND( Bi*Bi , + Bj*Bj, + Bk*Bk); + //printf("%f , %f\n", Bmag, EXPAND(Bi*Bi, + Bj*Bj, + Bk*Bk)); + //printf("%f , %f \n", 0.5*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i+1)), Vn); Bmag = sqrt(Bmag); Bmag = FMAX(1e-6*SMALL_NUMBER,Bmag); @@ -637,10 +698,11 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bn = Bn/Bmag; /* -- unit vector component -- */ q = kpar*bgradT*bn + knor*(dTn - bn*bgradT); + q = alpha(k,j,i)*q + (1-alpha(k,j,i))*clessQ(k,j,i)*Pn*Vn; Flux(ENG, k, j, i) -= q; - dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax); + dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax)*alpha(k,j,i); }); idfx::popRegion(); } diff --git a/src/fluid/fluid_defs.hpp b/src/fluid/fluid_defs.hpp index 2269fc803..90e18b876 100644 --- a/src/fluid/fluid_defs.hpp +++ b/src/fluid/fluid_defs.hpp @@ -52,6 +52,10 @@ using DiffusivityFunc = void (*) (DataBlock &, const real t, IdefixArray3D using BragDiffusivityFunc = void (*) (DataBlock &, const real t, IdefixArray3D &, IdefixArray3D &); +using FourArrayDiffusivityFunc = void (*) (DataBlock &, const real t, + IdefixArray3D &, IdefixArray3D &, + IdefixArray3D &, IdefixArray3D &); + // Deprecated signatures using SrcTermFuncOld = void (*) (DataBlock &, const real t, const real dt); From cb3bea853eff493db3d5b03f415c0aa98048c90b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Thu, 12 Dec 2024 16:29:24 +0100 Subject: [PATCH 002/144] Fixed undeclared CL arrays (GPU compiling) --- reference | 2 +- src/fluid/braginskii/bragThermalDiffusion.hpp | 2 ++ 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/reference b/reference index b675bceaa..609a60164 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit b675bceaa6aabc01dded346e2d631857f698dc76 +Subproject commit 609a60164461fb2d4fbeffa89ce148acf1191525 diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 217039994..187209ee2 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -260,6 +260,8 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, real kparConstant = this->kpar; IdefixArray3D knorArr = this->knorArr; IdefixArray3D kparArr = this->kparArr; + IdefixArray3D alpha = this->alpha; + IdefixArray3D clessQ = this->clessQ; if(haveThermalDiffusion == UserDefFunction && dir == IDIR) { if(diffusivityFunc) { From 6ec6d0db33c0f1c6ac2637fa400c832ec8a83640 Mon Sep 17 00:00:00 2001 From: Hal Bal Date: Sat, 14 Dec 2024 10:18:43 +0100 Subject: [PATCH 003/144] collisionless tc as an option of bragTDiffusion --- src/fluid/braginskii/bragThermalDiffusion.cpp | 22 ++- src/fluid/braginskii/bragThermalDiffusion.hpp | 155 +++++++++++------- src/fluid/fluid_defs.hpp | 10 +- 3 files changed, 116 insertions(+), 71 deletions(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index 2d340adb0..43477c9d6 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -27,11 +27,17 @@ void BragThermalDiffusion::ShowConfig() { } else if (status.status==UserDefFunction) { idfx::cout << "Braginskii Thermal Diffusion: ENABLED with user-defined diffusivity function." << std::endl; - if(!diffusivityFunc) { + if(!bragDiffusivityFunc) { IDEFIX_ERROR("No braginskii thermal diffusion function has been enrolled"); } + } else if (status.status==CollisionLess) { + idfx::cout << "CollisionLess / Braginskii Thermal Diffusion: ENABLED with user-defined " + "diffusivity function."<< std::endl; + if(!clessDiffusivityFunc) { + IDEFIX_ERROR("No collisionless / Braginskii thermal diffusion function has been enrolled"); + } } else { - IDEFIX_ERROR("Unknown braginskii thermal diffusion mode"); + IDEFIX_ERROR("Unknown Braginskii thermal diffusion mode"); } if(status.isExplicit) { idfx::cout << "Braginskii Thermal Diffusion: uses an explicit time integration." << std::endl; @@ -46,12 +52,20 @@ void BragThermalDiffusion::ShowConfig() { } } -void BragThermalDiffusion::EnrollBragThermalDiffusivity(FourArrayDiffusivityFunc myFunc) { +void BragThermalDiffusion::EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc myFunc) { if(this->status.status != UserDefFunction) { IDEFIX_WARNING("Braginskii thermal diffusivity enrollment requires Hydro/BragThermalDiffusion " "to be set to userdef in .ini file"); } - this->diffusivityFunc = myFunc; + this->bragDiffusivityFunc = myFunc; +} + +void BragThermalDiffusion::EnrollClessThermalDiffusivity(FourArrayDiffusivityFunc myFunc) { + if(this->status.status != UserDefFunction) { + IDEFIX_WARNING("Collisionless/Braginskii thermal diffusivity enrollment requires " + "Hydro/BragThermalDiffusion to be set to collisionless in .ini file"); + } + this->clessDiffusivityFunc = myFunc; } void BragThermalDiffusion::AddBragDiffusiveFlux(int dir, const real t, diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 187209ee2..8cf892e5a 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -35,13 +35,14 @@ class BragThermalDiffusion { void AddBragDiffusiveFluxLim(int, const real, const IdefixArray4D &); // Enroll user-defined thermal conductivity - void EnrollBragThermalDiffusivity(FourArrayDiffusivityFunc); + void EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc); + void EnrollClessThermalDiffusivity(FourArrayDiffusivityFunc); IdefixArray3D heatSrc; // Source terms of the thermal operator IdefixArray3D knorArr; IdefixArray3D kparArr; - IdefixArray3D alpha; // Transition from Brag to collisionless tc - IdefixArray3D clessQ; // Collisionless tc flux coefficient + IdefixArray3D clessAlpha; // Transition from Brag to collisionless tc + IdefixArray3D clessBeta; // Collisionless tc flux coefficient // pre-computed geometrical factors in non-cartesian geometry IdefixArray1D one_dmu; @@ -52,7 +53,10 @@ class BragThermalDiffusion { // status of the module ParabolicModuleStatus &status; - FourArrayDiffusivityFunc diffusivityFunc; + TwoArrayDiffusivityFunc bragDiffusivityFunc; + FourArrayDiffusivityFunc clessDiffusivityFunc; + + bool includeCollisionlessTD{false}; bool haveSlopeLimiter{false}; @@ -107,17 +111,26 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid } else if(input.Get("Hydro","bragTDiffusion",2).compare("userdef") == 0) { this->status.status = UserDefFunction; this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + } else if(input.Get("Hydro","bragTDiffusion",2).compare("collisionless") == 0) { + this->includeCollisionlessTD = true; + this->status.status = CollisionLess; + this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->alpha = IdefixArray3D("ClessThermalDiffusionAlphaArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->clessQ = IdefixArray3D("ClessThermalDiffusionClessQ",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->clessAlpha = IdefixArray3D("ClessThermalDiffusionAlphaArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->clessBeta = IdefixArray3D("ClessThermalDiffusionBetaArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); } else { IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " "Can only be constant or userdef."); @@ -218,6 +231,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, HydroModuleStatus haveThermalDiffusion = this->status.status; bool haveSlopeLimiter = this->haveSlopeLimiter; + bool includeCollisionlessTD = this->includeCollisionlessTD; using SL = SlopeLimiter; int ibeg, iend, jbeg, jend, kbeg, kend; @@ -260,17 +274,26 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, real kparConstant = this->kpar; IdefixArray3D knorArr = this->knorArr; IdefixArray3D kparArr = this->kparArr; - IdefixArray3D alpha = this->alpha; - IdefixArray3D clessQ = this->clessQ; + IdefixArray3D clessAlpha = this->clessAlpha; + IdefixArray3D clessBeta = this->clessBeta; if(haveThermalDiffusion == UserDefFunction && dir == IDIR) { - if(diffusivityFunc) { + if(bragDiffusivityFunc) { idfx::pushRegion("UserDef::BragThermalDiffusivityFunction"); - diffusivityFunc(*this->data, t, kparArr, knorArr, alpha, clessQ); + bragDiffusivityFunc(*this->data, t, kparArr, knorArr); idfx::popRegion(); - } else { + } + else { IDEFIX_ERROR("No user-defined thermal diffusion function has been enrolled"); } + } else if(haveThermalDiffusion == CollisionLess && dir == IDIR) { + if (clessDiffusivityFunc) { + idfx::pushRegion("UserDef::ClessThermalDiffusivityFunction"); + clessDiffusivityFunc(*this->data, t, kparArr, knorArr, clessAlpha, clessBeta); + idfx::popRegion(); + } else { + IDEFIX_ERROR("No user-defined collisionless thermal diffusion function has been enrolled"); + } } idefix_for("BragDiffusiveFlux",kbeg, kend, jbeg, jend, ibeg, iend, @@ -292,7 +315,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, /////////////////////////////////////////// if(dir == IDIR) { - if(haveThermalDiffusion == UserDefFunction) { + if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { knor = HALF_F*(knorArr(k,j,i-1)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k,j,i-1)*kparArr(k,j,i))/(kparArr(k,j,i-1)+kparArr(k,j,i)); @@ -415,26 +438,27 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dTn = dTi; /* For collisionless / saturated heat flux */ - - dvp = Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i); - dvm = Vc(VX1,k,j,i) - Vc(VX1,k,j,i-1); - - dpp = Vc(PRS,k,j,i+1) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); - - if(haveSlopeLimiter) { - Vn = Vc(VX1,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); - } else { - Vn = 0.5*(Vc(VX1,k, j, i) + Vc(VX1,k,j,i+1)); - Pn = 0.5*(Vc(PRS,k, j, i) + Vc(PRS,k,j,i+1)); + if (includeCollisionlessTD) { + dvp = Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i); + dvm = Vc(VX1,k,j,i) - Vc(VX1,k,j,i-1); + + dpp = Vc(PRS,k,j,i+1) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); + + if(haveSlopeLimiter) { + Vn = Vc(VX1,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX1,k, j, i) + Vc(VX1,k,j,i+1)); + Pn = 0.5*(Vc(PRS,k, j, i) + Vc(PRS,k,j,i+1)); + } } } else if(dir == JDIR) { ////////////// // JDIR ///////////// - if(haveThermalDiffusion == UserDefFunction) { + if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { knor = HALF_F*(knorArr(k,j-1,i)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k,j-1,i)*kparArr(k,j,i))/(kparArr(k,j-1,i)+kparArr(k,j,i)); @@ -565,25 +589,26 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dTn = dTj; /* For the collisionless / saturated flux */ - - dvp = Vc(VX2,k,j+1,i) - Vc(VX2,k,j,i); - dvm = Vc(VX2,k,j,i) - Vc(VX2,k,j-1,i); - - dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); - - if(haveSlopeLimiter) { - Vn = Vc(VX2,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); - } else { - Vn = 0.5*(Vc(VX2,k,j, i) + Vc(VX2,k,j+1,i)); - Pn = 0.5*(Vc(PRS,k,j, i) + Vc(PRS,k,j+1,i)); - } + if(includeCollisionlessTD) { + dvp = Vc(VX2,k,j+1,i) - Vc(VX2,k,j,i); + dvm = Vc(VX2,k,j,i) - Vc(VX2,k,j-1,i); + + dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); + + if(haveSlopeLimiter) { + Vn = Vc(VX2,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX2,k,j, i) + Vc(VX2,k,j+1,i)); + Pn = 0.5*(Vc(PRS,k,j, i) + Vc(PRS,k,j+1,i)); + } + } } else if(dir == KDIR) { ////////////// // KDIR ///////////// - if(haveThermalDiffusion == UserDefFunction) { + if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { knor = HALF_F*(knorArr(k-1,j,i)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k-1,j,i)*kparArr(k,j,i))/(kparArr(k-1,j,i)+kparArr(k,j,i)); @@ -673,18 +698,20 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dTn = dTk; /* For the collisionless / saturated flux */ - dvp = Vc(VX3,k+1,j,i) - Vc(VX3,k,j,i); - dvm = Vc(VX3,k,j,i) - Vc(VX3,k-1,j,i); + if(includeCollisionlessTD) { + dvp = Vc(VX3,k+1,j,i) - Vc(VX3,k,j,i); + dvm = Vc(VX3,k,j,i) - Vc(VX3,k-1,j,i); - dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); + dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); - if(haveSlopeLimiter) { - Vn = Vc(VX3,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); - } else { - Vn = 0.5*(Vc(VX3,k,j,i) + Vc(VX3,k+1,j,i)); - Pn = 0.5*(Vc(PRS,k,j,i) + Vc(PRS,k+1,j,i)); + if(haveSlopeLimiter) { + Vn = Vc(VX3,k,j,i)+0.5*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + } else { + Vn = 0.5*(Vc(VX3,k,j,i) + Vc(VX3,k+1,j,i)); + Pn = 0.5*(Vc(PRS,k,j,i) + Vc(PRS,k+1,j,i)); + } } } // From here, gradients and normal have been computed, so we just need to get the fluxes @@ -700,11 +727,15 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bn = Bn/Bmag; /* -- unit vector component -- */ q = kpar*bgradT*bn + knor*(dTn - bn*bgradT); - q = alpha(k,j,i)*q + (1-alpha(k,j,i))*clessQ(k,j,i)*Pn*Vn; - + if(includeCollisionlessTD) { + q = clessAlpha(k,j,i)*q + (1-clessAlpha(k,j,i))*clessBeta(k,j,i)*Pn*Vn; + } Flux(ENG, k, j, i) -= q; + dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax); - dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax)*alpha(k,j,i); + if(includeCollisionlessTD) { + dMax(k,j,i) *= clessAlpha(k,j,i); + } }); idfx::popRegion(); } diff --git a/src/fluid/fluid_defs.hpp b/src/fluid/fluid_defs.hpp index 90e18b876..62a2099c4 100644 --- a/src/fluid/fluid_defs.hpp +++ b/src/fluid/fluid_defs.hpp @@ -25,7 +25,7 @@ class Fluid; // Parabolic terms can have different status -enum HydroModuleStatus {Disabled, Constant, UserDefFunction }; +enum HydroModuleStatus {Disabled, Constant, UserDefFunction, CollisionLess}; // Structure to describe the status of parabolic modules struct ParabolicModuleStatus { @@ -49,12 +49,12 @@ using SrcTermFunc = void (*) (Fluid *, const real t, const real dt); using EmfBoundaryFunc = void (*) (DataBlock &, const real t); using DiffusivityFunc = void (*) (DataBlock &, const real t, IdefixArray3D &); -using BragDiffusivityFunc = void (*) (DataBlock &, const real t, - IdefixArray3D &, IdefixArray3D &); +using TwoArrayDiffusivityFunc = void (*) (DataBlock &, const real t, + IdefixArray3D &, IdefixArray3D &); using FourArrayDiffusivityFunc = void (*) (DataBlock &, const real t, - IdefixArray3D &, IdefixArray3D &, - IdefixArray3D &, IdefixArray3D &); + IdefixArray3D &, IdefixArray3D &, + IdefixArray3D &, IdefixArray3D &); // Deprecated signatures using SrcTermFuncOld = void (*) (DataBlock &, const real t, const real dt); From 9ac669865703c68324b6ef35999cc786deaaf8c7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Mon, 16 Dec 2024 10:32:16 +0100 Subject: [PATCH 004/144] idefix error includes collisionless status --- src/fluid/braginskii/bragThermalDiffusion.hpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 8cf892e5a..ca1cf115d 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -133,7 +133,7 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid data->np_tot[IDIR]); } else { IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " - "Can only be constant or userdef."); + "Can only be constant, userdef or collisionless."); } } else { IDEFIX_ERROR("I cannot create a BragThermalDiffusion object without bragTDiffusion defined" @@ -728,13 +728,13 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bn = Bn/Bmag; /* -- unit vector component -- */ q = kpar*bgradT*bn + knor*(dTn - bn*bgradT); if(includeCollisionlessTD) { - q = clessAlpha(k,j,i)*q + (1-clessAlpha(k,j,i))*clessBeta(k,j,i)*Pn*Vn; + q = clessAlpha(k,j,i)*q + (1-clessAlpha(k,j,i))*clessBeta(k,j,i)*Pn*Vn; } Flux(ENG, k, j, i) -= q; dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax); if(includeCollisionlessTD) { - dMax(k,j,i) *= clessAlpha(k,j,i); + dMax(k,j,i) *= clessAlpha(k,j,i); } }); idfx::popRegion(); From 94a71d229c565fe21be263c4f06d65b4555477ed Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Fri, 20 Dec 2024 15:58:55 +0100 Subject: [PATCH 005/144] Added a saturation option for collisionless formulation --- src/fluid/braginskii/bragThermalDiffusion.cpp | 15 +- src/fluid/braginskii/bragThermalDiffusion.hpp | 164 +++++++++++------- src/fluid/fluid_defs.hpp | 2 +- 3 files changed, 113 insertions(+), 68 deletions(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index 43477c9d6..ee1d5b996 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -27,15 +27,9 @@ void BragThermalDiffusion::ShowConfig() { } else if (status.status==UserDefFunction) { idfx::cout << "Braginskii Thermal Diffusion: ENABLED with user-defined diffusivity function." << std::endl; - if(!bragDiffusivityFunc) { + if(!bragDiffusivityFunc && !clessDiffusivityFunc) { IDEFIX_ERROR("No braginskii thermal diffusion function has been enrolled"); } - } else if (status.status==CollisionLess) { - idfx::cout << "CollisionLess / Braginskii Thermal Diffusion: ENABLED with user-defined " - "diffusivity function."<< std::endl; - if(!clessDiffusivityFunc) { - IDEFIX_ERROR("No collisionless / Braginskii thermal diffusion function has been enrolled"); - } } else { IDEFIX_ERROR("Unknown Braginskii thermal diffusion mode"); } @@ -50,12 +44,15 @@ void BragThermalDiffusion::ShowConfig() { if(haveSlopeLimiter) { idfx::cout << "Braginskii Thermal Diffusion: uses a slope limiter." << std::endl; } + if(includeCollisionlessTD) { + idfx::cout << "Saturation with collisionless flux is enabled." << std::endl; + } } void BragThermalDiffusion::EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc myFunc) { if(this->status.status != UserDefFunction) { IDEFIX_WARNING("Braginskii thermal diffusivity enrollment requires Hydro/BragThermalDiffusion " - "to be set to userdef in .ini file"); + "to be set to userdef in .ini file"); } this->bragDiffusivityFunc = myFunc; } @@ -63,7 +60,7 @@ void BragThermalDiffusion::EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc void BragThermalDiffusion::EnrollClessThermalDiffusivity(FourArrayDiffusivityFunc myFunc) { if(this->status.status != UserDefFunction) { IDEFIX_WARNING("Collisionless/Braginskii thermal diffusivity enrollment requires " - "Hydro/BragThermalDiffusion to be set to collisionless in .ini file"); + "Hydro/BragThermalDiffusion to be set to userdef in .ini file"); } this->clessDiffusivityFunc = myFunc; } diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index ca1cf115d..db01497b7 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -41,8 +41,8 @@ class BragThermalDiffusion { IdefixArray3D heatSrc; // Source terms of the thermal operator IdefixArray3D knorArr; IdefixArray3D kparArr; - IdefixArray3D clessAlpha; // Transition from Brag to collisionless tc - IdefixArray3D clessBeta; // Collisionless tc flux coefficient + IdefixArray3D clessAlphaArr; // Transition from Brag to collisionless tc + IdefixArray3D clessBetaArr; // Collisionless tc flux coefficient (before pv) // pre-computed geometrical factors in non-cartesian geometry IdefixArray1D one_dmu; @@ -67,6 +67,7 @@ class BragThermalDiffusion { // constant diffusion coefficient (when needed) real knor, kpar; + real clessAlpha, clessBeta; // equation of state (required to get the heat capacity) EquationOfState *eos; @@ -104,36 +105,55 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid IDEFIX_ERROR("Unknown braginskii thermal diffusion limiter in idefix.ini. " "Can only be vanleer, mc or nolimiter."); } - if(input.Get("Hydro","bragTDiffusion",2).compare("constant") == 0) { - this->kpar = input.Get("Hydro","bragTDiffusion",3); - this->knor = input.GetOrSet("Hydro","bragTDiffusion",4,0.); - this->status.status = Constant; - } else if(input.Get("Hydro","bragTDiffusion",2).compare("userdef") == 0) { - this->status.status = UserDefFunction; - this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - } else if(input.Get("Hydro","bragTDiffusion",2).compare("collisionless") == 0) { - this->includeCollisionlessTD = true; - this->status.status = CollisionLess; - this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->clessAlpha = IdefixArray3D("ClessThermalDiffusionAlphaArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - this->clessBeta = IdefixArray3D("ClessThermalDiffusionBetaArray",data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); + if(input.Get("Hydro","bragTDiffusion",2).compare("nosat") == 0) { + if(input.Get("Hydro","bragTDiffusion",3).compare("constant") == 0) { + this->kpar = input.Get("Hydro","bragTDiffusion",4); + this->knor = input.GetOrSet("Hydro","bragTDiffusion",5,0.); + this->status.status = Constant; + } else if(input.Get("Hydro","bragTDiffusion",3).compare("userdef") == 0) { + this->status.status = UserDefFunction; + this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + } else { + IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " + "Can only be constant or userdef."); + } + } else if(input.Get("Hydro","bragTDiffusion",2).compare("wcollisionless") == 0.0) { + if(input.Get("Hydro","bragTDiffusion",3).compare("constant") == 0) { + this->includeCollisionlessTD = true; + this->kpar = input.Get("Hydro","bragTDiffusion",4); + this->knor = input.GetOrSet("Hydro","bragTDiffusion",5,0.); + this->clessAlpha = input.GetOrSet("Hydro","bragTDiffusion",6,1.); + this->clessBeta = input.GetOrSet("Hydro","bragTDiffusion",7,0.); + this->status.status = Constant; + } else if(input.Get("Hydro","bragTDiffusion",3).compare("userdef") == 0) { + this->includeCollisionlessTD = true; + this->status.status = UserDefFunction; + this->kparArr = IdefixArray3D("BragThermalDiffusionKparArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->knorArr = IdefixArray3D("BragThermalDiffusionKnorArray",data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->clessAlphaArr = IdefixArray3D("ClessThermalDiffusionAlphaArray", + data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + this->clessBetaArr = IdefixArray3D("ClessThermalDiffusionBetaArray", + data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + } else { + IDEFIX_ERROR("Unknown braginskii/collsiionless thermal diffusion definition in idefix.ini. " + "Can only be constant or userdef."); + } } else { - IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " - "Can only be constant, userdef or collisionless."); + IDEFIX_ERROR("Unknown braginskii thermal diffusion saturation in idefix.ini. " + "Can only be nosat or wcollisionless."); } } else { IDEFIX_ERROR("I cannot create a BragThermalDiffusion object without bragTDiffusion defined" @@ -156,7 +176,7 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid // and therefore not available as such in the DataBlock. // It is rather defined as PRS/RHO. // Special spatial derivative macros are therefore needed and defined here -// directly at the right cell interface according to the direciton of the flux. +// directly at the right cell interface according to the direction of the flux. #define D_DX_I_T(q) (q(PRS,k,j,i)/q(RHO,k,j,i) - q(PRS,k,j,i - 1)/q(RHO,k,j,i - 1)) #define D_DY_J_T(q) (q(PRS,k,j,i)/q(RHO,k,j,i) - q(PRS,k,j - 1,i)/q(RHO,k,j - 1,i)) #define D_DZ_K_T(q) (q(PRS,k,j,i)/q(RHO,k,j,i) - q(PRS,k - 1,j,i)/q(RHO,k - 1,j,i)) @@ -272,27 +292,31 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, #endif real knorConstant = this->knor; real kparConstant = this->kpar; + real clessAlphaConst = this->clessAlpha; + real clessBetaConst = this->clessBeta; IdefixArray3D knorArr = this->knorArr; IdefixArray3D kparArr = this->kparArr; - IdefixArray3D clessAlpha = this->clessAlpha; - IdefixArray3D clessBeta = this->clessBeta; + IdefixArray3D clessAlphaArr = this->clessAlphaArr; + IdefixArray3D clessBetaArr = this->clessBetaArr; - if(haveThermalDiffusion == UserDefFunction && dir == IDIR) { + if(includeCollisionlessTD == false && haveThermalDiffusion == UserDefFunction && dir == IDIR) { if(bragDiffusivityFunc) { idfx::pushRegion("UserDef::BragThermalDiffusivityFunction"); bragDiffusivityFunc(*this->data, t, kparArr, knorArr); idfx::popRegion(); } else { - IDEFIX_ERROR("No user-defined thermal diffusion function has been enrolled"); + IDEFIX_ERROR("No user-defined Braginskii thermal diffusion function has been enrolled"); } - } else if(haveThermalDiffusion == CollisionLess && dir == IDIR) { + } else if(includeCollisionlessTD == true && haveThermalDiffusion == UserDefFunction + && dir == IDIR) { if (clessDiffusivityFunc) { idfx::pushRegion("UserDef::ClessThermalDiffusivityFunction"); - clessDiffusivityFunc(*this->data, t, kparArr, knorArr, clessAlpha, clessBeta); + clessDiffusivityFunc(*this->data, t, kparArr, knorArr, clessAlphaArr, clessBetaArr); idfx::popRegion(); } else { - IDEFIX_ERROR("No user-defined collisionless thermal diffusion function has been enrolled"); + IDEFIX_ERROR("No user-defined Braginskii/collisionless " + "thermal diffusion function has been enrolled"); } } @@ -306,8 +330,8 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, [[maybe_unused]] real dTi, dTj, dTk, dTn; dTi = dTj = dTk = dTn = ZERO_F; - - [[maybe_unused]] real dvp, dvm, dpp, dpm, Pn, Vn; /* For the collisionless / saturated flux */ + /* For the collisionless / saturated flux */ + [[maybe_unused]] real clessAlpha, clessBeta, dvp, dvm, dpp, dpm, Pn, Vn; real locdmax = 0; /////////////////////////////////////////// @@ -315,16 +339,24 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, /////////////////////////////////////////// if(dir == IDIR) { - if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { + if(haveThermalDiffusion == UserDefFunction) { knor = HALF_F*(knorArr(k,j,i-1)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k,j,i-1)*kparArr(k,j,i))/(kparArr(k,j,i-1)+kparArr(k,j,i)); } else { kpar = HALF_F*(kparArr(k,j,i-1)+kparArr(k,j,i)); } + if(includeCollisionlessTD) { + clessAlpha=HALF_F*(clessAlphaArr(k,j,i-1)+clessAlphaArr(k,j,i)); + clessBeta=HALF_F*(clessBetaArr(k,j,i-1)+clessAlphaArr(k,j,i)); + } } else { knor = knorConstant; kpar = kparConstant; + if(includeCollisionlessTD) { + clessAlpha=clessAlphaConst; + clessBeta=clessBetaConst; + } } D_EXPAND( Bi = BX_I; , @@ -446,11 +478,11 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); if(haveSlopeLimiter) { - Vn = Vc(VX1,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + Vn = Vc(VX1,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); } else { - Vn = 0.5*(Vc(VX1,k, j, i) + Vc(VX1,k,j,i+1)); - Pn = 0.5*(Vc(PRS,k, j, i) + Vc(PRS,k,j,i+1)); + Vn = HALF_F*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i-1)); + Pn = HALF_F*(Vc(PRS,k,j,i) + Vc(PRS,k,j,i-1)); } } } else if(dir == JDIR) { @@ -458,16 +490,24 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, // JDIR ///////////// - if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { + if(haveThermalDiffusion == UserDefFunction) { knor = HALF_F*(knorArr(k,j-1,i)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k,j-1,i)*kparArr(k,j,i))/(kparArr(k,j-1,i)+kparArr(k,j,i)); } else { kpar = HALF_F*(kparArr(k,j-1,i)+kparArr(k,j,i)); } + if(includeCollisionlessTD) { + clessAlpha=HALF_F*(clessAlphaArr(k,j-1,i)+clessAlphaArr(k,j,i)); + clessBeta=HALF_F*(clessBetaArr(k,j-1,i)+clessAlphaArr(k,j,i)); + } } else { knor = knorConstant; kpar = kparConstant; + if(includeCollisionlessTD) { + clessAlpha=clessAlphaConst; + clessBeta=clessBetaConst; + } } EXPAND( Bi = BX_J; , @@ -597,27 +637,35 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); if(haveSlopeLimiter) { - Vn = Vc(VX2,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + Vn = Vc(VX2,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); } else { - Vn = 0.5*(Vc(VX2,k,j, i) + Vc(VX2,k,j+1,i)); - Pn = 0.5*(Vc(PRS,k,j, i) + Vc(PRS,k,j+1,i)); + Vn = 0.5*(Vc(VX2,k,j-1,i) + Vc(VX2,k,j,i)); + Pn = 0.5*(Vc(PRS,k,j-1,i) + Vc(PRS,k,j,i)); } } } else if(dir == KDIR) { ////////////// // KDIR ///////////// - if(haveThermalDiffusion == UserDefFunction || haveThermalDiffusion == CollisionLess) { + if(haveThermalDiffusion == UserDefFunction) { knor = HALF_F*(knorArr(k-1,j,i)+knorArr(k,j,i)); if(haveSlopeLimiter) { kpar = 2.*(kparArr(k-1,j,i)*kparArr(k,j,i))/(kparArr(k-1,j,i)+kparArr(k,j,i)); } else { kpar = HALF_F*(kparArr(k-1,j,i)+kparArr(k,j,i)); } + if(includeCollisionlessTD) { + clessAlpha=HALF_F*(clessAlphaArr(k-1,j,i)+clessAlphaArr(k,j,i)); + clessBeta=HALF_F*(clessBetaArr(k-1,j,i)+clessBetaArr(k,j,i)); + } } else { knor = knorConstant; kpar = kparConstant; + if(includeCollisionlessTD) { + clessAlpha=clessAlphaConst; + clessBeta=clessBetaConst; + } } Bi = BX_K; @@ -706,11 +754,11 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); if(haveSlopeLimiter) { - Vn = Vc(VX3,k,j,i)+0.5*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)+0.5*SL::PLMLim(dpp, dpm); + Vn = Vc(VX3,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); } else { - Vn = 0.5*(Vc(VX3,k,j,i) + Vc(VX3,k+1,j,i)); - Pn = 0.5*(Vc(PRS,k,j,i) + Vc(PRS,k+1,j,i)); + Vn = HALF_F*(Vc(VX3,k-1,j,i) + Vc(VX3,k,j,i)); + Pn = HALF_F*(Vc(PRS,k-1,j,i) + Vc(PRS,k,j,i)); } } } @@ -728,13 +776,13 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bn = Bn/Bmag; /* -- unit vector component -- */ q = kpar*bgradT*bn + knor*(dTn - bn*bgradT); if(includeCollisionlessTD) { - q = clessAlpha(k,j,i)*q + (1-clessAlpha(k,j,i))*clessBeta(k,j,i)*Pn*Vn; + q = clessAlpha*q + (1-clessAlpha)*clessBeta*Pn*Vn; } Flux(ENG, k, j, i) -= q; dMax(k,j,i) = FMAX(dMax(k,j,i),locdmax); if(includeCollisionlessTD) { - dMax(k,j,i) *= clessAlpha(k,j,i); + dMax(k,j,i) *= clessAlpha; } }); idfx::popRegion(); diff --git a/src/fluid/fluid_defs.hpp b/src/fluid/fluid_defs.hpp index 62a2099c4..1d040071c 100644 --- a/src/fluid/fluid_defs.hpp +++ b/src/fluid/fluid_defs.hpp @@ -25,7 +25,7 @@ class Fluid; // Parabolic terms can have different status -enum HydroModuleStatus {Disabled, Constant, UserDefFunction, CollisionLess}; +enum HydroModuleStatus {Disabled, Constant, UserDefFunction}; // Structure to describe the status of parabolic modules struct ParabolicModuleStatus { From e2f7a9a16bf97e2f76245757bbf91cdba188a120 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 18:07:36 +0100 Subject: [PATCH 006/144] add a column Density example --- test/utils/columnDensity/column.cpp | 215 +++++++++++++++++++++++ test/utils/columnDensity/column.hpp | 48 +++++ test/utils/columnDensity/definitions.hpp | 4 + test/utils/columnDensity/idefix.ini | 24 +++ test/utils/columnDensity/setup.cpp | 154 ++++++++++++++++ 5 files changed, 445 insertions(+) create mode 100644 test/utils/columnDensity/column.cpp create mode 100644 test/utils/columnDensity/column.hpp create mode 100644 test/utils/columnDensity/definitions.hpp create mode 100644 test/utils/columnDensity/idefix.ini create mode 100644 test/utils/columnDensity/setup.cpp diff --git a/test/utils/columnDensity/column.cpp b/test/utils/columnDensity/column.cpp new file mode 100644 index 000000000..9ad4c3573 --- /dev/null +++ b/test/utils/columnDensity/column.cpp @@ -0,0 +1,215 @@ +#include "column.hpp" +#include "loop.hpp" + +Column::Column(int dir, int sign, int variable, DataBlock *data) : direction(dir), sign(sign), variable(variable) { + idfx::pushRegion("Column::Column"); + this->np_tot = data->np_tot; + this->np_int = data->np_int; + this->beg = data->beg; + + if(dir>= DIMENSIONS || dir < IDIR) IDEFIX_ERROR("Unknown direction for Column constructor"); + + // Allocate the array on which we do the average + this->ColumnArray = IdefixArray3D("ColumnArray",np_tot[KDIR], np_tot[JDIR], np_tot[IDIR]); + + // Elementary volumes and area + this->Volume = data->dV; + this->Area = data->A[dir]; + + // allocate helper array + if(dir == IDIR) { + localSum = IdefixArray2D("localSum",np_tot[KDIR], np_tot[JDIR]); + } + if(dir == JDIR) { + localSum = IdefixArray2D("localSum",np_tot[KDIR], np_tot[IDIR]); + } + if(dir == KDIR) { + localSum = IdefixArray2D("localSum",np_tot[JDIR], np_tot[IDIR]); + } + #ifdef WITH_MPI + // Create sub-MPI communicator dedicated to scan + int remainDims[3] = {false, false, false}; + remainDims[dir] = true; + MPI_Cart_sub(data->mygrid->CartComm, remainDims, &this->ColumnComm); + MPI_Comm_rank(this->ColumnComm, &this->MPIrank); + MPI_Comm_size(this->ColumnComm, &this->MPIsize); + + // create MPI class for boundary Xchanges + int ntarget = 0; + std::vector mapVars; + mapVars.push_back(ntarget); + + this->mpi.Init(data->mygrid, mapVars, data->nghost.data(), data->np_int.data()); + this->nproc = data->mygrid->nproc; + #endif + idfx::popRegion(); +} + +void Column::ComputeColumn(IdefixArray4D in) { + idfx::pushRegion("Column::ComputeColumn"); + const int nk = np_int[KDIR]; + const int nj = np_int[JDIR]; + const int ni = np_int[IDIR]; + const int kb = beg[KDIR]; + const int jb = beg[JDIR]; + const int ib = beg[IDIR]; + const int ke = kb+nk; + const int je = jb+nj; + const int ie = ib+ni; + + const int direction = this->direction; + auto column = this->ColumnArray; + auto dV = this->Volume; + auto A = this->Area; + auto localSum = this->localSum; + + const int var = this->variable; + if(direction==IDIR) { + // Inspired from loop.hpp + Kokkos::parallel_for("ColumnX1", team_policy (nk*nj, Kokkos::AUTO), + KOKKOS_LAMBDA (member_type team_member) { + int k = team_member.league_rank() / nj; + int j = team_member.league_rank() - k*nj + jb; + k += kb; + Kokkos::parallel_scan(Kokkos::TeamThreadRange<>(team_member,ib,ie), + [=] (int i, real &partial_sum, bool is_final) { + partial_sum += in(var,k,j,i)*dV(k,j,i) / (0.5*(A(k,j,i)+A(k,j,i+1))); + if(is_final) column(k,j,i) = partial_sum; + //partial_sum += in(var,k,j,i)*dV(k,j,i) / (0.5*(A(k,j,i)+A(k,j,i+1))); + }); + }); + } + if(direction==JDIR) { + // Inspired from loop.hpp + Kokkos::parallel_for("ColumnX2", team_policy (nk*ni, Kokkos::AUTO), + KOKKOS_LAMBDA (member_type team_member) { + int k = team_member.league_rank() / ni; + int i = team_member.league_rank() - k*ni + ib; + k += kb; + Kokkos::parallel_scan(Kokkos::TeamThreadRange<>(team_member,jb,je), + [=] (int j, real &partial_sum, bool is_final) { + partial_sum += in(var,k,j,i)*dV(k,j,i) / (0.5*(A(k,j,i)+A(k,j+1,i))); + if(is_final) column(k,j,i) = partial_sum; + }); + }); + } + if(direction==KDIR) { + // Inspired from loop.hpp + Kokkos::parallel_for("ColumnX2", team_policy (nj*ni, Kokkos::AUTO), + KOKKOS_LAMBDA (member_type team_member) { + int j = team_member.league_rank() / ni; + int i = team_member.league_rank() - j*ni + ib; + j += jb; + Kokkos::parallel_scan(Kokkos::TeamThreadRange<>(team_member,kb,ke), + [=] (int k, real &partial_sum, bool is_final) { + partial_sum += in(var,k,j,i)*dV(k,j,i) / (0.5*(A(k,j,i)+A(k+1,j,i))); + if(is_final) column(k,j,i) = partial_sum; + }); + }); + } + + #ifdef WITH_MPI + // Load the current sum + int dst,src; + MPI_Cart_shift(this->ColumnComm,0, 1, &src, &dst); + int size = localSum.extent(0)*localSum.extent(1); + if(MPIrank>0) { + MPI_Status status; + // Get the cumulative sum from previous processes + Kokkos::fence(); + MPI_Recv(localSum.data(), size, realMPI, src, 20, ColumnComm, &status); + // Add this to our cumulative sum + idefix_for("Addsum",kb,ke,jb,je,ib,ie, + KOKKOS_LAMBDA(int k, int j, int i) { + if(direction == IDIR) column(k,j,i) += localSum(k,j); + if(direction == JDIR) column(k,j,i) += localSum(k,i); + if(direction == KDIR) column(k,j,i) += localSum(j,i); + }); + } // rank =0 + // Get the final sum + if(MPIrank < MPIsize-1) { + if(direction==IDIR) { + idefix_for("Loadsum",kb,ke,jb,je, + KOKKOS_LAMBDA(int k, int j) { + localSum(k,j) = column(k,j,ie-1); + }); + } + if(direction==JDIR) { + idefix_for("Loadsum",kb,ke,ib,ie, + KOKKOS_LAMBDA(int k, int i) { + localSum(k,i) = column(k,je-1,i); + }); + } + if(direction==KDIR) { + idefix_for("Loadsum",jb,je,ib,ie, + KOKKOS_LAMBDA(int j, int i) { + localSum(j,i) = column(ke-1,j,i); + }); + } + // And send it + Kokkos::fence(); + MPI_Send(localSum.data(),size, realMPI, dst, 20, ColumnComm); + } // MPIrank small enough + #endif + // If we need it backwards + if(sign<0) { + // Compute total cumulative sum in the last subdomain + if(direction == IDIR) { + idefix_for("Loadsum",kb,ke,jb,je, + KOKKOS_LAMBDA(int k, int j) { + localSum(k,j) = column(k,j,ie-1) + in(var,k,j,ie-1) * dV(k,j,ie-1) / (0.5*(A(k,j,ie-1)+A(k,j,ie))); + }); + } + if(direction == JDIR) { + idefix_for("Loadsum",kb,ke,ib,ie, + KOKKOS_LAMBDA(int k, int i) { + localSum(k,i) = column(k,je-1,i) + in(var,k,je-1,i) * dV(k,je-1,i) / (0.5*(A(k,je-1,i)+A(k,je,i))); + }); + } + if(direction == KDIR) { + idefix_for("Loadsum",jb,je,ib,ie, + KOKKOS_LAMBDA(int j, int i) { + localSum(j,i) = column(ke-1,j,i) + in(var,ke-1,j,i) * dV(ke-1,j,i) / (0.5*(A(ke-1,j,i)+A(ke,j,i))); + }); + } + + #ifdef WITH_MPI + Kokkos::fence(); + MPI_Bcast(localSum.data(),size, realMPI, MPIsize-1, ColumnComm); + #endif + // All substract the local column from the full column + + idefix_for("Subsum",kb,ke,jb,je,ib,ie, + KOKKOS_LAMBDA(int k, int j, int i) { + if(direction==IDIR) column(k,j,i) = localSum(k,j)-column(k,j,i); + if(direction==JDIR) column(k,j,i) = localSum(k,i)-column(k,j,i); + if(direction==KDIR) column(k,j,i) = localSum(j,i)-column(k,j,i); + }); + } // sign <0 + // Xchange boundary elements when using MPI to ensure that column + // density in the ghost zones are coherent + #ifdef WITH_MPI + // Create a 4D array that contains our column data + this->arr4D = IdefixArray4D (column.data(), 1, this->np_tot[KDIR], + this->np_tot[JDIR], + this->np_tot[IDIR]); + + for(int dir = 0 ; dir < DIMENSIONS ; dir++) { + // MPI Exchange data when needed + if(nproc[dir]>1) { + switch(dir) { + case 0: + this->mpi.ExchangeX1(this->arr4D); + break; + case 1: + this->mpi.ExchangeX2(this->arr4D); + break; + case 2: + this->mpi.ExchangeX3(this->arr4D); + break; + } + } + } + #endif + idfx::popRegion(); +} diff --git a/test/utils/columnDensity/column.hpp b/test/utils/columnDensity/column.hpp new file mode 100644 index 000000000..b4cc5b539 --- /dev/null +++ b/test/utils/columnDensity/column.hpp @@ -0,0 +1,48 @@ +#ifndef COLUMN_HPP_ +#define COLUMN_HPP_ + +#include "idefix.hpp" +#include "input.hpp" +#include "output.hpp" +#include "grid.hpp" +#include "dataBlock.hpp" +#include "dataBlockHost.hpp" +#include +#include + + + +class Column { + public: + // Constructor from Setup arguments + Column(int dir, int sign, int variable, DataBlock *); + void ComputeColumn(IdefixArray4D in); + IdefixArray3D GetColumn() { + return (this->ColumnArray); + } + private: + IdefixArray3D ColumnArray; + int direction; // The direction along which the column is computed + int sign; // whether we integrate from the left or from the right + int variable; // The variable we use to compute the column + std::array np_tot; + std::array np_int; + std::array beg; + + IdefixArray3D Area; + IdefixArray3D Volume; + + IdefixArray2D localSum; + #ifdef WITH_MPI + Mpi mpi; // Mpi object when WITH_MPI is set + MPI_Comm ColumnComm; + int MPIrank; + int MPIsize; + + IdefixArray4D arr4D; // Dummy array 4D used for MPI xchanges + std::array nproc; // 3D size of the MPI cartesian geometry + + #endif +}; + +#endif // COLUMN_HPP_ diff --git a/test/utils/columnDensity/definitions.hpp b/test/utils/columnDensity/definitions.hpp new file mode 100644 index 000000000..3b581bd62 --- /dev/null +++ b/test/utils/columnDensity/definitions.hpp @@ -0,0 +1,4 @@ +#define COMPONENTS 3 +#define DIMENSIONS 3 + +#define GEOMETRY CARTESIAN diff --git a/test/utils/columnDensity/idefix.ini b/test/utils/columnDensity/idefix.ini new file mode 100644 index 000000000..2d994315c --- /dev/null +++ b/test/utils/columnDensity/idefix.ini @@ -0,0 +1,24 @@ +[Grid] +X1-grid 1 0.0 64 u 1.0 +X2-grid 1 0.0 64 u 1.0 +X3-grid 1 0.0 64 u 1.0 + +[TimeIntegrator] +CFL 0.8 +tstop 0.0 +nstages 2 + +[Hydro] +solver hllc +gamma 1.4 + +[Boundary] +X1-beg periodic +X1-end periodic +X2-beg periodic +X2-end periodic +X3-beg periodic +X3-end periodic + +[Output] +analysis 0.01 diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp new file mode 100644 index 000000000..73d98cbae --- /dev/null +++ b/test/utils/columnDensity/setup.cpp @@ -0,0 +1,154 @@ +#include "idefix.hpp" +#include "setup.hpp" +#include "column.hpp" + + +Column *columnX1Left; +Column *columnX1Right; +Column *columnX2Left; +Column *columnX2Right; +Column *columnX3Left; +Column *columnX3Right; + +// Analyse data to check that column density works as expected +void Analysis(DataBlock & data) { + + DataBlockHost d(data); + + columnX1Left->ComputeColumn(data.hydro->Vc); + columnX1Right->ComputeColumn(data.hydro->Vc); + columnX2Left->ComputeColumn(data.hydro->Vc); + columnX2Right->ComputeColumn(data.hydro->Vc); + columnX3Left->ComputeColumn(data.hydro->Vc); + columnX3Right->ComputeColumn(data.hydro->Vc); + + IdefixArray3D columnDensityLeft, columnDensityRight; + IdefixArray3D::HostMirror columnDensityLeftHost, columnDensityRightHost; + // IDIR + columnDensityLeft = columnX1Left->GetColumn(); + columnDensityRight = columnX1Right->GetColumn(); + columnDensityLeftHost = Kokkos::create_mirror_view(columnDensityLeft); + columnDensityRightHost = Kokkos::create_mirror_view(columnDensityRight); + Kokkos::deep_copy(columnDensityLeftHost,columnDensityLeft); + Kokkos::deep_copy(columnDensityRightHost,columnDensityRight); + + real errMax = 0.0; + + for(int k = data.beg[KDIR]; k < data.end[KDIR] ; k++) { + for(int j = data.beg[JDIR]; j < data.end[JDIR] ; j++) { + for(int i = data.beg[IDIR]; i < data.end[IDIR] ; i++) { + real err = std::fabs(columnDensityLeftHost(k,j,i)-d.xr[IDIR](i)); + if(err>errMax) errMax=err; + err = std::fabs(columnDensityRightHost(k,j,i)-(1-d.xl[IDIR](i))); + if(err>errMax) errMax=err; + } + } + } + idfx::cout << "Error on column density in IDIR=" << std::scientific << errMax << std::endl; + if(errMax>1e-14) { + IDEFIX_ERROR("Error above tolerance"); + } + // JDIR + columnDensityLeft = columnX2Left->GetColumn(); + columnDensityRight = columnX2Right->GetColumn(); + columnDensityLeftHost = Kokkos::create_mirror_view(columnDensityLeft); + columnDensityRightHost = Kokkos::create_mirror_view(columnDensityRight); + Kokkos::deep_copy(columnDensityLeftHost,columnDensityLeft); + Kokkos::deep_copy(columnDensityRightHost,columnDensityRight); + + errMax = 0.0; + + for(int k = data.beg[KDIR]; k < data.end[KDIR] ; k++) { + for(int j = data.beg[JDIR]; j < data.end[JDIR] ; j++) { + for(int i = data.beg[IDIR]; i < data.end[IDIR] ; i++) { + real err = std::fabs(columnDensityLeftHost(k,j,i)-d.xr[JDIR](j)); + if(err>errMax) errMax=err; + err = std::fabs(columnDensityRightHost(k,j,i)-(1-d.xl[JDIR](j))); + if(err>errMax) errMax=err; + } + } + } + idfx::cout << "Error on column density in JDIR=" << std::scientific << errMax << std::endl; + if(errMax>1e-14) { + IDEFIX_ERROR("Error above tolerance"); + } + // KDIR + columnDensityLeft = columnX3Left->GetColumn(); + columnDensityRight = columnX3Right->GetColumn(); + columnDensityLeftHost = Kokkos::create_mirror_view(columnDensityLeft); + columnDensityRightHost = Kokkos::create_mirror_view(columnDensityRight); + Kokkos::deep_copy(columnDensityLeftHost,columnDensityLeft); + Kokkos::deep_copy(columnDensityRightHost,columnDensityRight); + + errMax = 0.0; + + for(int k = data.beg[KDIR]; k < data.end[KDIR] ; k++) { + for(int j = data.beg[JDIR]; j < data.end[JDIR] ; j++) { + for(int i = data.beg[IDIR]; i < data.end[IDIR] ; i++) { + real err = std::fabs(columnDensityLeftHost(k,j,i)-d.xr[KDIR](k)); + if(err>errMax) errMax=err; + err = std::fabs(columnDensityRightHost(k,j,i)-(1-d.xl[KDIR](k))); + if(err>errMax) errMax=err; + } + } + } + idfx::cout << "Error on column density in KDIR=" << std::scientific << errMax << std::endl; + if(errMax>1e-14) { + IDEFIX_ERROR("Error above tolerance"); + } + +} + +void InternalBoundary(Fluid * hydro, const real t) { + IdefixArray4D Vc = hydro->Vc; + idefix_for("InternalBoundary",0,hydro->data->np_tot[KDIR], + 0,hydro->data->np_tot[JDIR], + 0,hydro->data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + // Cancel any motion that could be happening + Vc(VX1,k,j,i) = 0.0; + Vc(VX2,k,j,i) = 0.0; + Vc(VX3,k,j,i) = 0.0; + }); +} + + +// Initialisation routine. Can be used to allocate +// Arrays or variables which are used later on +Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { + output.EnrollAnalysis(&Analysis); + data.hydro->EnrollInternalBoundary(&InternalBoundary); + + columnX1Left = new Column(IDIR, 1, RHO, &data); + columnX1Right = new Column(IDIR, -1, RHO, &data); + columnX2Left = new Column(JDIR, 1, RHO, &data); + columnX2Right = new Column(JDIR, -1, RHO, &data); + columnX3Left = new Column(KDIR, 1, RHO, &data); + columnX3Right = new Column(KDIR, -1, RHO, &data); + // Initialise the output file +} + +// This routine initialize the flow +// Note that data is on the device. +// One can therefore define locally +// a datahost and sync it, if needed +void Setup::InitFlow(DataBlock &data) { + // Create a host copy + DataBlockHost d(data); + + + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + + d.Vc(RHO,k,j,i) = 1.0; + d.Vc(VX1,k,j,i) = ZERO_F; + d.Vc(PRS,k,j,i) = 1.0; + + } + } + } + + // Send it all, if needed + d.SyncToDevice(); +} From 26ffc60820205069aa7c810cbd2375e42a2ac855 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 18:15:31 +0100 Subject: [PATCH 007/144] add some documentation --- test/utils/columnDensity/column.hpp | 8 ++++++-- test/utils/columnDensity/setup.cpp | 5 +++++ 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/test/utils/columnDensity/column.hpp b/test/utils/columnDensity/column.hpp index b4cc5b539..9defe7c6b 100644 --- a/test/utils/columnDensity/column.hpp +++ b/test/utils/columnDensity/column.hpp @@ -11,15 +11,19 @@ #include - +// A class to implement a parralel cumulative sum class Column { public: // Constructor from Setup arguments Column(int dir, int sign, int variable, DataBlock *); + // dir : direction along which the integration is performed + // sign: +1 for an integration from left to right, -1 for an integration from right to left (backwards) + // variable: index of the variable along which we do the integral (since the intput array is 4D) void ComputeColumn(IdefixArray4D in); + // Effectively compute integral from the input array in parameter IdefixArray3D GetColumn() { return (this->ColumnArray); - } + }// Return the column density private: IdefixArray3D ColumnArray; int direction; // The direction along which the column is computed diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp index 73d98cbae..ebc131de7 100644 --- a/test/utils/columnDensity/setup.cpp +++ b/test/utils/columnDensity/setup.cpp @@ -34,6 +34,11 @@ void Analysis(DataBlock & data) { real errMax = 0.0; + // Because this particular setup has a constant density =1, we expect + // the column density from the left to match the cell right coordinates, + // and the column density from the right to match L-the cell left coordinate (where L is the box size) + // here we have L=1 + // This routine checks that all of the available column densities do match the expected values. for(int k = data.beg[KDIR]; k < data.end[KDIR] ; k++) { for(int j = data.beg[JDIR]; j < data.end[JDIR] ; j++) { for(int i = data.beg[IDIR]; i < data.end[IDIR] ; i++) { From a1e6e674743123cb73eee86d4833faaebc73e743 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 18:18:40 +0100 Subject: [PATCH 008/144] add it to the tests --- .github/workflows/idefix-ci-jobs.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index c0e622966..dfb89e0fb 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -201,3 +201,5 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/lookupTable -all $TESTME_OPTIONS - name: Dump Image run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/dumpImage -all $TESTME_OPTIONS + - name: Column density + run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/columnDensity -all $TESTME_OPTIONS From 9c58596070646975bb7c3c3295904aa80ee34c1f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 18:36:28 +0100 Subject: [PATCH 009/144] imrove documentation --- src/utils/CMakeLists.txt | 2 + .../columnDensity => src/utils}/column.cpp | 30 ++++++-- src/utils/column.hpp | 69 +++++++++++++++++++ test/utils/columnDensity/column.hpp | 52 -------------- 4 files changed, 96 insertions(+), 57 deletions(-) rename {test/utils/columnDensity => src/utils}/column.cpp (89%) create mode 100644 src/utils/column.hpp delete mode 100644 test/utils/columnDensity/column.hpp diff --git a/src/utils/CMakeLists.txt b/src/utils/CMakeLists.txt index b36f8a08e..afb4f57d4 100644 --- a/src/utils/CMakeLists.txt +++ b/src/utils/CMakeLists.txt @@ -5,4 +5,6 @@ target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/dumpImage.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/dumpImage.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/lookupTable.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/column.cpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/column.hpp ) diff --git a/test/utils/columnDensity/column.cpp b/src/utils/column.cpp similarity index 89% rename from test/utils/columnDensity/column.cpp rename to src/utils/column.cpp index 9ad4c3573..838f1d9ce 100644 --- a/test/utils/columnDensity/column.cpp +++ b/src/utils/column.cpp @@ -1,7 +1,24 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + + +#include +#include + #include "column.hpp" -#include "loop.hpp" +#include "idefix.hpp" +#include "input.hpp" +#include "output.hpp" +#include "grid.hpp" +#include "dataBlock.hpp" +#include "dataBlockHost.hpp" -Column::Column(int dir, int sign, int variable, DataBlock *data) : direction(dir), sign(sign), variable(variable) { +Column::Column(int dir, int sign, int variable, DataBlock *data) + : direction(dir), sign(sign), variable(variable) { idfx::pushRegion("Column::Column"); this->np_tot = data->np_tot; this->np_int = data->np_int; @@ -157,19 +174,22 @@ void Column::ComputeColumn(IdefixArray4D in) { if(direction == IDIR) { idefix_for("Loadsum",kb,ke,jb,je, KOKKOS_LAMBDA(int k, int j) { - localSum(k,j) = column(k,j,ie-1) + in(var,k,j,ie-1) * dV(k,j,ie-1) / (0.5*(A(k,j,ie-1)+A(k,j,ie))); + localSum(k,j) = column(k,j,ie-1) + in(var,k,j,ie-1) * dV(k,j,ie-1) + / (0.5*(A(k,j,ie-1)+A(k,j,ie))); }); } if(direction == JDIR) { idefix_for("Loadsum",kb,ke,ib,ie, KOKKOS_LAMBDA(int k, int i) { - localSum(k,i) = column(k,je-1,i) + in(var,k,je-1,i) * dV(k,je-1,i) / (0.5*(A(k,je-1,i)+A(k,je,i))); + localSum(k,i) = column(k,je-1,i) + in(var,k,je-1,i) * dV(k,je-1,i) + / (0.5*(A(k,je-1,i)+A(k,je,i))); }); } if(direction == KDIR) { idefix_for("Loadsum",jb,je,ib,ie, KOKKOS_LAMBDA(int j, int i) { - localSum(j,i) = column(ke-1,j,i) + in(var,ke-1,j,i) * dV(ke-1,j,i) / (0.5*(A(ke-1,j,i)+A(ke,j,i))); + localSum(j,i) = column(ke-1,j,i) + in(var,ke-1,j,i) * dV(ke-1,j,i) + / (0.5*(A(ke-1,j,i)+A(ke,j,i))); }); } diff --git a/src/utils/column.hpp b/src/utils/column.hpp new file mode 100644 index 000000000..feb0a8537 --- /dev/null +++ b/src/utils/column.hpp @@ -0,0 +1,69 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef UTILS_COLUMN_HPP_ +#define UTILS_COLUMN_HPP_ + +#include +#include + +#include "idefix.hpp" +#include "dataBlock.hpp" + + + +// A class to implement a parralel cumulative sum +class Column { + public: + //////////////////////////////////////////////////////////////////////////////////// + /// @brief Constructor of a cumulative sum(=column density) from setup's arguments + /// @param dir direction along which the integration is performed + /// @param sign: +1 for an integration from left to right, -1 for an integration from right to + /// left i.e (backwards) + /// @param variable: index of the variable along which we do the integral (since the + /// intput array is 4D) + /////////////////////////////////////////////////////////////////////////////////// + Column(int dir, int sign, int variable, DataBlock *); + + /////////////////////////////////////////////////////////////////////////////////// + /// @brief Effectively compute integral from the input array in argument + /////////////////////////////////////////////////////////////////////////////////// + void ComputeColumn(IdefixArray4D in); + + /////////////////////////////////////////////////////////////////////////////////// + /// @brief Get a reference to the computed column density array + /////////////////////////////////////////////////////////////////////////////////// + IdefixArray3D GetColumn() { + return (this->ColumnArray); + } + + private: + IdefixArray3D ColumnArray; + int direction; // The direction along which the column is computed + int sign; // whether we integrate from the left or from the right + int variable; // The variable we use to compute the column + std::array np_tot; + std::array np_int; + std::array beg; + + IdefixArray3D Area; + IdefixArray3D Volume; + + IdefixArray2D localSum; + #ifdef WITH_MPI + Mpi mpi; // Mpi object when WITH_MPI is set + MPI_Comm ColumnComm; + int MPIrank; + int MPIsize; + + IdefixArray4D arr4D; // Dummy array 4D used for MPI xchanges + std::array nproc; // 3D size of the MPI cartesian geometry + + #endif +}; + +#endif // UTILS_COLUMN_HPP_ diff --git a/test/utils/columnDensity/column.hpp b/test/utils/columnDensity/column.hpp deleted file mode 100644 index 9defe7c6b..000000000 --- a/test/utils/columnDensity/column.hpp +++ /dev/null @@ -1,52 +0,0 @@ -#ifndef COLUMN_HPP_ -#define COLUMN_HPP_ - -#include "idefix.hpp" -#include "input.hpp" -#include "output.hpp" -#include "grid.hpp" -#include "dataBlock.hpp" -#include "dataBlockHost.hpp" -#include -#include - - -// A class to implement a parralel cumulative sum -class Column { - public: - // Constructor from Setup arguments - Column(int dir, int sign, int variable, DataBlock *); - // dir : direction along which the integration is performed - // sign: +1 for an integration from left to right, -1 for an integration from right to left (backwards) - // variable: index of the variable along which we do the integral (since the intput array is 4D) - void ComputeColumn(IdefixArray4D in); - // Effectively compute integral from the input array in parameter - IdefixArray3D GetColumn() { - return (this->ColumnArray); - }// Return the column density - private: - IdefixArray3D ColumnArray; - int direction; // The direction along which the column is computed - int sign; // whether we integrate from the left or from the right - int variable; // The variable we use to compute the column - std::array np_tot; - std::array np_int; - std::array beg; - - IdefixArray3D Area; - IdefixArray3D Volume; - - IdefixArray2D localSum; - #ifdef WITH_MPI - Mpi mpi; // Mpi object when WITH_MPI is set - MPI_Comm ColumnComm; - int MPIrank; - int MPIsize; - - IdefixArray4D arr4D; // Dummy array 4D used for MPI xchanges - std::array nproc; // 3D size of the MPI cartesian geometry - - #endif -}; - -#endif // COLUMN_HPP_ From 6283fd5e2997d3502f81b43cfc9110c76b3216f7 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 18:50:44 +0100 Subject: [PATCH 010/144] add doc link for column density --- doc/source/faq.rst | 3 +++ 1 file changed, 3 insertions(+) diff --git a/doc/source/faq.rst b/doc/source/faq.rst index 75a07a68b..4c7bc056b 100644 --- a/doc/source/faq.rst +++ b/doc/source/faq.rst @@ -73,3 +73,6 @@ I want to test a modification to *Idefix* source code specific to my problem wit I want to use a lookup table from a CSV file in my idefix_loop. How could I proceed? Use the ``LookupTable`` class (see :ref:`LookupTableClass`) + +I want to compute a cumulative sum (e.g a column density) on the fly. How could I proceed? + Use the ``Column`` class (see :class:`::Column`) From 8277ed0fdff7114f2c77ff8b30abfa30972c9cab Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 12 Jan 2025 20:16:30 +0100 Subject: [PATCH 011/144] missing testme file --- test/utils/columnDensity/testme.py | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) create mode 100755 test/utils/columnDensity/testme.py diff --git a/test/utils/columnDensity/testme.py b/test/utils/columnDensity/testme.py new file mode 100755 index 000000000..6f017d7d8 --- /dev/null +++ b/test/utils/columnDensity/testme.py @@ -0,0 +1,23 @@ +#!/usr/bin/env python3 + +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) +import pytools.idfx_test as tst + +test=tst.idfxTest() + +test.configure() +test.compile() +# this test succeeds if it runs successfully +test.run() + +test.mpi = True +test.configure() +test.compile() +# this test succeeds if it runs successfully +test.run() From 31ae1b8a47168fcf09cf1f4be6d6794d5a19b33e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 14 Jan 2025 15:13:38 +0100 Subject: [PATCH 012/144] add a 3D interface for column density computation --- src/utils/column.cpp | 21 +++++++++++------- src/utils/column.hpp | 15 ++++++++----- test/utils/columnDensity/setup.cpp | 34 +++++++++++++++++++----------- 3 files changed, 45 insertions(+), 25 deletions(-) diff --git a/src/utils/column.cpp b/src/utils/column.cpp index 838f1d9ce..a774d4927 100644 --- a/src/utils/column.cpp +++ b/src/utils/column.cpp @@ -17,8 +17,8 @@ #include "dataBlock.hpp" #include "dataBlockHost.hpp" -Column::Column(int dir, int sign, int variable, DataBlock *data) - : direction(dir), sign(sign), variable(variable) { +Column::Column(int dir, int sign, DataBlock *data) + : direction(dir), sign(sign) { idfx::pushRegion("Column::Column"); this->np_tot = data->np_tot; this->np_int = data->np_int; @@ -62,7 +62,7 @@ Column::Column(int dir, int sign, int variable, DataBlock *data) idfx::popRegion(); } -void Column::ComputeColumn(IdefixArray4D in) { +void Column::ComputeColumn(IdefixArray4D in, const int var) { idfx::pushRegion("Column::ComputeColumn"); const int nk = np_int[KDIR]; const int nj = np_int[JDIR]; @@ -80,7 +80,6 @@ void Column::ComputeColumn(IdefixArray4D in) { auto A = this->Area; auto localSum = this->localSum; - const int var = this->variable; if(direction==IDIR) { // Inspired from loop.hpp Kokkos::parallel_for("ColumnX1", team_policy (nk*nj, Kokkos::AUTO), @@ -210,7 +209,7 @@ void Column::ComputeColumn(IdefixArray4D in) { // density in the ghost zones are coherent #ifdef WITH_MPI // Create a 4D array that contains our column data - this->arr4D = IdefixArray4D (column.data(), 1, this->np_tot[KDIR], + IdefixArray4D arr4D(column.data(), 1, this->np_tot[KDIR], this->np_tot[JDIR], this->np_tot[IDIR]); @@ -219,13 +218,13 @@ void Column::ComputeColumn(IdefixArray4D in) { if(nproc[dir]>1) { switch(dir) { case 0: - this->mpi.ExchangeX1(this->arr4D); + this->mpi.ExchangeX1(arr4D); break; case 1: - this->mpi.ExchangeX2(this->arr4D); + this->mpi.ExchangeX2(arr4D); break; case 2: - this->mpi.ExchangeX3(this->arr4D); + this->mpi.ExchangeX3(arr4D); break; } } @@ -233,3 +232,9 @@ void Column::ComputeColumn(IdefixArray4D in) { #endif idfx::popRegion(); } + +void Column::ComputeColumn(IdefixArray3D in) { + // 4D alias + IdefixArray4D arr4D(in.data(), 1, in.extent(2), in.extent(1), in.extent(0)); + return this->ComputeColumn(arr4D,0); +} diff --git a/src/utils/column.hpp b/src/utils/column.hpp index feb0a8537..43383cbe6 100644 --- a/src/utils/column.hpp +++ b/src/utils/column.hpp @@ -24,15 +24,22 @@ class Column { /// @param dir direction along which the integration is performed /// @param sign: +1 for an integration from left to right, -1 for an integration from right to /// left i.e (backwards) + /////////////////////////////////////////////////////////////////////////////////// + Column(int dir, int sign, DataBlock *); + + /////////////////////////////////////////////////////////////////////////////////// + /// @brief Effectively compute integral from the input array in argument + /// @param in: 4D input array /// @param variable: index of the variable along which we do the integral (since the /// intput array is 4D) /////////////////////////////////////////////////////////////////////////////////// - Column(int dir, int sign, int variable, DataBlock *); + void ComputeColumn(IdefixArray4D in, int variable); - /////////////////////////////////////////////////////////////////////////////////// + /////////////////////////////////////////////////////////////////////////////////// /// @brief Effectively compute integral from the input array in argument + /// @param in: 3D input array /////////////////////////////////////////////////////////////////////////////////// - void ComputeColumn(IdefixArray4D in); + void ComputeColumn(IdefixArray3D in); /////////////////////////////////////////////////////////////////////////////////// /// @brief Get a reference to the computed column density array @@ -45,7 +52,6 @@ class Column { IdefixArray3D ColumnArray; int direction; // The direction along which the column is computed int sign; // whether we integrate from the left or from the right - int variable; // The variable we use to compute the column std::array np_tot; std::array np_int; std::array beg; @@ -60,7 +66,6 @@ class Column { int MPIrank; int MPIsize; - IdefixArray4D arr4D; // Dummy array 4D used for MPI xchanges std::array nproc; // 3D size of the MPI cartesian geometry #endif diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp index ebc131de7..b27b6b1f3 100644 --- a/test/utils/columnDensity/setup.cpp +++ b/test/utils/columnDensity/setup.cpp @@ -15,12 +15,22 @@ void Analysis(DataBlock & data) { DataBlockHost d(data); - columnX1Left->ComputeColumn(data.hydro->Vc); - columnX1Right->ComputeColumn(data.hydro->Vc); - columnX2Left->ComputeColumn(data.hydro->Vc); - columnX2Right->ComputeColumn(data.hydro->Vc); - columnX3Left->ComputeColumn(data.hydro->Vc); - columnX3Right->ComputeColumn(data.hydro->Vc); + // Try the 4D array interface + columnX1Left->ComputeColumn(data.hydro->Vc,RHO); + columnX1Right->ComputeColumn(data.hydro->Vc,RHO); + + // Try the 3D array interface + IdefixArray3D rho("rho",data.np_tot[KDIR],data.np_tot[JDIR],data.np_tot[IDIR]); + auto Vc = data.hydro->Vc; + + idefix_for("init rho",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], + KOKKOS_LAMBDA(int k, int j, int i) { + rho(k,j,i) = Vc(RHO,k,j,i); + }); + columnX2Left->ComputeColumn(rho); + columnX2Right->ComputeColumn(rho); + columnX3Left->ComputeColumn(rho); + columnX3Right->ComputeColumn(rho); IdefixArray3D columnDensityLeft, columnDensityRight; IdefixArray3D::HostMirror columnDensityLeftHost, columnDensityRightHost; @@ -124,12 +134,12 @@ Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { output.EnrollAnalysis(&Analysis); data.hydro->EnrollInternalBoundary(&InternalBoundary); - columnX1Left = new Column(IDIR, 1, RHO, &data); - columnX1Right = new Column(IDIR, -1, RHO, &data); - columnX2Left = new Column(JDIR, 1, RHO, &data); - columnX2Right = new Column(JDIR, -1, RHO, &data); - columnX3Left = new Column(KDIR, 1, RHO, &data); - columnX3Right = new Column(KDIR, -1, RHO, &data); + columnX1Left = new Column(IDIR, 1, &data); + columnX1Right = new Column(IDIR, -1, &data); + columnX2Left = new Column(JDIR, 1, &data); + columnX2Right = new Column(JDIR, -1, &data); + columnX3Left = new Column(KDIR, 1, &data); + columnX3Right = new Column(KDIR, -1, &data); // Initialise the output file } From d6560366a1c3a3d6c8c2dabb6c61426b56aaad71 Mon Sep 17 00:00:00 2001 From: Hal Bal Date: Wed, 15 Jan 2025 10:05:44 +0100 Subject: [PATCH 013/144] Upwind scheme for cless TC with limiters + tests --- reference | 2 +- src/fluid/braginskii/bragThermalDiffusion.hpp | 97 +++++++----- test/MHD/MTI/idefix-rkl.ini | 2 +- test/MHD/MTI/idefix-sl.ini | 2 +- test/MHD/MTI/idefix.ini | 2 +- test/MHD/clessTDiffusion/CMakeLists.txt | 2 + test/MHD/clessTDiffusion/definitions.hpp | 5 + test/MHD/clessTDiffusion/idefix.ini | 41 +++++ test/MHD/clessTDiffusion/python/testidefix.py | 40 +++++ test/MHD/clessTDiffusion/setup.cpp | 149 ++++++++++++++++++ test/MHD/clessTDiffusion/testme.py | 42 +++++ test/MHD/sphBragTDiffusion/idefix.ini | 2 +- 12 files changed, 342 insertions(+), 44 deletions(-) create mode 100644 test/MHD/clessTDiffusion/CMakeLists.txt create mode 100644 test/MHD/clessTDiffusion/definitions.hpp create mode 100644 test/MHD/clessTDiffusion/idefix.ini create mode 100644 test/MHD/clessTDiffusion/python/testidefix.py create mode 100644 test/MHD/clessTDiffusion/setup.cpp create mode 100755 test/MHD/clessTDiffusion/testme.py diff --git a/reference b/reference index 609a60164..99f339c43 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 609a60164461fb2d4fbeffa89ce148acf1191525 +Subproject commit 99f339c43d98274a925282cc96252c5a0fa9374f diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index db01497b7..64037420f 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -122,7 +122,7 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid IDEFIX_ERROR("Unknown braginskii thermal diffusion definition in idefix.ini. " "Can only be constant or userdef."); } - } else if(input.Get("Hydro","bragTDiffusion",2).compare("wcollisionless") == 0.0) { + } else if(input.Get("Hydro","bragTDiffusion",2).compare("wcless") == 0.0) { if(input.Get("Hydro","bragTDiffusion",3).compare("constant") == 0) { this->includeCollisionlessTD = true; this->kpar = input.Get("Hydro","bragTDiffusion",4); @@ -148,12 +148,12 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid data->np_tot[JDIR], data->np_tot[IDIR]); } else { - IDEFIX_ERROR("Unknown braginskii/collsiionless thermal diffusion definition in idefix.ini. " + IDEFIX_ERROR("Unknown braginskii/collisionless thermal diffusion definition in idefix.ini. " "Can only be constant or userdef."); } } else { IDEFIX_ERROR("Unknown braginskii thermal diffusion saturation in idefix.ini. " - "Can only be nosat or wcollisionless."); + "Can only be nosat or wcless."); } } else { IDEFIX_ERROR("I cannot create a BragThermalDiffusion object without bragTDiffusion defined" @@ -220,7 +220,7 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid //We now define spatial average macros for the magnetic field. // The magnetic field appears in the expression of the Braginskii heat flux. -// It is therefore needed at the right cell interface according to the direction of the flux. +// It is therefore needed at the left cell interface according to the direction of the flux. #define BX_I Vs(BX1s,k,j,i) #define BY_J Vs(BX2s,k,j,i) #define BZ_K Vs(BX3s,k,j,i) @@ -348,7 +348,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, } if(includeCollisionlessTD) { clessAlpha=HALF_F*(clessAlphaArr(k,j,i-1)+clessAlphaArr(k,j,i)); - clessBeta=HALF_F*(clessBetaArr(k,j,i-1)+clessAlphaArr(k,j,i)); + clessBeta=HALF_F*(clessBetaArr(k,j,i-1)+clessBetaArr(k,j,i)); } } else { knor = knorConstant; @@ -470,21 +470,28 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dTn = dTi; /* For collisionless / saturated heat flux */ - if (includeCollisionlessTD) { - dvp = Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i); - dvm = Vc(VX1,k,j,i) - Vc(VX1,k,j,i-1); + if (includeCollisionlessTD) { + if(haveSlopeLimiter) { + dvp = Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i); + dvm = Vc(VX1,k,j,i) - Vc(VX1,k,j,i-1); - dpp = Vc(PRS,k,j,i+1) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); + dpp = Vc(PRS,k,j,i+1) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); - if(haveSlopeLimiter) { - Vn = Vc(VX1,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); - } else { - Vn = HALF_F*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i-1)); - Pn = HALF_F*(Vc(PRS,k,j,i) + Vc(PRS,k,j,i-1)); - } - } + /* Upwind scheme */ + if (Vc(VX1,k,j,i) > 0.0) { + Vn = Vc(VX1,k,j,i-1)+HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i-1)+HALF_F*SL::PLMLim(dpm, dpp); + } + else { + Vn = Vc(VX1,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); + } + } else { + Vn = HALF_F*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i-1)); + Pn = HALF_F*(Vc(PRS,k,j,i) + Vc(PRS,k,j,i-1)); + } + } } else if(dir == JDIR) { ////////////// // JDIR @@ -499,7 +506,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, } if(includeCollisionlessTD) { clessAlpha=HALF_F*(clessAlphaArr(k,j-1,i)+clessAlphaArr(k,j,i)); - clessBeta=HALF_F*(clessBetaArr(k,j-1,i)+clessAlphaArr(k,j,i)); + clessBeta=HALF_F*(clessBetaArr(k,j-1,i)+clessBetaArr(k,j,i)); } } else { knor = knorConstant; @@ -629,21 +636,27 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dTn = dTj; /* For the collisionless / saturated flux */ - if(includeCollisionlessTD) { - dvp = Vc(VX2,k,j+1,i) - Vc(VX2,k,j,i); - dvm = Vc(VX2,k,j,i) - Vc(VX2,k,j-1,i); + if(includeCollisionlessTD) { + if(haveSlopeLimiter) { + dvp = Vc(VX2,k,j+1,i) - Vc(VX2,k,j,i); + dvm = Vc(VX2,k,j,i) - Vc(VX2,k,j-1,i); - dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); + dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); - if(haveSlopeLimiter) { - Vn = Vc(VX2,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); - } else { - Vn = 0.5*(Vc(VX2,k,j-1,i) + Vc(VX2,k,j,i)); - Pn = 0.5*(Vc(PRS,k,j-1,i) + Vc(PRS,k,j,i)); - } - } + /* Upwind scheme */ + if (Vc(VX2,k,j,i) > 0.0) { + Vn = Vc(VX2,k,j-1,i)+HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j-1,i)+HALF_F*SL::PLMLim(dpm, dpp); + } else { + Vn = Vc(VX2,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); + } + } else { + Vn = HALF_F*(Vc(VX2,k,j-1,i) + Vc(VX2,k,j,i)); + Pn = HALF_F*(Vc(PRS,k,j-1,i) + Vc(PRS,k,j,i)); + } + } } else if(dir == KDIR) { ////////////// // KDIR @@ -747,15 +760,21 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, /* For the collisionless / saturated flux */ if(includeCollisionlessTD) { - dvp = Vc(VX3,k+1,j,i) - Vc(VX3,k,j,i); - dvm = Vc(VX3,k,j,i) - Vc(VX3,k-1,j,i); + if(haveSlopeLimiter) { + dvp = Vc(VX3,k+1,j,i) - Vc(VX3,k,j,i); + dvm = Vc(VX3,k,j,i) - Vc(VX3,k-1,j,i); - dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); - dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); + dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); + dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); - if(haveSlopeLimiter) { - Vn = Vc(VX3,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); + /* Upwind scheme */ + if (Vc(VX3,k,j,i) > 0.0) { + Vn = Vc(VX3,k-1,j,i)+HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k-1,j,i)+HALF_F*SL::PLMLim(dpp, dpm); + } else { + Vn = Vc(VX3,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); + } } else { Vn = HALF_F*(Vc(VX3,k-1,j,i) + Vc(VX3,k,j,i)); Pn = HALF_F*(Vc(PRS,k-1,j,i) + Vc(PRS,k,j,i)); diff --git a/test/MHD/MTI/idefix-rkl.ini b/test/MHD/MTI/idefix-rkl.ini index 1b9b11eb2..09e9eb72d 100644 --- a/test/MHD/MTI/idefix-rkl.ini +++ b/test/MHD/MTI/idefix-rkl.ini @@ -12,7 +12,7 @@ nstages 3 [Hydro] solver hlld gamma 1.6666666666666666 -bragTDiffusion rkl nolimiter userdef +bragTDiffusion rkl nolimiter nosat userdef bragViscosity rkl nolimiter userdef [Gravity] diff --git a/test/MHD/MTI/idefix-sl.ini b/test/MHD/MTI/idefix-sl.ini index f2c9deb2b..aa707914f 100644 --- a/test/MHD/MTI/idefix-sl.ini +++ b/test/MHD/MTI/idefix-sl.ini @@ -12,7 +12,7 @@ nstages 3 [Hydro] solver hlld gamma 1.6666666666666666 -bragTDiffusion rkl mc userdef +bragTDiffusion rkl mc nosat userdef bragViscosity rkl vanleer userdef [Gravity] diff --git a/test/MHD/MTI/idefix.ini b/test/MHD/MTI/idefix.ini index 7a09c406c..a159c4f70 100644 --- a/test/MHD/MTI/idefix.ini +++ b/test/MHD/MTI/idefix.ini @@ -12,7 +12,7 @@ nstages 3 [Hydro] solver hlld gamma 1.6666666666666666 -bragTDiffusion explicit nolimiter userdef +bragTDiffusion explicit nolimiter nosat userdef bragViscosity explicit nolimiter userdef [Gravity] diff --git a/test/MHD/clessTDiffusion/CMakeLists.txt b/test/MHD/clessTDiffusion/CMakeLists.txt new file mode 100644 index 000000000..aa9abdd74 --- /dev/null +++ b/test/MHD/clessTDiffusion/CMakeLists.txt @@ -0,0 +1,2 @@ +enable_idefix_property(Idefix_MHD) +set_idefix_property(Idefix_RECONSTRUCTION Parabolic) diff --git a/test/MHD/clessTDiffusion/definitions.hpp b/test/MHD/clessTDiffusion/definitions.hpp new file mode 100644 index 000000000..21b1f8733 --- /dev/null +++ b/test/MHD/clessTDiffusion/definitions.hpp @@ -0,0 +1,5 @@ +#define COMPONENTS 3 +#define DIMENSIONS 1 +#define GEOMETRY SPHERICAL + +#define SMALL_PRESSURE_TEMPERATURE (0.1) diff --git a/test/MHD/clessTDiffusion/idefix.ini b/test/MHD/clessTDiffusion/idefix.ini new file mode 100644 index 000000000..9c444b928 --- /dev/null +++ b/test/MHD/clessTDiffusion/idefix.ini @@ -0,0 +1,41 @@ +[Grid] +X1-grid 1 1.0 256 l 40.0 +X2-grid 1 1.4708 1 u 1.6708 +X3-grid 1 0.9892 1 u 1.0108 + +[TimeIntegrator] +CFL 0.4 +CFL_max_var 1.1 # not used +tstop 300.0 +first_dt 1.e-6 +nstages 2 + +[Hydro] +solver hlld +gamma 1.6666666666666 +bragTDiffusion rkl mc wcless userdef + +[Gravity] +potential central +Mcentral 1.0 + +[Boundary] +X1-beg userdef +X1-end outflow +X2-beg periodic +X2-end periodic +X3-beg periodic +X3-end periodic + +[Setup] +UNIT_DENSITY 1.6726e-16 +UNIT_LENGTH 6.9570e10 +UNIT_VELOCITY 4.3670e7 +cs_vesc 0.26 +va_vesc 0.3 +k0 9e-7 + +[Output] +vtk 100.0 +dmp 300.0 +log 10 diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py new file mode 100644 index 000000000..444816d1f --- /dev/null +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -0,0 +1,40 @@ +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) +from pytools.vtk_io import readVTK +import numpy as np +import inifix + +conf = inifix.load("../idefix.ini") +gamma = conf["Hydro"]["gamma"] +kappa = conf["Hydro"]["bragTDiffusion"][-1] + +current_VTK = readVTK('../data.0003.vtk', geometry='spherical') + +rho = current_VTK.data['RHO'].squeeze() +prs = current_VTK.data['PRS'].squeeze() +r = current_VTK.r + +idx1=np.where(r > 20)[0][0] +idx2=np.where(r > 30)[0][0] + +def gamma_prime(gamma, beta): + return (gamma+beta*(gamma-1))/(1+beta*(gamma-1)) + +success = True +eps = 1e-2 + +gamma_eff = np.gradient(prs, r)/np.gradient(rho, r)*rho/prs + +Error=np.abs(gamma_eff[idx1:idx2]-gamma_prime(gamma, 1.5)).mean() +if Error > eps: + success=False + +if success: + print("SUCCESS") + print("Error: {0}".format(Error)) + sys.exit(0) +else: + print("Failed") + print("Error: {0}".format(Error)) + sys.exit(1) diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp new file mode 100644 index 000000000..624e1d72b --- /dev/null +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -0,0 +1,149 @@ +#include "idefix.hpp" +#include "setup.hpp" + +real udenGlob; +real ulenGlob; +real uvelGlob; +real gammaGlob; +real cs_vescGlob; +real va_vescGlob; +real k0_Glob; +real ParkerWind(real); + +void MyClessThermalConductivity(DataBlock &data, const real t, IdefixArray3D &kparArr, IdefixArray3D &knorArr, IdefixArray3D &alpha, IdefixArray3D &clessQ) { + IdefixArray4D Vc = data.hydro->Vc; + IdefixArray1D x1 = data.x[IDIR]; + IdefixArray1D x2 = data.x[JDIR]; + real norm = 1.6726e-24*0.5/(udenGlob*uvelGlob*ulenGlob*1.3807e-16); + real uTemp=0.5*uvelGlob*uvelGlob*1.6726e-24/1.3807e-16; + real k0 = k0_Glob*norm; + idefix_for("MyThConductivity",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + kparArr(k,j,i) = k0*pow(Vc(PRS,k,j,i)/Vc(RHO,k,j,i)*uTemp,2.5); + knorArr(k,j,i) = 0.; + alpha(k,j,i) = (1.0-tanh(x1(i)-10))/2; + clessQ(k,j,i) = -1.5; + }); +} + +// User-defined boundaries +void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { + + DataBlock *data = hydro->data; + + if( (dir==IDIR) && (side == left)) { + IdefixArray4D Vc = hydro->Vc; + IdefixArray4D Vs = hydro->Vs; + IdefixArray1D x1 = data->x[IDIR]; + + real rc,vc,vwind0; + real cs=cs_vescGlob*sqrt(2.); + real va_vesc = va_vescGlob; + real PonRho; + + PonRho = cs*cs; + rc = 0.25 / (cs_vescGlob*cs_vescGlob); + vc = cs; + vwind0 = ParkerWind(1./rc) * cs; + + hydro->boundary->BoundaryFor("UserDefBoundary", dir, side, + KOKKOS_LAMBDA (int k, int j, int i) { + real r = x1(i); + real mu = va_vesc * sqrt(2.); + Vc(RHO,k,j,i) = vwind0/(vwind0 * r * r); + Vc(PRS,k,j,i) = PonRho * Vc(RHO, k, j, i); + Vc(VX1,k,j,i) = vwind0; + Vc(VX2,k,j,i) = 0.0; + Vc(VX3,k,j,i) = 0.0; + Vc(BX1,k,j,i) = mu / (r*r); + Vc(BX2,k,j,i) = 0.0; + Vc(BX3,k,j,i) = 0.0; + + }); + } +} + +// Initialisation routine. Can be used to allocate +// Arrays or variables which are used later on +Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { + // Set the function for userdefboundary + data.hydro->EnrollUserDefBoundary(&UserDefBoundary); + data.hydro->bragThermalDiffusion->EnrollClessThermalDiffusivity(&MyClessThermalConductivity); + gammaGlob=input.Get("Hydro", "gamma", 0); + udenGlob=input.Get("Setup", "UNIT_DENSITY",0); + ulenGlob=input.Get("Setup", "UNIT_LENGTH",0); + uvelGlob=input.Get("Setup", "UNIT_VELOCITY",0); + cs_vescGlob=input.Get("Setup", "cs_vesc", 0); + va_vescGlob=input.Get("Setup", "va_vesc", 0); + k0_Glob = input.Get("Setup", "k0", 0); +} + +// This routine initialize the flow +// Note that data is on the device. +// One can therefore define locally +// a datahost and sync it, if needed +void Setup::InitFlow(DataBlock &data) { + // Create a host copy + DataBlockHost d(data); + + real r,th,rl; + real PonRho, vwind0, rc, vc; + real cs=cs_vescGlob*sqrt(2.); + + + rc = 0.25 / (cs_vescGlob*cs_vescGlob); + vwind0 = ParkerWind(1./rc) * cs; + PonRho = cs*cs; + real mu = va_vescGlob * sqrt(2.); + + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + r=d.x[IDIR](i); + th=d.x[JDIR](j); + real vwind; + + vwind = ParkerWind(r/rc) * cs; + + d.Vc(RHO,k,j,i) = 1.0*vwind0/(vwind * r * r); + d.Vc(PRS,k,j,i) = PonRho * d.Vc(RHO, k, j, i); + d.Vc(VX1,k,j,i) = vwind; + d.Vc(VX2,k,j,i) = 0.0; + d.Vc(VX3,k,j,i) = 0.0; + + rl=d.xl[IDIR](i); // Radius on the left side of the cell + d.Vs(BX1s, k, j, i) = mu / (rl*rl); + + } + } + } + // Send it all, if needed + d.SyncToDevice(); +} + +// Analyse data to produce an output +void MakeAnalysis(DataBlock & data) { +} + +/**************************************************/ +real ParkerWind(real x) +/* Parker wind velocity in unit of iso sound speed + x = radius / critical radius. +**************************************************/ +{ + real v, f; + real vref; + + v = 1e-7; + f = v*v-2*log(v)-4/x-4*log(x)+3; + if (x>1) {v=10;} + while (fabs(f) > 1e-10){ + vref = v; + v = v - 0.5*f/(v-1/v); + while (v < 0){ + v = (v + vref)/2; + } + f = v*v-2*log(v)-4/x-4*log(x)+3; + } + return v; +} diff --git a/test/MHD/clessTDiffusion/testme.py b/test/MHD/clessTDiffusion/testme.py new file mode 100755 index 000000000..6ed5b1648 --- /dev/null +++ b/test/MHD/clessTDiffusion/testme.py @@ -0,0 +1,42 @@ +#!/usr/bin/env python3 + +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) + +import pytools.idfx_test as tst + + +def testMe(test): + test.configure() + test.compile() + inifiles=["idefix.ini"] + + # loop on all the ini files for this test + name = "dump.0001.dmp" + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=2e-15) + + +test=tst.idfxTest() + +if not test.all: + if(test.check): + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) +else: + test.noplot = True + test.vectPot=False + test.single=False + test.reconstruction=2 + test.mpi=False + testMe(test) diff --git a/test/MHD/sphBragTDiffusion/idefix.ini b/test/MHD/sphBragTDiffusion/idefix.ini index 35ac54e8b..795ae7bb2 100644 --- a/test/MHD/sphBragTDiffusion/idefix.ini +++ b/test/MHD/sphBragTDiffusion/idefix.ini @@ -13,7 +13,7 @@ nstages 3 [Hydro] solver hlld gamma 1.4 -bragTDiffusion rkl nolimiter constant 50.0 +bragTDiffusion rkl nolimiter nosat constant 50.0 [Setup] amplitude 1e-4 From 7c10ec052d60128aea8d4dd90ee32c8a13f9b06b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 15 Jan 2025 18:06:53 +0100 Subject: [PATCH 014/144] fix dimensions for alias --- src/utils/column.cpp | 2 +- test/utils/columnDensity/idefix.ini | 4 ++-- test/utils/columnDensity/setup.cpp | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/utils/column.cpp b/src/utils/column.cpp index a774d4927..34d55f56b 100644 --- a/src/utils/column.cpp +++ b/src/utils/column.cpp @@ -235,6 +235,6 @@ void Column::ComputeColumn(IdefixArray4D in, const int var) { void Column::ComputeColumn(IdefixArray3D in) { // 4D alias - IdefixArray4D arr4D(in.data(), 1, in.extent(2), in.extent(1), in.extent(0)); + IdefixArray4D arr4D(in.data(), 1, in.extent(0), in.extent(1), in.extent(2)); return this->ComputeColumn(arr4D,0); } diff --git a/test/utils/columnDensity/idefix.ini b/test/utils/columnDensity/idefix.ini index 2d994315c..5e80c8bce 100644 --- a/test/utils/columnDensity/idefix.ini +++ b/test/utils/columnDensity/idefix.ini @@ -1,7 +1,7 @@ [Grid] X1-grid 1 0.0 64 u 1.0 -X2-grid 1 0.0 64 u 1.0 -X3-grid 1 0.0 64 u 1.0 +X2-grid 1 0.0 32 u 1.0 +X3-grid 1 0.0 16 u 1.0 [TimeIntegrator] CFL 0.8 diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp index b27b6b1f3..fe7c57e69 100644 --- a/test/utils/columnDensity/setup.cpp +++ b/test/utils/columnDensity/setup.cpp @@ -23,7 +23,7 @@ void Analysis(DataBlock & data) { IdefixArray3D rho("rho",data.np_tot[KDIR],data.np_tot[JDIR],data.np_tot[IDIR]); auto Vc = data.hydro->Vc; - idefix_for("init rho",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], + idefix_for("init rho",data.beg[KDIR],data.end[KDIR],data.beg[JDIR],data.end[JDIR],data.beg[IDIR],data.end[IDIR], KOKKOS_LAMBDA(int k, int j, int i) { rho(k,j,i) = Vc(RHO,k,j,i); }); From 79e70cf233f0ef0dec55e916b8c5ad723ba123ac Mon Sep 17 00:00:00 2001 From: Jean Kempf Date: Thu, 16 Jan 2025 14:12:10 +0100 Subject: [PATCH 015/144] updated ShowConfig functions from braginskii tc and viscosity to display which slope limiter is used, fixed typo in the braginskii doc --- doc/source/modules/braginskii.rst | 2 +- src/fluid/braginskii/bragThermalDiffusion.cpp | 12 ++++++++++-- src/fluid/braginskii/bragThermalDiffusion.hpp | 5 +++++ src/fluid/braginskii/bragViscosity.cpp | 10 +++++++++- src/fluid/braginskii/bragViscosity.hpp | 4 ++++ 5 files changed, 29 insertions(+), 4 deletions(-) diff --git a/doc/source/modules/braginskii.rst b/doc/source/modules/braginskii.rst index e657cedd0..ccc841f4f 100644 --- a/doc/source/modules/braginskii.rst +++ b/doc/source/modules/braginskii.rst @@ -37,7 +37,7 @@ though adapted to vector quantities. cell interface by a simple arithmetic average (Eq. (6)-(7) from Sharma & Hammett 2007). However in the same paper, the authors showed that this implementation can lead to - unphysical heat flux from high to low temperature regions. + unphysical heat flux from low to high temperature regions. So we implemented slope limiters for the computation of these transverse heat fluxes, as described in Eq. (17) from Sharma & Hammett (2007). Only the van Leer and the Monotonized Central (MC) limiters are available diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index ee1d5b996..a898ab8bd 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -42,10 +42,18 @@ void BragThermalDiffusion::ShowConfig() { IDEFIX_ERROR("Unknown time integrator for braginskii thermal diffusion."); } if(haveSlopeLimiter) { - idfx::cout << "Braginskii Thermal Diffusion: uses a slope limiter." << std::endl; + if(haveMonotizedCentral) { + idfx::cout << "Braginskii Thermal Diffusion: uses the monotonized central slope limiter." << std::endl; + } + else if(haveVanLeer) { + idfx::cout << "Braginskii Thermal Diffusion: uses the van Leer slope limiter." << std::endl; + } + else { + IDEFIX_ERROR("Unknown slope limiter for braginskii thermal diffusion."); + } } if(includeCollisionlessTD) { - idfx::cout << "Saturation with collisionless flux is enabled." << std::endl; + idfx::cout << "Braginskii Thermal Diffusion: saturation with collisionless flux is enabled." << std::endl; } } diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 64037420f..2a103a491 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -59,6 +59,9 @@ class BragThermalDiffusion { bool includeCollisionlessTD{false}; bool haveSlopeLimiter{false}; + bool haveMonotizedCentral{false}; + bool haveVanLeer{false}; + bool haveMinmod{false}; // helper array IdefixArray4D &Vc; @@ -91,9 +94,11 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid if(input.CheckEntry("Hydro","bragTDiffusion")>=0) { if(input.Get("Hydro","bragTDiffusion",1).compare("mc") == 0) { this->haveSlopeLimiter = true; + this->haveMonotizedCentral = true; limiter = PLMLimiter::McLim; } else if(input.Get("Hydro","bragTDiffusion",1).compare("vanleer") == 0) { this->haveSlopeLimiter = true; + this->haveVanLeer = true; limiter = PLMLimiter::VanLeer; } else if(input.Get("Hydro","bragTDiffusion",1).compare("minmod") == 0) { IDEFIX_ERROR("The minmod slope limiter is not available because it has been " diff --git a/src/fluid/braginskii/bragViscosity.cpp b/src/fluid/braginskii/bragViscosity.cpp index 6d5007b50..e05019a43 100644 --- a/src/fluid/braginskii/bragViscosity.cpp +++ b/src/fluid/braginskii/bragViscosity.cpp @@ -59,7 +59,15 @@ void BragViscosity::ShowConfig() { IDEFIX_ERROR("Unknown time integrator for braginskii viscosity."); } if(haveSlopeLimiter) { - idfx::cout << "Braginskii Viscosity: uses a slope limiter." << std::endl; + if(haveMonotizedCentral) { + idfx::cout << "Braginskii Viscosity: uses the monotonized central slope limiter." << std::endl; + } + else if(haveVanLeer) { + idfx::cout << "Braginskii Viscosity: uses the van Leer slope limiter." << std::endl; + } + else { + IDEFIX_ERROR("Unknown slope limiter for braginskii viscosity."); + } } #if GEOMETRY == CYLINDRICAL || GEOMETRY == POLAR diff --git a/src/fluid/braginskii/bragViscosity.hpp b/src/fluid/braginskii/bragViscosity.hpp index 7a8d2b756..5340110a8 100644 --- a/src/fluid/braginskii/bragViscosity.hpp +++ b/src/fluid/braginskii/bragViscosity.hpp @@ -52,6 +52,8 @@ class BragViscosity { DiffusivityFunc bragViscousDiffusivityFunc; bool haveSlopeLimiter{false}; + bool haveMonotizedCentral{false}; + bool haveVanLeer{false}; IdefixArray4D &Vc; IdefixArray4D &Vs; @@ -78,9 +80,11 @@ BragViscosity::BragViscosity(Input &input, Grid &grid, Fluid *hydroin): if(input.CheckEntry("Hydro","bragViscosity")>=0) { if(input.Get("Hydro","bragViscosity",1).compare("vanleer") == 0) { this->haveSlopeLimiter = true; + this->haveVanLeer = true; limiter = PLMLimiter::VanLeer; } else if(input.Get("Hydro","bragViscosity",1).compare("mc") == 0) { this->haveSlopeLimiter = true; + this->haveMonotizedCentral = true; limiter = PLMLimiter::McLim; } else if (input.Get("Hydro","bragViscosity",1).compare("nolimiter") == 0) { this->haveSlopeLimiter = false; From d0f348a823da191a9b5e1c869c0d25aefb779e50 Mon Sep 17 00:00:00 2001 From: Marc Coiffier Date: Fri, 17 Jan 2025 18:19:42 +0100 Subject: [PATCH 016/144] =?UTF-8?q?G=C3=A9n=C3=A9ration=20automatique=20de?= =?UTF-8?q?=20plots=20de=20performance=20dans=20la=20doc?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- doc/python_requirements.txt | 1 + doc/source/bench-jeanzay.json | 122 ++++++++++++++++++++++++++++++++ doc/source/conf.py | 1 + doc/source/performances.rst | 20 ++++-- doc/source/plot_idefix_bench.py | 14 ++++ 5 files changed, 153 insertions(+), 5 deletions(-) create mode 100755 doc/source/bench-jeanzay.json create mode 100644 doc/source/plot_idefix_bench.py diff --git a/doc/python_requirements.txt b/doc/python_requirements.txt index 35f72dcf7..c75fa02b7 100644 --- a/doc/python_requirements.txt +++ b/doc/python_requirements.txt @@ -14,3 +14,4 @@ exhale==0.3.7 m2r2==0.3.2 sphinx-copybutton==0.5.2 #sphinxcontrib-applehelp==1.0.7 +matplotlib==3.10.0 diff --git a/doc/source/bench-jeanzay.json b/doc/source/bench-jeanzay.json new file mode 100755 index 000000000..f58d38d42 --- /dev/null +++ b/doc/source/bench-jeanzay.json @@ -0,0 +1,122 @@ +[ + { + "date": "2025-01-17_15:33:13", + "gpumodel": "v100", + "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 1.192208E+8 + }, + { + "nbgpu": 2, + "cell_updates": 1.178276E+8 + }, + { + "nbgpu": 4, + "cell_updates": 1.151014E+8 + } + ] + }, + { + "date": "2025-01-17_15:35:16", + "gpumodel": "v100", + "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 1.192139E+8 + }, + { + "nbgpu": 2, + "cell_updates": 1.178690E+8 + }, + { + "nbgpu": 4, + "cell_updates": 1.092092E+8 + }, + { + "nbgpu": 8, + "cell_updates": 7.464571E+7 + }, + { + "nbgpu": 16, + "cell_updates": 7.485223E+7 + }, + { + "nbgpu": 32, + "cell_updates": 6.795755E+7 + } + ] + }, + { + "date": "2025-01-17_16:57:02", + "gpumodel": "v100", + "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 1.192784E+8 + }, + { + "nbgpu": 2, + "cell_updates": 1.117701E+8 + }, + { + "nbgpu": 4, + "cell_updates": 1.087580E+8 + }, + { + "nbgpu": 8, + "cell_updates": 7.472364E+7 + }, + { + "nbgpu": 16, + "cell_updates": 7.554497E+7 + }, + { + "nbgpu": 32, + "cell_updates": 6.669339E+7 + } + ] + }, + { + "date": "2025-01-17_17:09:39", + "gpumodel": "a100", + "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 2.035935E+8 + }, + { + "nbgpu": 2, + "cell_updates": 1.992927E+8 + }, + { + "nbgpu": 4, + "cell_updates": 1.958386E+8 + }, + { + "nbgpu": 8, + "cell_updates": 1.929568E+8 + } + ] + }, + { + "date": "2025-01-17_17:23:13", + "gpumodel": "h100", + "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 3.083581E+8 + } + ] + } +] diff --git a/doc/source/conf.py b/doc/source/conf.py index 24f9709bb..6f0cffa44 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -35,6 +35,7 @@ extensions = [ "sphinx_rtd_theme", 'sphinx_git', + 'matplotlib.sphinxext.plot_directive', "breathe", "exhale", "m2r2", diff --git a/doc/source/performances.rst b/doc/source/performances.rst index 84042685e..985991e34 100644 --- a/doc/source/performances.rst +++ b/doc/source/performances.rst @@ -33,16 +33,26 @@ CPU performances | IDRIS/Jean Zay | Intel Cascade Lake | 0.62 | +---------------------+--------------------+----------------------------------------------------+ - GPU performances ================ +.. plot:: + + import plot_idefix_bench + plot_idefix_bench.do_plot('Performance on NVidia V100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'v100') + +.. plot:: + + import plot_idefix_bench + plot_idefix_bench.do_plot('Performance on NVidia A100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'a100') + +.. plot:: + + import plot_idefix_bench + plot_idefix_bench.do_plot('Performance on NVidia H100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'h100') + +----------------------+--------------------+----------------------------------------------------+ | Cluster name | GPU | Performances (in 10\ :sup:`6` cell/s/GPU) | +======================+====================+====================================================+ -| IDRIS/Jean Zay | NVIDIA V100 | 110 | -+----------------------+--------------------+----------------------------------------------------+ -| IDRIS/Jean Zay | NVIDIA A100 | 194 | -+----------------------+--------------------+----------------------------------------------------+ | CINES/Adastra | AMD Mi250 | 250 | +----------------------+--------------------+----------------------------------------------------+ diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py new file mode 100644 index 000000000..cd45aa5a9 --- /dev/null +++ b/doc/source/plot_idefix_bench.py @@ -0,0 +1,14 @@ +import matplotlib.pyplot as plt +import json + +def do_plot(title, bench_file, gpumodel): + with open(bench_file, 'r') as f: + benches = json.load(f) + + select = [bench for bench in benches if bench['gpumodel'] == gpumodel][-1] + xs = [r['nbgpu'] for r in select['results']] + ys = [r['cell_updates'] for r in select['results']] + + plt.xscale("log") + plt.plot(xs, ys) + plt.title(title) From a61eb61af47c10e7caf0810a0560457af1ea809d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Mon, 20 Jan 2025 12:33:43 +0100 Subject: [PATCH 017/144] Updated doc for Collisionless TC --- doc/source/modules/braginskii.rst | 63 ++++++++++++++++++++++++++++--- reference | 2 +- 2 files changed, 59 insertions(+), 6 deletions(-) diff --git a/doc/source/modules/braginskii.rst b/doc/source/modules/braginskii.rst index ccc841f4f..4c1c4dd6f 100644 --- a/doc/source/modules/braginskii.rst +++ b/doc/source/modules/braginskii.rst @@ -4,7 +4,7 @@ Braginskii module =================== Equations solved and methods ---------------------------- +---------------------------- The ``Braginskii`` module implements the anisotropic heat and momentum fluxes specific to weakly collisional, magnetised plasma like the intracluster medium @@ -72,18 +72,69 @@ of the Braginskii heat flux and viscosity. .. _braginskiiParameterSection: + +Saturation with collisionless heat flux +--------------------------------------- + +The ``Braginskii`` module can include a collisionless saturation of the Braginskii heat flux. +The heat flux is then computed as follows: + +:math:`q = \alpha (q_B + q_\perp) + (1-\alpha)\beta*p*v`, + +where :math:`\alpha \in [0,1]` controls the transition between the Braginskii heat flux and the collisionless heat flux +and :math:`\beta` controls the amplitude of the collisionless heat flux (typically :math:`\beta \in [1,4]`, see Hollweg 1976). + +.. note:: + As a result, even with :math:`\kappa_\perp = 0`, the heat flux is no longer necessarilly strictly aligned with the magnetic field. +.. note:: + The collisionless heat flux is a hyperbolic term and the diffusion coefficient is set proportional to :math:`\alpha`. +.. note:: + If selected, slope limiters are also used in the collisionless flux, where an upwind scheme has been implemented for stability. +.. note:: + This saturation has been thought to be used mostly using the uerdef function that takes four arrays as input and is enrolled through + ``data.hydro->bragThermalDiffusion->EnrollClessThermalDiffusivity()`` + Main parameters of the module ----------------------------- The ``Braginskii`` module can be enabled adding one or two lines in the ``[Hydro]`` section -starting with the keyword -`bragTDiffusion` or/and *bragViscosity*. The following table summarises the different options +starting with the keyword `bragTDiffusion` or/and *bragViscosity*. The following tables summarise the different options associated to the activation of the Braginskii module: +--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ | Column | Entry name | Parameter type | Comment | +========+=======================+=========================+=======================================================================================+ -| 0 | bragModule | string | | Activates Braginskii diffusion. Can be ``bragTDiffusion`` or ``bragViscosity``. | +| 0 | bragTDiffusion | string | | Activates Braginskii thermal diffusion. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 1 | integration | string | | Specifies the type of scheme to be used to integrate the parabolic term. | +| | | | | Can be ``rkl`` or ``explicit``. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 2 | slope limiter | string | | Choose the type of limiter to be used to compute anisotropic transverse flux terms. | +| | | | | Can be ``mc``, ``vanleer`` or ``nolimiter``. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 3 | saturation mode | string | | Include or not collisionless saturation. Can be ``nosat`` or ``wcless``. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 4 | diffusivity type | string | | Specifies the type of diffusivity wanted. Can be ``constant`` or ``userdef``. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 5 | parallel diffusivity | real | | Mandatory if the diffusivity type is ``constant``. Not needed otherwise. | +| | | | | Value of the parallel diffusivity. Should be a real number. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 6 | normal diffusivity | real | | When bragModule ``bragTDiffusion`` and diffusivity type ``constant``, | +| | | | | value of the normal diffusivity. Should be a real number. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 7 | alpha collisionless | real | | If the diffusivity type is ``constant`` and saturation is ``wcless``. | +| | | | | Set to 1 if not provided. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| 8 | beta collisionless | real | | If the diffusivity type is ``constant`` and saturation is ``wcless``. | +| | | | | Set to 0 if not provided. | ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ + +for the *bragViscosity*: + ++--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ +| Column | Entry name | Parameter type | Comment | ++========+=======================+=========================+=======================================================================================+ +| 0 | bragViscosity | string | | Activates Braginskii viscosity. | +--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ | 1 | integration | string | | Specifies the type of scheme to be used to integrate the parabolic term. | | | | | | Can be ``rkl`` or ``explicit``. | @@ -101,7 +152,7 @@ associated to the activation of the Braginskii module: +--------+-----------------------+-------------------------+---------------------------------------------------------------------------------------+ Numerical checks ---------------- +---------------- In Cartesian geometry, the ``Braginskii`` module has been tested with many setups and in all configurations of magnetic polarisation: @@ -119,3 +170,5 @@ The same goes for the anisotropic heat flux in Cylindrical/Polar geometry while the anisotropic viscosity has *never* been tested in this geometry. In spherical geometry, both ``Braginskii`` operators have been partially validated (diffusion along the polar axis has not been directly tested). + +The collisionless saturation has been tested in 1D and 2D spherical geometry. diff --git a/reference b/reference index 99f339c43..609a60164 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 99f339c43d98274a925282cc96252c5a0fa9374f +Subproject commit 609a60164461fb2d4fbeffa89ce148acf1191525 From 7bef7a974c409fea952dc75ea5f81e51f657e783 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Mon, 20 Jan 2025 16:46:27 +0100 Subject: [PATCH 018/144] Corrected doc typo --- doc/source/modules/braginskii.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/source/modules/braginskii.rst b/doc/source/modules/braginskii.rst index 4c1c4dd6f..d9cb4f2d8 100644 --- a/doc/source/modules/braginskii.rst +++ b/doc/source/modules/braginskii.rst @@ -91,7 +91,7 @@ and :math:`\beta` controls the amplitude of the collisionless heat flux (typical .. note:: If selected, slope limiters are also used in the collisionless flux, where an upwind scheme has been implemented for stability. .. note:: - This saturation has been thought to be used mostly using the uerdef function that takes four arrays as input and is enrolled through + This saturation has been thought to be used mostly using the userdef function that takes four arrays as input and is enrolled through ``data.hydro->bragThermalDiffusion->EnrollClessThermalDiffusivity()`` Main parameters of the module From 8f48bc2b34f5223be8de1faa61d2c5bd05cf95b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Tue, 21 Jan 2025 13:22:36 +0100 Subject: [PATCH 019/144] Corrected typo --- src/fluid/braginskii/bragThermalDiffusion.cpp | 14 +++++++------- src/fluid/braginskii/bragThermalDiffusion.hpp | 4 ++-- src/fluid/braginskii/bragViscosity.cpp | 9 ++++----- 3 files changed, 13 insertions(+), 14 deletions(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index a898ab8bd..0dd0b0331 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -42,18 +42,18 @@ void BragThermalDiffusion::ShowConfig() { IDEFIX_ERROR("Unknown time integrator for braginskii thermal diffusion."); } if(haveSlopeLimiter) { - if(haveMonotizedCentral) { - idfx::cout << "Braginskii Thermal Diffusion: uses the monotonized central slope limiter." << std::endl; - } - else if(haveVanLeer) { + if(haveMonotonizedCentral) { + idfx::cout << "Braginskii Thermal Diffusion: " + "uses the monotonized central slope limiter." << std::endl; + } else if(haveVanLeer) { idfx::cout << "Braginskii Thermal Diffusion: uses the van Leer slope limiter." << std::endl; - } - else { + } else { IDEFIX_ERROR("Unknown slope limiter for braginskii thermal diffusion."); } } if(includeCollisionlessTD) { - idfx::cout << "Braginskii Thermal Diffusion: saturation with collisionless flux is enabled." << std::endl; + idfx::cout << "Braginskii Thermal Diffusion: saturation" + " with collisionless flux is enabled." << std::endl; } } diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 2a103a491..d05c20b4e 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -59,7 +59,7 @@ class BragThermalDiffusion { bool includeCollisionlessTD{false}; bool haveSlopeLimiter{false}; - bool haveMonotizedCentral{false}; + bool haveMonotonizedCentral{false}; bool haveVanLeer{false}; bool haveMinmod{false}; @@ -94,7 +94,7 @@ BragThermalDiffusion::BragThermalDiffusion(Input &input, Grid &grid, Fluid if(input.CheckEntry("Hydro","bragTDiffusion")>=0) { if(input.Get("Hydro","bragTDiffusion",1).compare("mc") == 0) { this->haveSlopeLimiter = true; - this->haveMonotizedCentral = true; + this->haveMonotonizedCentral = true; limiter = PLMLimiter::McLim; } else if(input.Get("Hydro","bragTDiffusion",1).compare("vanleer") == 0) { this->haveSlopeLimiter = true; diff --git a/src/fluid/braginskii/bragViscosity.cpp b/src/fluid/braginskii/bragViscosity.cpp index e05019a43..e53ab2c65 100644 --- a/src/fluid/braginskii/bragViscosity.cpp +++ b/src/fluid/braginskii/bragViscosity.cpp @@ -60,12 +60,11 @@ void BragViscosity::ShowConfig() { } if(haveSlopeLimiter) { if(haveMonotizedCentral) { - idfx::cout << "Braginskii Viscosity: uses the monotonized central slope limiter." << std::endl; - } - else if(haveVanLeer) { + idfx::cout << "Braginskii Viscosity: uses the " + "monotonized central slope limiter." << std::endl; + } else if(haveVanLeer) { idfx::cout << "Braginskii Viscosity: uses the van Leer slope limiter." << std::endl; - } - else { + } else { IDEFIX_ERROR("Unknown slope limiter for braginskii viscosity."); } } From 1f891c76289640fdd25ac27f451a1c6d7be06c3b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Jan 2025 17:34:37 +0100 Subject: [PATCH 020/144] add global routines to dump Idefix arrays (useful for debugging or checking that everything works as expected) --- src/global.hpp | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/src/global.hpp b/src/global.hpp index 8651f9748..0cf57e15f 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -44,6 +44,34 @@ IdefixArray1D ConvertVectorToIdefixArray(std::vector &inputVector) { return(outArr); } +///< dump Idefix array to a numpy array on disk +template +void dumpArray(std::string filename, IdefixArray3D array) { + IdefixHostArray3D hArray = Kokkos::create_mirror(array); + Kokkos::deep_copy(hArray,array); + + std::array shape; + bool fortran_order{false}; + shape[0] = array.extent(0); + shape[1] = array.extent(1); + shape[2] = array.extent(2); + npy::SaveArrayAsNumpy(filename, fortran_order, 3, shape.data(), hArray.data()); +} + +template +void dumpArray(std::string filename, IdefixArray4D array) { + IdefixHostArray4D hArray = Kokkos::create_mirror(array); + Kokkos::deep_copy(hArray,array); + + std::array shape; + bool fortran_order{false}; + shape[0] = array.extent(0); + shape[1] = array.extent(1); + shape[2] = array.extent(2); + shape[3] = array.extent(3); + npy::SaveArrayAsNumpy(filename, fortran_order, 4, shape.data(), hArray.data()); +} + } // namespace idfx class idfx::IdefixOutStream { From afc3e4dbb2cd052360cdbbe2ca4473e128491752 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Jan 2025 17:37:24 +0100 Subject: [PATCH 021/144] add missing header --- src/global.hpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/global.hpp b/src/global.hpp index 0cf57e15f..1a8944163 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -11,6 +11,7 @@ #include #include #include "arrays.hpp" +#include "npy.hpp" namespace idfx { int initialize(); // Initialisation routine for idefix From e840e2f938f05f64ad153c2fd54db457844e68b8 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Jan 2025 21:23:47 +0100 Subject: [PATCH 022/144] revert back to old reference commit sha to avoid merge conflicts --- reference | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reference b/reference index 609a60164..99f339c43 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 609a60164461fb2d4fbeffa89ce148acf1191525 +Subproject commit 99f339c43d98274a925282cc96252c5a0fa9374f From ac104701e4900c45888eda1b162483b7e240f5f4 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 22 Jan 2025 09:36:35 +0100 Subject: [PATCH 023/144] go back to last reference before fork --- reference | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reference b/reference index 99f339c43..b675bceaa 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 99f339c43d98274a925282cc96252c5a0fa9374f +Subproject commit b675bceaa6aabc01dded346e2d631857f698dc76 From 76e399aadfc86e48add05dc079b9d6131de320de Mon Sep 17 00:00:00 2001 From: Marc Coiffier Date: Fri, 24 Jan 2025 11:56:44 +0100 Subject: [PATCH 024/144] =?UTF-8?q?R=C3=A9cup=C3=A9ration=20des=20derniers?= =?UTF-8?q?=20benchmarks=20sur=20JeanZay?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- doc/source/bench-jeanzay.json | 24 ++++++++++++++++++++++++ 1 file changed, 24 insertions(+) mode change 100755 => 100644 doc/source/bench-jeanzay.json diff --git a/doc/source/bench-jeanzay.json b/doc/source/bench-jeanzay.json old mode 100755 new mode 100644 index f58d38d42..6d5fd5ca1 --- a/doc/source/bench-jeanzay.json +++ b/doc/source/bench-jeanzay.json @@ -80,6 +80,14 @@ { "nbgpu": 32, "cell_updates": 6.669339E+7 + }, + { + "nbgpu": 64, + "cell_updates": 5.497455E+7 + }, + { + "nbgpu": 128, + "cell_updates": 5.440610E+7 } ] }, @@ -104,6 +112,22 @@ { "nbgpu": 8, "cell_updates": 1.929568E+8 + }, + { + "nbgpu": 16, + "cell_updates": 9.408132E+7 + }, + { + "nbgpu": 32, + "cell_updates": 5.937487E+7 + }, + { + "nbgpu": 64, + "cell_updates": 4.159838E+7 + }, + { + "nbgpu": 128, + "cell_updates": 5.061931E+7 } ] }, From 49a56ee5b83d0822831bcb8f41859104bee5ea41 Mon Sep 17 00:00:00 2001 From: Marc Coiffier Date: Fri, 24 Jan 2025 14:33:29 +0100 Subject: [PATCH 025/144] =?UTF-8?q?R=C3=A9cup=C3=A9ration=20de=20benchs=20?= =?UTF-8?q?pour=20H100;=20ajout=20de=20labels=20aux=20axes?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- doc/source/bench-jeanzay.json | 64 +++++++++++++++++++++++++++++++++ doc/source/plot_idefix_bench.py | 7 ++-- 2 files changed, 69 insertions(+), 2 deletions(-) diff --git a/doc/source/bench-jeanzay.json b/doc/source/bench-jeanzay.json index 6d5fd5ca1..7ded6914e 100644 --- a/doc/source/bench-jeanzay.json +++ b/doc/source/bench-jeanzay.json @@ -142,5 +142,69 @@ "cell_updates": 3.083581E+8 } ] + }, + { + "date": "2025-01-24_13:02:08", + "gpumodel": "h100", + "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 3.076537E+8 + } + ] + }, + { + "date": "2025-01-24_13:04:02", + "gpumodel": "h100", + "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 3.032686E+8 + }, + { + "nbgpu": 2, + "cell_updates": 3.007089E+8 + }, + { + "nbgpu": 4, + "cell_updates": 2.938962E+8 + } + ] + }, + { + "date": "2025-01-24_14:17:30", + "gpumodel": "h100", + "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", + "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "results": [ + { + "nbgpu": 1, + "cell_updates": 3.074363E+8 + }, + { + "nbgpu": 2, + "cell_updates": 3.009340E+8 + }, + { + "nbgpu": 4, + "cell_updates": 2.938868E+8 + }, + { + "nbgpu": 8, + "cell_updates": 2.833054E+8 + }, + { + "nbgpu": 16, + "cell_updates": 2.822483E+8 + }, + { + "nbgpu": 32, + "cell_updates": 2.817151E+8 + } + ] } ] diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py index cd45aa5a9..ac91b787e 100644 --- a/doc/source/plot_idefix_bench.py +++ b/doc/source/plot_idefix_bench.py @@ -8,7 +8,10 @@ def do_plot(title, bench_file, gpumodel): select = [bench for bench in benches if bench['gpumodel'] == gpumodel][-1] xs = [r['nbgpu'] for r in select['results']] ys = [r['cell_updates'] for r in select['results']] - - plt.xscale("log") + + plt.xscale("log", base=2) plt.plot(xs, ys) + plt.ylim(0,max(ys)*1.1) + plt.xlabel("Number of GPUs") + plt.ylabel("Performance (cells / second / GPU)") plt.title(title) From 0cb52eaeecb730f3264344e2b5c6ccd36c18c92e Mon Sep 17 00:00:00 2001 From: "pre-commit-ci-lite[bot]" <117423508+pre-commit-ci-lite[bot]@users.noreply.github.com> Date: Fri, 24 Jan 2025 13:34:54 +0000 Subject: [PATCH 026/144] [pre-commit.ci lite] apply automatic fixes --- doc/source/performances.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/source/performances.rst b/doc/source/performances.rst index 985991e34..6f8c88b2f 100644 --- a/doc/source/performances.rst +++ b/doc/source/performances.rst @@ -50,7 +50,7 @@ GPU performances import plot_idefix_bench plot_idefix_bench.do_plot('Performance on NVidia H100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'h100') - + +----------------------+--------------------+----------------------------------------------------+ | Cluster name | GPU | Performances (in 10\ :sup:`6` cell/s/GPU) | +======================+====================+====================================================+ From 0c07a8e2f309489ccc9c7e836f16271ef1783105 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Wed, 29 Jan 2025 08:35:10 +0100 Subject: [PATCH 027/144] Use a std::vector of IdefixArray as input for the userdef braginskii diffusion --- doc/source/modules/braginskii.rst | 5 +- src/fluid/braginskii/bragThermalDiffusion.cpp | 13 +--- src/fluid/braginskii/bragThermalDiffusion.hpp | 65 ++++++++++--------- src/fluid/fluid_defs.hpp | 8 +-- test/MHD/MTI/setup.cpp | 6 +- test/MHD/clessTDiffusion/CMakeLists.txt | 1 - test/MHD/clessTDiffusion/python/testidefix.py | 2 +- test/MHD/clessTDiffusion/setup.cpp | 26 +++++--- 8 files changed, 64 insertions(+), 62 deletions(-) diff --git a/doc/source/modules/braginskii.rst b/doc/source/modules/braginskii.rst index d9cb4f2d8..fd5f2b8fc 100644 --- a/doc/source/modules/braginskii.rst +++ b/doc/source/modules/braginskii.rst @@ -76,7 +76,7 @@ of the Braginskii heat flux and viscosity. Saturation with collisionless heat flux --------------------------------------- -The ``Braginskii`` module can include a collisionless saturation of the Braginskii heat flux. +The ``Braginskii`` module can include a collisionless saturation of the Braginskii heat flux, typically due to supra-thermal electrons. The heat flux is then computed as follows: :math:`q = \alpha (q_B + q_\perp) + (1-\alpha)\beta*p*v`, @@ -91,8 +91,7 @@ and :math:`\beta` controls the amplitude of the collisionless heat flux (typical .. note:: If selected, slope limiters are also used in the collisionless flux, where an upwind scheme has been implemented for stability. .. note:: - This saturation has been thought to be used mostly using the userdef function that takes four arrays as input and is enrolled through - ``data.hydro->bragThermalDiffusion->EnrollClessThermalDiffusivity()`` + This saturation has been thought to be used mostly using the userdef function that takes four userdef arrays as input. Main parameters of the module ----------------------------- diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index 0dd0b0331..f251d0b0c 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -19,7 +19,6 @@ #include "eos.hpp" - void BragThermalDiffusion::ShowConfig() { if(status.status==Constant) { idfx::cout << "Braginskii Thermal Diffusion: ENABLED with constant diffusivity kpar=" @@ -27,7 +26,7 @@ void BragThermalDiffusion::ShowConfig() { } else if (status.status==UserDefFunction) { idfx::cout << "Braginskii Thermal Diffusion: ENABLED with user-defined diffusivity function." << std::endl; - if(!bragDiffusivityFunc && !clessDiffusivityFunc) { + if(!bragDiffusivityFunc) { IDEFIX_ERROR("No braginskii thermal diffusion function has been enrolled"); } } else { @@ -57,7 +56,7 @@ void BragThermalDiffusion::ShowConfig() { } } -void BragThermalDiffusion::EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc myFunc) { +void BragThermalDiffusion::EnrollBragThermalDiffusivity(BragDiffusivityFunc myFunc) { if(this->status.status != UserDefFunction) { IDEFIX_WARNING("Braginskii thermal diffusivity enrollment requires Hydro/BragThermalDiffusion " "to be set to userdef in .ini file"); @@ -65,14 +64,6 @@ void BragThermalDiffusion::EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc this->bragDiffusivityFunc = myFunc; } -void BragThermalDiffusion::EnrollClessThermalDiffusivity(FourArrayDiffusivityFunc myFunc) { - if(this->status.status != UserDefFunction) { - IDEFIX_WARNING("Collisionless/Braginskii thermal diffusivity enrollment requires " - "Hydro/BragThermalDiffusion to be set to userdef in .ini file"); - } - this->clessDiffusivityFunc = myFunc; -} - void BragThermalDiffusion::AddBragDiffusiveFlux(int dir, const real t, const IdefixArray4D &Flux) { idfx::pushRegion("BragThermalDiffusion::AddBragDiffusiveFlux"); diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index d05c20b4e..7b1875ff9 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -9,6 +9,7 @@ #define FLUID_BRAGINSKII_BRAGTHERMALDIFFUSION_HPP_ #include +#include #include "idefix.hpp" #include "input.hpp" @@ -35,8 +36,7 @@ class BragThermalDiffusion { void AddBragDiffusiveFluxLim(int, const real, const IdefixArray4D &); // Enroll user-defined thermal conductivity - void EnrollBragThermalDiffusivity(TwoArrayDiffusivityFunc); - void EnrollClessThermalDiffusivity(FourArrayDiffusivityFunc); + void EnrollBragThermalDiffusivity(BragDiffusivityFunc); IdefixArray3D heatSrc; // Source terms of the thermal operator IdefixArray3D knorArr; @@ -53,8 +53,7 @@ class BragThermalDiffusion { // status of the module ParabolicModuleStatus &status; - TwoArrayDiffusivityFunc bragDiffusivityFunc; - FourArrayDiffusivityFunc clessDiffusivityFunc; + BragDiffusivityFunc bragDiffusivityFunc; bool includeCollisionlessTD{false}; @@ -307,7 +306,8 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, if(includeCollisionlessTD == false && haveThermalDiffusion == UserDefFunction && dir == IDIR) { if(bragDiffusivityFunc) { idfx::pushRegion("UserDef::BragThermalDiffusivityFunction"); - bragDiffusivityFunc(*this->data, t, kparArr, knorArr); + std::vector> userdefArr = {kparArr, knorArr}; + bragDiffusivityFunc(*this->data, t, userdefArr); idfx::popRegion(); } else { @@ -315,9 +315,10 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, } } else if(includeCollisionlessTD == true && haveThermalDiffusion == UserDefFunction && dir == IDIR) { - if (clessDiffusivityFunc) { + if (bragDiffusivityFunc) { idfx::pushRegion("UserDef::ClessThermalDiffusivityFunction"); - clessDiffusivityFunc(*this->data, t, kparArr, knorArr, clessAlphaArr, clessBetaArr); + std::vector> userdefArr = {kparArr, knorArr, clessAlphaArr, clessBetaArr}; + bragDiffusivityFunc(*this->data, t, userdefArr); idfx::popRegion(); } else { IDEFIX_ERROR("No user-defined Braginskii/collisionless " @@ -484,14 +485,14 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j,i-1); /* Upwind scheme */ - if (Vc(VX1,k,j,i) > 0.0) { - Vn = Vc(VX1,k,j,i-1)+HALF_F*SL::PLMLim(dvm, dvp); - Pn = Vc(PRS,k,j,i-1)+HALF_F*SL::PLMLim(dpm, dpp); - } - else { - Vn = Vc(VX1,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); - } + if (Vc(VX1,k,j,i) > 0.0) { + Vn = Vc(VX1,k,j,i-1)+HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i-1)+HALF_F*SL::PLMLim(dpm, dpp); + } + else { + Vn = Vc(VX1,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); + } } else { Vn = HALF_F*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i-1)); Pn = HALF_F*(Vc(PRS,k,j,i) + Vc(PRS,k,j,i-1)); @@ -649,14 +650,14 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpp = Vc(PRS,k,j+1,i) - Vc(PRS,k,j,i); dpm = Vc(PRS,k,j,i) - Vc(PRS,k,j-1,i); - /* Upwind scheme */ - if (Vc(VX2,k,j,i) > 0.0) { - Vn = Vc(VX2,k,j-1,i)+HALF_F*SL::PLMLim(dvm, dvp); - Pn = Vc(PRS,k,j-1,i)+HALF_F*SL::PLMLim(dpm, dpp); - } else { - Vn = Vc(VX2,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); - } + /* Upwind scheme */ + if (Vc(VX2,k,j,i) > 0.0) { + Vn = Vc(VX2,k,j-1,i)+HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j-1,i)+HALF_F*SL::PLMLim(dpm, dpp); + } else { + Vn = Vc(VX2,k,j,i)-HALF_F*SL::PLMLim(dvm, dvp); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpm, dpp); + } } else { Vn = HALF_F*(Vc(VX2,k,j-1,i) + Vc(VX2,k,j,i)); Pn = HALF_F*(Vc(PRS,k,j-1,i) + Vc(PRS,k,j,i)); @@ -772,14 +773,14 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, dpp = Vc(PRS,k+1,j,i) - Vc(PRS,k,j,i); dpm = Vc(PRS,k,j,i) - Vc(PRS,k-1,j,i); - /* Upwind scheme */ - if (Vc(VX3,k,j,i) > 0.0) { - Vn = Vc(VX3,k-1,j,i)+HALF_F*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k-1,j,i)+HALF_F*SL::PLMLim(dpp, dpm); - } else { - Vn = Vc(VX3,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); - Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); - } + /* Upwind scheme */ + if (Vc(VX3,k,j,i) > 0.0) { + Vn = Vc(VX3,k-1,j,i)+HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k-1,j,i)+HALF_F*SL::PLMLim(dpp, dpm); + } else { + Vn = Vc(VX3,k,j,i)-HALF_F*SL::PLMLim(dvp, dvm); + Pn = Vc(PRS,k,j,i)-HALF_F*SL::PLMLim(dpp, dpm); + } } else { Vn = HALF_F*(Vc(VX3,k-1,j,i) + Vc(VX3,k,j,i)); Pn = HALF_F*(Vc(PRS,k-1,j,i) + Vc(PRS,k,j,i)); @@ -790,8 +791,8 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bgradT = D_EXPAND( Bi*dTi , + Bj*dTj, +Bk*dTk); Bmag = D_EXPAND( Bi*Bi , + Bj*Bj, + Bk*Bk); + // EXPAND can yield uexpected behaviour when DIMENSIONS < COMPONENTS //printf("%f , %f\n", Bmag, EXPAND(Bi*Bi, + Bj*Bj, + Bk*Bk)); - //printf("%f , %f \n", 0.5*(Vc(VX1,k,j,i) + Vc(VX1,k,j,i+1)), Vn); Bmag = sqrt(Bmag); Bmag = FMAX(1e-6*SMALL_NUMBER,Bmag); diff --git a/src/fluid/fluid_defs.hpp b/src/fluid/fluid_defs.hpp index 1d040071c..3f68c9b49 100644 --- a/src/fluid/fluid_defs.hpp +++ b/src/fluid/fluid_defs.hpp @@ -8,6 +8,7 @@ #ifndef FLUID_FLUID_DEFS_HPP_ #define FLUID_FLUID_DEFS_HPP_ +#include #include "../idefix.hpp" @@ -49,12 +50,9 @@ using SrcTermFunc = void (*) (Fluid *, const real t, const real dt); using EmfBoundaryFunc = void (*) (DataBlock &, const real t); using DiffusivityFunc = void (*) (DataBlock &, const real t, IdefixArray3D &); -using TwoArrayDiffusivityFunc = void (*) (DataBlock &, const real t, - IdefixArray3D &, IdefixArray3D &); -using FourArrayDiffusivityFunc = void (*) (DataBlock &, const real t, - IdefixArray3D &, IdefixArray3D &, - IdefixArray3D &, IdefixArray3D &); +using BragDiffusivityFunc = void (*) (DataBlock &, const real, + std::vector> &); // Deprecated signatures using SrcTermFuncOld = void (*) (DataBlock &, const real t, const real dt); diff --git a/test/MHD/MTI/setup.cpp b/test/MHD/MTI/setup.cpp index e631f7b2b..1608b5eca 100644 --- a/test/MHD/MTI/setup.cpp +++ b/test/MHD/MTI/setup.cpp @@ -39,9 +39,13 @@ void Potential(DataBlock& data, const real t, IdefixArray1D& x1, IdefixArr } -void MyBragThermalConductivity(DataBlock &data, const real t, IdefixArray3D &kparArr, IdefixArray3D &knorArr) { +void MyBragThermalConductivity(DataBlock &data, const real t, std::vector> &userdefArr) { IdefixArray4D Vc = data.hydro->Vc; IdefixArray1D x2 = data.x[JDIR]; + + IdefixArray3D kparArr = userdefArr[0]; + IdefixArray3D knorArr = userdefArr[1]; + real ksi = ksiGlob; idefix_for("MyThConductivity",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], KOKKOS_LAMBDA (int k, int j, int i) { diff --git a/test/MHD/clessTDiffusion/CMakeLists.txt b/test/MHD/clessTDiffusion/CMakeLists.txt index aa9abdd74..629aed2d1 100644 --- a/test/MHD/clessTDiffusion/CMakeLists.txt +++ b/test/MHD/clessTDiffusion/CMakeLists.txt @@ -1,2 +1 @@ enable_idefix_property(Idefix_MHD) -set_idefix_property(Idefix_RECONSTRUCTION Parabolic) diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py index 444816d1f..9427aca82 100644 --- a/test/MHD/clessTDiffusion/python/testidefix.py +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -22,7 +22,7 @@ def gamma_prime(gamma, beta): return (gamma+beta*(gamma-1))/(1+beta*(gamma-1)) success = True -eps = 1e-2 +eps = 3e-4 gamma_eff = np.gradient(prs, r)/np.gradient(rho, r)*rho/prs diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index 624e1d72b..7c6e7eb2a 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -10,19 +10,28 @@ real va_vescGlob; real k0_Glob; real ParkerWind(real); -void MyClessThermalConductivity(DataBlock &data, const real t, IdefixArray3D &kparArr, IdefixArray3D &knorArr, IdefixArray3D &alpha, IdefixArray3D &clessQ) { +const real kB{1.3807e-16}; +const real mp{1.6726e-24}; + +void MyClessThermalConductivity(DataBlock &data, const real t, std::vector> &userdefArr) { IdefixArray4D Vc = data.hydro->Vc; IdefixArray1D x1 = data.x[IDIR]; IdefixArray1D x2 = data.x[JDIR]; - real norm = 1.6726e-24*0.5/(udenGlob*uvelGlob*ulenGlob*1.3807e-16); - real uTemp=0.5*uvelGlob*uvelGlob*1.6726e-24/1.3807e-16; + + IdefixArray3D kparArr = userdefArr[0]; + IdefixArray3D knorArr = userdefArr[1]; + IdefixArray3D clessAlpha = userdefArr[2]; + IdefixArray3D clessBeta = userdefArr[3]; + + real norm = mp*0.5/(udenGlob*uvelGlob*ulenGlob*kB); + real uTemp=0.5*uvelGlob*uvelGlob*mp/kB; real k0 = k0_Glob*norm; - idefix_for("MyThConductivity",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], + idefix_for("MyClessThConductivity",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], KOKKOS_LAMBDA (int k, int j, int i) { kparArr(k,j,i) = k0*pow(Vc(PRS,k,j,i)/Vc(RHO,k,j,i)*uTemp,2.5); knorArr(k,j,i) = 0.; - alpha(k,j,i) = (1.0-tanh(x1(i)-10))/2; - clessQ(k,j,i) = -1.5; + clessAlpha(k,j,i) = (1.0-tanh(x1(i)-10))/2; + clessBeta(k,j,i) = -1.5; }); } @@ -39,6 +48,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { real rc,vc,vwind0; real cs=cs_vescGlob*sqrt(2.); real va_vesc = va_vescGlob; + real mu = va_vesc * sqrt(2.); real PonRho; PonRho = cs*cs; @@ -49,7 +59,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { hydro->boundary->BoundaryFor("UserDefBoundary", dir, side, KOKKOS_LAMBDA (int k, int j, int i) { real r = x1(i); - real mu = va_vesc * sqrt(2.); + Vc(RHO,k,j,i) = vwind0/(vwind0 * r * r); Vc(PRS,k,j,i) = PonRho * Vc(RHO, k, j, i); Vc(VX1,k,j,i) = vwind0; @@ -68,7 +78,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { // Set the function for userdefboundary data.hydro->EnrollUserDefBoundary(&UserDefBoundary); - data.hydro->bragThermalDiffusion->EnrollClessThermalDiffusivity(&MyClessThermalConductivity); + data.hydro->bragThermalDiffusion->EnrollBragThermalDiffusivity(&MyClessThermalConductivity); gammaGlob=input.Get("Hydro", "gamma", 0); udenGlob=input.Get("Setup", "UNIT_DENSITY",0); ulenGlob=input.Get("Setup", "UNIT_LENGTH",0); From 250610a19b14c537515ef54f09a780c39bf180f7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Wed, 29 Jan 2025 08:43:52 +0100 Subject: [PATCH 028/144] corrected typo --- src/fluid/braginskii/bragThermalDiffusion.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 7b1875ff9..116ff9a03 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -791,7 +791,7 @@ void BragThermalDiffusion::AddBragDiffusiveFluxLim(int dir, const real t, bgradT = D_EXPAND( Bi*dTi , + Bj*dTj, +Bk*dTk); Bmag = D_EXPAND( Bi*Bi , + Bj*Bj, + Bk*Bk); - // EXPAND can yield uexpected behaviour when DIMENSIONS < COMPONENTS + // EXPAND can yield unexpected behaviour when DIMENSIONS < COMPONENTS //printf("%f , %f\n", Bmag, EXPAND(Bi*Bi, + Bj*Bj, + Bk*Bk)); Bmag = sqrt(Bmag); Bmag = FMAX(1e-6*SMALL_NUMBER,Bmag); From 898fcf3e91f416395f3d9ced590ce1df8f365e08 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sun, 9 Feb 2025 21:36:47 +0100 Subject: [PATCH 029/144] add some doc --- doc/source/programmingguide.rst | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/doc/source/programmingguide.rst b/doc/source/programmingguide.rst index 18795b50a..4bd7c69f7 100644 --- a/doc/source/programmingguide.rst +++ b/doc/source/programmingguide.rst @@ -645,6 +645,27 @@ It may also be useful to implement debug-only safeguards with custom logic that fit `RUNTIME_CHECK_*` macros. This can be achieved by using the compiler directive `#ifdef RUNTIME_CHECKS` directly. +Dump an array to a file +----------------------- + +It is usually difficult to know what Idefix arrays effectively contains, especially when running on GPU. +To help with this difficulty, Idefix provides a global function ``DumpArray`` that can be used +to dump a ``IdefixArray`` to a numpy file (that can be read from python). This feature can be used +for debugging purpose as: + + +.. code-block:: c++ + + #include "idefix.hpp" + + IdefixArray3D myArray("debugMe",10,10,10); + + idfx::DumpArray("myFilename.npy",myArray); // Dump the array content to a numpy file named "myFilename.npy" + + +Note that the array is automatically transfered from the GPU, if needed. + + Minimal skeleton ================ From 241c69c8b524caeea33c73cdc4f20db6f0151470 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 10 Feb 2025 08:52:58 +0100 Subject: [PATCH 030/144] refactor DumpArray --- src/global.hpp | 32 +++++++++----------------------- 1 file changed, 9 insertions(+), 23 deletions(-) diff --git a/src/global.hpp b/src/global.hpp index 1a8944163..265699b29 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -46,31 +46,17 @@ IdefixArray1D ConvertVectorToIdefixArray(std::vector &inputVector) { } ///< dump Idefix array to a numpy array on disk -template -void dumpArray(std::string filename, IdefixArray3D array) { - IdefixHostArray3D hArray = Kokkos::create_mirror(array); - Kokkos::deep_copy(hArray,array); +template +void DumpArray(std::string filename, ArrayType array) { + auto hArray = Kokkos::create_mirror(array); + Kokkos::deep_copy(hArray, array); - std::array shape; + std::array shape; bool fortran_order{false}; - shape[0] = array.extent(0); - shape[1] = array.extent(1); - shape[2] = array.extent(2); - npy::SaveArrayAsNumpy(filename, fortran_order, 3, shape.data(), hArray.data()); -} - -template -void dumpArray(std::string filename, IdefixArray4D array) { - IdefixHostArray4D hArray = Kokkos::create_mirror(array); - Kokkos::deep_copy(hArray,array); - - std::array shape; - bool fortran_order{false}; - shape[0] = array.extent(0); - shape[1] = array.extent(1); - shape[2] = array.extent(2); - shape[3] = array.extent(3); - npy::SaveArrayAsNumpy(filename, fortran_order, 4, shape.data(), hArray.data()); + for (size_t i = 0; i < ArrayType::rank; ++i) { + shape[i] = array.extent(i); + } + npy::SaveArrayAsNumpy(filename, fortran_order, ArrayType::rank, shape.data(), hArray.data()); } } // namespace idfx From ab340ed54c34892826716dfa12d57958f76fb102 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 10 Feb 2025 17:55:33 +0100 Subject: [PATCH 031/144] implements a 1st order IMEX1 solver for polydisperse dust species --- src/dataBlock/evolveStage.cpp | 10 ++ src/fluid/drag.cpp | 194 +++++++++++++++++++++++ src/fluid/drag.hpp | 28 +++- src/fluid/evolveStage.hpp | 6 +- test/Dust/DustEnergy/idefix-implicit.ini | 36 +++++ test/Dust/DustEnergy/testme.py | 2 +- test/Dust/DustyWave/idefix-implicit.ini | 36 +++++ test/Dust/DustyWave/testme.py | 2 +- 8 files changed, 309 insertions(+), 5 deletions(-) create mode 100644 test/Dust/DustEnergy/idefix-implicit.ini create mode 100644 test/Dust/DustyWave/idefix-implicit.ini diff --git a/src/dataBlock/evolveStage.cpp b/src/dataBlock/evolveStage.cpp index 981c060ae..c97c9f713 100644 --- a/src/dataBlock/evolveStage.cpp +++ b/src/dataBlock/evolveStage.cpp @@ -19,6 +19,16 @@ void DataBlock::EvolveStage() { for(int i = 0 ; i < dust.size() ; i++) { dust[i]->EvolveStage(this->t,this->dt); } + // Add implicit term for dust drag + if(dust[0]->drag->IsImplicit()) { + for(int i = 0 ; i < dust.size() ; i++) { + dust[i]->drag->AddImplicitBackReaction(this->dt,dust[0]->drag->implicitFactor); + } + dust[0]->drag->NormalizeImplicitBackReaction(this->dt); + for(int i = 0 ; i < dust.size() ; i++) { + dust[i]->drag->AddImplicitFluidMomentum(this->dt); + } + } } idfx::popRegion(); diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index d24e0bea7..46542147f 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -21,6 +21,10 @@ void Drag::AddDragForce(const real dt) { EquationOfState eos = *(this->eos); + if(implicit) { + IDEFIX_ERROR("Add DragForce should not be called when drag is implicit"); + } + auto userGammai = this->gammai; if(type == Type::Userdef) { if(userDrag != NULL) { @@ -78,9 +82,199 @@ void Drag::AddDragForce(const real dt) { }); idfx::popRegion(); } +// +// $ p_g^{(n+1)}=p_g^{(n)}+\sum_i\frac{\rho_g\gamma_i dt}{1+\rho_g \gamma_i dt}p_i^{(n)} $ +// We accumulate in the array "prefactor" +// $ \sum_i\frac{\rho_i\gamma_i dt}{1+\rho_g\gamma_i dt} +// + +void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) { + if(!feedback) { + // no feedback, no need for anything + return; + } + idfx::pushRegion("AddImplicitFluidMomentum"); + + auto UcGas = this->UcGas; + auto VcGas = this->VcGas; + auto UcDust = this->UcDust; + auto VcDust = this->VcDust; + + const Type type = this->type; + real dragCoeff = this->dragCoeff; + bool feedback = this->feedback; + + bool isFirst = this->instanceNumber == 0; + + EquationOfState eos = *(this->eos); + + if(!implicit) { + IDEFIX_ERROR("AddImplicitGasMomentum should not be called when drag is explicit"); + } + + auto userGammai = this->gammai; + if(type == Type::Userdef) { // If feedback enabled, + // the coefficients were already computed in the gas + // momentum pass + if(userDrag != NULL) { + idfx::pushRegion("Drag::UserDrag"); + userDrag(data, dragCoeff, userGammai); + idfx::popRegion(); + } else { + IDEFIX_ERROR("No User-defined drag function has been enrolled"); + } + } + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) + // Where gamma is computed according to the choice of drag type + idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + real gamma; // The drag coefficient + if(type == Type::Gamma) { + gamma = dragCoeff; + + } else if(type == Type::Tau) { + // In this case, the coefficient is the stopping time (assumed constant) + gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); + } else if(type == Type::Size) { + real cs; + // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs + // Get the sound speed + #if HAVE_ENERGY == 1 + cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) + *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); + #else + cs = eos.GetWaveSpeed(k,j,i); + #endif + gamma = cs/dragCoeff; + } else if(type == Type::Userdef) { + gamma = userGammai(k,j,i); + } + + const real factor = VcDust(RHO,k,j,i)*gamma*dt/(1+VcGas(RHO,k,j,i)*gamma*dt); + if(isFirst) { + preFactor(k,j,i) = factor; + } else { + preFactor(k,j,i) += factor; + } + + for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { + UcGas(n,k,j,i) += dt * gamma * VcGas(RHO,k,j,i) * UcDust(n,k,j,i) / + (1 + VcGas(RHO,k,j,i)*dt*gamma); + } + }); + idfx::popRegion(); +} + +void Drag::NormalizeImplicitBackReaction(const real dt) { + if(!feedback) { + // no feedback, no need for anything + return; + } + idfx::pushRegion("AddImplicitFluidMomentum"); + + auto UcGas = this->UcGas; + auto preFactor = this->implicitFactor; + + if(!implicit) { + IDEFIX_ERROR("AddImplicitGasMomentum should not be called when drag is explicit"); + } + + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) + // Where gamma is computed according to the choice of drag type + idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + const real factor = 1+preFactor(k,j,i); + for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { + UcGas(n,k,j,i) /= factor; + } + }); + idfx::popRegion(); +} + +void Drag::AddImplicitFluidMomentum(const real dt) { + idfx::pushRegion("AddImplicitFluidMomentum"); + + auto UcGas = this->UcGas; + auto VcGas = this->VcGas; + auto UcDust = this->UcDust; + auto VcDust = this->VcDust; + auto InvDt = this->InvDt; + + const Type type = this->type; + real dragCoeff = this->dragCoeff; + bool feedback = this->feedback; + + EquationOfState eos = *(this->eos); + + if(!implicit) { + IDEFIX_ERROR("AddImplicitGasMomentum should not be called when drag is explicit"); + } + + auto userGammai = this->gammai; + if(type == Type::Userdef && !feedback) { // If feedback enabled, + // the coefficients were already computed in the gas + // momentum pass + if(userDrag != NULL) { + idfx::pushRegion("Drag::UserDrag"); + userDrag(data, dragCoeff, userGammai); + idfx::popRegion(); + } else { + IDEFIX_ERROR("No User-defined drag function has been enrolled"); + } + } + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) + // Where gamma is computed according to the choice of drag type + idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + real gamma; // The drag coefficient + if(type == Type::Gamma) { + gamma = dragCoeff; + + } else if(type == Type::Tau) { + // In this case, the coefficient is the stopping time (assumed constant) + gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); + } else if(type == Type::Size) { + real cs; + // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs + // Get the sound speed + #if HAVE_ENERGY == 1 + cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) + *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); + #else + cs = eos.GetWaveSpeed(k,j,i); + #endif + gamma = cs/dragCoeff; + } else if(type == Type::Userdef) { + gamma = userGammai(k,j,i); + } + + for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { + real oldUc = UcDust(n,k,j,i); + UcDust(n,k,j,i) = (oldUc + dt * gamma * VcDust(RHO,k,j,i) * UcGas(n,k,j,i)) / + (1 + VcGas(RHO,k,j,i)*dt*gamma); + + #if HAVE_ENERGY == 1 + real dp = UcDust(n,k,j,i) - oldUc; + + // We add back the energy dissipated for the dust which is not accounted for + // (since there is no energy equation for dust grains) + + // TODO(GL): this should be disabled in the case of a true multifluid system where + // both fluids have a proper energy equation + UcGas(ENG,k,j,i) -= dp*VcDust(n,k,j,i); + #endif + } + }); + idfx::popRegion(); +} void Drag::ShowConfig() { idfx::cout << "Drag: Using "; + if(implicit) { + idfx::cout << " IMPLICIT "; + } else { + idfx::cout << " EXPLICIT "; + } switch(type) { case Type::Gamma: idfx::cout << "constant gamma"; diff --git a/src/fluid/drag.hpp b/src/fluid/drag.hpp index d5f7a5a73..c676a88eb 100644 --- a/src/fluid/drag.hpp +++ b/src/fluid/drag.hpp @@ -24,7 +24,16 @@ class Drag { Drag(Input &, Fluid *); void ShowConfig(); // print configuration void AddDragForce(const real); + + ////////////////////////// + // Implicit functions + void AddImplicitBackReaction(const real, IdefixArray3D); // Add the back reaction + void NormalizeImplicitBackReaction(const real); // Normalize the implicit back reaction + void AddImplicitFluidMomentum(const real); // Add the implicit drag force on dust grains + ///////////////////////// + void EnrollUserDrag(UserDefDragFunc); // User defined drag function enrollment + bool IsImplicit() const { return implicit; } // Check if the drag is implicit IdefixArray4D UcDust; // Dust conservative quantities IdefixArray4D UcGas; // Gas conservative quantities @@ -32,12 +41,17 @@ class Drag { IdefixArray4D VcGas; // Gas primitive quantities IdefixArray3D InvDt; // The InvDt of current dust specie IdefixArray3D gammai; // the drag coefficient (only used for user-defined dust grains) + IdefixArray3D implicitFactor; // The prefactor used by the implicit timestepping + Type type; private: DataBlock* data; real dragCoeff; bool feedback{false}; + bool implicit{false}; + int instanceNumber; + UserDefDragFunc userDrag{NULL}; @@ -92,11 +106,21 @@ Drag::Drag(Input &input, Fluid *hydroin): IDEFIX_ERROR(msg); } // Fetch the drag coefficient for the current specie. - const int n = hydroin->instanceNumber; - this->dragCoeff = input.Get(BlockName,"drag",n+1); + this->instanceNumber = hydroin->instanceNumber; + this->dragCoeff = input.Get(BlockName,"drag",instanceNumber+1); // Feedback is true by default, but can be switched off. this->feedback = input.GetOrSet(BlockName,"drag_feedback",0,true); + + this->implicit = input.GetOrSet(BlockName,"drag_implicit",0,false); + + if(implicit && instanceNumber == 0) { + this->implicitFactor = IdefixArray3D("ImplicitFactor", + data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + } + } else { IDEFIX_ERROR("A [Drag] block is required in your input file to define the drag force."); } diff --git a/src/fluid/evolveStage.hpp b/src/fluid/evolveStage.hpp index 06754d0b7..31dae5b7d 100644 --- a/src/fluid/evolveStage.hpp +++ b/src/fluid/evolveStage.hpp @@ -61,7 +61,11 @@ void Fluid::EvolveStage(const real t, const real dt) { if(haveSourceTerms) AddSourceTerms(t, dt); // Step 5: add drag when needed - if(haveDrag) drag->AddDragForce(dt); + if(haveDrag) { + if(!drag->IsImplicit()) { + drag->AddDragForce(dt); + } + } if constexpr(Phys::mhd) { #if DIMENSIONS >= 2 diff --git a/test/Dust/DustEnergy/idefix-implicit.ini b/test/Dust/DustEnergy/idefix-implicit.ini new file mode 100644 index 000000000..9ba3c781a --- /dev/null +++ b/test/Dust/DustEnergy/idefix-implicit.ini @@ -0,0 +1,36 @@ +# This test checks that the total energy (thermal+dust kinetic+gas kinetic) +# is effectively conserved when drag is present + +[Grid] +X1-grid 1 0.0 500 u 1.0 +X2-grid 1 0.0 1 u 1.0 +X3-grid 1 0.0 1 u 1.0 + +[TimeIntegrator] +CFL 0.8 +tstop 1.0 +first_dt 1.e-4 +nstages 2 + +[Hydro] +solver hllc +gamma 1.4 + +[Dust] +nSpecies 1 +drag tau 1.0 +drag_feedback yes +drag_implicit yes + +[Boundary] +X1-beg periodic +X1-end periodic +X2-beg outflow +X2-end outflow +X3-beg outflow +X3-end outflow + +[Output] +dmp 1.0 +analysis 0.01 +log 1000 diff --git a/test/Dust/DustEnergy/testme.py b/test/Dust/DustEnergy/testme.py index f3b413e83..7187d299b 100755 --- a/test/Dust/DustEnergy/testme.py +++ b/test/Dust/DustEnergy/testme.py @@ -15,7 +15,7 @@ def testMe(test): test.configure() test.compile() - inifiles=["idefix.ini"] + inifiles=["idefix.ini","idefix-implicit.ini"] # loop on all the ini files for this test for ini in inifiles: diff --git a/test/Dust/DustyWave/idefix-implicit.ini b/test/Dust/DustyWave/idefix-implicit.ini new file mode 100644 index 000000000..05da6ccce --- /dev/null +++ b/test/Dust/DustyWave/idefix-implicit.ini @@ -0,0 +1,36 @@ +# This test checks the dissipation of a sound wave by a dust grains +# partially coupled to the gas (Riols & Lesur 2018, appendix A) + +[Grid] +X1-grid 1 0.0 500 u 1.0 +X2-grid 1 0.0 1 u 1.0 +X3-grid 1 0.0 1 u 1.0 + +[TimeIntegrator] +CFL 0.8 +tstop 10.0 +first_dt 1.e-4 +nstages 2 + +[Hydro] +solver hllc +csiso constant 1.0 + +[Dust] +nSpecies 1 +drag tau 1.0e-3 +drag_feedback yes +drag_implicit yes + +[Boundary] +X1-beg periodic +X1-end periodic +X2-beg outflow +X2-end outflow +X3-beg outflow +X3-end outflow + +[Output] +dmp 10.0 +analysis 0.01 +log 1000 diff --git a/test/Dust/DustyWave/testme.py b/test/Dust/DustyWave/testme.py index b6a75ce3c..2b03d1636 100755 --- a/test/Dust/DustyWave/testme.py +++ b/test/Dust/DustyWave/testme.py @@ -15,7 +15,7 @@ def testMe(test): test.configure() test.compile() - inifiles=["idefix.ini"] + inifiles=["idefix.ini","idefix-implicit.ini"] # loop on all the ini files for this test for ini in inifiles: From c0fbc84fe593b1ca599fa1c89a960d2f0c81b877 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Victor=20R=C3=A9ville?= Date: Tue, 11 Feb 2025 07:07:33 +0100 Subject: [PATCH 032/144] switch for std.vector.at() in userdef TD tests --- test/MHD/MTI/setup.cpp | 4 ++-- test/MHD/clessTDiffusion/setup.cpp | 8 ++++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/test/MHD/MTI/setup.cpp b/test/MHD/MTI/setup.cpp index 1608b5eca..552f76465 100644 --- a/test/MHD/MTI/setup.cpp +++ b/test/MHD/MTI/setup.cpp @@ -43,8 +43,8 @@ void MyBragThermalConductivity(DataBlock &data, const real t, std::vector Vc = data.hydro->Vc; IdefixArray1D x2 = data.x[JDIR]; - IdefixArray3D kparArr = userdefArr[0]; - IdefixArray3D knorArr = userdefArr[1]; + IdefixArray3D kparArr = userdefArr.at(0); + IdefixArray3D knorArr = userdefArr.at(1); real ksi = ksiGlob; idefix_for("MyThConductivity",0,data.np_tot[KDIR],0,data.np_tot[JDIR],0,data.np_tot[IDIR], diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index 7c6e7eb2a..651a81f53 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -18,10 +18,10 @@ void MyClessThermalConductivity(DataBlock &data, const real t, std::vector x1 = data.x[IDIR]; IdefixArray1D x2 = data.x[JDIR]; - IdefixArray3D kparArr = userdefArr[0]; - IdefixArray3D knorArr = userdefArr[1]; - IdefixArray3D clessAlpha = userdefArr[2]; - IdefixArray3D clessBeta = userdefArr[3]; + IdefixArray3D kparArr = userdefArr.at(0); + IdefixArray3D knorArr = userdefArr.at(1); + IdefixArray3D clessAlpha = userdefArr.at(2); + IdefixArray3D clessBeta = userdefArr.at(3); real norm = mp*0.5/(udenGlob*uvelGlob*ulenGlob*kB); real uTemp=0.5*uvelGlob*uvelGlob*mp/kB; From 22eaf5b872f26e8ec2f4a329497e2ef4805ed315 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 10:33:14 +0100 Subject: [PATCH 033/144] refactor dust drag law --- src/fluid/drag.cpp | 188 ++++++++++-------------- src/fluid/drag.hpp | 91 +++++++----- test/Dust/DustyWave/idefix-implicit.ini | 2 +- 3 files changed, 127 insertions(+), 154 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 46542147f..7739d84d9 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -5,7 +5,12 @@ // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #include "drag.hpp" +#include + #include "physics.hpp" + + + void Drag::AddDragForce(const real dt) { idfx::pushRegion("Drag::AddDragForce"); @@ -15,51 +20,20 @@ void Drag::AddDragForce(const real dt) { auto VcDust = this->VcDust; auto InvDt = this->InvDt; - const Type type = this->type; - real dragCoeff = this->dragCoeff; bool feedback = this->feedback; - EquationOfState eos = *(this->eos); - if(implicit) { IDEFIX_ERROR("Add DragForce should not be called when drag is implicit"); } - auto userGammai = this->gammai; - if(type == Type::Userdef) { - if(userDrag != NULL) { - idfx::pushRegion("Drag::UserDrag"); - userDrag(data, dragCoeff, userGammai); - idfx::popRegion(); - } else { - IDEFIX_ERROR("No User-defined drag function has been enrolled"); - } - } + auto gammaDrag = this->gammaDrag; + gammaDrag.RefreshUserDrag(data); + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) // Where gamma is computed according to the choice of drag type idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA (int k, int j, int i) { - real gamma; // The drag coefficient - if(type == Type::Gamma) { - gamma = dragCoeff; - - } else if(type == Type::Tau) { - // In this case, the coefficient is the stopping time (assumed constant) - gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); - } else if(type == Type::Size) { - real cs; - // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs - // Get the sound speed - #if HAVE_ENERGY == 1 - cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) - *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); - #else - cs = eos.GetWaveSpeed(k,j,i); - #endif - gamma = cs/dragCoeff; - } else if(type == Type::Userdef) { - gamma = userGammai(k,j,i); - } + real gamma = gammaDrag.GetGamma(k,j,i); // The drag coefficient real dp = dt * gamma * VcDust(RHO,k,j,i) * VcGas(RHO,k,j,i); for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { @@ -97,58 +71,26 @@ void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) auto UcGas = this->UcGas; auto VcGas = this->VcGas; - auto UcDust = this->UcDust; auto VcDust = this->VcDust; - const Type type = this->type; - real dragCoeff = this->dragCoeff; bool feedback = this->feedback; bool isFirst = this->instanceNumber == 0; - EquationOfState eos = *(this->eos); if(!implicit) { IDEFIX_ERROR("AddImplicitGasMomentum should not be called when drag is explicit"); } - auto userGammai = this->gammai; - if(type == Type::Userdef) { // If feedback enabled, - // the coefficients were already computed in the gas - // momentum pass - if(userDrag != NULL) { - idfx::pushRegion("Drag::UserDrag"); - userDrag(data, dragCoeff, userGammai); - idfx::popRegion(); - } else { - IDEFIX_ERROR("No User-defined drag function has been enrolled"); - } - } + auto gammaDrag = this->gammaDrag; + gammaDrag.RefreshUserDrag(data); + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) // Where gamma is computed according to the choice of drag type idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA (int k, int j, int i) { - real gamma; // The drag coefficient - if(type == Type::Gamma) { - gamma = dragCoeff; - - } else if(type == Type::Tau) { - // In this case, the coefficient is the stopping time (assumed constant) - gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); - } else if(type == Type::Size) { - real cs; - // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs - // Get the sound speed - #if HAVE_ENERGY == 1 - cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) - *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); - #else - cs = eos.GetWaveSpeed(k,j,i); - #endif - gamma = cs/dragCoeff; - } else if(type == Type::Userdef) { - gamma = userGammai(k,j,i); - } + real gamma = gammaDrag.GetGamma(k,j,i); // The drag coefficient + const real factor = VcDust(RHO,k,j,i)*gamma*dt/(1+VcGas(RHO,k,j,i)*gamma*dt); if(isFirst) { @@ -200,53 +142,20 @@ void Drag::AddImplicitFluidMomentum(const real dt) { auto VcDust = this->VcDust; auto InvDt = this->InvDt; - const Type type = this->type; - real dragCoeff = this->dragCoeff; bool feedback = this->feedback; - EquationOfState eos = *(this->eos); - if(!implicit) { IDEFIX_ERROR("AddImplicitGasMomentum should not be called when drag is explicit"); } - auto userGammai = this->gammai; - if(type == Type::Userdef && !feedback) { // If feedback enabled, - // the coefficients were already computed in the gas - // momentum pass - if(userDrag != NULL) { - idfx::pushRegion("Drag::UserDrag"); - userDrag(data, dragCoeff, userGammai); - idfx::popRegion(); - } else { - IDEFIX_ERROR("No User-defined drag function has been enrolled"); - } - } + auto gammaDrag = this->gammaDrag; + if(!feedback) gammaDrag.RefreshUserDrag(data); + // Compute a drag force fd = - gamma*rhod*rhog*(vd-vg) // Where gamma is computed according to the choice of drag type idefix_for("DragForce",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA (int k, int j, int i) { - real gamma; // The drag coefficient - if(type == Type::Gamma) { - gamma = dragCoeff; - - } else if(type == Type::Tau) { - // In this case, the coefficient is the stopping time (assumed constant) - gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); - } else if(type == Type::Size) { - real cs; - // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs - // Get the sound speed - #if HAVE_ENERGY == 1 - cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) - *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); - #else - cs = eos.GetWaveSpeed(k,j,i); - #endif - gamma = cs/dragCoeff; - } else if(type == Type::Userdef) { - gamma = userGammai(k,j,i); - } + real gamma = gammaDrag.GetGamma(k,j,i); // The drag coefficient for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { real oldUc = UcDust(n,k,j,i); @@ -275,17 +184,17 @@ void Drag::ShowConfig() { } else { idfx::cout << " EXPLICIT "; } - switch(type) { - case Type::Gamma: + switch(gammaDrag.type) { + case GammaDrag::Type::Gamma: idfx::cout << "constant gamma"; break; - case Type::Tau: + case GammaDrag::Type::Tau: idfx::cout << "constant stopping time"; break; - case Type::Size: + case GammaDrag::Type::Size: idfx::cout << "constant dust size"; break; - case Type::Userdef: + case GammaDrag::Type::Userdef: idfx::cout << "user-defined"; break; } @@ -299,8 +208,59 @@ void Drag::ShowConfig() { } void Drag::EnrollUserDrag(UserDefDragFunc func) { + gammaDrag.EnrollUserDrag(func); +} + +//////////////////////////////////////////// +// GammaDrag function definitions +//////////////////////////////////////////// + +void GammaDrag::RefreshUserDrag(DataBlock *data) { + if(type == Type::Userdef) { + if(userDrag != NULL) { + idfx::pushRegion("GammaDrag::UserDrag"); + userDrag(data, dragCoeff, gammai); + idfx::popRegion(); + } else { + IDEFIX_ERROR("No User-defined drag function has been enrolled"); + } + } +} + +void GammaDrag::EnrollUserDrag(UserDefDragFunc func) { if(type != Type::Userdef) { IDEFIX_ERROR("User-defined drag function requires drag entry to be set to \"userdef\""); } this->userDrag = func; } + +GammaDrag::GammaDrag(Input &input, std::string BlockName, int instanceNumber, DataBlock *data) { + if(input.CheckEntry(BlockName,"drag")>=0) { + std::string dragType = input.Get(BlockName,"drag",0); + if(dragType.compare("gamma") == 0) { + this->type = Type::Gamma; + } else if(dragType.compare("tau") == 0) { + this->type = Type::Tau; + this->VcGas = data->hydro->Vc; + } else if(dragType.compare("size") == 0) { + this->type = Type::Size; + this->eos = *(data->hydro->eos.get()); + this->VcGas = data->hydro->Vc; + } else if(dragType.compare("userdef") == 0) { + this->type = Type::Userdef; + this->gammai = IdefixArray3D("UserDrag", + data->np_tot[KDIR], + data->np_tot[JDIR], + data->np_tot[IDIR]); + } else { + std::stringstream msg; + msg << "Unknown drag type \"" << dragType + << "\" in your input file." << std::endl + << "Allowed values are: gamma, tau, epstein, stokes, userdef." << std::endl; + + IDEFIX_ERROR(msg); + } + } + // Fetch the drag coefficient for the current specie. + this->dragCoeff = input.Get(BlockName,"drag",instanceNumber+1); +} diff --git a/src/fluid/drag.hpp b/src/fluid/drag.hpp index c676a88eb..26332eff8 100644 --- a/src/fluid/drag.hpp +++ b/src/fluid/drag.hpp @@ -15,10 +15,52 @@ using UserDefDragFunc = void (*) (DataBlock *, real beta, IdefixArray3D &gammai); +/* A class that holds the kind of drag law we intend to use */ +class GammaDrag { + public: + enum class Type{Gamma, Tau, Size, Userdef}; + GammaDrag() = default; + GammaDrag(Input &, std::string BlockName, int instanceNumber, DataBlock *data); + void EnrollUserDrag(UserDefDragFunc); + void RefreshUserDrag(DataBlock *); + + KOKKOS_INLINE_FUNCTION real GetGamma(const int k, const int j, const int i) const { + real gamma; // The drag coefficient + if(type == Type::Gamma) { + gamma = dragCoeff; + + } else if(type == Type::Tau) { + // In this case, the coefficient is the stopping time (assumed constant) + gamma = 1/(dragCoeff*VcGas(RHO,k,j,i)); + } else if(type == Type::Size) { + real cs; + // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs + // Get the sound speed + #if HAVE_ENERGY == 1 + cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) + *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); + #else + cs = eos.GetWaveSpeed(k,j,i); + #endif + gamma = cs/dragCoeff; + } else if(type == Type::Userdef) { + gamma = gammai(k,j,i); + } + return gamma; + } + + Type type; + real dragCoeff; + EquationOfState eos; + IdefixArray3D gammai; + IdefixArray4D VcGas; + + UserDefDragFunc userDrag{NULL}; +}; + class Drag { public: - enum class Type{Gamma, Tau, Size, Userdef}; // Different types of implementation for the drag force. template Drag(Input &, Fluid *); @@ -40,24 +82,20 @@ class Drag { IdefixArray4D VcDust; // Gas primitive quantities IdefixArray4D VcGas; // Gas primitive quantities IdefixArray3D InvDt; // The InvDt of current dust specie - IdefixArray3D gammai; // the drag coefficient (only used for user-defined dust grains) IdefixArray3D implicitFactor; // The prefactor used by the implicit timestepping - Type type; + GammaDrag gammaDrag; // The drag law private: DataBlock* data; - real dragCoeff; bool feedback{false}; bool implicit{false}; int instanceNumber; +}; + - UserDefDragFunc userDrag{NULL}; - // Sound speed computation - EquationOfState *eos; -}; #include "fluid.hpp" @@ -72,47 +110,22 @@ Drag::Drag(Input &input, Fluid *hydroin): // Save the parent hydro object this->data = hydroin->data; - // We use the EOS of the basic fluid instance, as there is no EOS for dust! - this->eos = hydroin->data->hydro->eos.get(); // Check in which block we should fetch our information - std::string BlockName; + std::string blockName; if(Phys::dust) { - BlockName = "Dust"; + blockName = "Dust"; } else { IDEFIX_ERROR("Drag is currently implemented only for dusty fuids"); } - if(input.CheckEntry(BlockName,"drag")>=0) { - std::string dragType = input.Get(BlockName,"drag",0); - if(dragType.compare("gamma") == 0) { - this->type = Type::Gamma; - } else if(dragType.compare("tau") == 0) { - this->type = Type::Tau; - } else if(dragType.compare("size") == 0) { - this->type = Type::Size; - } else if(dragType.compare("userdef") == 0) { - this->type = Type::Userdef; - this->gammai = IdefixArray3D("UserDrag", - data->np_tot[KDIR], - data->np_tot[JDIR], - data->np_tot[IDIR]); - } else { - std::stringstream msg; - msg << "Unknown drag type \"" << dragType - << "\" in your input file." << std::endl - << "Allowed values are: gamma, tau, epstein, stokes, userdef." << std::endl; - - IDEFIX_ERROR(msg); - } - // Fetch the drag coefficient for the current specie. + if(input.CheckEntry(blockName,"drag")>=0) { this->instanceNumber = hydroin->instanceNumber; - this->dragCoeff = input.Get(BlockName,"drag",instanceNumber+1); + this->gammaDrag = GammaDrag(input,blockName,instanceNumber,data); // Feedback is true by default, but can be switched off. - this->feedback = input.GetOrSet(BlockName,"drag_feedback",0,true); - - this->implicit = input.GetOrSet(BlockName,"drag_implicit",0,false); + this->feedback = input.GetOrSet(blockName,"drag_feedback",0,true); + this->implicit = input.GetOrSet(blockName,"drag_implicit",0,false); if(implicit && instanceNumber == 0) { this->implicitFactor = IdefixArray3D("ImplicitFactor", diff --git a/test/Dust/DustyWave/idefix-implicit.ini b/test/Dust/DustyWave/idefix-implicit.ini index 05da6ccce..726585e0b 100644 --- a/test/Dust/DustyWave/idefix-implicit.ini +++ b/test/Dust/DustyWave/idefix-implicit.ini @@ -18,7 +18,7 @@ csiso constant 1.0 [Dust] nSpecies 1 -drag tau 1.0e-3 +drag tau 1.0 drag_feedback yes drag_implicit yes From cbcc63fffd13e8f3ec7cbc58bcd88a2ec0112e31 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 10:35:35 +0100 Subject: [PATCH 034/144] clean up --- src/fluid/drag.cpp | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 7739d84d9..791cdf889 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -6,11 +6,8 @@ // *********************************************************************************** #include "drag.hpp" #include - #include "physics.hpp" - - void Drag::AddDragForce(const real dt) { idfx::pushRegion("Drag::AddDragForce"); From 05ca488b9b069397532f5a9f3970b5a45c0d29d6 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 14:11:04 +0100 Subject: [PATCH 035/144] change signature of userdef drag function --- src/fluid/drag.cpp | 3 ++- src/fluid/drag.hpp | 6 ++---- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 791cdf889..bbbf11b20 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -216,7 +216,7 @@ void GammaDrag::RefreshUserDrag(DataBlock *data) { if(type == Type::Userdef) { if(userDrag != NULL) { idfx::pushRegion("GammaDrag::UserDrag"); - userDrag(data, dragCoeff, gammai); + userDrag(data, instanceNumber, dragCoeff, gammai); idfx::popRegion(); } else { IDEFIX_ERROR("No User-defined drag function has been enrolled"); @@ -260,4 +260,5 @@ GammaDrag::GammaDrag(Input &input, std::string BlockName, int instanceNumber, Da } // Fetch the drag coefficient for the current specie. this->dragCoeff = input.Get(BlockName,"drag",instanceNumber+1); + this->instanceNumber = instanceNumber; } diff --git a/src/fluid/drag.hpp b/src/fluid/drag.hpp index 26332eff8..29eca3097 100644 --- a/src/fluid/drag.hpp +++ b/src/fluid/drag.hpp @@ -13,7 +13,7 @@ #include "fluid_defs.hpp" #include "eos.hpp" -using UserDefDragFunc = void (*) (DataBlock *, real beta, IdefixArray3D &gammai); +using UserDefDragFunc = void (*) (DataBlock *, int n, real beta, IdefixArray3D &gammai); /* A class that holds the kind of drag law we intend to use */ class GammaDrag { @@ -55,6 +55,7 @@ class GammaDrag { IdefixArray3D gammai; IdefixArray4D VcGas; + int instanceNumber; UserDefDragFunc userDrag{NULL}; }; @@ -94,9 +95,6 @@ class Drag { }; - - - #include "fluid.hpp" template From 6fbd722439179c67bf22518098d1b210ebede845 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 14:11:57 +0100 Subject: [PATCH 036/144] add the dustyShock test from Benitez-Llambay 2019 --- test/Dust/DustyShock/definitions.hpp | 5 ++ test/Dust/DustyShock/idefix-implicit.ini | 36 +++++++++ test/Dust/DustyShock/idefix.ini | 35 ++++++++ test/Dust/DustyShock/python/testidefix.py | 97 ++++++++++++++++++++++ test/Dust/DustyShock/setup.cpp | 99 +++++++++++++++++++++++ test/Dust/DustyShock/testme.py | 39 +++++++++ 6 files changed, 311 insertions(+) create mode 100644 test/Dust/DustyShock/definitions.hpp create mode 100644 test/Dust/DustyShock/idefix-implicit.ini create mode 100644 test/Dust/DustyShock/idefix.ini create mode 100755 test/Dust/DustyShock/python/testidefix.py create mode 100644 test/Dust/DustyShock/setup.cpp create mode 100755 test/Dust/DustyShock/testme.py diff --git a/test/Dust/DustyShock/definitions.hpp b/test/Dust/DustyShock/definitions.hpp new file mode 100644 index 000000000..cdbe23d6e --- /dev/null +++ b/test/Dust/DustyShock/definitions.hpp @@ -0,0 +1,5 @@ +#define COMPONENTS 1 +#define DIMENSIONS 1 +#define ISOTHERMAL + +#define GEOMETRY CARTESIAN diff --git a/test/Dust/DustyShock/idefix-implicit.ini b/test/Dust/DustyShock/idefix-implicit.ini new file mode 100644 index 000000000..e83d5bf44 --- /dev/null +++ b/test/Dust/DustyShock/idefix-implicit.ini @@ -0,0 +1,36 @@ +# This test checks the behaviour of a dust sound shock +# following the 4 fluids test of Benitez-Llambay+ 2019 + +[Grid] +X1-grid 1 0.0 400 u 40.0 +X2-grid 1 0.0 1 u 1.0 +X3-grid 1 0.0 1 u 1.0 + +[TimeIntegrator] +CFL 0.8 +tstop 500.0 +first_dt 1.e-4 +nstages 2 + +[Hydro] +solver hllc +csiso constant 1.0 + +[Dust] +nSpecies 3 +drag userdef 1.0 3.0 5.0 +drag_feedback yes +drag_implicit yes + +[Boundary] +X1-beg userdef +X1-end userdef +X2-beg outflow +X2-end outflow +X3-beg outflow +X3-end outflow + +[Output] +# dmp 10.0 +vtk 500.0 +log 1000 diff --git a/test/Dust/DustyShock/idefix.ini b/test/Dust/DustyShock/idefix.ini new file mode 100644 index 000000000..1b9c9ea2e --- /dev/null +++ b/test/Dust/DustyShock/idefix.ini @@ -0,0 +1,35 @@ +# This test checks the behaviour of a dust sound shock +# following the 4 fluids test of Benitez-Llambay+ 2019 + +[Grid] +X1-grid 1 0.0 400 u 40.0 +X2-grid 1 0.0 1 u 1.0 +X3-grid 1 0.0 1 u 1.0 + +[TimeIntegrator] +CFL 0.8 +tstop 500.0 +first_dt 1.e-4 +nstages 2 + +[Hydro] +solver hllc +csiso constant 1.0 + +[Dust] +nSpecies 3 +drag userdef 1.0 3.0 5.0 +drag_feedback yes + +[Boundary] +X1-beg userdef +X1-end userdef +X2-beg outflow +X2-end outflow +X3-beg outflow +X3-end outflow + +[Output] +# dmp 10.0 +vtk 500.0 +log 1000 diff --git a/test/Dust/DustyShock/python/testidefix.py b/test/Dust/DustyShock/python/testidefix.py new file mode 100755 index 000000000..8fca15a3f --- /dev/null +++ b/test/Dust/DustyShock/python/testidefix.py @@ -0,0 +1,97 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +Created on Thu Mar 5 11:29:41 2020 + +@author: glesur +""" + +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) +from pytools.vtk_io import readVTK +import argparse +import numpy as np +import matplotlib.pyplot as plt +from scipy.integrate import solve_ivp + +parser = argparse.ArgumentParser() +parser.add_argument("-noplot", + default=False, + help="disable plotting", + action="store_true") + + +args, unknown=parser.parse_known_args() + +V=readVTK('../data.0001.vtk', geometry='cartesian') + +# Find where the shock starts +istart = np.argwhere(V.data['RHO'][:,0,0]>2.0)[0][0]-1 + +# Compute analytical solution +M=2 # Mach number +K=np.asarray([1,3,5])/M # Drag coefficients + +# (56) from Benitez-Llambay 2018 +def get_wg(Mach, wi): + coeff=[1,np.sum(wi-1)-1/Mach**2-1,1/Mach**2] + solution=np.roots(coeff) + return(np.min(solution)) + +# (55) from Benitez-Llambay 2018 +def rhs(t,wi,Mach,K): + wg = get_wg(Mach,wi) + return K*(wg-wi) + +wi0=np.asarray([1.0,1.0,1.0]) +x=V.x[istart:] +arguments=M,K + +sol = solve_ivp(rhs, t_span=[x[0],x[-1]], y0=wi0, t_eval=x,args=arguments) + +# compute gas velocity +wg=np.zeros(len(x)) +for i in range(0,len(wg)): + wg[i]=get_wg(M,sol.y[:,i]) + + +if(not args.noplot): + plt.figure(1) + plt.plot(V.x,V.data['RHO'][:,0,0],'o',markersize=4,color='tab:purple') + plt.plot(x,1/wg,color='tab:purple') + plt.plot(V.x,V.data['Dust0_RHO'][:,0,0],'o',markersize=4,color='tab:orange') + plt.plot(x,1/sol.y[0,:],color='tab:orange') + plt.plot(V.x,V.data['Dust1_RHO'][:,0,0],'o',markersize=4,color='tab:blue') + plt.plot(x,1/sol.y[1,:],color='tab:blue') + plt.plot(V.x,V.data['Dust2_RHO'][:,0,0],'o',markersize=4,color='tab:green') + plt.plot(x,1/sol.y[2,:],color='tab:green') + plt.xlim([0,10]) + plt.title('Density') + + plt.figure(2) + plt.plot(V.x,V.data['VX1'][:,0,0],'o',markersize=4,color='tab:purple') + plt.plot(x,M*wg,color='tab:purple') + plt.plot(V.x[::4],V.data['Dust0_VX1'][::4,0,0],'o',markersize=4,color='tab:orange') + plt.plot(x,M*sol.y[0,:],color='tab:orange') + plt.plot(V.x[::4],V.data['Dust1_VX1'][::4,0,0],'o',markersize=4,color='tab:blue') + plt.plot(x,M*sol.y[1,:],color='tab:blue') + plt.plot(V.x[::4],V.data['Dust2_VX1'][::4,0,0],'o',markersize=4,color='tab:green') + plt.plot(x,M*sol.y[2,:],color='tab:green') + + plt.xlim([0,10]) + plt.title('Velocity') + + plt.ioff() + plt.show() + +# Compute the error on the dust densities + +error=np.mean(np.fabs(V.data['Dust0_RHO'][istart:,0,0]-1/sol.y[0,:]) + np.fabs(V.data['Dust1_RHO'][istart:,0,0]-1/sol.y[1,:]) + np.fabs(V.data['Dust2_RHO'][istart:,0,0]-1/sol.y[2,:])) / 3 +print("Error=%e"%error) +if error<3.6e-2: + print("SUCCESS!") + sys.exit(0) +else: + print("FAILURE!") + sys.exit(1) diff --git a/test/Dust/DustyShock/setup.cpp b/test/Dust/DustyShock/setup.cpp new file mode 100644 index 000000000..f8632248a --- /dev/null +++ b/test/Dust/DustyShock/setup.cpp @@ -0,0 +1,99 @@ +#include "idefix.hpp" +#include "setup.hpp" + +#define FILENAME "timevol.dat" + +void MyDrag(DataBlock *data, int n, real beta, IdefixArray3D &gamma) { + // Compute the drag coefficient gamma from the input beta + auto VcGas = data->hydro->Vc; + auto VcDust = data->dust[n]->Vc; + + idefix_for("MyDrag",0,data->np_tot[KDIR],0,data->np_tot[JDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int j, int i) { + gamma(k,j,i) = beta/VcGas(RHO,k,j,i)/VcDust(RHO,k,j,i); + }); +} + + +void ApplyBoundary(DataBlock *data, IdefixArray4D Vc, int dir, BoundarySide side) { + if(dir==IDIR) { + int iref,ibeg,iend; + if(side == left) { + iref = data->beg[IDIR]; + ibeg = 0; + iend = data->beg[IDIR]; + } else { + iref =data->end[IDIR] - 1; + ibeg=data->end[IDIR]; + iend=data->np_tot[IDIR]; + } + int nvar = Vc.extent(0); + idefix_for("UserDefBoundary",0,data->np_tot[KDIR],0,data->np_tot[JDIR],ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + for(int n = 0 ; n < nvar ; n++) { + Vc(n,k,j,i) = Vc(n,k,j,iref ); + } + }); + } +} + +void UserdefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { + ApplyBoundary(hydro->data, hydro->Vc, dir, side); +} + +void UserdefBoundaryDust(Fluid *dust, int dir, BoundarySide side, real t) { + ApplyBoundary(dust->data, dust->Vc, dir, side); +} + + +// Initialisation routine. Can be used to allocate +// Arrays or variables which are used later on +Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { + + data.hydro->EnrollUserDefBoundary(&UserdefBoundary); + if(data.haveDust) { + int nSpecies = data.dust.size(); + for(int n = 0 ; n < nSpecies ; n++) { + data.dust[n]->EnrollUserDefBoundary(&UserdefBoundaryDust); + data.dust[n]->drag->EnrollUserDrag(&MyDrag); + } + } + +} + +// This routine initialize the flow +// Note that data is on the device. +// One can therefore define locally +// a datahost and sync it, if needed +void Setup::InitFlow(DataBlock &data) { + // Create a host copy + DataBlockHost d(data); + + const real x0 = 4.0; + + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + real x = d.x[IDIR](i); + + d.Vc(RHO,k,j,i) = (x < x0) ? 1.0 : 16.0; + d.Vc(VX1,k,j,i) = (x < x0) ? 2.0 : 0.125; + + for(int n = 0 ; n < data.dust.size(); n++) { + d.dustVc[n](RHO,k,j,i) = (x < x0) ? 1.0 : 16.0; + d.dustVc[n](VX1,k,j,i) = (x < x0) ? 2.0 : 0.125; + } + + + } + } + } + + // Send it all, if needed + d.SyncToDevice(); +} + +// Analyse data to produce an output +void MakeAnalysis(DataBlock & data) { + +} diff --git a/test/Dust/DustyShock/testme.py b/test/Dust/DustyShock/testme.py new file mode 100755 index 000000000..2b03d1636 --- /dev/null +++ b/test/Dust/DustyShock/testme.py @@ -0,0 +1,39 @@ +#!/usr/bin/env python3 + +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) + +import pytools.idfx_test as tst + +name="dump.0001.dmp" + +def testMe(test): + test.configure() + test.compile() + inifiles=["idefix.ini","idefix-implicit.ini"] + + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name,tolerance=1e-14) + + +test=tst.idfxTest() + +if not test.all: + if(test.check): + test.checkOnly(filename=name) + else: + testMe(test) +else: + test.noplot = True + test.reconstruction=2 + testMe(test) From 60740e78eecd2e70ea5bd0768ec100f017a8356d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 14:20:18 +0100 Subject: [PATCH 037/144] add back dump files for reference --- test/Dust/DustyShock/idefix-implicit.ini | 2 +- test/Dust/DustyShock/idefix.ini | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/test/Dust/DustyShock/idefix-implicit.ini b/test/Dust/DustyShock/idefix-implicit.ini index e83d5bf44..2d92a0a52 100644 --- a/test/Dust/DustyShock/idefix-implicit.ini +++ b/test/Dust/DustyShock/idefix-implicit.ini @@ -31,6 +31,6 @@ X3-beg outflow X3-end outflow [Output] -# dmp 10.0 +dmp 500.0 vtk 500.0 log 1000 diff --git a/test/Dust/DustyShock/idefix.ini b/test/Dust/DustyShock/idefix.ini index 1b9c9ea2e..a98ebd097 100644 --- a/test/Dust/DustyShock/idefix.ini +++ b/test/Dust/DustyShock/idefix.ini @@ -30,6 +30,6 @@ X3-beg outflow X3-end outflow [Output] -# dmp 10.0 +dmp 500.0 vtk 500.0 log 1000 From 4b8e277e51e78709642cb8cdd3a2f2d510afd240 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 14:21:02 +0100 Subject: [PATCH 038/144] update reference files for new dusyShock --- reference | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reference b/reference index b675bceaa..3e1555090 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit b675bceaa6aabc01dded346e2d631857f698dc76 +Subproject commit 3e1555090230ceb21ea6428d82c032734fef7488 From e844bc19c14b497b4e590b4a32feeff38d605308 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Feb 2025 17:03:09 +0100 Subject: [PATCH 039/144] add documentation for implicit dust module --- doc/source/modules/dust.rst | 41 +++++++++++++++++++++++++++++++++---- 1 file changed, 37 insertions(+), 4 deletions(-) diff --git a/doc/source/modules/dust.rst b/doc/source/modules/dust.rst index ca371dade..0cdac49ba 100644 --- a/doc/source/modules/dust.rst +++ b/doc/source/modules/dust.rst @@ -39,15 +39,45 @@ which guarantees total momentum conservation. -Drag CFL condition -------------------- -*Idefix* computes the drag terms with a time-explicit scheme. Hence, an addition CFL constraint arrises because of the drag: +Time Integration +---------------- + +*Idefix* can compute the drag with a 2nd order time-explicit (default) or 1st order time-implicit scheme. Each scheme has its pros and cons. The choice +is made by the user in the input file. + +Explicit scheme: drag CFL condition ++++++++++++++++++++++++++++++++++++ + +When using the time explicit scheme, an addition CFL constraint arrises because of the drag: .. math:: dt < \min(\frac{1}{\sum_i\gamma_i(\rho_i+\rho)}) -*Idefix* automatically adjusts the CFL to satisfy this inequality, in addition to the usual CFL condition. +*Idefix* automatically adjusts the CFL to satisfy this inequality, in addition to the usual CFL condition. This can severly limit the time step, +especially when the gas density is high. + +Implicit scheme ++++++++++++++++ + +When the drag is applied with a 1st order implicit scheme, the drag force is applied at the end of each step. In order to avoid +the complete inversion of the system, we follow a simplified inversion procedure, where we first update the gas momentum as: + +.. math:: + + v_g^{(n+1)}=\left(v_g^{(n)}+\sum_i\frac{\rho_i\gamma_i dt}{1+\rho \gamma_i dt}v_i^{(n)}\right)/\left(1+\sum_i\frac{\rho_i\gamma_i dt}{1+\rho\gamma_idt}\right) + +And then update the dust momentum as: + +.. math:: + + v_i^{(n+1)}=\left(v_i^{(n)}+\rho\gamma_i v_g^{(n+1)}dt\right)/(1+\rho\gamma_i dt) + +Note that the latter equation relies on the *updated* gas velocity. + +.. warning:: + While the implicit scheme is more stable than the explicit one, and it does not require any additional CFL condition, it is less accurate and + possibly lead to inacurrate dust velocities when :math:`dt\gg (\gamma_i\rho)^{-1}`. Use it at your own risk. Dust parameters --------------- @@ -66,6 +96,9 @@ The dust module can be enabled adding a block `[Dust]` in your input .ini file. +----------------+-------------------------+---------------------------------------------------------------------------------------------+ | drag_feedback | bool | | (optionnal) whether the gas feedback is enabled (default true). | +----------------+-------------------------+---------------------------------------------------------------------------------------------+ +| drag_implicit | bool | | (optionnal) whether the drag uses a 1st order implicit method. Otherwise use the | +| | | | 2nd order time-explicit scheme (default is false=time explicit) | ++----------------+-------------------------+---------------------------------------------------------------------------------------------+ The drag parameter :math:`\beta_i` above sets the functional form of :math:`\gamma_i(\rho, \rho_i, c_s)` depending on the drag type: From 78fae024a76ee95b94940ffacb8ad36ec0fd2a90 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 13 Feb 2025 13:57:46 +0100 Subject: [PATCH 040/144] use proper update variables istead of pre-stage ones --- src/fluid/drag.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index bbbf11b20..b6eb1b3d3 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -89,7 +89,7 @@ void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) real gamma = gammaDrag.GetGamma(k,j,i); // The drag coefficient - const real factor = VcDust(RHO,k,j,i)*gamma*dt/(1+VcGas(RHO,k,j,i)*gamma*dt); + const real factor = UcDust(RHO,k,j,i)*gamma*dt/(1+UcGas(RHO,k,j,i)*gamma*dt); if(isFirst) { preFactor(k,j,i) = factor; } else { @@ -97,8 +97,8 @@ void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) } for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { - UcGas(n,k,j,i) += dt * gamma * VcGas(RHO,k,j,i) * UcDust(n,k,j,i) / - (1 + VcGas(RHO,k,j,i)*dt*gamma); + UcGas(n,k,j,i) += dt * gamma * UcGas(RHO,k,j,i) * UcDust(n,k,j,i) / + (1 + UcGas(RHO,k,j,i)*dt*gamma); } }); idfx::popRegion(); @@ -156,8 +156,8 @@ void Drag::AddImplicitFluidMomentum(const real dt) { for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { real oldUc = UcDust(n,k,j,i); - UcDust(n,k,j,i) = (oldUc + dt * gamma * VcDust(RHO,k,j,i) * UcGas(n,k,j,i)) / - (1 + VcGas(RHO,k,j,i)*dt*gamma); + UcDust(n,k,j,i) = (oldUc + dt * gamma * UcDust(RHO,k,j,i) * UcGas(n,k,j,i)) / + (1 + UcGas(RHO,k,j,i)*dt*gamma); #if HAVE_ENERGY == 1 real dp = UcDust(n,k,j,i) - oldUc; @@ -167,7 +167,7 @@ void Drag::AddImplicitFluidMomentum(const real dt) { // TODO(GL): this should be disabled in the case of a true multifluid system where // both fluids have a proper energy equation - UcGas(ENG,k,j,i) -= dp*VcDust(n,k,j,i); + UcGas(ENG,k,j,i) -= dp*UcDust(n,k,j,i)/UcDust(RHO,k,j,i); #endif } }); From 59a91d3cea976f8de290ee461a609cc865ee0fa2 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 13 Feb 2025 14:07:17 +0100 Subject: [PATCH 041/144] switch off heating terms when feedback is disabled (feedback assumes rho_d is negligible, so this makes sense anyway) --- src/fluid/drag.cpp | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index b6eb1b3d3..a1aae441c 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -36,16 +36,17 @@ void Drag::AddDragForce(const real dt) { for(int n = MX1 ; n < MX1+COMPONENTS ; n++) { real dv = VcDust(n,k,j,i) - VcGas(n,k,j,i); UcDust(n,k,j,i) -= dp*dv; - if(feedback) UcGas(n,k,j,i) += dp*dv; - #if HAVE_ENERGY == 1 - // We add back the energy dissipated for the dust which is not accounted for - // (since there is no energy equation for dust grains) - - // TODO(GL): this should be disabled in the case of a true multifluid system where - // both fluids have a proper energy equation - UcGas(ENG,k,j,i) += dp*dv*VcDust(n,k,j,i); - #endif - } + if(feedback) { + UcGas(n,k,j,i) += dp*dv; + #if HAVE_ENERGY == 1 + // We add back the energy dissipated for the dust which is not accounted for + // (since there is no energy equation for dust grains) + + // TODO(GL): this should be disabled in the case of a true multifluid system where + // both fluids have a proper energy equation + UcGas(ENG,k,j,i) += dp*dv*VcDust(n,k,j,i); + #endif + } // feedback // Cfl constraint real idt = gamma*VcGas(RHO,k,j,i); if(feedback) idt += gamma*VcDust(RHO,k,j,i); @@ -167,7 +168,7 @@ void Drag::AddImplicitFluidMomentum(const real dt) { // TODO(GL): this should be disabled in the case of a true multifluid system where // both fluids have a proper energy equation - UcGas(ENG,k,j,i) -= dp*UcDust(n,k,j,i)/UcDust(RHO,k,j,i); + if(feedback) UcGas(ENG,k,j,i) -= dp*UcDust(n,k,j,i)/UcDust(RHO,k,j,i); #endif } }); From f1141eef04e8955cfa9a0d336b389ab87f9d2790 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 13 Feb 2025 14:09:21 +0100 Subject: [PATCH 042/144] typo --- src/fluid/drag.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index a1aae441c..8bc765160 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -47,6 +47,7 @@ void Drag::AddDragForce(const real dt) { UcGas(ENG,k,j,i) += dp*dv*VcDust(n,k,j,i); #endif } // feedback + } // Cfl constraint real idt = gamma*VcGas(RHO,k,j,i); if(feedback) idt += gamma*VcDust(RHO,k,j,i); From 9b2afc546fae579c34be795b4e26ab4fbb6d2c1d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 13 Feb 2025 14:13:00 +0100 Subject: [PATCH 043/144] restore energy conservation in implicit scheme with feedback --- src/fluid/drag.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 8bc765160..d1b5de954 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -169,7 +169,7 @@ void Drag::AddImplicitFluidMomentum(const real dt) { // TODO(GL): this should be disabled in the case of a true multifluid system where // both fluids have a proper energy equation - if(feedback) UcGas(ENG,k,j,i) -= dp*UcDust(n,k,j,i)/UcDust(RHO,k,j,i); + if(feedback) UcGas(ENG,k,j,i) -= dp*VcDust(n,k,j,i); #endif } }); From e8d34bb2b16671598f3fb20914368a3f53a1baea Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 13 Feb 2025 21:02:41 +0100 Subject: [PATCH 044/144] fix label of dust tracers with non-isothermal equation of state fix #320 --- src/fluid/fluid.hpp | 91 +++++++++++++++++++++++---------------------- 1 file changed, 47 insertions(+), 44 deletions(-) diff --git a/src/fluid/fluid.hpp b/src/fluid/fluid.hpp index ae809b489..44cace6bf 100644 --- a/src/fluid/fluid.hpp +++ b/src/fluid/fluid.hpp @@ -585,52 +585,55 @@ Fluid::Fluid(Grid &grid, Input &input, DataBlock *datain, int n) { } for(int i = 0 ; i < Phys::nvar+nTracer ; i++) { - switch(i) { - case RHO: - VcName.push_back("RHO"); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-RHO", RHO); - break; - case VX1: - VcName.push_back("VX1"); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX1", VX1, IDIR); - break; - case VX2: - VcName.push_back("VX2"); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX2", VX2, JDIR); - break; - case VX3: - VcName.push_back("VX3"); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX3", VX3, KDIR); - break; - case BX1: - VcName.push_back("BX1"); - // never save cell-centered BX1 in dumps - break; - case BX2: - VcName.push_back("BX2"); - #if DIMENSIONS < 2 - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-BX2", BX2, JDIR); - #endif - break; - case BX3: - VcName.push_back("BX3"); - #if DIMENSIONS < 3 - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-BX3", BX3, KDIR); - #endif - break; - case PRS: - VcName.push_back("PRS"); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-PRS", PRS); - break; - default: - if(i>=Phys::nvar) { - std::string tracerLabel = std::string("TR")+std::to_string(i-Phys::nvar); // ="TRn" - VcName.push_back(tracerLabel); - data->dump->RegisterVariable(Vc, outputPrefix+"Vc-"+tracerLabel, i); - } else { + if(i < Phys::nvar) { + // These are standard variable names + switch(i) { + case RHO: + VcName.push_back("RHO"); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-RHO", RHO); + break; + case VX1: + VcName.push_back("VX1"); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX1", VX1, IDIR); + break; + case VX2: + VcName.push_back("VX2"); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX2", VX2, JDIR); + break; + case VX3: + VcName.push_back("VX3"); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-VX3", VX3, KDIR); + break; + case BX1: + VcName.push_back("BX1"); + // never save cell-centered BX1 in dumps + break; + case BX2: + VcName.push_back("BX2"); + #if DIMENSIONS < 2 + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-BX2", BX2, JDIR); + #endif + break; + case BX3: + VcName.push_back("BX3"); + #if DIMENSIONS < 3 + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-BX3", BX3, KDIR); + #endif + break; + case PRS: + VcName.push_back("PRS"); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-PRS", PRS); + break; + default: + // unknown variable name (this should never happen, but who knows...) VcName.push_back("Vc-"+std::to_string(i)); data->vtk->RegisterVariable(Vc, outputPrefix+"Vc-"+std::to_string(i), i); - } + break; + } + } else { //if(i>=Phys::nvar) + std::string tracerLabel = std::string("TR")+std::to_string(i-Phys::nvar); // ="TRn" + VcName.push_back(tracerLabel); + data->dump->RegisterVariable(Vc, outputPrefix+"Vc-"+tracerLabel, i); } data->vtk->RegisterVariable(Vc, outputPrefix+VcName[i], i); #ifdef WITH_HDF5 From 34d9366527d8870651f268735a2874e9bc38c875 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 19 Feb 2025 21:37:54 +0100 Subject: [PATCH 045/144] fix a bug that could lead to Nans when using the RKL scheme on grids with small grid spacing (<1e-5) --- src/rkl/rkl.hpp | 5 ----- 1 file changed, 5 deletions(-) diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index a2f6734f9..6f6796209 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -763,11 +763,6 @@ void RKLegendre::CalcParabolicRHS(real t) { KOKKOS_LAMBDA (int n, int k, int j, int i) { real Ax = A(k,j,i); -#if GEOMETRY != CARTESIAN - if(Ax Date: Wed, 19 Feb 2025 22:22:19 +0100 Subject: [PATCH 046/144] change the way polar singularities are handled --- src/fluid/calcRightHandSide.hpp | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index c8738b4b2..b2e964ee4 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -162,9 +162,7 @@ struct Fluid_CorrectFluxFunctor { // Conserve angular momentum, hence flux is R*Bphi Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); if constexpr(Phys::mhd) { - if(Ax0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax; //avoid singularity around poles } } #endif // GEOMETRY==POLAR OR CYLINDRICAL @@ -175,17 +173,17 @@ struct Fluid_CorrectFluxFunctor { Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); #endif // COMPONENTS == 3 if constexpr(Phys::mhd) { - if(Ax0) { // avoid singularity around poles + EXPAND( , + Flux(iBTH,k,j,i) = Flux(iBTH,k,j,i) * x1m(i) / Ax; , + Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) * x1m(i) / Ax; ) + } } } else if constexpr (dir==JDIR) { #if COMPONENTS == 3 Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(sinx2m(j)); if constexpr(Phys::mhd) { - if(Ax0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax; // avoid singularity around poles } #endif // COMPONENTS = 3 } From 2874fda4bd24157089d1b6940562a8c4a96d35ff Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 19 Feb 2025 23:18:46 +0100 Subject: [PATCH 047/144] -refactor curvature terms without using a small number on all Areas -properly handles curvature on Bphi in 2.5D spherical with RKL --- src/rkl/rkl.hpp | 64 ++++++++++++++++++++++++++++++++++++++----------- 1 file changed, 50 insertions(+), 14 deletions(-) diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 6f6796209..0bc220c9e 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -770,19 +770,35 @@ void RKLegendre::CalcParabolicRHS(real t) { // Curvature terms #if (GEOMETRY == POLAR && COMPONENTS >= 2) \ || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) - if(dir==IDIR && nv==iMPHI) { - // Conserve angular momentum, hence flux is R*Vphi - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); + if(dir==IDIR) { + if(nv==iMPHI) { + Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1(i)); + } + if constexpr(Phys::mhd) { + if(nv==iBPHI) { + // No area for this one + if(Ax > 0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax;//avoid singularity around poles + } + } } #endif // GEOMETRY==POLAR OR CYLINDRICAL -#if GEOMETRY == SPHERICAL && COMPONENTS == 3 - if(dir==IDIR && nv==iMPHI) { - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); - } else if(dir==JDIR && nv==iMPHI) { - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(sm(j)); +#if GEOMETRY == SPHERICAL + if(dir==IDIR && nv==VX3) { + Flux(nv,k,j,i) = Flux(nv,k,j,i) * FABS(x1m(i)); + } else if(dir==JDIR && nv==VX3) { + Flux(nv,k,j,i) = Flux(nv,k,j,i) * FABS(sm(j)); + } + + if constexpr(Phys::mhd) { + if(dir == IDIR && Ax > 0 && (nv==BX3 || nv == BX2)) { + Flux(nv,k,j,i) = Flux(nv,k,j,i) * x1m(i) / Ax; + } + if(dir==JDIR && Ax > 0 && nv==BX3) { + Flux(nv,k,j,i) = Flux(nv,k,j,i) / Ax; + } } -#endif // GEOMETRY == SPHERICAL && COMPONENTS == 3 +#endif // GEOMETRY == SPHERICAL$ } ); @@ -813,17 +829,37 @@ void RKLegendre::CalcParabolicRHS(real t) { } #if GEOMETRY != CARTESIAN - #ifdef iMPHI - if((dir==IDIR) && (nv == iMPHI)) { + if(dir==IDIR) { + #ifdef iMPHI + if((nv == iMPHI)) { rhs /= x1(i); } + #endif // iMPHI + if constexpr(Phys::mhd) { + #if (GEOMETRY == POLAR || GEOMETRY == CYLINDRICAL) && (defined iBPHI) + if(nv==iBPHI) rhs = - 1 / dx(i) * (Flux(iBPHI, k, j, i+1) - Flux(iBPHI, k, j, i) ); + + #elif (GEOMETRY == SPHERICAL) + real q = 1 / (x1(i)*dx(i)); + if(nv == BX2 || nv == BX3) { + rhs = -q * ((Flux(nv, k, j, i+1) - Flux(nv, k, j, i) )); + } + #endif // GEOMETRY + } // MHD + } // dir==IDIR + if(dir==JDIR) { #if (GEOMETRY == SPHERICAL) && (COMPONENTS == 3) - if((dir==JDIR) && (nv == iMPHI)) { + if(nv == iMPHI) { rhs /= FABS(s(j)); } + if constexpr(Phys::mhd) { + if(nv == iBPHI) { + rhs = - 1 / (rt(i)*dx(j)) * (Flux(nv, k, j+1, i) - Flux(nv, k, j, i)); + } + } #endif // GEOMETRY - // Nothing for KDIR - #endif // iMPHI + } // dir==JDIR + // Nothing for KDIR #endif // GEOMETRY != CARTESIAN // store the field components From 461ae58a13c2a6734ae0e0faece47e828cc2d32b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 09:14:14 +0100 Subject: [PATCH 048/144] fix typo --- src/rkl/rkl.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 0bc220c9e..1ebebe5ad 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -772,7 +772,7 @@ void RKLegendre::CalcParabolicRHS(real t) { || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) if(dir==IDIR) { if(nv==iMPHI) { - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1(i)); + Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); } if constexpr(Phys::mhd) { if(nv==iBPHI) { From a4ed690b6acf4f4e23351a0cda7dcf2270291b15 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 09:45:34 +0100 Subject: [PATCH 049/144] fix capture on Cuda --- src/rkl/rkl.hpp | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 1ebebe5ad..3a7d37670 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -835,12 +835,15 @@ void RKLegendre::CalcParabolicRHS(real t) { rhs /= x1(i); } #endif // iMPHI + real dx_ = dx(i); + real x1_ = x1(i); + if constexpr(Phys::mhd) { #if (GEOMETRY == POLAR || GEOMETRY == CYLINDRICAL) && (defined iBPHI) - if(nv==iBPHI) rhs = - 1 / dx(i) * (Flux(iBPHI, k, j, i+1) - Flux(iBPHI, k, j, i) ); + if(nv==iBPHI) rhs = - 1 / dx_ * (Flux(iBPHI, k, j, i+1) - Flux(iBPHI, k, j, i) ); #elif (GEOMETRY == SPHERICAL) - real q = 1 / (x1(i)*dx(i)); + real q = 1 / (x1_*dx_); if(nv == BX2 || nv == BX3) { rhs = -q * ((Flux(nv, k, j, i+1) - Flux(nv, k, j, i) )); } @@ -852,9 +855,11 @@ void RKLegendre::CalcParabolicRHS(real t) { if(nv == iMPHI) { rhs /= FABS(s(j)); } + real dx_ = dx(j); + real rt_ = rt(i); if constexpr(Phys::mhd) { if(nv == iBPHI) { - rhs = - 1 / (rt(i)*dx(j)) * (Flux(nv, k, j+1, i) - Flux(nv, k, j, i)); + rhs = - 1 / (rt_*dx_) * (Flux(nv, k, j+1, i) - Flux(nv, k, j, i)); } } #endif // GEOMETRY From b3481f52365ce515c733f7b6e66a36c1214f451f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 13:02:33 +0100 Subject: [PATCH 050/144] do not make an exception when Area=0, as this artificiallykills off one of the EMF component when axisymmetric --- src/fluid/calcRightHandSide.hpp | 66 +++++++++++++++++---------------- src/rkl/rkl.hpp | 57 ++++++++++++++-------------- 2 files changed, 63 insertions(+), 60 deletions(-) diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index b2e964ee4..38ef76d5d 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -149,45 +149,49 @@ struct Fluid_CorrectFluxFunctor { Flux(MX1+meanDir,k,j,i) += meanV * Flux(RHO,k,j,i); } // Fargo & Rotation corrections - real Ax = A(k,j,i); + ////////////////////////////////////////////// + // Define correction factor for the fluxes + ////////////////////////////////////////////// - for(int nv = 0 ; nv < Phys::nvar ; nv++) { - Flux(nv,k,j,i) = Flux(nv,k,j,i) * Ax; - } + real Ax[Phys::nvar]; // corrected Area + for(int nv = 0 ; nv < Phys::nvar ; nv++) Ax[nv] = A(k,j,i); // Curvature terms -#if (GEOMETRY == POLAR && COMPONENTS >= 2) \ - || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) - if constexpr (dir==IDIR) { - // Conserve angular momentum, hence flux is R*Bphi - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); - if constexpr(Phys::mhd) { - if(Ax>0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax; //avoid singularity around poles + #if (GEOMETRY == POLAR && COMPONENTS >= 2) \ + || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) + if constexpr (dir==IDIR) { + // Conserve angular momentum, hence flux is R*Bphi + Ax[iMPHI] *= FABS(x1m(i)); + if constexpr(Phys::mhd) { + Ax[iBPHI] = 1.0; // corrected Flux is simply Bphi + } } - } -#endif // GEOMETRY==POLAR OR CYLINDRICAL + #endif // GEOMETRY==POLAR OR CYLINDRICAL -#if GEOMETRY == SPHERICAL - if constexpr(dir==IDIR) { - #if COMPONENTS == 3 - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); - #endif // COMPONENTS == 3 - if constexpr(Phys::mhd) { - if(Ax>0) { // avoid singularity around poles + #if GEOMETRY == SPHERICAL + if constexpr(dir==IDIR) { + #if COMPONENTS == 3 + Ax[iMPHI] *= FABS(x1m(i)); + #endif // COMPONENTS == 3 + if constexpr(Phys::mhd) { EXPAND( , - Flux(iBTH,k,j,i) = Flux(iBTH,k,j,i) * x1m(i) / Ax; , - Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) * x1m(i) / Ax; ) - } - } - } else if constexpr (dir==JDIR) { - #if COMPONENTS == 3 - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(sinx2m(j)); - if constexpr(Phys::mhd) { - if(Ax>0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax; // avoid singularity around poles + Ax[iBTH] = x1m(i); , + Ax[iBPHI] = x1m(i); ) + }// Phys::mhd + } else if constexpr (dir==JDIR) { + #if COMPONENTS == 3 + Ax[iMPHI] *= FABS(sinx2m(j)); + if constexpr(Phys::mhd) { + Ax[iBPHI] = 1.0; // corrected Flux is simply Bphi + } + #endif // COMPONENTS = 3 } - #endif // COMPONENTS = 3 + #endif // GEOMETRY == SPHERICAL + + // Finally correct the flux + for(int nv = 0 ; nv < Phys::nvar ; nv++) { + Flux(nv,k,j,i) = Flux(nv,k,j,i) * Ax[nv]; } -#endif // GEOMETRY == SPHERICAL } }; diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 3a7d37670..c8dd8cb96 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -762,43 +762,42 @@ void RKLegendre::CalcParabolicRHS(real t) { data->beg[IDIR],data->end[IDIR]+ioffset, KOKKOS_LAMBDA (int n, int k, int j, int i) { real Ax = A(k,j,i); - const int nv = varList(n); - Flux(nv,k,j,i) = Flux(nv,k,j,i) * Ax; - // Curvature terms -#if (GEOMETRY == POLAR && COMPONENTS >= 2) \ - || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) - if(dir==IDIR) { - if(nv==iMPHI) { - Flux(iMPHI,k,j,i) = Flux(iMPHI,k,j,i) * FABS(x1m(i)); - } - if constexpr(Phys::mhd) { - if(nv==iBPHI) { - // No area for this one - if(Ax > 0) Flux(iBPHI,k,j,i) = Flux(iBPHI,k,j,i) / Ax;//avoid singularity around poles + #if (GEOMETRY == POLAR && COMPONENTS >= 2) \ + || (GEOMETRY == CYLINDRICAL && COMPONENTS == 3) + if(dir==IDIR) { + if(nv==iMPHI) { + Ax *= FABS(x1m(i)); + } + if constexpr(Phys::mhd) { + if(nv==iBPHI) { + // No area for this one + Ax = 1; + } } } - } -#endif // GEOMETRY==POLAR OR CYLINDRICAL - -#if GEOMETRY == SPHERICAL - if(dir==IDIR && nv==VX3) { - Flux(nv,k,j,i) = Flux(nv,k,j,i) * FABS(x1m(i)); - } else if(dir==JDIR && nv==VX3) { - Flux(nv,k,j,i) = Flux(nv,k,j,i) * FABS(sm(j)); - } + #endif // GEOMETRY==POLAR OR CYLINDRICAL - if constexpr(Phys::mhd) { - if(dir == IDIR && Ax > 0 && (nv==BX3 || nv == BX2)) { - Flux(nv,k,j,i) = Flux(nv,k,j,i) * x1m(i) / Ax; + #if GEOMETRY == SPHERICAL + if(dir==IDIR && nv==VX3) { + Ax *= FABS(x1m(i)); + } else if(dir==JDIR && nv==VX3) { + Ax *= FABS(sm(j)); } - if(dir==JDIR && Ax > 0 && nv==BX3) { - Flux(nv,k,j,i) = Flux(nv,k,j,i) / Ax; + + if constexpr(Phys::mhd) { + if(dir == IDIR && (nv==BX3 || nv == BX2)) { + Ax = x1m(i); + } + if(dir==JDIR && nv==BX3) { + Ax = 1.0; + } } - } -#endif // GEOMETRY == SPHERICAL$ + #endif // GEOMETRY == SPHERICAL + + Flux(nv,k,j,i) = Flux(nv,k,j,i) * Ax; } ); From af6b3b7064000de48d69c5034635c520186e4670 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 21:08:11 +0100 Subject: [PATCH 051/144] update reference test change tolerance for dustywave to cope with the implicit drag --- reference | 2 +- test/Dust/DustyWave/python/testidefix.py | 7 ++----- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/reference b/reference index 3e1555090..5ecb95884 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 3e1555090230ceb21ea6428d82c032734fef7488 +Subproject commit 5ecb95884f845a23fa0baf45492770c30e22b4fc diff --git a/test/Dust/DustyWave/python/testidefix.py b/test/Dust/DustyWave/python/testidefix.py index c98bc8213..ad52d3306 100755 --- a/test/Dust/DustyWave/python/testidefix.py +++ b/test/Dust/DustyWave/python/testidefix.py @@ -35,9 +35,6 @@ # Get the minimal decay rate (this should be the one that pops up) tau=np.amax(np.imag(sol)) - - - # load the dat file produced by the setup raw=np.loadtxt('../timevol.dat',skiprows=1) t=raw[:,0] @@ -58,10 +55,10 @@ # Compute decay rate: tau_measured=t[-1]/(2*np.log(etot[-1]/etot[0])) # error on the decay rate: -error=(tau_measured-tau)/tau +error=np.abs((tau_measured-tau)/tau) print("error=%f"%error) -if(error<0.065): +if(error<0.07): print("Success!") else: print("Failure!") From 9ea85b0edcd1d4d7dd83ce9194dd79ba96f72d45 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 21:15:35 +0100 Subject: [PATCH 052/144] do not perform implicit capture --- src/fluid/drag.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index d1b5de954..06a88f025 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -71,6 +71,7 @@ void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) auto UcGas = this->UcGas; auto VcGas = this->VcGas; auto VcDust = this->VcDust; + auto UcDust = this->UcDust; bool feedback = this->feedback; From ff459c0d8691caf55d222779e5b8face02a5f243 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 20 Feb 2025 21:21:37 +0100 Subject: [PATCH 053/144] remove reference to useless feedback --- src/fluid/drag.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 06a88f025..4cf879cdd 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -73,8 +73,6 @@ void Drag::AddImplicitBackReaction(const real dt, IdefixArray3D preFactor) auto VcDust = this->VcDust; auto UcDust = this->UcDust; - bool feedback = this->feedback; - bool isFirst = this->instanceNumber == 0; From 3c9f26df2dddbe6d5c7f92b2a388d4b595e3950e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 21 Feb 2025 10:42:14 +0100 Subject: [PATCH 054/144] update signature of fargo+planet+dust drag function --- test/Dust/FargoPlanet/setup.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/Dust/FargoPlanet/setup.cpp b/test/Dust/FargoPlanet/setup.cpp index af611911d..8447efe0b 100644 --- a/test/Dust/FargoPlanet/setup.cpp +++ b/test/Dust/FargoPlanet/setup.cpp @@ -42,7 +42,7 @@ void MySoundSpeed(DataBlock &data, const real t, IdefixArray3D &cs) { // a = 20 cm * beta * (Sigma_phys/100 g.cm^-2) / (rho_s / 2 g.cm^-3) // NB: checked against A. Johansen+ (2007) -void MyDrag(DataBlock *data, real beta, IdefixArray3D &gamma) { +void MyDrag(DataBlock *data, int nSpecie, real beta, IdefixArray3D &gamma) { // Compute the drag coefficient gamma from the input beta auto x1 = data->x[IDIR]; real sigma0 = sigma0Glob; From 902c0032ecda2391819dda0d234612338b75a582 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 21 Feb 2025 10:35:00 +0100 Subject: [PATCH 055/144] add the job to the test suite --- .github/workflows/idefix-ci-jobs.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index dfb89e0fb..b95385e40 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -177,6 +177,8 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/sphBragTDiffusion -all $TESTME_OPTIONS - name: Spherical anisotropic viscosity run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/sphBragViscosity -all $TESTME_OPTIONS + - name: Collisionless thermal conduction + run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/clessTDiffusion -all $TESTME_OPTIONS Examples: needs: [Fargo, Dust, Planet, ShearingBox, SelfGravity] From 24a62e49eba5c49af1393490dacef8918497ef16 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 21 Feb 2025 10:37:17 +0100 Subject: [PATCH 056/144] update reference commit # --- reference | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/reference b/reference index 5ecb95884..c32894208 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 5ecb95884f845a23fa0baf45492770c30e22b4fc +Subproject commit c328942083b618a85b84eb16ce9fd35e67c00597 From c34b8190030ffb12ae6598597fe2d364e0a0bf57 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 21 Feb 2025 23:21:28 +0100 Subject: [PATCH 057/144] clean up test --- test/MHD/clessTDiffusion/setup.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index 651a81f53..dceafd125 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -45,7 +45,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { IdefixArray4D Vs = hydro->Vs; IdefixArray1D x1 = data->x[IDIR]; - real rc,vc,vwind0; + real rc,vwind0; real cs=cs_vescGlob*sqrt(2.); real va_vesc = va_vescGlob; real mu = va_vesc * sqrt(2.); @@ -96,8 +96,8 @@ void Setup::InitFlow(DataBlock &data) { // Create a host copy DataBlockHost d(data); - real r,th,rl; - real PonRho, vwind0, rc, vc; + real r,rl; + real PonRho, vwind0, rc; real cs=cs_vescGlob*sqrt(2.); @@ -110,7 +110,7 @@ void Setup::InitFlow(DataBlock &data) { for(int j = 0; j < d.np_tot[JDIR] ; j++) { for(int i = 0; i < d.np_tot[IDIR] ; i++) { r=d.x[IDIR](i); - th=d.x[JDIR](j); + real vwind; vwind = ParkerWind(r/rc) * cs; From 6f3bedd7fc7b425ad6cc86a0a537c8a7027b952c Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sat, 22 Feb 2025 11:33:27 +0100 Subject: [PATCH 058/144] too much cleaning --- test/MHD/clessTDiffusion/setup.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index dceafd125..4e369b2d3 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -45,7 +45,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { IdefixArray4D Vs = hydro->Vs; IdefixArray1D x1 = data->x[IDIR]; - real rc,vwind0; + real rc,vc,vwind0; real cs=cs_vescGlob*sqrt(2.); real va_vesc = va_vescGlob; real mu = va_vesc * sqrt(2.); From dbdd28d60a7f9f7ce605ba381b55a74c0f7e87ed Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sat, 22 Feb 2025 16:13:33 +0100 Subject: [PATCH 059/144] final cleanup --- test/MHD/clessTDiffusion/setup.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index 4e369b2d3..c540c0def 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -45,7 +45,7 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { IdefixArray4D Vs = hydro->Vs; IdefixArray1D x1 = data->x[IDIR]; - real rc,vc,vwind0; + real rc,vwind0; real cs=cs_vescGlob*sqrt(2.); real va_vesc = va_vescGlob; real mu = va_vesc * sqrt(2.); @@ -53,7 +53,6 @@ void UserDefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { PonRho = cs*cs; rc = 0.25 / (cs_vescGlob*cs_vescGlob); - vc = cs; vwind0 = ParkerWind(1./rc) * cs; hydro->boundary->BoundaryFor("UserDefBoundary", dir, side, From da2702497ade86da469624f7745ecad686e47b41 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 3 Mar 2025 13:06:59 +0100 Subject: [PATCH 060/144] check coarsening inside ghost zone, and detect Nan. Reduce memory footprint by copying only what's needed --- src/dataBlock/coarsen.cpp | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) diff --git a/src/dataBlock/coarsen.cpp b/src/dataBlock/coarsen.cpp index 2da3049cb..a922f226a 100644 --- a/src/dataBlock/coarsen.cpp +++ b/src/dataBlock/coarsen.cpp @@ -66,15 +66,18 @@ void DataBlock::CheckCoarseningLevels() { idfx::pushRegion("DataBlock::CheckCoarseningLevels()"); // Check that the coarsening levels we have are valid // NB: this is a costly procedure, we can't repeat it at each loop! - DataBlockHost d(*this); - d.SyncFromDevice(); for(int dir = 0 ; dir < DIMENSIONS ; dir++) { if(mygrid->coarseningDirection[dir]) { - IdefixHostArray2D arr = d.coarseningLevel[dir]; - const int Xt = (dir == IDIR ? JDIR : IDIR); - const int Xb = (dir == KDIR ? JDIR : KDIR); - for(int i = beg[Xt] ; i < end[Xt] ; i++) { - for(int j = beg[Xb] ; j < end[Xb] ; j++) { + IdefixHostArray2D arr = Kokkos::create_mirror_view_and_copy(Kokkos::HostSpace(), + coarseningLevel[dir]); + for(int i = 0 ; i < arr.extent(1) ; i++) { + for(int j = 0 ; j < arr.extent(0) ; j++) { + if(std::isnan(arr(j,i))) { + std::stringstream str; + str << "Incorrect grid coarsening levels" << std::endl; + str << "at (i,j)=("<< i << "," << j << "): Coarsening level is NaN!" << std::endl; + IDEFIX_ERROR(str); + } if(arr(j,i) < 1) { std::stringstream str; str << "Incorrect grid coarsening levels" << std::endl; From 8bed32b1e3835afa5c99285c441c482d54e37f00 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 3 Mar 2025 13:10:59 +0100 Subject: [PATCH 061/144] fix loop unrolling --- src/dataBlock/coarsen.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/dataBlock/coarsen.cpp b/src/dataBlock/coarsen.cpp index a922f226a..28d7b6690 100644 --- a/src/dataBlock/coarsen.cpp +++ b/src/dataBlock/coarsen.cpp @@ -70,8 +70,8 @@ void DataBlock::CheckCoarseningLevels() { if(mygrid->coarseningDirection[dir]) { IdefixHostArray2D arr = Kokkos::create_mirror_view_and_copy(Kokkos::HostSpace(), coarseningLevel[dir]); - for(int i = 0 ; i < arr.extent(1) ; i++) { - for(int j = 0 ; j < arr.extent(0) ; j++) { + for(int j = 0 ; j < arr.extent(0) ; j++) { + for(int i = 0 ; i < arr.extent(1) ; i++) { if(std::isnan(arr(j,i))) { std::stringstream str; str << "Incorrect grid coarsening levels" << std::endl; From 3d96f4104ff97bfde4dd1c446c880866300bfbaa Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 3 Mar 2025 17:39:43 +0100 Subject: [PATCH 062/144] add back axis flux tube test --- .github/workflows/idefix-ci-jobs.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index b95385e40..275ea1ce2 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -65,6 +65,8 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/OrszagTang -all $TESTME_OPTIONS - name: Orszag Tang 3D+restart tests run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/OrszagTang3D -all $TESTME_OPTIONS + - name: Axis Flux tube + run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/AxisFluxTube -all $TESTME_OPTIONS ParabolicMHD: runs-on: self-hosted From f283f7834b38172cdb3d34bc5edb78df88376e90 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 4 Mar 2025 10:24:50 +0100 Subject: [PATCH 063/144] remove analysis from axisfluxtube --- test/MHD/AxisFluxTube/setup.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/MHD/AxisFluxTube/setup.cpp b/test/MHD/AxisFluxTube/setup.cpp index 34009da85..4c30506d3 100644 --- a/test/MHD/AxisFluxTube/setup.cpp +++ b/test/MHD/AxisFluxTube/setup.cpp @@ -112,7 +112,7 @@ void CoarsenFunction(DataBlock &data) { Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { output.EnrollUserDefVariables(&ComputeUserVars); data.hydro->EnrollUserDefBoundary(&UserdefBoundary); - output.EnrollAnalysis(&Analysis); + //output.EnrollAnalysis(&Analysis); Rtorus = input.Get("Setup","Rtorus",0); Ztorus = input.Get("Setup","Ztorus",0); Rin = input.Get("Setup","Rin",0); From 4c9985fbdd64d8923626dc7b7c10218d10d14e2d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 4 Mar 2025 15:18:05 +0100 Subject: [PATCH 064/144] add environement to gitignore --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index 422647c3f..4de7fb76e 100644 --- a/.gitignore +++ b/.gitignore @@ -4,6 +4,7 @@ doc/source/_static/* doc/source/_public/* doc/source/api/* doc/source/xml/* +doc/env/* # compiled files **/__pycache__ From 3fb2236fd461f139c23fe12dbbed847cd4e03daf Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 4 Mar 2025 15:29:49 +0100 Subject: [PATCH 065/144] final improvement to error message on grid coarsening levels --- src/dataBlock/coarsen.cpp | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/dataBlock/coarsen.cpp b/src/dataBlock/coarsen.cpp index 28d7b6690..4c6b60ccd 100644 --- a/src/dataBlock/coarsen.cpp +++ b/src/dataBlock/coarsen.cpp @@ -74,22 +74,25 @@ void DataBlock::CheckCoarseningLevels() { for(int i = 0 ; i < arr.extent(1) ; i++) { if(std::isnan(arr(j,i))) { std::stringstream str; - str << "Incorrect grid coarsening levels" << std::endl; + str << "Nan in grid coarsening levels" << std::endl; str << "at (i,j)=("<< i << "," << j << "): Coarsening level is NaN!" << std::endl; IDEFIX_ERROR(str); } if(arr(j,i) < 1) { std::stringstream str; - str << "Incorrect grid coarsening levels" << std::endl; - str << "at (i,j)=("<< i << "," << j << "): Coarsening level < 1!" << std::endl; + str << "Coarsening level < 1!" << std::endl; + str << "at (i,j)=("<< i << "," << j << "): "; + str << "coarsening level= " << arr(j,i) << std::endl; IDEFIX_ERROR(str); } const int factor = 1 << (arr(j,i) - 1); if(np_int[dir] % factor != 0) { std::stringstream str; - str << "local grid size not divisible by coarsening level" << std::endl; - str << "at (i,j)=("<< i << "," << j << "): Coarsening level: "; - str << arr(j,i) << std::endl; + str << "Local grid size not divisible by coarsening level." << std::endl; + str << "at (i,j)=("<< i << "," << j << "): "; + str << "coarsening level= " << arr(j,i) << std::endl; + str << np_int[dir] << " cannot be divided by 2^" << arr(j,i)-1; + str << " = " << factor << std::endl; IDEFIX_ERROR(str); } } From 1d9d101860f1a6561030c2f59e04b27e544f5afe Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 4 Mar 2025 16:09:46 +0100 Subject: [PATCH 066/144] use one single plot update performance page --- doc/source/{bench-jeanzay.json => bench.json} | 0 doc/source/performances.rst | 17 +++----------- doc/source/plot_idefix_bench.py | 23 +++++++++++++------ 3 files changed, 19 insertions(+), 21 deletions(-) rename doc/source/{bench-jeanzay.json => bench.json} (100%) diff --git a/doc/source/bench-jeanzay.json b/doc/source/bench.json similarity index 100% rename from doc/source/bench-jeanzay.json rename to doc/source/bench.json diff --git a/doc/source/performances.rst b/doc/source/performances.rst index 6f8c88b2f..0cf8f862c 100644 --- a/doc/source/performances.rst +++ b/doc/source/performances.rst @@ -6,9 +6,8 @@ We report below the performances obtained on various architectures using Idefix. is the 3D MHD Orszag-Tang test problem with 2nd order reconstruction and uct_contact EMFS bundled in Idefix test suite, disabling passive tracers. The test is computed with a 128\ :sup:`3` resolution per MPI sub-domain on GPUs or 32\ :sup:`3` per MPI sub-domain on CPUs. All of the performances measures -have been obtained enabling MPI on *one full node*, but we report here the performance *per GPU* -(i.e. with 2 GCDs on AMD Mi250) or *per core* (on CPU), i.e. dividing the node performance by the number of GPU/core -to simplify the comparison with other clusters. +have been obtained enabling MPI and we reporte here the performance *per GPU*, *per GCD* (on Mi250) + or *per core* (on CPU). The complete scalability tests are available in Idefix `method paper `_. The performances mentionned below are updated for each major revision of Idefix, so they might slightly differ from the method paper. @@ -39,17 +38,7 @@ GPU performances .. plot:: import plot_idefix_bench - plot_idefix_bench.do_plot('Performance on NVidia V100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'v100') - -.. plot:: - - import plot_idefix_bench - plot_idefix_bench.do_plot('Performance on NVidia A100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'a100') - -.. plot:: - - import plot_idefix_bench - plot_idefix_bench.do_plot('Performance on NVidia H100 GPUs at Jean-Zay', 'bench-jeanzay.json', 'h100') + plot_idefix_bench.do_plot('Performance on NVidia and AMD GPUs', 'bench.json', ['v100','a100','h100']) +----------------------+--------------------+----------------------------------------------------+ | Cluster name | GPU | Performances (in 10\ :sup:`6` cell/s/GPU) | diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py index ac91b787e..43482eb04 100644 --- a/doc/source/plot_idefix_bench.py +++ b/doc/source/plot_idefix_bench.py @@ -1,17 +1,26 @@ import matplotlib.pyplot as plt import json -def do_plot(title, bench_file, gpumodel): +def do_plot(title, bench_file, gpumodels): with open(bench_file, 'r') as f: benches = json.load(f) - select = [bench for bench in benches if bench['gpumodel'] == gpumodel][-1] - xs = [r['nbgpu'] for r in select['results']] - ys = [r['cell_updates'] for r in select['results']] + plt.figure() + xmax=0 + ymax=0 + for gpumodel in gpumodels: + select = [bench for bench in benches if bench['gpumodel'] == gpumodel][-1] + + xs = [r['nbgpu'] for r in select['results']] + ys = [r['cell_updates'] for r in select['results']] + plt.plot(xs, ys,'o-',label=gpumodel) + xmax=max(xmax,max(xs)) + ymax=max(ymax,max(ys)) plt.xscale("log", base=2) - plt.plot(xs, ys) - plt.ylim(0,max(ys)*1.1) - plt.xlabel("Number of GPUs") + plt.ylim(0,ymax*1.1) + plt.xlim(1,xmax*1.1) + plt.legend() + plt.xlabel("Number of GPUs/GCDs") plt.ylabel("Performance (cells / second / GPU)") plt.title(title) From 4771bde1c29468d6084b8773a46dda11d4fdf5be Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 6 Mar 2025 10:13:29 +0100 Subject: [PATCH 067/144] Update Adastra Mi250 to lock Rocm version --- doc/source/reference/makefile.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/doc/source/reference/makefile.rst b/doc/source/reference/makefile.rst index aadc205c3..23052d92c 100644 --- a/doc/source/reference/makefile.rst +++ b/doc/source/reference/makefile.rst @@ -111,7 +111,8 @@ We recommend the following modules and environement variables on AdAstra: module load cpe/24.07 module load craype-accel-amd-gfx90a craype-x86-trento module load PrgEnv-cray - module load amd-mixed + module load amd-mixed/6.1.2 + module load rocm/6.1.2 module load cray-python/3.11.7 Finally, *Idefix* can be configured to run on Mi250 by enabling HIP and the desired architecture with the following options to ccmake: From b2168dfb0c10b87f04a6d7ce34243e3fdd323a47 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 10 Mar 2025 16:13:46 +0100 Subject: [PATCH 068/144] add benchmark data --- doc/source/bench.json | 162 +++++++++++++----------------------- doc/source/performances.rst | 12 ++- 2 files changed, 62 insertions(+), 112 deletions(-) diff --git a/doc/source/bench.json b/doc/source/bench.json index 7ded6914e..08a3c8040 100644 --- a/doc/source/bench.json +++ b/doc/source/bench.json @@ -1,209 +1,161 @@ [ { - "date": "2025-01-17_15:33:13", + "date": "2025-03-04_12:57:12", "gpumodel": "v100", - "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "idefix_commit": "2bc09a0d218459f278e2b28506a09e4591b103ae", + "bench_commit": "37161676db15115c38fed3f35c94fa447cbac7bd", "results": [ { "nbgpu": 1, - "cell_updates": 1.192208E+8 + "cell_updates": 1.193720E+8 }, { "nbgpu": 2, - "cell_updates": 1.178276E+8 + "cell_updates": 1.178864E+8 }, { "nbgpu": 4, - "cell_updates": 1.151014E+8 - } - ] - }, - { - "date": "2025-01-17_15:35:16", - "gpumodel": "v100", - "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", - "results": [ - { - "nbgpu": 1, - "cell_updates": 1.192139E+8 + "cell_updates": 1.155336E+8 }, { - "nbgpu": 2, - "cell_updates": 1.178690E+8 + "nbgpu": 8, + "cell_updates": 1.014338E+8 }, { - "nbgpu": 4, - "cell_updates": 1.092092E+8 + "nbgpu": 16, + "cell_updates": 9.855007E+7 }, { - "nbgpu": 8, - "cell_updates": 7.464571E+7 + "nbgpu": 32, + "cell_updates": 9.012061E+7 }, { - "nbgpu": 16, - "cell_updates": 7.485223E+7 + "nbgpu": 64, + "cell_updates": 8.538461E+7 }, { - "nbgpu": 32, - "cell_updates": 6.795755E+7 + "nbgpu": 128, + "cell_updates": 8.531021E+7 } ] }, { - "date": "2025-01-17_16:57:02", - "gpumodel": "v100", - "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "date": "2025-03-04_13:07:10", + "gpumodel": "a100", + "idefix_commit": "2bc09a0d218459f278e2b28506a09e4591b103ae", + "bench_commit": "b536949200e50fac68d8a46d5db38fc8e3f02da5", "results": [ { "nbgpu": 1, - "cell_updates": 1.192784E+8 + "cell_updates": 2.044728E+8 }, { "nbgpu": 2, - "cell_updates": 1.117701E+8 + "cell_updates": 2.003563E+8 }, { "nbgpu": 4, - "cell_updates": 1.087580E+8 + "cell_updates": 1.963512E+8 }, { "nbgpu": 8, - "cell_updates": 7.472364E+7 + "cell_updates": 1.933039E+8 }, { "nbgpu": 16, - "cell_updates": 7.554497E+7 + "cell_updates": 9.759154E+7 }, { "nbgpu": 32, - "cell_updates": 6.669339E+7 + "cell_updates": 6.369645E+7 }, { "nbgpu": 64, - "cell_updates": 5.497455E+7 + "cell_updates": 4.629474E+7 }, { "nbgpu": 128, - "cell_updates": 5.440610E+7 + "cell_updates": 4.580281E+7 } ] }, { - "date": "2025-01-17_17:09:39", - "gpumodel": "a100", - "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "date": "2025-03-04_13:16:01", + "gpumodel": "h100", + "idefix_commit": "2bc09a0d218459f278e2b28506a09e4591b103ae", + "bench_commit": "b536949200e50fac68d8a46d5db38fc8e3f02da5", "results": [ { "nbgpu": 1, - "cell_updates": 2.035935E+8 + "cell_updates": 3.079643E+8 }, { "nbgpu": 2, - "cell_updates": 1.992927E+8 + "cell_updates": 3.012300E+8 }, { "nbgpu": 4, - "cell_updates": 1.958386E+8 + "cell_updates": 2.944091E+8 }, { "nbgpu": 8, - "cell_updates": 1.929568E+8 + "cell_updates": 2.837224E+8 }, { "nbgpu": 16, - "cell_updates": 9.408132E+7 + "cell_updates": 2.827778E+8 }, { "nbgpu": 32, - "cell_updates": 5.937487E+7 + "cell_updates": 2.822657E+8 }, { "nbgpu": 64, - "cell_updates": 4.159838E+7 + "cell_updates": 2.767820E+8 }, { "nbgpu": 128, - "cell_updates": 5.061931E+7 + "cell_updates": 2.767322E+8 } ] }, { - "date": "2025-01-17_17:23:13", - "gpumodel": "h100", - "idefix_commit": "d0e82202ca90d0b664c71582962c2ae255bc6528", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", + "date": "2025-03-06_11:21:56", + "gpumodel": "mi250x", + "idefix_commit": "2bc09a0d218459f278e2b28506a09e4591b103ae", + "bench_commit": "868be0a87c6fcda665cbb62db7020aeff70dc62d", "results": [ { "nbgpu": 1, - "cell_updates": 3.083581E+8 - } - ] - }, - { - "date": "2025-01-24_13:02:08", - "gpumodel": "h100", - "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", - "results": [ - { - "nbgpu": 1, - "cell_updates": 3.076537E+8 - } - ] - }, - { - "date": "2025-01-24_13:04:02", - "gpumodel": "h100", - "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", - "results": [ - { - "nbgpu": 1, - "cell_updates": 3.032686E+8 + "cell_updates": 1.436580E+8 }, { "nbgpu": 2, - "cell_updates": 3.007089E+8 + "cell_updates": 1.372499E+8 }, { "nbgpu": 4, - "cell_updates": 2.938962E+8 - } - ] - }, - { - "date": "2025-01-24_14:17:30", - "gpumodel": "h100", - "idefix_commit": "54482d582361f1cd05c39717902f752b3d04ae6e", - "bench_commit": "a94bc00490b3c62f81f7713327f4388e44a2abea", - "results": [ - { - "nbgpu": 1, - "cell_updates": 3.074363E+8 + "cell_updates": 1.344528E+8 }, { - "nbgpu": 2, - "cell_updates": 3.009340E+8 + "nbgpu": 8, + "cell_updates": 1.293602E+8 }, { - "nbgpu": 4, - "cell_updates": 2.938868E+8 + "nbgpu": 16, + "cell_updates": 1.260359E+8 }, { - "nbgpu": 8, - "cell_updates": 2.833054E+8 + "nbgpu": 32, + "cell_updates": 1.204980E+8 }, { - "nbgpu": 16, - "cell_updates": 2.822483E+8 + "nbgpu": 64, + "cell_updates": 1.163099E+8 }, { - "nbgpu": 32, - "cell_updates": 2.817151E+8 + "nbgpu": 128, + "cell_updates": 1.192343E+8 } ] } diff --git a/doc/source/performances.rst b/doc/source/performances.rst index 0cf8f862c..deae1194e 100644 --- a/doc/source/performances.rst +++ b/doc/source/performances.rst @@ -7,7 +7,7 @@ is the 3D MHD Orszag-Tang test problem with 2nd order reconstruction and uct_con Idefix test suite, disabling passive tracers. The test is computed with a 128\ :sup:`3` resolution per MPI sub-domain on GPUs or 32\ :sup:`3` per MPI sub-domain on CPUs. All of the performances measures have been obtained enabling MPI and we reporte here the performance *per GPU*, *per GCD* (on Mi250) - or *per core* (on CPU). +or *per core* (on CPU). The complete scalability tests are available in Idefix `method paper `_. The performances mentionned below are updated for each major revision of Idefix, so they might slightly differ from the method paper. @@ -38,10 +38,8 @@ GPU performances .. plot:: import plot_idefix_bench - plot_idefix_bench.do_plot('Performance on NVidia and AMD GPUs', 'bench.json', ['v100','a100','h100']) + plot_idefix_bench.do_plot('Performance on NVidia and AMD GPUs', 'bench.json', ['v100','a100','h100','mi250x']) -+----------------------+--------------------+----------------------------------------------------+ -| Cluster name | GPU | Performances (in 10\ :sup:`6` cell/s/GPU) | -+======================+====================+====================================================+ -| CINES/Adastra | AMD Mi250 | 250 | -+----------------------+--------------------+----------------------------------------------------+ +.. note:: + + The inter-node communication on Jean Zay is not optimal on A100 nodes. A ticket is opened with IDRIS support to fix this issue. From d59ecf0eb5d89abd974cadd87fc7ef5997271dde Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Mar 2025 13:15:35 +0100 Subject: [PATCH 069/144] attempt at fixing Kokkos SYCL loop configuration (a proper benchmark would be needed). --- src/loop.hpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/loop.hpp b/src/loop.hpp index 8ad345dea..73afe53e1 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -51,6 +51,8 @@ typedef Kokkos::TeamPolicy<>::member_type member_type; constexpr LoopPattern defaultLoop = LoopPattern::RANGE; #elif defined(KOKKOS_ENABLE_HIP) constexpr LoopPattern defaultLoop = LoopPattern::RANGE; + #elif defined(KOKKOS_ENABLE_SYCL) + constexpr LoopPattern defaultLoop = LoopPattern::RANGE; #elif defined(KOKKOS_ENABLE_SERIAL) constexpr LoopPattern defaultLoop = LoopPattern::SIMDFOR; #else From ca9c8b0302c424f0f0b6439c4568979d9c21ef56 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 11 Mar 2025 13:22:26 +0100 Subject: [PATCH 070/144] tabs --- src/loop.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/loop.hpp b/src/loop.hpp index 73afe53e1..262c6ac12 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -51,7 +51,7 @@ typedef Kokkos::TeamPolicy<>::member_type member_type; constexpr LoopPattern defaultLoop = LoopPattern::RANGE; #elif defined(KOKKOS_ENABLE_HIP) constexpr LoopPattern defaultLoop = LoopPattern::RANGE; - #elif defined(KOKKOS_ENABLE_SYCL) + #elif defined(KOKKOS_ENABLE_SYCL) constexpr LoopPattern defaultLoop = LoopPattern::RANGE; #elif defined(KOKKOS_ENABLE_SERIAL) constexpr LoopPattern defaultLoop = LoopPattern::SIMDFOR; From dd702ab3e6d8a54b13e632773a00f78ab4b7247b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 12 Mar 2025 14:27:16 -0400 Subject: [PATCH 071/144] add a static_assert so that the error observed on syscl doesn't go unnoticed when a new architecture is tried --- src/loop.hpp | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/loop.hpp b/src/loop.hpp index 262c6ac12..b6a5a9a1f 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -310,6 +310,12 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { + // Check that Idefix Arrays can be assigned from SIMD loop + static_assert( + Kokkos::SpaceAccessibility::accessible, + "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." + ); for (auto n = NB; n < NE; n++) for (auto k = KB; k < KE; k++) for (auto j = JB; j < JE; j++) From 9d7c589b43f935ac10768cf49072cea597fb2e4d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 12 Mar 2025 14:32:08 -0400 Subject: [PATCH 072/144] do this for all loops --- src/loop.hpp | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/src/loop.hpp b/src/loop.hpp index b6a5a9a1f..062380118 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -128,6 +128,12 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { + // Check that Idefix Arrays can be assigned from SIMD loop + static_assert( + Kokkos::SpaceAccessibility::accessible, + "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." + ); for (auto j = JB; j < JE; j++) #pragma omp simd for (auto i = IB; i < IE; i++) @@ -212,6 +218,12 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { + // Check that Idefix Arrays can be assigned from SIMD loop + static_assert( + Kokkos::SpaceAccessibility::accessible, + "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." + ); for (auto k = KB; k < KE; k++) for (auto j = JB; j < JE; j++) #pragma omp simd From 217a812a9a2bf82b676004ecee5b21eaf043796b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 12 Mar 2025 14:46:13 -0400 Subject: [PATCH 073/144] catch misbehaved loops earlier (fix cuda!), and be more explicit. --- src/loop.hpp | 29 +++++++++++++---------------- 1 file changed, 13 insertions(+), 16 deletions(-) diff --git a/src/loop.hpp b/src/loop.hpp index 062380118..20933ec91 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -34,6 +34,12 @@ typedef Kokkos::TeamPolicy<>::member_type member_type; // Check if the user requested a specific loop unrolling strategy #if defined(LOOP_PATTERN_SIMD) + // Check that Idefix Arrays can be assigned from SIMD loop + static_assert( + Kokkos::SpaceAccessibility::accessible, + "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." + ); constexpr LoopPattern defaultLoop = LoopPattern::SIMDFOR; #elif defined(LOOP_PATTERN_1DRANGE) constexpr LoopPattern defaultLoop = LoopPattern::RANGE; @@ -54,6 +60,13 @@ typedef Kokkos::TeamPolicy<>::member_type member_type; #elif defined(KOKKOS_ENABLE_SYCL) constexpr LoopPattern defaultLoop = LoopPattern::RANGE; #elif defined(KOKKOS_ENABLE_SERIAL) + // Check that Idefix Arrays can be assigned from SIMD loop + static_assert( + Kokkos::SpaceAccessibility::accessible, + "Idefix Arrays cannot be accessed from Host, but Device is unknown/untested. " + "Ask the developers to add support." + ); constexpr LoopPattern defaultLoop = LoopPattern::SIMDFOR; #else #warning "Unknown target architeture: default to MDrange" @@ -129,11 +142,6 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { // Check that Idefix Arrays can be assigned from SIMD loop - static_assert( - Kokkos::SpaceAccessibility::accessible, - "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." - ); for (auto j = JB; j < JE; j++) #pragma omp simd for (auto i = IB; i < IE; i++) @@ -219,11 +227,6 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { // Check that Idefix Arrays can be assigned from SIMD loop - static_assert( - Kokkos::SpaceAccessibility::accessible, - "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." - ); for (auto k = KB; k < KE; k++) for (auto j = JB; j < JE; j++) #pragma omp simd @@ -322,12 +325,6 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { - // Check that Idefix Arrays can be assigned from SIMD loop - static_assert( - Kokkos::SpaceAccessibility::accessible, - "Idefix Arrays cannot be accessed from SIMD loop. You should try another loop pattern." - ); for (auto n = NB; n < NE; n++) for (auto k = KB; k < KE; k++) for (auto j = JB; j < JE; j++) From e58f72452254ef5650fd3529452af56eae1337f1 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 12 Mar 2025 16:32:48 -0400 Subject: [PATCH 074/144] cleaning up --- src/loop.hpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/loop.hpp b/src/loop.hpp index 20933ec91..42192fa84 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -141,7 +141,6 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { - // Check that Idefix Arrays can be assigned from SIMD loop for (auto j = JB; j < JE; j++) #pragma omp simd for (auto i = IB; i < IE; i++) @@ -226,7 +225,6 @@ inline void idefix_for(const std::string & NAME, // SIMD FOR loops } else if constexpr(defaultLoop == LoopPattern::SIMDFOR) { - // Check that Idefix Arrays can be assigned from SIMD loop for (auto k = KB; k < KE; k++) for (auto j = JB; j < JE; j++) #pragma omp simd From 939f0cdf362498f371acab02cc62b0a135c8d66f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 31 Mar 2025 16:07:53 +0200 Subject: [PATCH 075/144] fix axis current regularisation along the south pole --- src/fluid/boundary/axis.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index b77fe3b5f..3ad67f0a0 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -128,12 +128,12 @@ void Axis::RegularizeCurrentSide(int side) { real deltaPhi = data->mygrid->xend[KDIR] - data->mygrid->xbeg[KDIR]; // Use the circulation around the pole of Bphi to determine Jr on the pole: - // Delta phi r^2(1-cos theta) Jr = int r sin(theta) Bphi dphi + // 1/2*Delta phi r^2 sin theta^2 Jr = int r sin(theta) Bphi dphi idefix_for("fixJ",0,data->np_tot[KDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA(int k,int i) { real th = x2(jc); - real fact = sign*sin(th)/(deltaPhi*x1(i)*(1-cos(th))); + real fact = 2*sign/(deltaPhi*x1(i)*sin(th)); J(IDIR, k,js,i) = BAvg(i)*fact; }); From 8e0481e93e07c94b9d6e2e1706b552058257cb12 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 14 Apr 2025 21:01:52 +0200 Subject: [PATCH 076/144] make divB check diemsionless --- src/fluid/checkDivB.hpp | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/src/fluid/checkDivB.hpp b/src/fluid/checkDivB.hpp index f9aac45c2..c78f6b3e0 100644 --- a/src/fluid/checkDivB.hpp +++ b/src/fluid/checkDivB.hpp @@ -30,14 +30,30 @@ real Fluid::CheckDivB() { data->beg[IDIR], data->end[IDIR], KOKKOS_LAMBDA (int k, int j, int i, real &divBmax) { [[maybe_unused]] real dB1,dB2,dB3; + [[maybe_unused]] real d1, d2, d3; + [[maybe_unused]] real B1,B2,B3; dB1=dB2=dB3=ZERO_F; + d1=d2=d3=ZERO_F; + B1=B2=B3=ZERO_F; + D_EXPAND( dB1=(Ax1(k,j,i+1)*Vs(BX1s,k,j,i+1)-Ax1(k,j,i)*Vs(BX1s,k,j,i)); , dB2=(Ax2(k,j+1,i)*Vs(BX2s,k,j+1,i)-Ax2(k,j,i)*Vs(BX2s,k,j,i)); , dB3=(Ax3(k+1,j,i)*Vs(BX3s,k+1,j,i)-Ax3(k,j,i)*Vs(BX3s,k,j,i)); ) - divBmax=FMAX(FABS(D_EXPAND(dB1, +dB2, +dB3))/dV(k,j,i),divBmax); + D_EXPAND( d1=0.5*(Ax1(k,j,i+1) + Ax1(k,j,i)); , + d2=0.5*(Ax2(k,j+1,i) + Ax2(k,j,i)); , + d3=0.5*(Ax3(k+1,j,i) + Ax3(k,j,i)); ) + + D_EXPAND( B1=0.5*(Vs(BX1s,k,j,i+1) + Vs(BX1s,k,j,i)); , + B2=0.5*(Vs(BX2s,k,j+1,i) + Vs(BX2s,k,j,i)); , + B3=0.5*(Vs(BX3s,k+1,j,i) + Vs(BX3s,k,j,i)); ) + + real amplitude = 1e-40; + amplitude += D_EXPAND( std::fabs(B1)*d1, + std::fabs(B2)*d2, + std::fabs(B3)*d3 ); + + divBmax=FMAX(FABS(D_EXPAND(dB1, +dB2, +dB3))/amplitude,divBmax); }, Kokkos::Max(divB) // reduction ); From d894627578db1f80322c9daadbcee26ef161dd78 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 16 Apr 2025 11:22:03 +0200 Subject: [PATCH 077/144] use one single extra parameter for dump time output --- src/output/output.cpp | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/output/output.cpp b/src/output/output.cpp index a67cb1666..9df188926 100644 --- a/src/output/output.cpp +++ b/src/output/output.cpp @@ -55,8 +55,13 @@ Output::Output(Input &input, DataBlock &data) dumpPeriod = input.Get("Output","dmp",0); dumpLast = data.t - dumpPeriod; // dump something in the next CheckForWrite() if(input.CheckEntry("Output","dmp")>1) { - dumpTimePeriod = input.Get("Output","dmp",1); - std::string dumpTimeExtension = input.Get("Output","dmp",2); + std::string dumpString = input.Get("Output","dmp",1); + try { + dumpTimePeriod = std::stod(dumpString.substr(0, dumpString.size()-1), NULL); + } catch(const std::exception& e) { + IDEFIX_ERROR("The dump time period should be a number followed by a unit (s, m, h or d)"); + } + std::string dumpTimeExtension = dumpString.substr(dumpString.size()-1,1); if(dumpTimeExtension.compare("s")==0) { dumpTimePeriod *= 1.0; // Dump time period is in seconds by default } else if (dumpTimeExtension.compare("m")==0) { From 83986d0efd681945bae6da2e5fba852d6014fa5d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 16 Apr 2025 11:28:57 +0200 Subject: [PATCH 078/144] add doc for wallclock dump outputs --- doc/source/reference/idefix.ini.rst | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/doc/source/reference/idefix.ini.rst b/doc/source/reference/idefix.ini.rst index c9f9c5785..1fa05cc67 100644 --- a/doc/source/reference/idefix.ini.rst +++ b/doc/source/reference/idefix.ini.rst @@ -388,8 +388,10 @@ This section describes the outputs *Idefix* produces. For more details about eac +================+=========================+==================================================================================================+ | log | integer | | Time interval between log outputs, in code steps (default 100). | +----------------+-------------------------+--------------------------------------------------------------------------------------------------+ -| dmp | float | | Time interval between dump outputs, in code units. | -| | | | If negative, periodic dump outputs are disabled. | +| dmp | float, float+char | | 1st parameter: Code time interval between dump outputs, in code units. | +| | | | If negative, the first parameter is ignored. | +| | | | 2nd parameter (optional): Wallclock time interval between two dumps. The ending character | +| | | | can be "s" (seconds) "m" (minutes) "h" (hours) or "d" (days) | +----------------+-------------------------+--------------------------------------------------------------------------------------------------+ | dmp_dir | string | | directory for dump file outputs. Default to "./" | | | | | The directory is automatically created if it does not exist. | From 1be41152ea576f1534887ddbaf866905a53fe47a Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 25 Apr 2025 09:13:37 +0200 Subject: [PATCH 079/144] Add units (#338) --- doc/source/reference/idefix.ini.rst | 25 ++++++++- src/CMakeLists.txt | 2 + src/global.cpp | 2 + src/global.hpp | 2 + src/gravity/gravity.cpp | 16 +++++- src/main.cpp | 5 ++ src/units.cpp | 55 ++++++++++++++++++ src/units.hpp | 87 +++++++++++++++++++++++++++++ 8 files changed, 192 insertions(+), 2 deletions(-) create mode 100644 src/units.cpp create mode 100644 src/units.hpp diff --git a/doc/source/reference/idefix.ini.rst b/doc/source/reference/idefix.ini.rst index 1fa05cc67..2de3e9136 100644 --- a/doc/source/reference/idefix.ini.rst +++ b/doc/source/reference/idefix.ini.rst @@ -265,8 +265,10 @@ section as followed: +----------------+-------------------------+---------------------------------------------------------------------------------------------+ | Mcentral | real | | Mass of the central object when a central potential is enabled (see above). Default is 1. | +----------------+-------------------------+---------------------------------------------------------------------------------------------+ -| gravCst | real | | Set the value of the gravitational constant :math:`G_c` used by the central | +| gravCst | real or string | | Set the value of the gravitational constant :math:`G_c` used by the central | | | | | mass potential and self-gravitational potential (when enabled) ). Default is 1. | +| | | | If set to "units", Idefix will compute the gravitational constant from the user units | +| | | | defined in the units section (see :ref:`unitsSection`). | +----------------+-------------------------+---------------------------------------------------------------------------------------------+ | bodyForce | string | | Adds an acceleration vector to each cell of the domain. The only value allowed | | | | | is ``userdef``. The ``Gravity`` class then expects a user-defined bodyforce function to | @@ -310,7 +312,28 @@ of gravitational potential in the ``Gravity`` section (see :ref:`gravitySection` | | | | Default is 1 (i.e. self-gravity is computed at every cycle). | +----------------+-------------------------+---------------------------------------------------------------------------------------------+ +.. _unitsSection: +``Units`` section +------------------ + +This optional section controls how the code handles units. By default, Idefix work "unit free" and this section is not useful. +However, some physical processes like self-gravity or radiative transfer require the explicit use of units to define natural constants. +These entries define how one code units should be converted to CGS units. When used, the following values should be set: + ++----------------+--------------------+-----------------------------------------------------------------------------------------------------------+ +| Entry name | Parameter type | Comment | ++================+====================+===========================================================================================================+ +| length | float | The code unit length: 1 code unit = `length` cm. 1 by default. | ++----------------+--------------------+-----------------------------------------------------------------------------------------------------------+ +| velocity | float | The code unit velocity: 1 code unit = `velocity` cm/s. 1 by default. | ++----------------+--------------------+-----------------------------------------------------------------------------------------------------------+ +| density | float | The code unit density: 1 code unit = `density` g/cm^3. 1 by default. | ++----------------+--------------------+-----------------------------------------------------------------------------------------------------------+ + +.. note:: + The units module automatically reconstruct all of the units (time, temperature, magnetic field, etc.) from the above 3 fondamental constants. These can + all be obtained from the global object ``idfx::units``. Note however that the code outputs remain in code units, even if `[Units]` are defined. ``RKL`` section ------------------ diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 727f21504..08dd93c61 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -28,6 +28,8 @@ target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/reduce.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/setup.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/setup.cpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/units.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/units.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/timeIntegrator.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/timeIntegrator.cpp ) diff --git a/src/global.cpp b/src/global.cpp index 4d9499d96..dd7cb573b 100644 --- a/src/global.cpp +++ b/src/global.cpp @@ -11,6 +11,7 @@ #include "idefix.hpp" #include "global.hpp" #include "profiler.hpp" +#include "units.hpp" #ifdef WITH_MPI #include "mpi.hpp" @@ -29,6 +30,7 @@ IdefixOutStream cout; IdefixErrStream cerr; Profiler prof; LoopPattern defaultLoopPattern; +Units units; #ifdef DEBUG static int regionIndent = 0; diff --git a/src/global.hpp b/src/global.hpp index 265699b29..5a9ea70fb 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -20,6 +20,7 @@ void safeExit(int ); // Exit the code class IdefixOutStream; class IdefixErrStream; class Profiler; +class Units; extern int prank; //< parallel rank extern int psize; @@ -29,6 +30,7 @@ extern Profiler prof; //< profiler (for memory & performance u extern double mpiCallsTimer; //< time significant MPI calls extern LoopPattern defaultLoopPattern; //< default loop patterns (for idefix_for loops) extern bool warningsAreErrors; //< whether warnings should be considered as errors +extern Units units; //< Units for the run void pushRegion(const std::string&); void popRegion(); diff --git a/src/gravity/gravity.cpp b/src/gravity/gravity.cpp index c0096c51e..a39b00063 100644 --- a/src/gravity/gravity.cpp +++ b/src/gravity/gravity.cpp @@ -12,13 +12,27 @@ #include "dataBlock.hpp" #include "output.hpp" #include "input.hpp" +#include "units.hpp" Gravity::Gravity(Input &input, DataBlock *datain) { idfx::pushRegion("Gravity::Gravity"); this->data = datain; // Gravitational constant G - this->gravCst = input.GetOrSet("Gravity","gravCst",0, 1.0); + // should we compute it from the units? + if(input.CheckEntry("Gravity","gravCst")>=0) { + if(input.Get("Gravity","gravCst",0).compare("units") == 0) { + // User ask us to compute the gravitational constants from the units + + this->gravCst = idfx::units.GetDensity() * idfx::units.GetTime() * idfx::units.GetTime() + * idfx::units.G; + } else { + this->gravCst = input.Get("Gravity","gravCst",0); + } + } else { // default value to 1.0 + this->gravCst = 1.0; + } + // Gravitational potential int nPotential = input.CheckEntry("Gravity","potential"); if(nPotential >=0) { diff --git a/src/main.cpp b/src/main.cpp index d21793d1d..164c134ee 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -30,6 +30,7 @@ #include "idefix.hpp" #include "profiler.hpp" #include "input.hpp" +#include "units.hpp" #include "grid.hpp" #include "gridHost.hpp" #include "fluid.hpp" @@ -79,6 +80,9 @@ int main( int argc, char* argv[] ) { input.PrintLogo(); idfx::cout << "Main: initialization stage." << std::endl; + // Init the units when needed + idfx::units.Init(input); + // Allocate the grid on device Grid grid(input); // Allocate the grid image on host @@ -112,6 +116,7 @@ int main( int argc, char* argv[] ) { << std::endl; } input.ShowConfig(); + idfx::units.ShowConfig(); grid.ShowConfig(); data.ShowConfig(); Tint.ShowConfig(); diff --git a/src/units.cpp b/src/units.cpp new file mode 100644 index 000000000..2baf97b1e --- /dev/null +++ b/src/units.cpp @@ -0,0 +1,55 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#include "units.hpp" +#include "idefix.hpp" +#include "input.hpp" + + +void idfx::Units::Init(Input &input) { + if(input.CheckBlock("Units")) { + this->_length = input.GetOrSet("Units","length",0,1.0); + this->_velocity = input.GetOrSet("Units","velocity",0,1.0); + this->_density = input.GetOrSet("Units","density",0,1.0); + this->ComputeUnits(); + } +} + +void idfx::Units::SetDensity(const real in) { + this->_density = in; + this->ComputeUnits(); +} + +void idfx::Units::SetLength(const real in) { + this->_length = in; + this->ComputeUnits(); +} + +void idfx::Units::SetVelocity(const real in) { + this->_velocity = in; + this->ComputeUnits(); +} + +void idfx::Units::ShowConfig() { + if(_isInitialized) { + idfx::cout << "Units: [Length] = " << this->_length << " cm" << std::endl; + idfx::cout << "Units: [Velocity] = " << this->_velocity << " cm/s" << std::endl; + idfx::cout << "Units: [Density] = " << this->_density << " g/cm3" << std::endl; + idfx::cout << "Units: [Energy] = " << this->_energy << " erg/cm3" << std::endl; + idfx::cout << "Units: [Time] = " << this->_time << " s" << std::endl; + idfx::cout << "Units: [Temperature] = " << this->_Kelvin << " K" << std::endl; + idfx::cout << "Units: [Mag. Field] = " << this->_magField << " G" << std::endl; + } +} + +void idfx::Units::ComputeUnits() { + this->_isInitialized = true; + this->_magField = std::sqrt(4*M_PI*_density*_velocity*_velocity); + this->_Kelvin = u * _velocity*_velocity/k_B; + this->_energy = _density*_velocity*_velocity; + this->_time = _length/_velocity; +} diff --git a/src/units.hpp b/src/units.hpp new file mode 100644 index 000000000..ffafdd4f1 --- /dev/null +++ b/src/units.hpp @@ -0,0 +1,87 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef UNITS_HPP_ +#define UNITS_HPP_ + +#include "idefix.hpp" + +// Units class implemented in CGS +// Constants taken from Astropy +class Input; +namespace idfx { +class Units { + public: + void Init(Input &input); + + + const real u{1.6605390666e-24}; // Atomic mass unit (g) + const real m_p{1.67262192369e-24}; // Proton mass unit (g) + const real m_n{1.67492749804e-24}; // neutron mass unit (g) + const real m_e{9.1093837015e-28}; // electron mass unit (g) + const real k_B{1.380649e-16}; // Boltzmann constant (erg/K) + const real sigma_sb{5.6703744191844314e-05}; // Stephan Boltzmann constant (g/(K^4 s^3)) + const real ar{7.5646e-15}; // Radiation constant + // = 4*sigma_sb/c (g/(K^4 s^2 cm)) + const real c{29979245800.0}; // Speed of light (cm/s) + const real M_sun{1.988409870698051e+33}; // Solar mass (g) + const real R_sun{69570000000.0}; // Solar radius (cm) + const real M_earth{5.972167867791379e+27}; // Earth mass (g) + const real R_earth{637810000.0}; // Earth radius (cm) + const real G{6.674299999999999e-8}; // Gravitatonal constant (cm3 / (g s2)) + const real h{6.62607015e-27}; // Planck constant (erg.s) + const real pc{3.08568e+18}; // Parsec (cm) + const real au{1.49597892e13}; // Astronomical unit (cm) + const real e{4.80320425e-10}; // Elementary charge (cm^3/2 g^1/2 s^-1) + + + // User-defined units, non user-modifiable + // L (cm) = L (code) * Units::length + KOKKOS_INLINE_FUNCTION real GetLength() const {return _length;} + // V(cm/s) = V(code) * Units::velocity + KOKKOS_INLINE_FUNCTION real GetVelocity() const {return _velocity;} + // density (g/cm^3) = density(code) * Units::density + KOKKOS_INLINE_FUNCTION real GetDensity() const {return _density;} + + // Deduced units from user-defined units + // T(K) = P(code)/rho(code) * mu * Units::Kelvin + KOKKOS_INLINE_FUNCTION real GetKelvin() const {return _Kelvin;} + // B(G) = B(code) * Units::MagField + KOKKOS_INLINE_FUNCTION real GetMagField() const {return _magField;} + // energy(erg/cm3) = energy(code) * Units::energy + KOKKOS_INLINE_FUNCTION real GetEnergy() const {return _energy;} + // time(s) = time(code) * Units::time + KOKKOS_INLINE_FUNCTION real GetTime() const {return _time;} + + KOKKOS_INLINE_FUNCTION bool GetIsInitialized() const {return _isInitialized;} + + // code-style change of the units + void SetLength(const real); + void SetVelocity(const real); + void SetDensity(const real); + + // Show the configuration + void ShowConfig(); + + private: + bool _isInitialized{false}; + // read-write variables + real _length{1.0}; + real _velocity{1.0}; + real _density{1.0}; + + // Deduced units from user-defined units + real _Kelvin{1.0}; + real _magField{1.0}; + real _time{1.0}; + real _energy{1.0}; + + // Recompute deduced user-units + void ComputeUnits(); +}; +} // namespace idfx +#endif // UNITS_HPP_ From e4b5a8300cd2554777d1dd249f3743062693d72e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 16 May 2025 18:30:27 +0200 Subject: [PATCH 080/144] add Kokkos::fence at the beginning of profiling regions to fix profiling (#341) --- src/global.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/global.cpp b/src/global.cpp index dd7cb573b..1ed33ba11 100644 --- a/src/global.cpp +++ b/src/global.cpp @@ -66,6 +66,7 @@ int initialize() { void pushRegion(const std::string& kName) { Kokkos::Profiling::pushRegion(kName); if(prof.perfEnabled) { + Kokkos::fence(); prof.currentRegion = prof.currentRegion->GetChild(kName); prof.currentRegion->Start(); } From b22cd2502ebe9ca47b344652e6a22f27dd56e89d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 12 Jun 2025 14:08:01 +0200 Subject: [PATCH 081/144] fix the energetic of ShearingBox+Fargo (#346) * fix the energetic of ShearingBox+Fargo The work done by the gravity force was not properly removed when using fargo --- reference | 2 +- src/fluid/addSourceTerms.hpp | 3 --- src/fluid/calcRightHandSide.hpp | 12 +++++++++--- 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/reference b/reference index c32894208..c4082b99a 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit c328942083b618a85b84eb16ce9fd35e67c00597 +Subproject commit c4082b99a4c542def3177c96cb35b1c9d9002f18 diff --git a/src/fluid/addSourceTerms.hpp b/src/fluid/addSourceTerms.hpp index a0cb5a719..e3f745868 100644 --- a/src/fluid/addSourceTerms.hpp +++ b/src/fluid/addSourceTerms.hpp @@ -83,9 +83,6 @@ struct Fluid_AddSourceTermsFunctor { Uc(MX1,k,j,i) += TWO_F * dt * Vc(RHO,k,j,i) * OmegaZ * Vc(VX2,k,j,i); Uc(MX2,k,j,i) += - TWO_F * dt * Vc(RHO,k,j,i) * OmegaZ * Vc(VX1,k,j,i); } - if(haveFargo) { - Uc(MX1,k,j,i) += TWO_F * dt * Vc(RHO,k,j,i) * OmegaZ * sbS * x1(i); - } #endif // fetch fargo velocity when required [[maybe_unused]] real fargoV = ZERO_F; diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index 38ef76d5d..7777d1c22 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -472,12 +472,18 @@ struct Fluid_CalcRHSFunctor { // Body force if(needBodyForce) { - rhs[MX1+dir] += dt * Vc(RHO,k,j,i) * bodyForce(dir,k,j,i); + real bf = bodyForce(dir,k,j,i); + #if GEOMETRY == CARTESIAN + if(haveFargo && dir==IDIR) { + // Remove Body force that is already compensated by Fargo shear*Rotation + bf -= -2*Omega*sbS * x1(i); + } + #endif + rhs[MX1+dir] += dt * Vc(RHO,k,j,i) * bf; if constexpr(Phys::pressure) { // rho * v . f, where rhov is taken as a volume average of Flux(RHO) rhs[ENG] += HALF_F * dtdV * dl * - (Flux(RHO,k,j,i) + Flux(RHO, k+koffset, j+joffset, i+ioffset)) * - bodyForce(dir,k,j,i); + (Flux(RHO,k,j,i) + Flux(RHO, k+koffset, j+joffset, i+ioffset)) * bf; } // Pressure // Particular cases if we do not sweep all of the components From 81f9143335718d52362c44442b76b2d0c570f030 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 16 Jun 2025 17:33:25 +0200 Subject: [PATCH 082/144] Fix axis and reflective boundary conditions (#345) * fix axis BX2s reconstruction when axis is not used on both sides of the X2 domain (#342) * fix reflective with MHD and DIMENSIONS < 3 (#343) --- src/fluid/boundary/axis.cpp | 53 +++++---------------------------- src/fluid/boundary/axis.hpp | 5 ++-- src/fluid/boundary/boundary.hpp | 50 ++++++++++++++++++------------- 3 files changed, 40 insertions(+), 68 deletions(-) diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index 3ad67f0a0..e447aefc8 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -358,65 +358,28 @@ void Axis::EnforceAxisBoundary(int side) { // Reconstruct Bx2s taking care of the sides where an axis is lying -void Axis::ReconstructBx2s() { - idfx::pushRegion("Axis::ReconstructBx2s"); +void Axis::RegularizeBX2s() { + idfx::pushRegion("Axis::RegularizeBX2s"); #if DIMENSIONS >= 2 && MHD == YES IdefixArray4D Vs = this->Vs; - IdefixArray3D Ax1=data->A[IDIR]; - IdefixArray3D Ax2=data->A[JDIR]; - IdefixArray3D Ax3=data->A[KDIR]; - int nstart = data->beg[JDIR]-1; - int nend = data->end[JDIR]; - int ntot = data->np_tot[JDIR]; - - bool haveleft = axisLeft; - bool haveright = axisRight; - - if(haveleft) { - // This loop is a copy of ReconstructNormalField, with the proper sign when we cross the axis - idefix_for("Axis::ReconstructBX2sLeft",0,data->np_tot[KDIR],0,data->np_tot[IDIR], - KOKKOS_LAMBDA (int k, int i) { - for(int j = nstart ; j>=0 ; j-- ) { - Vs(BX2s,k,j,i) = 1.0 / Ax2(k,j,i) * ( Ax2(k,j+1,i)*Vs(BX2s,k,j+1,i) - +(D_EXPAND( Ax1(k,j,i+1) * Vs(BX1s,k,j,i+1) - Ax1(k,j,i) * Vs(BX1s,k,j,i) , - , - - ( Ax3(k+1,j,i) * Vs(BX3s,k+1,j,i) - - Ax3(k,j,i) * Vs(BX3s,k,j,i) )))); - } - } - ); - } - if(haveright) { - // This loop is a copy of ReconstructNormalField, with the proper sign when we cross the axis - idefix_for("Axis::ReconstructBX2sRight",0,data->np_tot[KDIR],0,data->np_tot[IDIR], - KOKKOS_LAMBDA (int k, int i) { - for(int j = nend ; jend[JDIR]; int jleft = data->beg[JDIR]; if(isTwoPi) { #ifdef AXIS_BX2S_USE_ATHENA_REGULARISATION - if(haveleft) FixBx2sAxisGhostAverage(left); - if(haveright) FixBx2sAxisGhostAverage(right); + if(axisLeft) FixBx2sAxisGhostAverage(left); + if(axisRight) FixBx2sAxisGhostAverage(right); #else - if(haveleft) FixBx2sAxis(left); - if(haveright) FixBx2sAxis(right); + if(axisLeft) FixBx2sAxis(left); + if(axisRight) FixBx2sAxis(right); #endif } else { + bool haveleft = axisLeft; + bool haveright = axisRight; idefix_for("Axis:BoundaryAvg",0,data->np_tot[KDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA (int k, int i) { if(haveleft) { diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index a1c3054b3..b74697862 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -29,7 +29,7 @@ class Axis { void RegularizeEMFs(); // Regularize the EMF sitting on the axis void RegularizeCurrent(); // Regularize the currents along the axis void EnforceAxisBoundary(int side); // Enforce the boundary conditions (along X2) - void ReconstructBx2s(); // Reconstruct BX2s in the ghost zone using divB=0 + void RegularizeBX2s(); // Regularize BX2s on the axis void ShowConfig(); @@ -42,6 +42,8 @@ class Axis { void ExchangeMPI(int side); // Function has to be public for GPU, but its technically // a private function + bool haveLeftAxis() const { return axisLeft; } ///< Check if the axis is on the left + bool haveRightAxis() const { return axisRight; } ///< Check if the axis is on the right private: bool isTwoPi = false; @@ -147,7 +149,6 @@ Axis::Axis(Boundary *boundary) { Kokkos::deep_copy(symmetryVc, symmetryVcHost); if constexpr(Phys::mhd) { - idfx::cout << "Phys MHD" << std::endl; symmetryVs = IdefixArray1D("Axis:SymmetryVs",DIMENSIONS); IdefixArray1D::HostMirror symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); // Init the array diff --git a/src/fluid/boundary/boundary.hpp b/src/fluid/boundary/boundary.hpp index 86909936f..897c1ce10 100644 --- a/src/fluid/boundary/boundary.hpp +++ b/src/fluid/boundary/boundary.hpp @@ -112,6 +112,8 @@ class Boundary { IdefixArray4D Vs; ///< reference to face-centered array that we should sync std::unique_ptr axis; ///< Axis object, initialised if needed. bool haveAxis{false}; + bool haveLeftAxis{false}; ///< True if the left boundary is an axis + bool haveRightAxis{false}; ///< True if the right boundary is an axis private: friend class Axis; @@ -137,6 +139,8 @@ Boundary::Boundary(Fluid* fluid) { if(data->haveAxis) { this->axis = std::make_unique(this); this->haveAxis = true; + this->haveLeftAxis = axis->haveLeftAxis(); + this->haveRightAxis = axis->haveRightAxis(); } @@ -464,30 +468,34 @@ void Boundary::ReconstructNormalField(int dir) { if(dir==JDIR) { nstart = data->beg[JDIR]-1; nend = data->end[JDIR]; - if(!this->haveAxis) { - idefix_for("ReconstructBX2s",0,data->np_tot[KDIR],0,data->np_tot[IDIR], - KOKKOS_LAMBDA (int k, int i) { - if(reconstructLeft) { - for(int j = nstart ; j>=0 ; j-- ) { - Vs(BX2s,k,j,i) = 1.0 / Ax2(k,j,i) * ( Ax2(k,j+1,i)*Vs(BX2s,k,j+1,i) - +(D_EXPAND( Ax1(k,j,i+1) * Vs(BX1s,k,j,i+1) - Ax1(k,j,i) * Vs(BX1s,k,j,i) , - , - + Ax3(k+1,j,i) * Vs(BX3s,k+1,j,i) - Ax3(k,j,i) * Vs(BX3s,k,j,i) ))); - } + #if DIMENSIONS == 3 + const int signLeft = haveLeftAxis ? -1 : 1; // left axis is in the negative direction + const int signRight = haveRightAxis ? -1 : 1; // right axis is in the negative direction + #endif + + idefix_for("ReconstructBX2s",0,data->np_tot[KDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA (int k, int i) { + if(reconstructLeft) { + for(int j = nstart ; j>=0 ; j-- ) { + Vs(BX2s,k,j,i) = 1.0 / Ax2(k,j,i) * ( Ax2(k,j+1,i)*Vs(BX2s,k,j+1,i) + +(D_EXPAND( Ax1(k,j,i+1) * Vs(BX1s,k,j,i+1) - Ax1(k,j,i) * Vs(BX1s,k,j,i) , + , + + signLeft*(Ax3(k+1,j,i) * Vs(BX3s,k+1,j,i) - Ax3(k,j,i) * Vs(BX3s,k,j,i) )))); } - if(reconstructRight) { - for(int j = nend ; jReconstructBx2s(); + axis->RegularizeBX2s(); } } #endif @@ -686,7 +694,7 @@ void Boundary::EnforceReflective(int dir, BoundarySide side ) { const int jref = (dir==JDIR) ? 2*(jghost + side*nxj) - j - 1 : j; const int kref = (dir==KDIR) ? 2*(kghost + side*nxk) - k - 1 : k; - const int sign = (n == VX1+dir) ? -1.0 : 1.0; + const int sign = (n == VX1+dir || (n >= BX1 && n != BX1+dir)) ? -1.0 : 1.0; Vc(n,k,j,i) = sign * Vc(n,kref,jref,iref); }); From bea1c7bd2bb7b12ed215031e620f24df3b2cdedd Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sat, 18 Oct 2025 10:31:30 +0200 Subject: [PATCH 083/144] fix "size" drag force with adiabatic equation of state (sound speed was (#353) --- src/fluid/drag.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/fluid/drag.hpp b/src/fluid/drag.hpp index 29eca3097..63b5e1bdb 100644 --- a/src/fluid/drag.hpp +++ b/src/fluid/drag.hpp @@ -37,8 +37,8 @@ class GammaDrag { // Assume a fixed size, hence for both Epstein or Stokes, gamma~1/rho_g/cs // Get the sound speed #if HAVE_ENERGY == 1 - cs = std::sqrt(eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i) - *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i))); + cs = std::sqrt( eos.GetGamma(VcGas(PRS,k,j,i),VcGas(RHO,k,j,i)) + *VcGas(PRS,k,j,i)/VcGas(RHO,k,j,i)); #else cs = eos.GetWaveSpeed(k,j,i); #endif From cde3a14c68ee65e71fe07adb4c23347cfa9556ad Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sat, 18 Oct 2025 19:10:21 +0200 Subject: [PATCH 084/144] Doc updates (#354) --- doc/source/faq.rst | 13 ++- doc/source/index.rst | 1 + doc/source/testing.rst | 117 ++++++++++++++++++++++ doc/source/testing/idfxTest.rst | 172 ++++++++++++++++++++++++++++++++ 4 files changed, 301 insertions(+), 2 deletions(-) create mode 100644 doc/source/testing.rst create mode 100644 doc/source/testing/idfxTest.rst diff --git a/doc/source/faq.rst b/doc/source/faq.rst index 4c7bc056b..4dd198318 100644 --- a/doc/source/faq.rst +++ b/doc/source/faq.rst @@ -61,9 +61,18 @@ How can I stop the code without loosing the current calculation? I'm doing performance measures. How do I disable all outputs in *Idefix*? Add ``-nowrite`` when you call *Idefix* executable. +VTK output appears corrupted when running with MPI (OpenMPI) + Some OpenMPI configurations (notably OpenMPI 4 with the ompio component) can produce corrupted VTK/VTU output when running with MPI enabled. This appears to be caused by bugs in OpenMPI's ompio I/O component. + Disable ompio so OpenMPI falls back to ROMIO (MPICH's MPI-IO), which is typically more stable: -Developement ------------- + .. code-block:: console + + mpirun --mca io ^ompio ... + + This has resolved intermittent corruption for several users. See issue #348 for discussion and reports. + +Development +----------- I have a serious bug (e.g. segmentation fault), in my setup, how do I proceed? Add ``-DIdefix_DEBUG=ON`` to ``cmake`` and recompile to find out exactly where the code crashes (see :ref:`debugging`). diff --git a/doc/source/index.rst b/doc/source/index.rst index 411d73d6d..d36ab39be 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -122,6 +122,7 @@ The Idefix collaboration benefited from funding from the “Programme National d reference modules programmingguide + testing performances kokkos contributing diff --git a/doc/source/testing.rst b/doc/source/testing.rst new file mode 100644 index 000000000..888ac2057 --- /dev/null +++ b/doc/source/testing.rst @@ -0,0 +1,117 @@ +Continuous Integration (CI) tests +================================ + +This document describes the GitHub Actions continuous-integration setup used to run the Idefix +test-suite. The CI is implemented by two workflows checked in .github/workflows: + +- .github/workflows/idefix-ci.yml +- .github/workflows/idefix-ci-jobs.yml + +Overview +-------- + +The CI is split in two layers: + +- A top-level workflow (.github/workflows/idefix-ci.yml) that: + + - runs a Linter job (pre-commit) on push / PR / manual dispatch, + - then calls a reusable workflow for different compiler/backends (intel, gcc, cuda) + providing two inputs: TESTME_OPTIONS and IDEFIX_COMPILER. + +- A reusable workflow (.github/workflows/idefix-ci-jobs.yml) that: + + - defines the actual test jobs grouped by physics domain (ShocksHydro, ParabolicHydro, + ShocksMHD, ParabolicMHD, Fargo, ShearingBox, SelfGravity, Planet, Dust, Braginskii, + Examples, Utils), + - runs test scripts on self-hosted runners, + - expects the repository to be checked out with submodules, + - invokes the repository-provided CI helper scripts to configure / build / run tests. + +Key configuration points +------------------------ + +- Inputs passed from the top-level workflow: + + - TESTME_OPTIONS (string): flags forwarded to the per-test runner (examples: -cuda, -Werror, + -intel, -all). + - IDEFIX_COMPILER (string): which compiler the tests should use (e.g. icc, gcc, nvcc). + +- Environment variables set by the reusable workflow: + + - IDEFIX_COMPILER, TESTME_OPTIONS, PYTHONPATH, IDEFIX_DIR + +- Linter job: + + - Runs only when repository is the main project (not arbitrary forks). + - Uses actions/setup-python and runs pre-commit (pre-commit/action@v3 and pre-commit-ci/lite). + - Prevents regressions in style and common mistakes before running heavy test jobs. + +- Test execution: + + - All test jobs call the repository script scripts/ci/run-tests with a test directory + and the TESTME_OPTIONS flags. Example invocation (from the workflows): + scripts/ci/run-tests $IDEFIX_DIR/test/HD/sod -all $TESTME_OPTIONS + + - The reusable workflow is written to execute many test directories in separate job steps, + so each physics group is kept logically separated in CI logs. + +Runners and prerequisites +------------------------- + +- The heavy numerical tests run on self-hosted runners (see runs-on: self-hosted). + The CI assumes appropriate hardware and dependencies are available on those runners + (compilers, MPI, GPUs when CUDA/HIP flags are used, required system libraries). + +- The workflows check out the repository and its submodules. Submodules must be available + on the CI machines. + +How tests are driven (testme scripts) +------------------------------------- + +Each test directory contains a small Python "testMe" driver that uses the helper Python +class documented in the repository: + +- See the test helper documentation: :doc:`idfxTest ` + +That helper (idfxTest) is responsible for: + +- parsing TESTME_OPTIONS-like flags (precision, MPI, CUDA, reconstruction, vector potential, etc.), +- calling configure / compile / run, +- performing standard python checks and non-regression (RMSE) comparisons against + reference dumps, +- optionally creating / updating reference dumps (init mode). + +Practical examples +------------------ + +- Example of a CI invocation (triggered by workflows): + + - Top-level workflow calls the reusable jobs workflow for each compiler/back-end, e.g. + TESTME_OPTIONS="-cuda -Werror" IDEFIX_COMPILER=nvcc + +- Running tests locally (developer machine) + - You can mimic what CI does by calling the repository helper script directly. Example: + scripts/ci/run-tests /path/to/idefix/test/HD/sod -all -mpi -dec 2 2 -reconstruction 3 -single + +Notes for maintainers +--------------------- + +- The reusable jobs workflow contains a commented concurrency block for optional cancellation + of in-flight runs — consider enabling it if you want to auto-cancel redundant CI runs. +- Because tests are run on self-hosted runners, ensure the pools have the required compilers, + MPI stacks and GPU drivers for the requested TESTME_OPTIONS. +- Keep TESTME_OPTIONS in sync with the options understood by the test helper documented in + :doc:`idfxTest `. + +Relevant files +-------------- + +- Workflow entry point: .github/workflows/idefix-ci.yml +- Reusable jobs: .github/workflows/idefix-ci-jobs.yml +- Test helper documentation: :doc:`idfxTest ` + +.. toctree:: + :maxdepth: 2 + :caption: Contents: + + testing/idfxTest.rst diff --git a/doc/source/testing/idfxTest.rst b/doc/source/testing/idfxTest.rst new file mode 100644 index 000000000..b425d3fe2 --- /dev/null +++ b/doc/source/testing/idfxTest.rst @@ -0,0 +1,172 @@ +========= +idfxTest +========= + +.. autoclass:: idfxTest + :members: + :undoc-members: + :show-inheritance: + +Overview +-------- + +The ``idfxTest`` class provides a high-level interface for automating the configuration, compilation, execution, and regression testing of Idefix simulations. It is designed to be used in test scripts (such as ``testme.py``) to streamline the testing workflow, including handling reference files and plotting differences. + +Constructor and Command-Line Options +------------------------------------ + +The constructor parses command-line arguments using ``argparse``. These options can be passed directly to the test script or via the command line. The following options are available: + +.. list-table:: + :header-rows: 1 + + * - Option + - Attribute + - Description + * - ``-noplot`` + - ``noplot`` + - Disable plotting in standard tests (default: True). + * - ``-ploterr`` + - ``ploterr`` + - Enable plotting of differences when regression tests fail. + * - ``-cmake OPT [OPT ...]`` + - ``cmake`` + - Extra CMake options (list of strings). + * - ``-definitions FILE`` + - ``definitions`` + - Specify a custom ``definitions.hpp`` file. + * - ``-dec NX NY NZ`` + - ``dec`` + - MPI domain decomposition (list of integers). + * - ``-check`` + - ``check`` + - Only perform regression tests without compilation. + * - ``-cuda`` + - ``cuda`` + - Enable CUDA backend for Nvidia GPUs. + * - ``-intel`` + - ``intel`` + - Use Intel OneAPI compilers. + * - ``-hip`` + - ``hip`` + - Enable HIP backend for AMD GPUs. + * - ``-single`` + - ``single`` + - Enable single precision. + * - ``-vectPot`` + - ``vectPot`` + - Enable vector potential formulation. + * - ``-reconstruction N`` + - ``reconstruction`` + - Set reconstruction scheme (2=PLM, 3=LimO3, 4=PPM). + * - ``-idefixDir PATH`` + - ``idefixDir`` + - Set the directory for Idefix source files (default: ``$IDEFIX_DIR``). + * - ``-mpi`` + - ``mpi`` + - Enable MPI parallelism. + * - ``-all`` + - ``all`` + - Run the full test suite with multiple configurations. + * - ``-init`` + - ``init`` + - Reinitialize reference files for non-regression tests. + * - ``-Werror`` + - ``Werror`` + - Treat compiler warnings as errors. + +Main Methods +------------ + +.. list-table:: + :header-rows: 1 + + * - Method + - Description + * - ``configure`` + - Runs CMake to configure the build system for Idefix, using options set by command-line flags (e.g., precision, MPI, CUDA, etc.). + * - ``compile`` + - Compiles the Idefix code using ``make`` with the specified number of parallel jobs. + * - ``run`` + - Executes the Idefix binary, optionally with MPI, using the provided input file and runtime options. + * - ``checkOnly`` + - Performs regression testing only, without compiling or running the code (useful for checking outputs after a manual run). + * - ``standardTest`` + - Runs any Python-based standard tests (e.g., ``testidefix.py``) present in the test directory for additional validation. + * - ``nonRegressionTest`` + - Compares the output dump file to a reference file using RMSE; fails if the error exceeds the tolerance. + * - ``compareDump`` + - Compares two arbitrary dump files using the same logic as ``nonRegressionTest``. + * - ``makeReference`` + - Copies the specified output file to the reference directory, updating the reference for future regression tests. + +Usage Example +------------- + +Below is an example inspired by ``testme.py`` from ``test/HD/sod/testme.py``. This demonstrates a typical workflow for running tests and performing regression checks. + +.. code-block:: python + + import pytools.idfx_test as tst + + name = "dump.0001.dmp" + + def testMe(test): + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-hll.ini", "idefix-hllc.ini", "idefix-tvdlf.ini"] + if test.reconstruction == 4: + inifiles = ["idefix-rk3.ini", "idefix-hllc-rk3.ini"] + + # Loop over all ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name) + + test = tst.idfxTest() + + if not test.all: + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) + else: + test.noplot = True + for rec in range(2, 5): + test.vectPot = False + test.single = False + test.reconstruction = rec + test.mpi = False + testMe(test) + + # Test in single precision + test.reconstruction = 2 + test.single = True + testMe(test) + +How to Run +---------- + +You can run the test script from the command line, passing any of the supported options. For example: + +.. code-block:: bash + + python testme.py -mpi -dec 2 2 -reconstruction 3 -single -ploterr -idefixDir /path/to/idefix + +This will configure, compile, and run the test in MPI mode with a 2x2 domain decomposition, third-order reconstruction, single precision, and plotting enabled for regression errors. + +Reference File Management +------------------------ + +- Reference files are stored in ``$IDEFIX_DIR/reference/``. +- The filename is generated based on precision, reconstruction, input file, and vector potential settings. +- Use ``test.init`` to regenerate reference files (dangerous: overwrites existing references). + +Regression Testing +------------------ + +- The ``nonRegressionTest`` method compares output dumps to reference files using RMSE. +- If the error exceeds the tolerance, the test fails and (optionally) plots the difference. From 7ff2f424dd0606ac8fb2785e179ae202a3174d11 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 27 Nov 2025 14:05:21 +0100 Subject: [PATCH 085/144] Fix axis regularisation (#356) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit fix to ensure that temporal evolution is exactly identical in spherical 2.5D and 3D (non 2pi) and 3D (2pi) in non-ideal MHD. - Ensure Ex1 regularisation is applied even when azimuthal domain is non-2pi (as Ex1 can be non-zero on the axis in non-ideal MHD) - Ensure Jx1 regularisation on the axis (circulation around the axis) is consistent with the discretisation used to compute the electrical current in the rest of the domain - Ensure Bphi evolution in 2.5D (using cell-centered fluxes) is consistent with the evolution using full CT in 3D (using edge-centered EMFs). Co-authored-by: Clément Robert --------- Co-authored-by: Clément Robert --- src/fluid/boundary/axis.cpp | 53 ++++++++++++++------------------- src/fluid/calcRightHandSide.hpp | 2 +- test/IO/pydefix/README.md | 7 +++++ 3 files changed, 30 insertions(+), 32 deletions(-) diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index e447aefc8..afdeb8655 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -28,39 +28,31 @@ void Axis::SymmetrizeEx1Side(int jref) { IdefixArray3D Ex1 = this->ex; IdefixArray1D Ex1Avg = this->Ex1Avg; - if(isTwoPi) { - idefix_for("Ex1_ini",0,data->np_tot[IDIR], - KOKKOS_LAMBDA(int i) { - Ex1Avg(i) = ZERO_F; - }); - - idefix_for("Ex1_Symmetrize",data->beg[KDIR],data->end[KDIR],0,data->np_tot[IDIR], - KOKKOS_LAMBDA(int k,int i) { - Kokkos::atomic_add(&Ex1Avg(i), Ex1(k,jref,i)); + idefix_for("Ex1_ini",0,data->np_tot[IDIR], + KOKKOS_LAMBDA(int i) { + Ex1Avg(i) = ZERO_F; }); - if(needMPIExchange) { - #ifdef WITH_MPI - Kokkos::fence(); - // sum along all of the processes on the same r - MPI_Allreduce(MPI_IN_PLACE, Ex1Avg.data(), data->np_tot[IDIR], realMPI, - MPI_SUM, data->mygrid->AxisComm); - #endif - } - int ncells=data->mygrid->np_int[KDIR]; - - idefix_for("Ex1_Store",0,data->np_tot[KDIR],0,data->np_tot[IDIR], - KOKKOS_LAMBDA(int k,int i) { - Ex1(k,jref,i) = Ex1Avg(i)/((real) ncells); - }); - } else { - // if we're not doing full two pi, the flow is symmetric with respect to the axis, and the axis - // EMF is simply zero - idefix_for("Ex1_Store",0,data->np_tot[KDIR],0,data->np_tot[IDIR], + idefix_for("Ex1_Symmetrize",data->beg[KDIR],data->end[KDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA(int k,int i) { - Ex1(k,jref,i) = ZERO_F; + Kokkos::atomic_add(&Ex1Avg(i), Ex1(k,jref,i)); }); + if(needMPIExchange) { + #ifdef WITH_MPI + Kokkos::fence(); + // sum along all of the processes on the same r + MPI_Allreduce(MPI_IN_PLACE, Ex1Avg.data(), data->np_tot[IDIR], realMPI, + MPI_SUM, data->mygrid->AxisComm); + #endif } + + int ncells=data->mygrid->np_int[KDIR]; + + idefix_for("Ex1_Store",0,data->np_tot[KDIR],0,data->np_tot[IDIR], + KOKKOS_LAMBDA(int k,int i) { + Ex1(k,jref,i) = Ex1Avg(i)/((real) ncells); + }); + #endif } @@ -100,9 +92,9 @@ void Axis::RegularizeCurrentSide(int side) { sign = -1; } IdefixArray1D BAvg = this->Ex1Avg; - IdefixArray1D x2 = data->x[JDIR]; IdefixArray1D x1 = data->x[IDIR]; IdefixArray1D dx3 = data->dx[KDIR]; + IdefixArray1D dx2 = data->dx[JDIR]; idefix_for("B_ini",0,data->np_tot[IDIR], KOKKOS_LAMBDA(int i) { @@ -132,8 +124,7 @@ void Axis::RegularizeCurrentSide(int side) { idefix_for("fixJ",0,data->np_tot[KDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA(int k,int i) { - real th = x2(jc); - real fact = 2*sign/(deltaPhi*x1(i)*sin(th)); + real fact = 2*sign/(deltaPhi*x1(i)*dx2(jc)); J(IDIR, k,js,i) = BAvg(i)*fact; }); diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index 7777d1c22..0a0d3e194 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -363,7 +363,7 @@ struct Fluid_CalcRHSFunctor { #if (GEOMETRY == SPHERICAL) && (COMPONENTS == 3) rhs[iMPHI] /= FABS(sinx2(j)); if constexpr(Phys::mhd) { - rhs[iBPHI] = -dt / (rt(i)*dx(j)) * (Flux(iBPHI, k, j+1, i) - Flux(iBPHI, k, j, i)); + rhs[iBPHI] = -dt / (x1(i)*dx(j)) * (Flux(iBPHI, k, j+1, i) - Flux(iBPHI, k, j, i)); } // MHD #endif // GEOMETRY } diff --git a/test/IO/pydefix/README.md b/test/IO/pydefix/README.md index 820a0958e..8dd3f5b4f 100644 --- a/test/IO/pydefix/README.md +++ b/test/IO/pydefix/README.md @@ -42,3 +42,10 @@ export pybind11_DIR=env/lib/python3.10/site-packages/pybind11 ``` you can then run cmake which should be able to find pybind11, and compile the code. + +If while running the code using a python interpreter in an environment, you run into errors stating that some module +installed in your environement is not present. This is because pybind11 does not always capture your venv. You need to force the following environement variables (replace XX by your python version) + +```bash +export PYTHONPATH=$VIRTUAL_ENV/lib/python3.XX/site-packages:$PYTHONPATH +``` From 3a8e37b6fedb9596e2a91e4fdb7afc324e5e5f9c Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 15 Dec 2025 13:36:43 +0100 Subject: [PATCH 086/144] Fix BXs consistency accross mpi decomposition (#357) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit This PR fixes a long-standing issue causing the face-centered magnetic field component B (referred to as BXs) to drift at MPI subdomain boundaries during long integrations. The drift occurs because neighboring subdomains may compute slightly different edge EMFs—likely due to roundoff differences—resulting in inconsistent BXs values across shared boundaries. This bug is subtle and can manifest in several ways: A sudden increase in div(B) after restarting from a dump file. Because the dump stores only one of the two possible BXs values at each subdomain boundary, any accumulated mismatch becomes visible upon restart. Unexpected or non-physical BXs values at subdomain edges when using vector potentials. Historically, these edge zones were not exchanged, under the assumption that each subdomain’s computed values were sufficient. In practice, this allowed roundoff-level discrepancies to accumulate over time. This PR introduces a consistent synchronization rule: the BXs value from the left side (=start) of each subdomain is treated as the authoritative value and overwrites the corresponding right-side value of the left-side neighbour. This ensures deterministic and stable edge values. The change increases the communication cost by roughly ~5% due to the larger exchange buffer. Finally, note that a similar issue can also arise in serial runs with periodic boundary conditions, and this PR fixes that case as well. Because of these changes, this PR represents a major refactoring of the MPI exchange routines and boundary conditions logic, that all now relies on pre-defined bounding boxes. The new edge zones are now handled only for internal and strictly periodic (i.e., non–shearing-box) boundary conditions, simplifying and unifying the overall approach. List of commits: * fix non blocking mpi comms * avoid overwriting data when there is no neighbour * fix pack/unpak loop name for debug * fix non-sending X1 direction * back to mpi_persistent * fix linter * - use the left domain as the reference domain for EMFs (instead of averaging) to be coherent with BXs exchange routine - check that vector potential follow the same boundary logic as the EMF (left domain is the reference) Note: BCs on the vector potential is only apply after boundary conditions, since EMFs boundary conditions ensure that the vector potential will always be consistent later. Todo: - enforce these boundary conditions with vector potential with periodic boundary conditions and without MPI (as is done for EMFs) - check that BXs normal is also consistent when MPI is off with periodic BCs * fix file spellink * Check shearing box with MPI. As expected, shearingbox+MPI is broken as we should not reset the surface field in this case. * refactor MPI exchange routine. In the future, will allow exchange routines not to exchange normal field last active zone when shearing box is enabled. For this, the refactoring include an optional parameter "overwriteBXn" in each exchange direction * fix shearing boxes * boundaryFor implemented with variable boundingBoxes, now allowing to overwrite BXs normal only with periodic boundary conditions to save the shearing box * Final fix to the vector potential consistancy in serial, to do the same as with MPI * -fix bounding box implementation for serial BCs -fix gauge for AmbipolarCShock to be compatible with periodic boundary conditions along x2 * cleaning up exchange routine * fix nghost bug in mpi exchanger * use a single exchanger for fargo with domain decomposition * Different message tag for each mpi exchanger * -ensure that mpi is using the datablock's boundary conditions -fix missing fences with shearing box BCs * fix linter * fix linter #2 * Update src/fluid/constrainedTransport/enforceEMFBoundary.hpp Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> * add missing pushRegion * Update src/fluid/boundary/axis.hpp Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> * fix typo --------- Co-authored-by: glesur Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> --- .gitignore | 5 + CMakeLists.txt | 6 +- reference | 2 +- src/dataBlock/dataBlock.cpp | 1 + src/dataBlock/fargo.cpp | 9 +- src/dataBlock/fargo.hpp | 10 +- src/fluid/boundary/axis.cpp | 19 +- src/fluid/boundary/axis.hpp | 17 +- src/fluid/boundary/boundary.hpp | 181 ++-- src/fluid/constrainedTransport/CMakeLists.txt | 1 + .../constrainedTransport/EMFexchange.hpp | 76 +- .../constrainedTransport.hpp | 13 +- .../enforceEMFBoundary.hpp | 119 +-- .../enforceVectorPotentialBoundary.hpp | 36 + src/gravity/laplacian.cpp | 2 +- src/macros.hpp | 1 - src/main.cpp | 4 +- src/mpi.cpp | 992 ------------------ src/mpi.hpp | 269 ----- src/mpi/CMakeLists.txt | 7 + src/mpi/buffer.hpp | 195 ++++ src/mpi/exchanger.cpp | 308 ++++++ src/mpi/exchanger.hpp | 82 ++ src/mpi/mpi.cpp | 265 +++++ src/mpi/mpi.hpp | 74 ++ src/rkl/rkl.hpp | 3 +- src/utils/column.cpp | 2 +- test/MHD/AmbipolarCshock3D/idefix-rkl.ini | 4 +- test/MHD/AmbipolarCshock3D/idefix.ini | 4 +- test/MHD/AmbipolarCshock3D/setup.cpp | 47 +- test/MHD/AmbipolarCshock3D/testme.py | 2 +- test/MHD/OrszagTang3D/setup.cpp | 4 +- test/MHD/ShearingBox/testme.py | 3 + 33 files changed, 1240 insertions(+), 1523 deletions(-) create mode 100644 src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp delete mode 100644 src/mpi.cpp delete mode 100644 src/mpi.hpp create mode 100644 src/mpi/CMakeLists.txt create mode 100644 src/mpi/buffer.hpp create mode 100644 src/mpi/exchanger.cpp create mode 100644 src/mpi/exchanger.hpp create mode 100644 src/mpi/mpi.cpp create mode 100644 src/mpi/mpi.hpp diff --git a/.gitignore b/.gitignore index 4de7fb76e..88b83a749 100644 --- a/.gitignore +++ b/.gitignore @@ -22,6 +22,9 @@ CMakeFiles CMakeCache.txt cmake_install.cmake Makefile.local +git-state.txt +Kokkos_Version_info.* + # test artifacts test/**/*.o @@ -36,6 +39,8 @@ test/**/KokkosCore* test/**/*.csv test/**/*.pyc test/**/*.dat +test/**/cmake_packages* +test/**/ # machine specific cache and hidden files .* diff --git a/CMakeLists.txt b/CMakeLists.txt index 364ee4ef3..a7c856ddd 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -99,10 +99,7 @@ if(Idefix_MPI) add_compile_definitions("WITH_MPI") find_package(MPI REQUIRED) target_link_libraries(idefix MPI::MPI_CXX) - target_sources(idefix - PUBLIC src/mpi.cpp - PUBLIC src/mpi.hpp - ) + add_subdirectory(src/mpi) endif() if(Idefix_HDF5) @@ -234,6 +231,7 @@ target_include_directories(idefix PUBLIC src/gravity src/utils src/utils/iterativesolver + src/mpi src ) diff --git a/reference b/reference index c4082b99a..1028989b3 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit c4082b99a4c542def3177c96cb35b1c9d9002f18 +Subproject commit 1028989b3847200da9b54ed74df0d5c0b0d13045 diff --git a/src/dataBlock/dataBlock.cpp b/src/dataBlock/dataBlock.cpp index 81874cef6..2877a8346 100644 --- a/src/dataBlock/dataBlock.cpp +++ b/src/dataBlock/dataBlock.cpp @@ -367,6 +367,7 @@ real DataBlock::ComputeTimestep() { void DataBlock::DeriveVectorPotential() { if constexpr(DefaultPhysics::mhd) { #ifdef EVOLVE_VECTOR_POTENTIAL + hydro->emf->EnforceVectorPotentialBoundary(hydro->Ve); hydro->emf->ComputeMagFieldFromA(hydro->Ve, hydro->Vs); #endif } diff --git a/src/dataBlock/fargo.cpp b/src/dataBlock/fargo.cpp index a509ef886..7aa2d26a5 100644 --- a/src/dataBlock/fargo.cpp +++ b/src/dataBlock/fargo.cpp @@ -138,10 +138,15 @@ Fargo::Fargo(Input &input, int nmax, DataBlock *data) { for(int i=0 ; i < nvar ; i++) { vars.push_back(i); } + #if GEOMETRY == CARTESIAN || GEOMETRY == POLAR + const int dirShift = JDIR; + #elif GEOMETRY == SPHERICAL + const int dirShift = KDIR; + #endif #if MHD == YES - this->mpi.Init(data->mygrid, vars, this->nghost.data(), data->np_int.data(), true); + this->mpiExchanger.Init(data->mygrid, dirShift, vars, this->nghost, data->np_int, true); #else - this->mpi.Init(data->mygrid, vars, this->nghost.data(), data->np_int.data()); + this->mpiExchanger.Init(data->mygrid, dirShift, vars, this->nghost, data->np_int, false); #endif } #endif diff --git a/src/dataBlock/fargo.hpp b/src/dataBlock/fargo.hpp index 099c99350..a1efcb2b6 100644 --- a/src/dataBlock/fargo.hpp +++ b/src/dataBlock/fargo.hpp @@ -11,7 +11,7 @@ #include #include "idefix.hpp" #ifdef WITH_MPI - #include "mpi.hpp" + #include "exchanger.hpp" #endif #include "physics.hpp" @@ -63,7 +63,7 @@ class Fargo { IdefixArray4D scrhVs; #ifdef WITH_MPI - Mpi mpi; // Fargo-specific MPI layer + Exchanger mpiExchanger; // Fargo-specific MPI layer #endif std::array beg; @@ -290,11 +290,7 @@ void Fargo::StoreToScratch(Fluid* hydro) { } #if WITH_MPI if(haveDomainDecomposition) { - #if GEOMETRY == CARTESIAN || GEOMETRY == POLAR - this->mpi.ExchangeX2(scrhUc, scrhVs); - #elif GEOMETRY == SPHERICAL - this->mpi.ExchangeX3(scrhUc, scrhVs); - #endif + this->mpiExchanger.Exchange(scrhUc, scrhVs); } #endif } diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index afdeb8655..47f0c2954 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -22,10 +22,9 @@ void Axis::ShowConfig() { } -void Axis::SymmetrizeEx1Side(int jref) { +void Axis::SymmetrizeEx1Side(int jref, IdefixArray3D Ex1) { #if DIMENSIONS == 3 - IdefixArray3D Ex1 = this->ex; IdefixArray1D Ex1Avg = this->Ex1Avg; idefix_for("Ex1_ini",0,data->np_tot[IDIR], @@ -63,9 +62,7 @@ void Axis::SymmetrizeEx1Side(int jref) { // Hence, we enforce a regularisation of Ex3 for consistancy. -void Axis::RegularizeEx3side(int jref) { - IdefixArray3D Ex3 = this->ez; - +void Axis::RegularizeEx3side(int jref, IdefixArray3D Ex3) { idefix_for("Ex3_Regularise",0,data->np_tot[KDIR],0,data->np_tot[IDIR], KOKKOS_LAMBDA(int k,int i) { Ex3(k,jref,i) = 0.0; @@ -133,18 +130,20 @@ void Axis::RegularizeCurrentSide(int side) { // Average the Emf component along the axis -void Axis::RegularizeEMFs() { +void Axis::RegularizeEMFs(IdefixArray3D ex, + IdefixArray3D ey, + IdefixArray3D ez) { idfx::pushRegion("Axis::RegularizeEMFs"); if(this->axisLeft) { int jref = data->beg[JDIR]; - SymmetrizeEx1Side(jref); - RegularizeEx3side(jref); + SymmetrizeEx1Side(jref, ex); + RegularizeEx3side(jref, ez); } if(this->axisRight) { int jref = data->end[JDIR]; - SymmetrizeEx1Side(jref); - RegularizeEx3side(jref); + SymmetrizeEx1Side(jref, ex); + RegularizeEx3side(jref, ez); } idfx::popRegion(); diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index b74697862..1a1227b61 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -26,15 +26,16 @@ class Axis { public: template explicit Axis(Boundary *); // Initialisation - void RegularizeEMFs(); // Regularize the EMF sitting on the axis + void RegularizeEMFs(IdefixArray3D, IdefixArray3D, IdefixArray3D); + // Regularize the EMF sitting on the axis void RegularizeCurrent(); // Regularize the currents along the axis void EnforceAxisBoundary(int side); // Enforce the boundary conditions (along X2) void RegularizeBX2s(); // Regularize BX2s on the axis void ShowConfig(); - - void SymmetrizeEx1Side(int); // Symmetrize on a specific side (internal method) - void RegularizeEx3side(int); // Regularize Ex3 along the axis (internal method) + // Internal methods + void SymmetrizeEx1Side(int, IdefixArray3D); // Symmetrize on a specific side + void RegularizeEx3side(int side, IdefixArray3D ex3); // Regularize Ex3 along the axis void RegularizeCurrentSide(int); // Regularize J along the axis (internal method) void FixBx2sAxis(int side); // Fix BX2s on the axis using the field around it (internal) void FixBx2sAxisGhostAverage(int side); //Fix BX2s on the axis using the average of neighbouring @@ -76,9 +77,6 @@ class Axis { IdefixArray1D symmetryVc; IdefixArray1D symmetryVs; - IdefixArray3D ex; - IdefixArray3D ey; - IdefixArray3D ez; IdefixArray4D J; IdefixArray4D Vc; @@ -94,11 +92,6 @@ Axis::Axis(Boundary *boundary) { Vc = boundary->Vc; Vs = boundary->Vs; J = boundary->fluid->J; - if constexpr(Phys::mhd) { - ex = boundary->fluid->emf->ex; - ey = boundary->fluid->emf->ey; - ez = boundary->fluid->emf->ez; - } data = boundary->data; haveMHD = Phys::mhd; diff --git a/src/fluid/boundary/boundary.hpp b/src/fluid/boundary/boundary.hpp index 897c1ce10..4065cc60d 100644 --- a/src/fluid/boundary/boundary.hpp +++ b/src/fluid/boundary/boundary.hpp @@ -34,6 +34,8 @@ template using InternalBoundaryFunc = void (*) (Fluid *, const real t); using InternalBoundaryFuncOld = void (*) (DataBlock &, const real t); // DEPRECATED +using BoundingBox = std::array,3>; + template class Boundary { public: @@ -83,12 +85,22 @@ class Boundary { const BoundarySide &, Function ); + template + void BoundaryFor(const std::string &, + BoundingBox box, + Function ); + template void BoundaryForAll(const std::string &, const int &, const BoundarySide &, Function ); + template + void BoundaryForAll(const std::string &, + BoundingBox box, + Function ); + template void BoundaryForX1s(const std::string &, const int &, @@ -115,6 +127,10 @@ class Boundary { bool haveLeftAxis{false}; ///< True if the left boundary is an axis bool haveRightAxis{false}; ///< True if the right boundary is an axis + std::array,3> GhostBoxVc; ///< A bounding box for each ghost regions + std::array,3>,3> + GhostBoxVs; ///< A bounding box each Vs component + private: friend class Axis; Fluid *fluid; // pointer to parent hydro object @@ -154,6 +170,49 @@ Boundary::Boundary(Fluid* fluid) { data->nghost[IDIR]); } + // Initialise the Bounding Boxes for cell-centered variables + for(int dir = 0 ; dir < 3 ; dir++) { + // dir=direction along which we plan to apply the boundary conditions + for(int side = 0; side < 2 ; side++) { + // Side on which we apply the boundaries + for(int dim = 0 ; dim < 3 ; dim++) { + // Dimension of the datacube + if(dim != dir) { + GhostBoxVc[dir][side][dim][0] = 0; + GhostBoxVc[dir][side][dim][1] = data->np_tot[dim]; + } else { + GhostBoxVc[dir][side][dim][0] = side*(data->end[dim]); + GhostBoxVc[dir][side][dim][1] = side*(data->end[dim])+data->nghost[dim]; + } + } + } + } + + // Initialise the Bounding Boxes for face-centered variables (NB: we need one for each component) + for(int component = 0 ; component < DIMENSIONS ; component++) { + // Initialise the boxes for face-centered variables with the same bounding box + GhostBoxVs[component] = GhostBoxVc; + for(int dir = 0 ; dir < 3 ; dir++) { + for(int side = 0 ; side < 2 ; side++) { + // Add one element in the normal direction since we're staggered + GhostBoxVs[component][dir][side][component][1] += 1; + // Do not overwrite last active BXs normal if not serial+periodic + if(dir == component) { + if(side==left) { + if(data->mygrid->nproc[dir] > 1 || data->lbound[dir] != BoundaryType::periodic) { + GhostBoxVs[component][dir][side][component][1] -= 1; + } + } + if(side==right) { + if(data->mygrid->nproc[dir] > 1 || data->rbound[dir] != BoundaryType::periodic) { + GhostBoxVs[component][dir][side][component][0] += 1; + } + } + } + } + } + } + // Init MPI stack when needed #ifdef WITH_MPI //////////////////////////////////////////////////////////////////////////// @@ -185,7 +244,8 @@ Boundary::Boundary(Fluid* fluid) { } } - mpi.Init(data->mygrid, mapVars, data->nghost.data(), data->np_int.data(), Phys::mhd); + mpi.Init(data->mygrid, mapVars, data->nghost, data->np_int, + data->lbound, data->rbound, Phys::mhd); #endif // MPI idfx::popRegion(); @@ -970,54 +1030,47 @@ template template inline void Boundary::BoundaryForAll( const std::string & name, - const int &dir, - const BoundarySide &side, + BoundingBox box, Function function) { - const int nxi = data->np_int[IDIR]; - const int nxj = data->np_int[JDIR]; - const int nxk = data->np_int[KDIR]; - - const int ighost = data->nghost[IDIR]; - const int jghost = data->nghost[JDIR]; - const int kghost = data->nghost[KDIR]; - - // Boundaries of the loop - const int ibeg = (dir == IDIR) ? side*(ighost+nxi) : 0; - const int iend = (dir == IDIR) ? ighost + side*(ighost+nxi) : data->np_tot[IDIR]; - const int jbeg = (dir == JDIR) ? side*(jghost+nxj) : 0; - const int jend = (dir == JDIR) ? jghost + side*(jghost+nxj) : data->np_tot[JDIR]; - const int kbeg = (dir == KDIR) ? side*(kghost+nxk) : 0; - const int kend = (dir == KDIR) ? kghost + side*(kghost+nxk) : data->np_tot[KDIR]; - - idefix_for(name, 0, this->nVar, kbeg, kend, jbeg, jend, ibeg, iend, function); + idefix_for(name, 0, this->nVar, + box[KDIR][0], box[KDIR][1], + box[JDIR][0], box[JDIR][1], + box[IDIR][0], box[IDIR][1], + function); } template template -inline void Boundary::BoundaryFor( +inline void Boundary::BoundaryForAll( const std::string & name, const int &dir, const BoundarySide &side, Function function) { - const int nxi = data->np_int[IDIR]; - const int nxj = data->np_int[JDIR]; - const int nxk = data->np_int[KDIR]; - - const int ighost = data->nghost[IDIR]; - const int jghost = data->nghost[JDIR]; - const int kghost = data->nghost[KDIR]; - - // Boundaries of the loop - const int ibeg = (dir == IDIR) ? side*(ighost+nxi) : 0; - const int iend = (dir == IDIR) ? ighost + side*(ighost+nxi) : data->np_tot[IDIR]; - const int jbeg = (dir == JDIR) ? side*(jghost+nxj) : 0; - const int jend = (dir == JDIR) ? jghost + side*(jghost+nxj) : data->np_tot[JDIR]; - const int kbeg = (dir == KDIR) ? side*(kghost+nxk) : 0; - const int kend = (dir == KDIR) ? kghost + side*(kghost+nxk) : data->np_tot[KDIR]; + BoundaryForAll(name,GhostBoxVc[dir][side],function); +} +template +template +inline void Boundary::BoundaryFor( + const std::string & name, + BoundingBox box, + Function function) { + idefix_for(name, + box[KDIR][0], box[KDIR][1], + box[JDIR][0], box[JDIR][1], + box[IDIR][0], box[IDIR][1], + function); +} - idefix_for(name, kbeg, kend, jbeg, jend, ibeg, iend, function); +template +template +inline void Boundary::BoundaryFor( + const std::string & name, + const int &dir, + const BoundarySide &side, + Function function) { + BoundaryFor(name,GhostBoxVc[dir][side],function); } template @@ -1027,23 +1080,7 @@ inline void Boundary::BoundaryForX1s( const int &dir, const BoundarySide &side, Function function) { - const int nxi = data->np_int[IDIR]+1; - const int nxj = data->np_int[JDIR]; - const int nxk = data->np_int[KDIR]; - - const int ighost = data->nghost[IDIR]; - const int jghost = data->nghost[JDIR]; - const int kghost = data->nghost[KDIR]; - - // Boundaries of the loop - const int ibeg = (dir == IDIR) ? side*(ighost+nxi) : 0; - const int iend = (dir == IDIR) ? ighost + side*(ighost+nxi) : data->np_tot[IDIR]+1; - const int jbeg = (dir == JDIR) ? side*(jghost+nxj) : 0; - const int jend = (dir == JDIR) ? jghost + side*(jghost+nxj) : data->np_tot[JDIR]; - const int kbeg = (dir == KDIR) ? side*(kghost+nxk) : 0; - const int kend = (dir == KDIR) ? kghost + side*(kghost+nxk) : data->np_tot[KDIR]; - - idefix_for(name, kbeg, kend, jbeg, jend, ibeg, iend, function); + BoundaryFor(name,GhostBoxVs[BX1s][dir][side],function); } template @@ -1053,23 +1090,7 @@ inline void Boundary::BoundaryForX2s( const int &dir, const BoundarySide &side, Function function) { - const int nxi = data->np_int[IDIR]; - const int nxj = data->np_int[JDIR]+1; - const int nxk = data->np_int[KDIR]; - - const int ighost = data->nghost[IDIR]; - const int jghost = data->nghost[JDIR]; - const int kghost = data->nghost[KDIR]; - - // Boundaries of the loop - const int ibeg = (dir == IDIR) ? side*(ighost+nxi) : 0; - const int iend = (dir == IDIR) ? ighost + side*(ighost+nxi) : data->np_tot[IDIR]; - const int jbeg = (dir == JDIR) ? side*(jghost+nxj) : 0; - const int jend = (dir == JDIR) ? jghost + side*(jghost+nxj) : data->np_tot[JDIR]+1; - const int kbeg = (dir == KDIR) ? side*(kghost+nxk) : 0; - const int kend = (dir == KDIR) ? kghost + side*(kghost+nxk) : data->np_tot[KDIR]; - - idefix_for(name, kbeg, kend, jbeg, jend, ibeg, iend, function); + BoundaryFor(name,GhostBoxVs[BX2s][dir][side],function); } template @@ -1079,23 +1100,7 @@ inline void Boundary::BoundaryForX3s( const int &dir, const BoundarySide &side, Function function) { - const int nxi = data->np_int[IDIR]; - const int nxj = data->np_int[JDIR]; - const int nxk = data->np_int[KDIR]+1; - - const int ighost = data->nghost[IDIR]; - const int jghost = data->nghost[JDIR]; - const int kghost = data->nghost[KDIR]; - - // Boundaries of the loop - const int ibeg = (dir == IDIR) ? side*(ighost+nxi) : 0; - const int iend = (dir == IDIR) ? ighost + side*(ighost+nxi) : data->np_tot[IDIR]; - const int jbeg = (dir == JDIR) ? side*(jghost+nxj) : 0; - const int jend = (dir == JDIR) ? jghost + side*(jghost+nxj) : data->np_tot[JDIR]; - const int kbeg = (dir == KDIR) ? side*(kghost+nxk) : 0; - const int kend = (dir == KDIR) ? kghost + side*(kghost+nxk) : data->np_tot[KDIR]+1; - - idefix_for(name, kbeg, kend, jbeg, jend, ibeg, iend, function); + BoundaryFor(name,GhostBoxVs[BX3s][dir][side],function); } diff --git a/src/fluid/constrainedTransport/CMakeLists.txt b/src/fluid/constrainedTransport/CMakeLists.txt index 06efc782b..7d99b805c 100644 --- a/src/fluid/constrainedTransport/CMakeLists.txt +++ b/src/fluid/constrainedTransport/CMakeLists.txt @@ -5,6 +5,7 @@ target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/constrainedTransport.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/EMFexchange.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/enforceEMFBoundary.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/enforceVectorPotentialBoundary.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/evolveMagField.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/evolveVectorPotential.hpp ) diff --git a/src/fluid/constrainedTransport/EMFexchange.hpp b/src/fluid/constrainedTransport/EMFexchange.hpp index 187186271..f6e90f75a 100644 --- a/src/fluid/constrainedTransport/EMFexchange.hpp +++ b/src/fluid/constrainedTransport/EMFexchange.hpp @@ -14,16 +14,18 @@ #ifdef WITH_MPI template -void ConstrainedTransport::ExchangeAll() { - if(data->mygrid->nproc[IDIR]>1) this->ExchangeX1(); - if(data->mygrid->nproc[JDIR]>1) this->ExchangeX2(); - if(data->mygrid->nproc[KDIR]>1) this->ExchangeX3(); +void ConstrainedTransport::ExchangeAll(IdefixArray3D ex, + IdefixArray3D ey, + IdefixArray3D ez) { + if(data->mygrid->nproc[IDIR]>1) this->ExchangeX1(ey,ez); + if(data->mygrid->nproc[JDIR]>1) this->ExchangeX2(ex,ez); + if(data->mygrid->nproc[KDIR]>1) this->ExchangeX3(ex,ey); } // Exchange EMFs in X1 template -void ConstrainedTransport::ExchangeX1() { +void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3D ez) { idfx::pushRegion("Emf::ExchangeX1"); @@ -34,8 +36,6 @@ void ConstrainedTransport::ExchangeX1() { IdefixArray1D BufferLeft=BufferSendX1[faceLeft]; IdefixArray1D BufferRight=BufferSendX1[faceRight]; - IdefixArray3D ey=this->ey; - IdefixArray3D ez=this->ez; // If MPI Persistent, start receiving even before the buffers are filled @@ -61,7 +61,6 @@ void ConstrainedTransport::ExchangeX1() { idefix_for("LoadBufferX1Emfz",kbeg,kend,jbeg,jend+1, KOKKOS_LAMBDA (int k, int j) { - BufferLeft( (j-jbeg) + (k-kbeg)*(ny+1) ) = ez(k,j,ileft); BufferRight( (j-jbeg) + (k-kbeg)*(ny+1) ) = ez(k,j,iright); } ); @@ -70,7 +69,6 @@ void ConstrainedTransport::ExchangeX1() { idefix_for("LoadBufferX1Emfy",kbeg,kend+1,jbeg,jend, KOKKOS_LAMBDA (int k, int j) { - BufferLeft( (j-jbeg) + (k-kbeg)*ny + Vsindex ) = ey(k,j,ileft); BufferRight( (j-jbeg) + (k-kbeg)*ny + Vsindex ) = ey(k,j,iright); } ); @@ -91,29 +89,21 @@ void ConstrainedTransport::ExchangeX1() { BufferLeft=BufferRecvX1[faceLeft]; BufferRight=BufferRecvX1[faceRight]; - // We average the edge emfs zones + // Erase the emf with the one coming from the left process + idefix_for("StoreBufferX1Emfz",kbeg,kend,jbeg,jend+1, KOKKOS_LAMBDA (int k, int j) { if(lbound == internal || lbound == periodic) { - ez(k,j,ileft) = HALF_F*( - BufferLeft( (j-jbeg) + (k-kbeg)*(ny+1) ) + ez(k,j,ileft) ); - } - if(rbound == internal || rbound == periodic) { - ez(k,j,iright) = HALF_F*( - BufferRight( (j-jbeg) + (k-kbeg)*(ny+1) ) + ez(k,j,iright) ); + ez(k,j,ileft) = BufferLeft( (j-jbeg) + (k-kbeg)*(ny+1)); } }); + #if DIMENSIONS == 3 Vsindex = (ny+1)*nz; idefix_for("StoreBufferX1Emfy",kbeg,kend+1,jbeg,jend, KOKKOS_LAMBDA (int k, int j) { if(lbound == internal || lbound == periodic) { - ey(k,j,ileft) = HALF_F*( - BufferLeft( (j-jbeg) + (k-kbeg)*ny +Vsindex) + ey(k,j,ileft) ); - } - if(rbound == internal || rbound == periodic) { - ey(k,j,iright) = HALF_F*( - BufferRight( (j-jbeg) + (k-kbeg)*ny +Vsindex) + ey(k,j,iright) ); + ey(k,j,ileft) = BufferLeft( (j-jbeg) + (k-kbeg)*ny +Vsindex); } }); #endif @@ -124,7 +114,7 @@ void ConstrainedTransport::ExchangeX1() { // Exchange EMFs in X2 template -void ConstrainedTransport::ExchangeX2() { +void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3D ez) { idfx::pushRegion("Emf::ExchangeX2"); // Load the buffers with data @@ -133,8 +123,6 @@ void ConstrainedTransport::ExchangeX2() { [[maybe_unused]] int nz; IdefixArray1D BufferLeft=BufferSendX2[faceLeft]; IdefixArray1D BufferRight=BufferSendX2[faceRight]; - IdefixArray3D ex=this->ex; - IdefixArray3D ez=this->ez; // If MPI Persistent, start receiving even before the buffers are filled double tStart = MPI_Wtime(); @@ -158,7 +146,6 @@ void ConstrainedTransport::ExchangeX2() { idefix_for("LoadBufferX2Emfz",kbeg,kend,ibeg,iend+1, KOKKOS_LAMBDA (int k, int i) { - BufferLeft( (i-ibeg) + (k-kbeg)*(nx+1) ) = ez(k,jleft,i); BufferRight( (i-ibeg) + (k-kbeg)*(nx+1) ) = ez(k,jright,i); } ); @@ -167,7 +154,6 @@ void ConstrainedTransport::ExchangeX2() { idefix_for("LoadBufferX1Emfx",kbeg,kend+1,ibeg,iend, KOKKOS_LAMBDA (int k, int i) { - BufferLeft( (i-ibeg) + (k-kbeg)*nx + Vsindex ) = ex(k,jleft,i); BufferRight( (i-ibeg) + (k-kbeg)*nx + Vsindex ) = ex(k,jright,i); } ); @@ -191,12 +177,7 @@ void ConstrainedTransport::ExchangeX2() { idefix_for("StoreBufferX2Emfz",kbeg,kend,ibeg,iend+1, KOKKOS_LAMBDA (int k, int i) { if(lbound == internal || lbound == periodic) { - ez(k,jleft,i) = HALF_F*( - BufferLeft( (i-ibeg) + (k-kbeg)*(nx+1) ) + ez(k,jleft,i) ); - } - if(rbound == internal || rbound == periodic) { - ez(k,jright,i) = HALF_F*( - BufferRight( (i-ibeg) + (k-kbeg)*(nx+1) ) + ez(k,jright,i) ); + ez(k,jleft,i) = BufferLeft( (i-ibeg) + (k-kbeg)*(nx+1) ); } }); #if DIMENSIONS == 3 @@ -204,12 +185,7 @@ void ConstrainedTransport::ExchangeX2() { idefix_for("StoreBufferX1Emfy",kbeg,kend+1,ibeg,iend, KOKKOS_LAMBDA (int k, int i) { if(lbound == internal || lbound == periodic) { - ex(k,jleft,i) = HALF_F*( - BufferLeft( (i-ibeg) + (k-kbeg)*nx +Vsindex) + ex(k,jleft,i) ); - } - if(rbound == internal || rbound == periodic) { - ex(k,jright,i) = HALF_F*( - BufferRight( (i-ibeg) + (k-kbeg)*nx +Vsindex) + ex(k,jright,i) ); + ex(k,jleft,i) = BufferLeft( (i-ibeg) + (k-kbeg)*nx +Vsindex); } }); #endif @@ -220,7 +196,7 @@ void ConstrainedTransport::ExchangeX2() { // Exchange EMFs in X3 template -void ConstrainedTransport::ExchangeX3() { +void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3D ey) { idfx::pushRegion("Emf::ExchangeX3"); @@ -229,8 +205,6 @@ void ConstrainedTransport::ExchangeX3() { int nx,ny; IdefixArray1D BufferLeft=BufferSendX3[faceLeft]; IdefixArray1D BufferRight=BufferSendX3[faceRight]; - IdefixArray3D ex=this->ex; - IdefixArray3D ey=this->ey; int Vsindex = 0; @@ -259,7 +233,6 @@ void ConstrainedTransport::ExchangeX3() { idefix_for("LoadBufferX3Emfx",jbeg,jend+1,ibeg,iend, KOKKOS_LAMBDA (int j, int i) { - BufferLeft( (i-ibeg) + (j-jbeg)*nx ) = ex(kleft,j,i); BufferRight( (i-ibeg) + (j-jbeg)*nx ) = ex(kright,j,i); } ); @@ -267,7 +240,6 @@ void ConstrainedTransport::ExchangeX3() { idefix_for("LoadBufferX3Emfy",jbeg,jend,ibeg,iend+1, KOKKOS_LAMBDA (int j, int i) { - BufferLeft( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ) = ey(kleft,j,i); BufferRight( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ) = ey(kright,j,i); } ); @@ -290,12 +262,7 @@ void ConstrainedTransport::ExchangeX3() { idefix_for("StoreBufferX3Emfx",jbeg,jend+1,ibeg,iend, KOKKOS_LAMBDA (int j, int i) { if(lbound == internal || lbound == periodic) { - ex(kleft,j,i) = HALF_F*( - BufferLeft( (i-ibeg) + (j-jbeg)*nx ) + ex(kleft,j,i) ); - } - if(rbound == internal || rbound == periodic) { - ex(kright,j,i) = HALF_F*( - BufferRight( (i-ibeg) + (j-jbeg)*nx ) + ex(kright,j,i) ); + ex(kleft,j,i) = BufferLeft( (i-ibeg) + (j-jbeg)*nx ); } }); @@ -303,16 +270,9 @@ void ConstrainedTransport::ExchangeX3() { idefix_for("StoreBufferX3Emfy",jbeg,jend,ibeg,iend+1, KOKKOS_LAMBDA (int j, int i) { if(lbound == internal || lbound == periodic) { - ey(kleft,j,i) = HALF_F*( - BufferLeft( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ) + ey(kleft,j,i) ); - } - if(rbound == internal || rbound == periodic) { - ey(kright,j,i) = HALF_F*( - BufferRight( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ) + ey(kright,j,i) ); + ey(kleft,j,i) = BufferLeft( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ); } }); - - idfx::popRegion(); } diff --git a/src/fluid/constrainedTransport/constrainedTransport.hpp b/src/fluid/constrainedTransport/constrainedTransport.hpp index c32e4ec96..24c317c09 100644 --- a/src/fluid/constrainedTransport/constrainedTransport.hpp +++ b/src/fluid/constrainedTransport/constrainedTransport.hpp @@ -101,13 +101,17 @@ class ConstrainedTransport { // Routines for evolving the magnetic potential (only available when EVOLVE_VECTOR_POTENTIAL) void EvolveVectorPotential(real, IdefixArray4D &); void ComputeMagFieldFromA(IdefixArray4D &Vein, IdefixArray4D &Vsout); + void EnforceVectorPotentialBoundary(IdefixArray4D &Vein); // Enforce BCs on A + void EnforceEMFBoundaryPeriodic(IdefixArray3D ex, + IdefixArray3D ey, + IdefixArray3D ez); #ifdef WITH_MPI // Exchange surface EMFs to remove interprocess round off errors - void ExchangeAll(); - void ExchangeX1(); - void ExchangeX2(); - void ExchangeX3(); + void ExchangeAll(IdefixArray3D ex, IdefixArray3D ey, IdefixArray3D ez); + void ExchangeX1(IdefixArray3D ey, IdefixArray3D ez); + void ExchangeX2(IdefixArray3D ex, IdefixArray3D ez); + void ExchangeX3(IdefixArray3D ex, IdefixArray3D ey); #endif private: @@ -449,6 +453,7 @@ void ConstrainedTransport::ShowConfig() { #include "calcRiemannEmf.hpp" #include "EMFexchange.hpp" #include "enforceEMFBoundary.hpp" +#include "enforceVectorPotentialBoundary.hpp" #include "evolveMagField.hpp" #include "evolveVectorPotential.hpp" diff --git a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp index 192ec12e4..9d3d6913f 100644 --- a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp +++ b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp @@ -19,8 +19,9 @@ // This is because in some specific cases involving curvilinear coordinates, roundoff errors // can accumulate, leading to a small drift of face-values that should be strictly equal. // This behaviour is enabled using the flag below. - -//#define ENFORCE_EMF_CONSISTENCY +#ifdef EVOLVE_VECTOR_POTENTIAL + #define ENFORCE_EMF_CONSISTENCY +#endif template void ConstrainedTransport::EnforceEMFBoundary() { @@ -30,81 +31,73 @@ void ConstrainedTransport::EnforceEMFBoundary() { this->data->hydro->emfBoundaryFunc(*data, data->t); if(this->data->hydro->haveAxis) { - this->data->hydro->boundary->axis->RegularizeEMFs(); + this->data->hydro->boundary->axis->RegularizeEMFs(this->ex, this->ey, this->ez); } #ifdef ENFORCE_EMF_CONSISTENCY #ifdef WITH_MPI // This average the EMFs at the domain surface with immediate neighbours // to ensure the EMFs exactly match - this->ExchangeAll(); + this->ExchangeAll(this->ex, this->ey, this->ez); #endif #endif - IdefixArray3D ex = this->ex; - IdefixArray3D ey = this->ey; - IdefixArray3D ez = this->ez; - // Enforce specific EMF regularisation for(int dir=0 ; dir < DIMENSIONS ; dir++ ) { if(data->lbound[dir] == shearingbox || data->rbound[dir] == shearingbox) { SymmetrizeEMFShearingBox(); } - #ifdef ENFORCE_EMF_CONSISTENCY - if(data->lbound[dir] == periodic && data->rbound[dir] == periodic) { - // If domain decomposed, periodicity is already enforced by ExchangeAll - if(data->mygrid->nproc[dir] == 1) { - int ioffset = (dir == IDIR) ? data->np_int[IDIR] : 0; - int joffset = (dir == JDIR) ? data->np_int[JDIR] : 0; - int koffset = (dir == KDIR) ? data->np_int[KDIR] : 0; - - int ibeg = (dir == IDIR) ? data->beg[IDIR] : 0; - int iend = (dir == IDIR) ? data->beg[IDIR]+1 : data->np_tot[IDIR]; - int jbeg = (dir == JDIR) ? data->beg[JDIR] : 0; - int jend = (dir == JDIR) ? data->beg[JDIR]+1 : data->np_tot[JDIR]; - int kbeg = (dir == KDIR) ? data->beg[KDIR] : 0; - int kend = (dir == KDIR) ? data->beg[KDIR]+1 : data->np_tot[KDIR]; - idefix_for("BoundaryEMFPeriodic",kbeg,kend,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int k, int j, int i) { - real em; - - if(dir==IDIR) { - em = HALF_F*(ez(k,j,i)+ez(k,j,i+ioffset)); - ez(k,j,i) = em; - ez(k,j,i+ioffset) = em; - - #if DIMENSIONS == 3 - em = HALF_F*(ey(k,j,i)+ey(k,j,i+ioffset)); - ey(k,j,i) = em; - ey(k,j,i+ioffset) = em; - #endif - } - - if(dir==JDIR) { - em = HALF_F*(ez(k,j,i)+ez(k,j+joffset,i)); - ez(k,j,i) = em; - ez(k,j+joffset,i) = em; - - #if DIMENSIONS == 3 - em = HALF_F*(ex(k,j,i)+ex(k,j+joffset,i)); - ex(k,j,i) = em; - ex(k,j+joffset,i) = em; - #endif - } - - if(dir==KDIR) { - em = HALF_F*(ex(k,j,i)+ex(k+koffset,j,i)); - ex(k,j,i) = em; - ex(k+koffset,j,i) = em; - - em = HALF_F*(ey(k,j,i)+ey(k+koffset,j,i)); - ey(k,j,i) = em; - ey(k+koffset,j,i) = em; - } - }); - } + } + #ifdef ENFORCE_EMF_CONSISTENCY + EnforceEMFBoundaryPeriodic(this->ex, this->ey, this->ez); + #endif //ENFORCE_EMF_CONSISTENCY +#endif // MHD==YES + idfx::popRegion(); +} + +template +void ConstrainedTransport::EnforceEMFBoundaryPeriodic(IdefixArray3D ex, + IdefixArray3D ey, + IdefixArray3D ez) { + idfx::pushRegion("Emf::EnforceEMFBoundaryPeriodic"); + #if MHD == YES + for(int dir=0 ; dir < DIMENSIONS ; dir++ ) { + if(data->lbound[dir] == periodic && data->rbound[dir] == periodic) { + // If domain decomposed, periodicity is already enforced by ExchangeAll + if(data->mygrid->nproc[dir] == 1) { + int ioffset = (dir == IDIR) ? data->np_int[IDIR] : 0; + int joffset = (dir == JDIR) ? data->np_int[JDIR] : 0; + int koffset = (dir == KDIR) ? data->np_int[KDIR] : 0; + + int ibeg = (dir == IDIR) ? data->beg[IDIR] : 0; + int iend = (dir == IDIR) ? data->beg[IDIR]+1 : data->np_tot[IDIR]; + int jbeg = (dir == JDIR) ? data->beg[JDIR] : 0; + int jend = (dir == JDIR) ? data->beg[JDIR]+1 : data->np_tot[JDIR]; + int kbeg = (dir == KDIR) ? data->beg[KDIR] : 0; + int kend = (dir == KDIR) ? data->beg[KDIR]+1 : data->np_tot[KDIR]; + idefix_for("BoundaryEMFPeriodic",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + if(dir==IDIR) { + ez(k,j,i+ioffset) = ez(k,j,i); + #if DIMENSIONS == 3 + ey(k,j,i+ioffset) = ey(k,j,i); + #endif + } + + if(dir==JDIR) { + ez(k,j+joffset,i) = ez(k,j,i); + #if DIMENSIONS == 3 + ex(k,j+joffset,i) = ex(k,j,i); + #endif + } + + if(dir==KDIR) { + ex(k+koffset,j,i) = ex(k,j,i); + ey(k+koffset,j,i) = ey(k,j,i); + } + }); } - #endif //ENFORCE_EMF_CONSISTENCY + } } #endif // MHD==YES idfx::popRegion(); @@ -148,11 +141,13 @@ void ConstrainedTransport::SymmetrizeEMFShearingBox() { if(data->lbound[IDIR]==shearingbox) { // We send to our left (which, by periodicity, is the right end of the domain) // our value of sbEyL and get + Kokkos::fence(); MPI_Sendrecv(sbEyL.data(), size, realMPI, procLeft, 2001, sbEyR.data(), size, realMPI, procLeft, 2002, data->mygrid->CartComm, &status ); } if(data->rbound[IDIR]==shearingbox) { + Kokkos::fence(); // We send to our right (which, by periodicity, is the left end (=beginning) // of the domain) our value of sbEyR and get sbEyL MPI_Sendrecv(sbEyR.data(), size, realMPI, procRight, 2002, diff --git a/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp new file mode 100644 index 000000000..fea9b47b9 --- /dev/null +++ b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp @@ -0,0 +1,36 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef FLUID_CONSTRAINEDTRANSPORT_ENFORCEVECTORPOTENTIALBOUNDARY_HPP_ +#define FLUID_CONSTRAINEDTRANSPORT_ENFORCEVECTORPOTENTIALBOUNDARY_HPP_ +#include "constrainedTransport.hpp" + +template +void ConstrainedTransport::EnforceVectorPotentialBoundary(IdefixArray4D &Vein) { + idfx::pushRegion("Emf::EnforceVectorPotentialBoundary"); + + auto Ax1 = Kokkos::subview(Vein, IDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + auto Ax2 = Kokkos::subview(Vein, JDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + auto Ax3 = Kokkos::subview(Vein, KDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + + if(this->hydro->haveAxis) { + this->hydro->boundary->axis->RegularizeEMFs(Ax1, Ax2, Ax3); + } + + #ifdef ENFORCE_EMF_CONSISTENCY + #ifdef WITH_MPI + // This average the vector potential at the domain surface with immediate neighbours + // to ensure the vector potentials exactly match + + this->ExchangeAll(Ax1, Ax2, Ax3); + #endif + EnforceEMFBoundaryPeriodic(Ax1, Ax2, Ax3); + #endif + + idfx::popRegion(); +} +#endif // FLUID_CONSTRAINEDTRANSPORT_ENFORCEVECTORPOTENTIALBOUNDARY_HPP_ diff --git a/src/gravity/laplacian.cpp b/src/gravity/laplacian.cpp index 2300db82d..7ac329ea3 100644 --- a/src/gravity/laplacian.cpp +++ b/src/gravity/laplacian.cpp @@ -103,7 +103,7 @@ Laplacian::Laplacian(DataBlock *datain, std::array left std::vector mapVars; mapVars.push_back(ntarget); - this->mpi.Init(data->mygrid, mapVars, this->nghost.data(), this->np_int.data()); + this->mpi.Init(data->mygrid, mapVars, nghost, np_int, datain->lbound, datain->rbound, false); #endif idfx::popRegion(); diff --git a/src/macros.hpp b/src/macros.hpp index 2c7bda127..0df5f9430 100644 --- a/src/macros.hpp +++ b/src/macros.hpp @@ -25,7 +25,6 @@ #if COMPONENTS == 3 #define EXPAND(a,b,c) a b c #define SELECT(a,b,c) c - #endif #if DIMENSIONS == 1 diff --git a/src/main.cpp b/src/main.cpp index 164c134ee..7b2c00c85 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -192,7 +192,9 @@ int main( int argc, char* argv[] ) { try { Tint.Cycle(data); } catch(std::exception &e) { - idfx::cout << "Main: WARNING! Caught an exception in TimeIntegrator." << std::endl; + idfx::cout << std::endl + << "Main: WARNING! Caught an exception in TimeIntegrator." + << std::endl; #ifdef WITH_MPI if(!Mpi::CheckSync(5)) { std::stringstream message; diff --git a/src/mpi.cpp b/src/mpi.cpp deleted file mode 100644 index 4de7739cb..000000000 --- a/src/mpi.cpp +++ /dev/null @@ -1,992 +0,0 @@ -// *********************************************************************************** -// Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur -// and other code contributors -// Licensed under CeCILL 2.1 License, see COPYING for more information -// *********************************************************************************** - - -#include "mpi.hpp" -#include -#include -#include // NOLINT [build/c++11] -#include // NOLINT [build/c++11] -#include -#include -#include "idefix.hpp" -#include "dataBlock.hpp" - - -#if defined(OPEN_MPI) && OPEN_MPI -#include "mpi-ext.h" // Needed for CUDA-aware check */ -#endif - - -//#define MPI_NON_BLOCKING -#define MPI_PERSISTENT - -// init the number of instances -int Mpi::nInstances = 0; - -// MPI Routines exchange -void Mpi::ExchangeAll() { - IDEFIX_ERROR("Not Implemented"); -} - -/// -/// Initialise an instance of the MPI class. -/// @param grid: pointer to the grid object (needed to get the MPI neighbours) -/// @param inputMap: 1st indices of inputVc which are to be exchanged (i.e, the list of variables) -/// @param nghost: size of the ghost region in each direction -/// @param nint: size of the internal region in each direction -/// @param inputHaveVs: whether the instance should also treat face-centered variable -/// (optional, default false) -/// - -void Mpi::Init(Grid *grid, std::vector inputMap, - int nghost[3], int nint[3], - bool inputHaveVs) { - idfx::pushRegion("Mpi::Init"); - this->mygrid = grid; - - // increase the number of instances - nInstances++; - thisInstance=nInstances; - - // Transfer the vector of indices as an IdefixArray on the target - - // Allocate mapVars on target and copy it from the input argument list - this->mapVars = idfx::ConvertVectorToIdefixArray(inputMap); - this->mapNVars = inputMap.size(); - this->haveVs = inputHaveVs; - - // Compute indices of arrays we will be working with - for(int dir = 0 ; dir < 3 ; dir++) { - this->nghost[dir] = nghost[dir]; - this->nint[dir] = nint[dir]; - this->ntot[dir] = nint[dir]+2*nghost[dir]; - this->beg[dir] = nghost[dir]; - this->end[dir] = nghost[dir]+nint[dir]; - } - - ///////////////////////////////////////////////////////////////////////////// - // Init exchange datasets - bufferSizeX1 = 0; - bufferSizeX2 = 0; - bufferSizeX3 = 0; - - // Number of cells in X1 boundary condition: - bufferSizeX1 = nghost[IDIR] * nint[JDIR] * nint[KDIR] * mapNVars; - - if(haveVs) { - bufferSizeX1 += nghost[IDIR] * nint[JDIR] * nint[KDIR]; - #if DIMENSIONS>=2 - bufferSizeX1 += nghost[IDIR] * (nint[JDIR]+1) * nint[KDIR]; - #endif - - #if DIMENSIONS==3 - bufferSizeX1 += nghost[IDIR] * nint[JDIR] * (nint[KDIR]+1); - #endif // DIMENSIONS - } - - - BufferRecvX1[faceLeft ] = Buffer(bufferSizeX1); - BufferRecvX1[faceRight] = Buffer(bufferSizeX1); - BufferSendX1[faceLeft ] = Buffer(bufferSizeX1); - BufferSendX1[faceRight] = Buffer(bufferSizeX1); - - // Number of cells in X2 boundary condition (only required when problem >2D): -#if DIMENSIONS >= 2 - bufferSizeX2 = ntot[IDIR] * nghost[JDIR] * nint[KDIR] * mapNVars; - if(haveVs) { - // IDIR - bufferSizeX2 += (ntot[IDIR]+1) * nghost[JDIR] * nint[KDIR]; - #if DIMENSIONS>=2 - bufferSizeX2 += ntot[IDIR] * nghost[JDIR] * nint[KDIR]; - #endif - #if DIMENSIONS==3 - bufferSizeX2 += ntot[IDIR] * nghost[JDIR] * (nint[KDIR]+1); - #endif // DIMENSIONS - } - - BufferRecvX2[faceLeft ] = Buffer(bufferSizeX2); - BufferRecvX2[faceRight] = Buffer(bufferSizeX2); - BufferSendX2[faceLeft ] = Buffer(bufferSizeX2); - BufferSendX2[faceRight] = Buffer(bufferSizeX2); - -#endif -// Number of cells in X3 boundary condition (only required when problem is 3D): -#if DIMENSIONS ==3 - bufferSizeX3 = ntot[IDIR] * ntot[JDIR] * nghost[KDIR] * mapNVars; - - if(haveVs) { - // IDIR - bufferSizeX3 += (ntot[IDIR]+1) * ntot[JDIR] * nghost[KDIR]; - // JDIR - bufferSizeX3 += ntot[IDIR] * (ntot[JDIR]+1) * nghost[KDIR]; - // KDIR - bufferSizeX3 += ntot[IDIR] * ntot[JDIR] * nghost[KDIR]; - } - - BufferRecvX3[faceLeft ] = Buffer(bufferSizeX3); - BufferRecvX3[faceRight] = Buffer(bufferSizeX3); - BufferSendX3[faceLeft ] = Buffer(bufferSizeX3); - BufferSendX3[faceRight] = Buffer(bufferSizeX3); -#endif // DIMENSIONS - -#ifdef MPI_PERSISTENT - // Init persistent MPI communications - int procSend, procRecv; - - // X1-dir exchanges - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX1[faceRight].data(), bufferSizeX1, realMPI, procSend, - thisInstance*1000, mygrid->CartComm, &sendRequestX1[faceRight])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX1[faceLeft].data(), bufferSizeX1, realMPI, procRecv, - thisInstance*1000, mygrid->CartComm, &recvRequestX1[faceLeft])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX1[faceLeft].data(), bufferSizeX1, realMPI, procSend, - thisInstance*1000+1,mygrid->CartComm, &sendRequestX1[faceLeft])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX1[faceRight].data(), bufferSizeX1, realMPI, procRecv, - thisInstance*1000+1,mygrid->CartComm, &recvRequestX1[faceRight])); - - #if DIMENSIONS >= 2 - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX2[faceRight].data(), bufferSizeX2, realMPI, procSend, - thisInstance*1000+10, mygrid->CartComm, &sendRequestX2[faceRight])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX2[faceLeft].data(), bufferSizeX2, realMPI, procRecv, - thisInstance*1000+10, mygrid->CartComm, &recvRequestX2[faceLeft])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX2[faceLeft].data(), bufferSizeX2, realMPI, procSend, - thisInstance*1000+11, mygrid->CartComm, &sendRequestX2[faceLeft])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX2[faceRight].data(), bufferSizeX2, realMPI, procRecv, - thisInstance*1000+11, mygrid->CartComm, &recvRequestX2[faceRight])); - #endif - - #if DIMENSIONS == 3 - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX3[faceRight].data(), bufferSizeX3, realMPI, procSend, - thisInstance*1000+20, mygrid->CartComm, &sendRequestX3[faceRight])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX3[faceLeft].data(), bufferSizeX3, realMPI, procRecv, - thisInstance*1000+20, mygrid->CartComm, &recvRequestX3[faceLeft])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Send_init(BufferSendX3[faceLeft].data(), bufferSizeX3, realMPI, procSend, - thisInstance*1000+21, mygrid->CartComm, &sendRequestX3[faceLeft])); - - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX3[faceRight].data(), bufferSizeX3, realMPI, procRecv, - thisInstance*1000+21, mygrid->CartComm, &recvRequestX3[faceRight])); - #endif - -#endif // MPI_Persistent - - // say this instance is initialized. - isInitialized = true; - - idfx::popRegion(); -} - -// Destructor (clean up persistent communication channels) -Mpi::~Mpi() { - idfx::pushRegion("Mpi::~Mpi"); - if(isInitialized) { - // Properly clean up the mess - #ifdef MPI_PERSISTENT - idfx::cout << "Mpi(" << thisInstance - << "): Cleaning up MPI persistent communication channels" << std::endl; - for(int i=0 ; i< 2; i++) { - MPI_Request_free( &sendRequestX1[i]); - MPI_Request_free( &recvRequestX1[i]); - - #if DIMENSIONS >= 2 - MPI_Request_free( &sendRequestX2[i]); - MPI_Request_free( &recvRequestX2[i]); - #endif - - #if DIMENSIONS == 3 - MPI_Request_free( &sendRequestX3[i]); - MPI_Request_free( &recvRequestX3[i]); - #endif - } - #endif - if(thisInstance==1) { - idfx::cout << "Mpi(" << thisInstance << "): measured throughput is " - << bytesSentOrReceived/myTimer/1024.0/1024.0 << " MB/s" << std::endl; - idfx::cout << "Mpi(" << thisInstance << "): message sizes were " << std::endl; - idfx::cout << " X1: " << bufferSizeX1*sizeof(real)/1024.0/1024.0 << " MB" << std::endl; - idfx::cout << " X2: " << bufferSizeX2*sizeof(real)/1024.0/1024.0 << " MB" << std::endl; - idfx::cout << " X3: " << bufferSizeX3*sizeof(real)/1024.0/1024.0 << " MB" << std::endl; - } - isInitialized = false; - } - idfx::popRegion(); -} - -void Mpi::ExchangeX1(IdefixArray4D Vc, IdefixArray4D Vs) { - idfx::pushRegion("Mpi::ExchangeX1"); - - // Load the buffers with data - int ibeg,iend,jbeg,jend,kbeg,kend,offset,nx; - Buffer BufferLeft = BufferSendX1[faceLeft]; - Buffer BufferRight = BufferSendX1[faceRight]; - IdefixArray1D map = this->mapVars; - - // If MPI Persistent, start receiving even before the buffers are filled - myTimer -= MPI_Wtime(); - double tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX1)); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; -#endif - myTimer += MPI_Wtime(); - - // Coordinates of the ghost region which needs to be transfered - ibeg = 0; - iend = nghost[IDIR]; - nx = nghost[IDIR]; // Number of points in x - offset = end[IDIR]; // Distance between beginning of left and right ghosts - jbeg = beg[JDIR]; - jend = end[JDIR]; - - kbeg = beg[KDIR]; - kend = end[KDIR]; - - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - BufferLeft.Pack(Vc, map, std::make_pair(ibeg+nx, iend+nx), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vc, map, std::make_pair(ibeg+offset-nx, iend+offset-nx), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - // Load face-centered field in the buffer - if(haveVs) { - BufferLeft.Pack(Vs, BX1s,std::make_pair(ibeg+nx+1, iend+nx+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vs, BX1s, std::make_pair(ibeg+offset-nx, iend+offset-nx), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - #if DIMENSIONS >= 2 - - BufferLeft.Pack(Vs, BX2s,std::make_pair(ibeg+nx, iend+nx), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vs, BX2s, std::make_pair(ibeg+offset-nx, iend+offset-nx), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg , kend)); - - #endif - - #if DIMENSIONS == 3 - - BufferLeft.Pack(Vs, BX3s,std::make_pair(ibeg+nx, iend+nx), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend+1)); - - BufferRight.Pack(Vs, BX3s, std::make_pair(ibeg+offset-nx, iend+offset-nx), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend+1)); - - #endif - } - - // Wait for completion before sending out everything - Kokkos::fence(); - myTimer -= MPI_Wtime(); - tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX1)); - // Wait for buffers to be received - MPI_Waitall(2,recvRequestX1,recvStatus); - -#else - int procSend, procRecv; - - #ifdef MPI_NON_BLOCKING - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - MPI_Request sendRequest[2]; - MPI_Request recvRequest[2]; - - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX1[faceRight].data(), bufferSizeX1, realMPI, procSend, 100, - mygrid->CartComm, &sendRequest[0])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX1[faceLeft].data(), bufferSizeX1, realMPI, procRecv, 100, - mygrid->CartComm, &recvRequest[0])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX1[faceLeft].data(), bufferSizeX1, realMPI, procSend, 101, - mygrid->CartComm, &sendRequest[1])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX1[faceRight].data(), bufferSizeX1, realMPI, procRecv, 101, - mygrid->CartComm, &recvRequest[1])); - - // Wait for recv to complete (we don't care about the sends) - MPI_Waitall(2, recvRequest, recvStatus); - - #else - MPI_Status status; - // Send to the right - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX1[faceRight].data(), bufferSizeX1, realMPI, procSend, 100, - BufferRecvX1[faceLeft].data(), bufferSizeX1, realMPI, procRecv, 100, - mygrid->CartComm, &status)); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,0,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX1[faceLeft].data(), bufferSizeX1, realMPI, procSend, 101, - BufferRecvX1[faceRight].data(), bufferSizeX1, realMPI, procRecv, 101, - mygrid->CartComm, &status)); - #endif -#endif - myTimer += MPI_Wtime(); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; - // Unpack - BufferLeft=BufferRecvX1[faceLeft]; - BufferRight=BufferRecvX1[faceRight]; - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - BufferLeft.Unpack(Vc, map,std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vc, map,std::make_pair(ibeg+offset, iend+offset), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - // We fill the ghost zones - - if(haveVs) { - BufferLeft.Unpack(Vs, BX1s, std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vs, BX1s, std::make_pair(ibeg+offset+1, iend+offset+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - #if DIMENSIONS >= 2 - BufferLeft.Unpack(Vs, BX2s, std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vs, BX2s, std::make_pair(ibeg+offset, iend+offset), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg , kend)); - #endif - - #if DIMENSIONS == 3 - BufferLeft.Unpack(Vs, BX3s, std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend+1)); - - BufferRight.Unpack(Vs, BX3s, std::make_pair(ibeg+offset, iend+offset), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend+1)); - #endif - } - -myTimer -= MPI_Wtime(); -#ifdef MPI_NON_BLOCKING - // Wait for the sends if they have not yet completed - MPI_Waitall(2, sendRequest, sendStatus); -#endif - -#ifdef MPI_PERSISTENT - MPI_Waitall(2, sendRequestX1, sendStatus); -#endif - myTimer += MPI_Wtime(); - bytesSentOrReceived += 4*bufferSizeX1*sizeof(real); - - idfx::popRegion(); -} - - -void Mpi::ExchangeX2(IdefixArray4D Vc, IdefixArray4D Vs) { - idfx::pushRegion("Mpi::ExchangeX2"); - - // Load the buffers with data - int ibeg,iend,jbeg,jend,kbeg,kend,offset,ny; - Buffer BufferLeft=BufferSendX2[faceLeft]; - Buffer BufferRight=BufferSendX2[faceRight]; - IdefixArray1D map = this->mapVars; - -// If MPI Persistent, start receiving even before the buffers are filled - myTimer -= MPI_Wtime(); - double tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX2)); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; -#endif - myTimer += MPI_Wtime(); - - // Coordinates of the ghost region which needs to be transfered - ibeg = 0; - iend = ntot[IDIR]; - - jbeg = 0; - jend = nghost[JDIR]; - offset = end[JDIR]; // Distance between beginning of left and right ghosts - ny = nghost[JDIR]; - - kbeg = beg[KDIR]; - kend = end[KDIR]; - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - BufferLeft.Pack(Vc, map, std::make_pair(ibeg , iend), - std::make_pair(jbeg+ny , jend+ny), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vc, map, std::make_pair(ibeg , iend), - std::make_pair(jbeg+offset-ny , jend+offset-ny), - std::make_pair(kbeg , kend)); - - // Load face-centered field in the buffer - if(haveVs) { - BufferLeft.Pack(Vs, BX1s,std::make_pair(ibeg , iend+1), - std::make_pair(jbeg+ny , jend+ny), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vs, BX1s, std::make_pair(ibeg , iend+1), - std::make_pair(jbeg+offset-ny , jend+offset-ny), - std::make_pair(kbeg , kend)); - #if DIMENSIONS >= 2 - BufferLeft.Pack(Vs, BX2s,std::make_pair(ibeg , iend), - std::make_pair(jbeg+ny+1 , jend+ny+1), - std::make_pair(kbeg , kend)); - - BufferRight.Pack(Vs, BX2s, std::make_pair(ibeg , iend), - std::make_pair(jbeg+offset-ny , jend+offset-ny), - std::make_pair(kbeg , kend)); - #endif - #if DIMENSIONS == 3 - - BufferLeft.Pack(Vs, BX3s,std::make_pair(ibeg , iend), - std::make_pair(jbeg+ny , jend+ny), - std::make_pair(kbeg , kend+1)); - - BufferRight.Pack(Vs, BX3s, std::make_pair(ibeg , iend), - std::make_pair(jbeg+offset-ny , jend+offset-ny), - std::make_pair(kbeg , kend+1)); - - #endif - } - - // Send to the right - Kokkos::fence(); - - myTimer -= MPI_Wtime(); - tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX2)); - MPI_Waitall(2,recvRequestX2,recvStatus); - -#else - int procSend, procRecv; - - #ifdef MPI_NON_BLOCKING - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - MPI_Request sendRequest[2]; - MPI_Request recvRequest[2]; - - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX2[faceRight].data(), bufferSizeX2, realMPI, procSend, 100, - mygrid->CartComm, &sendRequest[0])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX2[faceLeft].data(), bufferSizeX2, realMPI, procRecv, 100, - mygrid->CartComm, &recvRequest[0])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX2[faceLeft].data(), bufferSizeX2, realMPI, procSend, 101, - mygrid->CartComm, &sendRequest[1])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX2[faceRight].data(), bufferSizeX2, realMPI, procRecv, 101, - mygrid->CartComm, &recvRequest[1])); - - // Wait for recv to complete (we don't care about the sends) - MPI_Waitall(2, recvRequest, recvStatus); - - #else - MPI_Status status; - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX2[faceRight].data(), bufferSizeX2, realMPI, procSend, 200, - BufferRecvX2[faceLeft].data(), bufferSizeX2, realMPI, procRecv, 200, - mygrid->CartComm, &status)); - - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX2[faceLeft].data(), bufferSizeX2, realMPI, procSend, 201, - BufferRecvX2[faceRight].data(), bufferSizeX2, realMPI, procRecv, 201, - mygrid->CartComm, &status)); - #endif -#endif - myTimer += MPI_Wtime(); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; - // Unpack - BufferLeft=BufferRecvX2[faceLeft]; - BufferRight=BufferRecvX2[faceRight]; - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - // We fill the ghost zones - BufferLeft.Unpack(Vc, map,std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vc, map,std::make_pair(ibeg , iend), - std::make_pair(jbeg+offset , jend+offset), - std::make_pair(kbeg , kend)); - // We fill the ghost zones - - if(haveVs) { - BufferLeft.Unpack(Vs, BX1s, std::make_pair(ibeg, iend+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vs, BX1s, std::make_pair(ibeg, iend+1), - std::make_pair(jbeg+offset , jend+offset), - std::make_pair(kbeg , kend)); - #if DIMENSIONS >= 2 - BufferLeft.Unpack(Vs, BX2s, std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vs, BX2s, std::make_pair(ibeg, iend), - std::make_pair(jbeg+offset+1, jend+offset+1), - std::make_pair(kbeg , kend)); - #endif - #if DIMENSIONS == 3 - BufferLeft.Unpack(Vs, BX3s, std::make_pair(ibeg, iend), - std::make_pair(jbeg, jend), - std::make_pair(kbeg, kend+1)); - - BufferRight.Unpack(Vs, BX3s,std::make_pair(ibeg , iend), - std::make_pair(jbeg+offset, jend+offset), - std::make_pair(kbeg , kend+1)); - #endif - } - - myTimer -= MPI_Wtime(); -#ifdef MPI_NON_BLOCKING - // Wait for the sends if they have not yet completed - MPI_Waitall(2, sendRequest, sendStatus); -#endif - -#ifdef MPI_PERSISTENT - MPI_Waitall(2, sendRequestX2, sendStatus); -#endif - myTimer += MPI_Wtime(); - bytesSentOrReceived += 4*bufferSizeX2*sizeof(real); - - idfx::popRegion(); -} - - -void Mpi::ExchangeX3(IdefixArray4D Vc, IdefixArray4D Vs) { - idfx::pushRegion("Mpi::ExchangeX3"); - - - // Load the buffers with data - int ibeg,iend,jbeg,jend,kbeg,kend,offset,nz; - Buffer BufferLeft=BufferSendX3[faceLeft]; - Buffer BufferRight=BufferSendX3[faceRight]; - IdefixArray1D map = this->mapVars; - - // If MPI Persistent, start receiving even before the buffers are filled - myTimer -= MPI_Wtime(); - - double tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX3)); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; -#endif - myTimer += MPI_Wtime(); - // Coordinates of the ghost region which needs to be transfered - ibeg = 0; - iend = ntot[IDIR]; - - jbeg = 0; - jend = ntot[JDIR]; - - kbeg = 0; - kend = nghost[KDIR]; - offset = end[KDIR]; // Distance between beginning of left and right ghosts - nz = nghost[KDIR]; - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - BufferLeft.Pack(Vc, map, std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+nz, kend+nz)); - - BufferRight.Pack(Vc, map, std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg + offset-nz, kend+ offset-nz)); - - // Load face-centered field in the buffer - if(haveVs) { - BufferLeft.Pack(Vs, BX1s,std::make_pair(ibeg , iend+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+nz , kend+nz)); - - BufferRight.Pack(Vs, BX1s, std::make_pair(ibeg , iend+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg + offset-nz, kend+ offset-nz)); - - #if DIMENSIONS >= 2 - - BufferLeft.Pack(Vs, BX2s,std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg+nz , kend+nz)); - - BufferRight.Pack(Vs, BX2s, std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg + offset-nz, kend+ offset-nz)); - - #endif - - #if DIMENSIONS == 3 - BufferLeft.Pack(Vs, BX3s,std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+nz+1 , kend+nz+1)); - - BufferRight.Pack(Vs, BX3s, std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg + offset-nz, kend+ offset-nz)); - #endif - } - - // Send to the right - Kokkos::fence(); - - myTimer -= MPI_Wtime(); - tStart = MPI_Wtime(); -#ifdef MPI_PERSISTENT - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX3)); - MPI_Waitall(2,recvRequestX3,recvStatus); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; - -#else - int procSend, procRecv; - - #ifdef MPI_NON_BLOCKING - MPI_Status sendStatus[2]; - MPI_Status recvStatus[2]; - MPI_Request sendRequest[2]; - MPI_Request recvRequest[2]; - - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX3[faceRight].data(), bufferSizeX3, realMPI, procSend, 100, - mygrid->CartComm, &sendRequest[0])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX3[faceLeft].data(), bufferSizeX3, realMPI, procRecv, 100, - mygrid->CartComm, &recvRequest[0])); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Isend(BufferSendX3[faceLeft].data(), bufferSizeX3, realMPI, procSend, 101, - mygrid->CartComm, &sendRequest[1])); - - MPI_SAFE_CALL(MPI_Irecv(BufferRecvX3[faceRight].data(), bufferSizeX3, realMPI, procRecv, 101, - mygrid->CartComm, &recvRequest[1])); - - // Wait for recv to complete (we don't care about the sends) - MPI_Waitall(2, recvRequest, recvStatus); - - #else - MPI_Status status; - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX3[faceRight].data(), bufferSizeX3, realMPI, procSend, 300, - BufferRecvX3[faceLeft].data(), bufferSizeX3, realMPI, procRecv, 300, - mygrid->CartComm, &status)); - - // Send to the left - // We receive from procRecv, and we send to procSend - MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,-1,&procRecv,&procSend )); - - MPI_SAFE_CALL(MPI_Sendrecv(BufferSendX3[faceLeft].data(), bufferSizeX3, realMPI, procSend, 301, - BufferRecvX3[faceRight].data(), bufferSizeX3, realMPI, procRecv, 301, - mygrid->CartComm, &status)); - #endif -#endif - myTimer += MPI_Wtime(); - idfx::mpiCallsTimer += MPI_Wtime() - tStart; - // Unpack - BufferLeft=BufferRecvX3[faceLeft]; - BufferRight=BufferRecvX3[faceRight]; - - BufferLeft.ResetPointer(); - BufferRight.ResetPointer(); - - - // We fill the ghost zones - BufferLeft.Unpack(Vc, map,std::make_pair(ibeg, iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vc, map,std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+offset , kend+offset)); - // We fill the ghost zones - - if(haveVs) { - BufferLeft.Unpack(Vs, BX1s, std::make_pair(ibeg, iend+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg , kend)); - - BufferRight.Unpack(Vs, BX1s, std::make_pair(ibeg, iend+1), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+offset , kend+offset)); - - #if DIMENSIONS >=2 - BufferLeft.Unpack(Vs, BX2s, std::make_pair(ibeg, iend), - std::make_pair(jbeg, jend+1), - std::make_pair(kbeg, kend)); - - BufferRight.Unpack(Vs, BX2s,std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend+1), - std::make_pair(kbeg+offset, kend+offset)); - #endif - - #if DIMENSIONS == 3 - BufferLeft.Unpack(Vs, BX3s, std::make_pair(ibeg, iend), - std::make_pair(jbeg, jend), - std::make_pair(kbeg, kend)); - - BufferRight.Unpack(Vs, BX3s,std::make_pair(ibeg , iend), - std::make_pair(jbeg , jend), - std::make_pair(kbeg+offset+1, kend+offset+1)); - #endif - } - - myTimer -= MPI_Wtime(); -#ifdef MPI_NON_BLOCKING - // Wait for the sends if they have not yet completed - MPI_Waitall(2, sendRequest, sendStatus); -#endif - -#ifdef MPI_PERSISTENT - MPI_Waitall(2, sendRequestX3, sendStatus); -#endif - myTimer += MPI_Wtime(); - bytesSentOrReceived += 4*bufferSizeX3*sizeof(real); - - idfx::popRegion(); -} - - - -void Mpi::CheckConfig() { - idfx::pushRegion("Mpi::CheckConfig"); - // compile time check - #ifdef KOKKOS_ENABLE_CUDA - #if defined(MPIX_CUDA_AWARE_SUPPORT) && !MPIX_CUDA_AWARE_SUPPORT - #error Your MPI library is not CUDA Aware (check Idefix requirements). - #endif - #endif /* MPIX_CUDA_AWARE_SUPPORT */ - - // Run-time check that we can do a reduce on device arrays - IdefixArray1D src("MPIChecksrc",1); - IdefixArray1D::HostMirror srcHost = Kokkos::create_mirror_view(src); - - if(idfx::prank == 0) { - srcHost(0) = 0; - Kokkos::deep_copy(src, srcHost); - } - - if(idfx::psize > 1) { - MPI_Comm_set_errhandler(MPI_COMM_WORLD, MPI_ERRORS_RETURN); - - // Capture segfaults - struct sigaction newHandler; - struct sigaction oldHandler; - memset(&newHandler, 0, sizeof(newHandler)); - newHandler.sa_flags = SA_SIGINFO; - newHandler.sa_sigaction = Mpi::SigErrorHandler; - sigaction(SIGSEGV, &newHandler, &oldHandler); - try { - // We next circulate the info round-robin accross all the nodes to check that - // MPI can exchange buffers in idefix arrays - - MPI_Status status; - int ierrSend, ierrRecv; - if(idfx::prank == 0) { - ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, idfx::prank+1, 1, MPI_COMM_WORLD); - ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::psize-1, 1, MPI_COMM_WORLD, &status); - } else { - ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::prank-1, 1, MPI_COMM_WORLD, &status); - // Add our own rank to the data - Kokkos::deep_copy(srcHost, src); - srcHost(0) += idfx::prank; - Kokkos::deep_copy(src, srcHost); - ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, (idfx::prank+1)%idfx::psize, 1, - MPI_COMM_WORLD); - } - - if(ierrSend != 0) { - char MPImsg[MPI_MAX_ERROR_STRING]; - int MPImsgLen; - MPI_Error_string(ierrSend, MPImsg, &MPImsgLen); - throw std::runtime_error(std::string(MPImsg, MPImsgLen)); - } - if(ierrRecv != 0) { - char MPImsg[MPI_MAX_ERROR_STRING]; - int MPImsgLen; - MPI_Error_string(ierrSend, MPImsg, &MPImsgLen); - throw std::runtime_error(std::string(MPImsg, MPImsgLen)); - } - } catch(std::exception &e) { - std::stringstream errmsg; - errmsg << "Your MPI library is unable to perform Send/Recv on Idefix arrays."; - errmsg << std::endl; - #ifdef KOKKOS_ENABLE_CUDA - errmsg << "Check that your MPI library is CUDA aware." << std::endl; - #elif defined(KOKKOS_ENABLE_HIP) - errmsg << "Check that your MPI library is RocM aware." << std::endl; - #else - errmsg << "Check your MPI library configuration." << std::endl; - #endif - errmsg << "Error: " << e.what() << std::endl; - IDEFIX_ERROR(errmsg); - } - // Restore old handlers - sigaction(SIGSEGV, &oldHandler, NULL ); - MPI_Comm_set_errhandler(MPI_COMM_WORLD, MPI_ERRORS_ARE_FATAL); - } - - // Check that we have the proper end result - Kokkos::deep_copy(srcHost, src); - int64_t size = static_cast(idfx::psize); - int64_t rank = static_cast(idfx::prank); - int64_t result = rank == 0 ? size*(size-1)/2 : rank*(rank+1)/2; - - if(srcHost(0) != result) { - idfx::cout << "got " << srcHost(0) << " expected " << result << std::endl; - std::stringstream errmsg; - errmsg << "Your MPI library managed to perform MPI exchanges on Idefix Arrays, but the result "; - errmsg << "is incorrect. " << std::endl; - errmsg << "Check your MPI library configuration." << std::endl; - IDEFIX_ERROR(errmsg); - } - idfx::popRegion(); -} - -void Mpi::SigErrorHandler(int nSignum, siginfo_t* si, void* vcontext) { - std::stringstream errmsg; - errmsg << "A segmentation fault was triggered while attempting to test your MPI library."; - errmsg << std::endl; - errmsg << "Your MPI library is unable to perform reductions on Idefix arrays."; - errmsg << std::endl; - #ifdef KOKKOS_ENABLE_CUDA - errmsg << "Check that your MPI library is CUDA aware." << std::endl; - #elif defined(KOKKOS_ENABLE_HIP) - errmsg << "Check that your MPI library is RocM aware." << std::endl; - #else - errmsg << "Check your MPI library configuration." << std::endl; - #endif - IDEFIX_ERROR(errmsg); -} - -// This routine check that all of the processes are synced. -// Returns true if this is the case, false otherwise - -bool Mpi::CheckSync(real timeout) { - // If no parallelism, then we're in sync! - if(idfx::psize == 1) return(true); - - int send = idfx::prank; - int recv = 0; - MPI_Request request; - - MPI_Iallreduce(&send, &recv, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD, &request); - - double start = MPI_Wtime(); - int flag = 0; - MPI_Status status; - - while((MPI_Wtime()-start < timeout) && !flag) { - MPI_Test(&request, &flag, &status); - // sleep for 10 ms - std::this_thread::sleep_for(std::chrono::milliseconds(10)); - } - if(!flag) { - // We did not managed to do an allreduce, so this is a failure. - return(false); - } - if(recv != idfx::psize*(idfx::psize-1)/2) { - IDEFIX_ERROR("wrong result for synchronisation"); - } - - return(true); -} diff --git a/src/mpi.hpp b/src/mpi.hpp deleted file mode 100644 index a4250a17c..000000000 --- a/src/mpi.hpp +++ /dev/null @@ -1,269 +0,0 @@ -// *********************************************************************************** -// Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur -// and other code contributors -// Licensed under CeCILL 2.1 License, see COPYING for more information -// *********************************************************************************** - -#ifndef MPI_HPP_ -#define MPI_HPP_ - -#include -#include -#include -#include "idefix.hpp" -#include "grid.hpp" - - -class DataBlock; -class Buffer { - public: - Buffer() = default; - explicit Buffer(size_t size): pointer{0}, array{IdefixArray1D("BufferArray",size)} { }; - - void* data() { - return(array.data()); - } - - int Size() { - return(array.size()); - } - - void ResetPointer() { - this->pointer = 0; - } - - void Pack(IdefixArray3D& in, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - - auto arr = this->array; - idefix_for("LoadBuffer3D",kb.first,kb.second,jb.first,jb.second,ib.first,ib.second, - KOKKOS_LAMBDA (int k, int j, int i) { - arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(k,j,i); - }); - - // Update pointer - this->pointer += ninjnk; - } - - void Pack(IdefixArray4D& in, - const int var, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - - auto arr = this->array; - idefix_for("LoadBuffer4D",kb.first,kb.second,jb.first,jb.second,ib.first,ib.second, - KOKKOS_LAMBDA (int k, int j, int i) { - arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(var, k,j,i); - }); - - // Update pointer - this->pointer += ninjnk; - } - - void Pack(IdefixArray4D& in, - IdefixArray1D& map, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - auto arr = this->array; - - idefix_for("LoadBuffer4D",0,map.size(), - kb.first,kb.second, - jb.first,jb.second, - ib.first,ib.second, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + n*ninjnk + offset ) = in(map(n), k,j,i); - }); - - // Update pointer - this->pointer += ninjnk*map.size(); - } - - void Unpack(IdefixArray3D& out, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - auto arr = this->array; - - idefix_for("LoadBuffer3D",kb.first,kb.second,jb.first,jb.second,ib.first,ib.second, - KOKKOS_LAMBDA (int k, int j, int i) { - out(k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ); - }); - - // Update pointer - this->pointer += ninjnk; - } - - void Unpack(IdefixArray4D& out, - const int var, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - - auto arr = this->array; - idefix_for("LoadBuffer3D",kb.first,kb.second,jb.first,jb.second,ib.first,ib.second, - KOKKOS_LAMBDA (int k, int j, int i) { - out(var,k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ); - }); - - // Update pointer - this->pointer += ninjnk; - } - - void Unpack(IdefixArray4D& out, - IdefixArray1D& map, - std::pair ib, - std::pair jb, - std::pair kb) { - const int ni = ib.second-ib.first; - const int ninj = (jb.second-jb.first)*ni; - const int ninjnk = (kb.second-kb.first)*ninj; - const int ibeg = ib.first; - const int jbeg = jb.first; - const int kbeg = kb.first; - const int offset = this->pointer; - - auto arr = this->array; - idefix_for("LoadBuffer4D",0,map.size(), - kb.first,kb.second, - jb.first,jb.second, - ib.first,ib.second, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - out(map(n),k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + n*ninjnk + offset ); - }); - - // Update pointer - this->pointer += ninjnk*map.size(); - } - - - private: - size_t pointer; - IdefixArray1D array; -}; - -class Mpi { - public: - Mpi() = default; - // MPI Exchange functions - void ExchangeAll(); ///< Exchange boundary elements in all directions (todo) - void ExchangeX1(IdefixArray4D inputVc, - IdefixArray4D inputVs = IdefixArray4D()); - ///< Exchange boundary elements in the X1 direction - void ExchangeX2(IdefixArray4D inputVc, - IdefixArray4D inputVs = IdefixArray4D()); - ///< Exchange boundary elements in the X2 direction - void ExchangeX3(IdefixArray4D inputVc, - IdefixArray4D inputVs = IdefixArray4D()); - ///< Exchange boundary elements in the X3 direction - - // Init from datablock - void Init(Grid *grid, std::vector inputMap, - int nghost[3], int nint[3], bool inputHaveVs = false ); - - // Check that MPI will work with the designated target (in particular GPU Direct) - static void CheckConfig(); - - // Check that MPI processes are synced - static bool CheckSync(real); - - - // Destructor - ~Mpi(); - - private: - // Because the MPI class initialise internal pointers, we do not allow copies of this class - // These lines should not be removed as they constitute a safeguard - Mpi(const Mpi&); - Mpi operator=(const Mpi&); - - static int nInstances; // total number of mpi instances in the code - int thisInstance; // unique number of the current instance - int nReferences; // # of references to this instance - bool isInitialized{false}; - - DataBlock *data; // pointer to datablock object - - enum {faceRight, faceLeft}; - - // Buffers for MPI calls - Buffer BufferSendX1[2]; - Buffer BufferSendX2[2]; - Buffer BufferSendX3[2]; - Buffer BufferRecvX1[2]; - Buffer BufferRecvX2[2]; - Buffer BufferRecvX3[2]; - - IdefixArray1D mapVars; - int mapNVars{0}; - - int nint[3]; //< number of internal elements of the arrays we treat - int nghost[3]; //< number of ghost zone of the arrays we treat - int ntot[3]; //< total number of cells of the arrays we treat - int beg[3]; //< begining index of the active zone - int end[3]; //< end index of the active zone - - int bufferSizeX1; - int bufferSizeX2; - int bufferSizeX3; - - bool haveVs{false}; - - // Requests for MPI persistent communications - MPI_Request sendRequestX1[2]; - MPI_Request sendRequestX2[2]; - MPI_Request sendRequestX3[2]; - MPI_Request recvRequestX1[2]; - MPI_Request recvRequestX2[2]; - MPI_Request recvRequestX3[2]; - - Grid *mygrid; - - // MPI throughput timer specific to this object - double myTimer{0}; - int64_t bytesSentOrReceived{0}; - - // Error handler used by CheckConfig - static void SigErrorHandler(int, siginfo_t* , void* ); -}; - -#endif // MPI_HPP_ diff --git a/src/mpi/CMakeLists.txt b/src/mpi/CMakeLists.txt new file mode 100644 index 000000000..6042da654 --- /dev/null +++ b/src/mpi/CMakeLists.txt @@ -0,0 +1,7 @@ +target_sources(idefix + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/buffer.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/exchanger.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/exchanger.cpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/mpi.hpp + PUBLIC ${CMAKE_CURRENT_LIST_DIR}/mpi.cpp +) diff --git a/src/mpi/buffer.hpp b/src/mpi/buffer.hpp new file mode 100644 index 000000000..ff4dff146 --- /dev/null +++ b/src/mpi/buffer.hpp @@ -0,0 +1,195 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef MPI_BUFFER_HPP_ +#define MPI_BUFFER_HPP_ + +#include "idefix.hpp" +#include "arrays.hpp" + +using BoundingBox = std::array,3>; + + +class Buffer { + public: + Buffer() = default; + explicit Buffer(size_t size): pointer{0}, array{IdefixArray1D("BufferArray",size)} {}; + + // Compute the size of a bounding box + static size_t ComputeBoxSize(BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + return(ninjnk); + } + + void* data() { + return(array.data()); + } + + int Size() { + return(array.size()); + } + + void ResetPointer() { + this->pointer = 0; + } + + void Pack(IdefixArray3D& in, BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("LoadBuffer3D",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(k,j,i); + }); + + // Update pointer + this->pointer += ninjnk; + } + + void Pack(IdefixArray4D& in, + const int var, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("LoadBuffer4D_var",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(var, k,j,i); + }); + + // Update pointer + this->pointer += ninjnk; + } + + void Pack(IdefixArray4D& in, + IdefixArray1D& map, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + auto arr = this->array; + + idefix_for("LoadBuffer4D_map",0,map.size(), + kbeg,kend, + jbeg,jend, + ibeg,iend, + KOKKOS_LAMBDA (int n, int k, int j, int i) { + arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + n*ninjnk + offset ) = in(map(n), k,j,i); + }); + + // Update pointer + this->pointer += ninjnk*map.size(); + } + + void Unpack(IdefixArray3D& out, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + auto arr = this->array; + + idefix_for("UnLoadBuffer3D",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + out(k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ); + }); + + // Update pointer + this->pointer += ninjnk; + } + + void Unpack(IdefixArray4D& out, + const int var, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("UnLoadBuffer4D_var",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + out(var,k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ); + }); + + // Update pointer + this->pointer += ninjnk; + } + + void Unpack(IdefixArray4D& out, + IdefixArray1D& map, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("UnLoadBuffer4D_map",0,map.size(), + kbeg,kend, + jbeg,jend, + ibeg,iend, + KOKKOS_LAMBDA (int n, int k, int j, int i) { + out(map(n),k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + n*ninjnk + offset ); + }); + + // Update pointer + this->pointer += ninjnk*map.size(); + } + + + private: + size_t pointer; + IdefixArray1D array; +}; + +#endif // MPI_BUFFER_HPP_ diff --git a/src/mpi/exchanger.cpp b/src/mpi/exchanger.cpp new file mode 100644 index 000000000..033ce4041 --- /dev/null +++ b/src/mpi/exchanger.cpp @@ -0,0 +1,308 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#include +#include "exchanger.hpp" +#include "idefix.hpp" +#include "buffer.hpp" +#include "grid.hpp" +#include "arrays.hpp" + +//#define MPI_NON_BLOCKING +#define MPI_PERSISTENT + +int Exchanger::nInstances = 0; + +void Exchanger::Init( + Grid *grid, + int direction, + std::vector inputMap, + std::array nghost, + std::array nint, + bool inputHaveVs, + std::array overwriteBXn) { + idfx::pushRegion("Exchanger::Init"); + this->grid = grid; + this->direction = direction; + // Allocate mapVars on target and copy it from the input argument list + this->mapVars = idfx::ConvertVectorToIdefixArray(inputMap); + this->mapNVars = inputMap.size(); + this->haveVs = inputHaveVs; + + // increase the number of instances + this->thisInstance = nInstances; + + // Compute indices of arrays we will be working with + for(int dir = 0 ; dir < 3 ; dir++) { + this->nghost[dir] = nghost[dir]; + this->nint[dir] = nint[dir]; + this->ntot[dir] = nint[dir]+2*nghost[dir]; + this->beg[dir] = nghost[dir]; + this->end[dir] = nghost[dir]+nint[dir]; + } + + ///////////////////////////////////////////////////////////////////////////// + // Init exchange datasets + // Buffer size direction are for sends (i.e. buffer left is for a send from the left side) + + // Make left buffer + // Init zone to the full domain + for(int dir = 0 ; dir < 3 ; dir++) { + if(dir < direction) { + boxRecv[faceLeft][dir][0] = 0; + boxRecv[faceLeft][dir][1] = ntot[dir]; + } else if(dir > direction) { + boxRecv[faceLeft][dir][0] = beg[dir]; + boxRecv[faceLeft][dir][1] = end[dir]; + } else { + // dir == direction + boxRecv[faceLeft][dir][0] = 0; + boxRecv[faceLeft][dir][1] = nghost[dir]; + } + } + // Copy all the boxes from boxRecvLeft + boxRecv[faceRight] = boxRecv[faceLeft]; + boxSend = boxRecv; + + // Adjust the indices for send and receive in the direction of interest + boxRecv[faceRight][direction][0] = end[direction]; + boxRecv[faceRight][direction][1] = ntot[direction]; + + boxSend[faceLeft][direction][0] = beg[direction]; + boxSend[faceLeft][direction][1] = beg[direction]+nghost[direction]; + + boxSend[faceRight][direction][0] = end[direction] - nghost[direction]; + boxSend[faceRight][direction][1] = end[direction]; + + // Face-centered boxes + + // Add one element in the field direction + for(int component = 0 ; component < 3 ; component++) { + // Init as centered boxes + boxSendVs[component] = boxSend; + boxRecvVs[component] = boxRecv; + const int normalDir = component; + if(component != direction) { + for(int face = 0 ; face <2 ; face++) { + boxSendVs[component][face][normalDir][1] += 1; + boxRecvVs[component][face][normalDir][1] += 1; + } + } else { + // component == direction + if(!overwriteBXn[faceLeft]) boxSendVs[component][faceLeft][normalDir][0] += 1; + boxSendVs[component][faceLeft][normalDir][1] += 1; + + if(!overwriteBXn[faceRight]) boxRecvVs[component][faceRight][normalDir][0] += 1; + boxRecvVs[component][faceRight][normalDir][1] += 1; + } + } + + // Compute buffer sizes + for(int face=0 ; face < 2 ; face++) { + bufferSizeSend[face] = mapNVars * Buffer::ComputeBoxSize(boxSend[face]); + bufferSizeRecv[face] = mapNVars * Buffer::ComputeBoxSize(boxRecv[face]); + if(haveVs) { + for(int component = 0 ; component CartComm,direction,1,&procRecv[faceLeft],&procSend[faceRight]); + MPI_Cart_shift(grid->CartComm,direction,-1,&procRecv[faceRight],&procSend[faceLeft]); + + #ifdef MPI_PERSISTENT + + // X1-dir exchanges + // We receive from procRecv, and we send to procSend + + MPI_Send_init(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, + procSend[faceRight], thisInstance*2, + grid->CartComm, &sendRequest[faceRight]); + + MPI_Recv_init(BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, + procRecv[faceLeft],thisInstance*2, + grid->CartComm, &recvRequest[faceLeft]); + + // Send to the left + // We receive from procRecv, and we send to procSend + + MPI_Send_init(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, + procSend[faceLeft],thisInstance*2+1, + grid->CartComm, &sendRequest[faceLeft]); + + MPI_Recv_init(BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, + procRecv[faceRight], thisInstance*2+1, + grid->CartComm, &recvRequest[faceRight]); + + #endif // MPI_PERSISTENT + + // say this instance is initialized. + isInitialized = true; + nInstances++; + + idfx::popRegion(); +} + +Exchanger::~Exchanger() { + idfx::pushRegion("Exchanger::~Exchanger"); + if(isInitialized) { + // Properly clean up the mess + #ifdef MPI_PERSISTENT + for(int i=0 ; i< 2; i++) { + MPI_Request_free( &sendRequest[i]); + MPI_Request_free( &recvRequest[i]); + } + #endif + isInitialized = false; + } + idfx::popRegion(); +} + +void Exchanger::Exchange(IdefixArray4D Vc, IdefixArray4D Vs) { + idfx::pushRegion("Mpi::ExchangeX1"); + // Load the buffers with data + Buffer BufferLeft = BufferSend[faceLeft]; + Buffer BufferRight = BufferSend[faceRight]; + IdefixArray1D map = this->mapVars; + + bool recvRight = (procRecv[faceRight] != MPI_PROC_NULL); + bool recvLeft = (procRecv[faceLeft] != MPI_PROC_NULL); + + // If MPI Persistent, start receiving even before the buffers are filled + myTimer -= MPI_Wtime(); + double tStart = MPI_Wtime(); +#ifdef MPI_PERSISTENT + MPI_Status sendStatus[2]; + MPI_Status recvStatus[2]; + + MPI_Startall(2, recvRequest); + idfx::mpiCallsTimer += MPI_Wtime() - tStart; +#endif + myTimer += MPI_Wtime(); + + BufferLeft.ResetPointer(); + BufferRight.ResetPointer(); + + BufferLeft.Pack(Vc, map, boxSend[faceLeft]); + BufferRight.Pack(Vc, map, boxSend[faceRight]); + // Load face-centered field in the buffer + if(haveVs) { + for(int component = 0 ; component < DIMENSIONS ; component++) { + BufferLeft.Pack(Vs, component, boxSendVs[component][faceLeft]); + BufferRight.Pack(Vs, component, boxSendVs[component][faceRight]); + } + } + + // Wait for completion before sending out everything + Kokkos::fence(); + myTimer -= MPI_Wtime(); + tStart = MPI_Wtime(); +#ifdef MPI_PERSISTENT + MPI_Startall(2, sendRequest); + // Wait for buffers to be received + MPI_Waitall(2,recvRequest,recvStatus); + +#else + + #ifdef MPI_NON_BLOCKING + MPI_Status sendStatus[2]; + MPI_Status recvStatus[2]; + MPI_Request sendRequest[2]; + MPI_Request recvRequest[2]; + + // We receive from procRecv, and we send to procSend + + MPI_Isend(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, + procSend[faceRight], 100, mygrid->CartComm, &sendRequest[0]); + + MPI_Irecv(BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, + procRecv[faceLeft], 100, mygrid->CartComm, &recvRequest[0]); + // Send to the left + // We receive from procRecv, and we send to procSend + + MPI_Isend(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, + procSend[faceLeft], 101, mygrid->CartComm, &sendRequest[1]); + + MPI_Irecv(BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, + procRecv[faceRight], 101, mygrid->CartComm, &recvRequest[1]); + + // Wait for recv to complete (we don't care about the sends) + MPI_Waitall(2, recvRequest, recvStatus); + + #else + MPI_Status status; + // Send to the right + // We receive from procRecv, and we send to procSend + + MPI_Sendrecv(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, + procSend[faceRight], 100, + BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, + procRecv[faceLeft], 100, + grid->CartComm, &status); + + // Send to the left + // We receive from procRecv, and we send to procSend + + MPI_Sendrecv(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, + procSend[faceLeft], 101, + BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, + procRecv[faceRight], 101, + grid->CartComm, &status); + #endif +#endif +myTimer += MPI_Wtime(); +idfx::mpiCallsTimer += MPI_Wtime() - tStart; +// Unpack +BufferLeft=BufferRecv[faceLeft]; +BufferRight=BufferRecv[faceRight]; + +BufferLeft.ResetPointer(); +BufferRight.ResetPointer(); + +if(recvLeft) { + BufferLeft.Unpack(Vc, map, boxRecv[faceLeft]); + if(haveVs) { + for(int component = 0 ; component < DIMENSIONS ; component++) { + BufferLeft.Unpack(Vs, component, boxRecvVs[component][faceLeft]); + } + } +} +if(recvRight) { + BufferRight.Unpack(Vc, map, boxRecv[faceRight]); + if(haveVs) { + for(int component = 0 ; component < DIMENSIONS ; component++) { + BufferRight.Unpack(Vs, component, boxRecvVs[component][faceRight]); + } + } +} +myTimer -= MPI_Wtime(); +#ifdef MPI_NON_BLOCKING + // Wait for the sends if they have not yet completed + MPI_Waitall(2, sendRequest, sendStatus); +#endif + +#ifdef MPI_PERSISTENT + MPI_Waitall(2, sendRequest, sendStatus); +#endif + myTimer += MPI_Wtime(); + bytesSentOrReceived += (bufferSizeRecv[faceLeft] + +bufferSizeSend[faceLeft] + +bufferSizeRecv[faceRight] + +bufferSizeSend[faceRight])*sizeof(real); + + idfx::popRegion(); +} diff --git a/src/mpi/exchanger.hpp b/src/mpi/exchanger.hpp new file mode 100644 index 000000000..2e1affcb0 --- /dev/null +++ b/src/mpi/exchanger.hpp @@ -0,0 +1,82 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef MPI_EXCHANGER_HPP_ +#define MPI_EXCHANGER_HPP_ + +#include + +#include +#include +#include +#include "idefix.hpp" +#include "grid.hpp" +#include "buffer.hpp" +#include "arrays.hpp" + +class Grid; + +class Exchanger { + public: + Exchanger() = default; + void Init( Grid* grid, + int direction, + std::vector inputMap, + std::array nghost, + std::array nint, + bool inputHaveVs = false, + std::array overwriteBXn = {true, true}); + + void Exchange(IdefixArray4D Vc, IdefixArray4D Vs); + ~Exchanger(); + + static int nInstances; // total number of mpi instances in the code + int thisInstance; // unique number of the current instance + bool isInitialized{false}; + + // MPI throughput timer specific to this object + double myTimer{0}; + int64_t bytesSentOrReceived{0}; + + // Buffer sizes for throughput calculations + std::array bufferSizeSend; + std::array bufferSizeRecv; + + private: + enum {faceRight, faceLeft}; + + std::array boxSend, boxRecv; // bounding boxes for each face + std::array,3> boxSendVs, boxRecvVs; // 3= 3 field components + + // Buffers for MPI calls + Buffer BufferSend[2]; + Buffer BufferRecv[2]; + + int procSend[2]; // MPI process to send to in X1 direction + int procRecv[2]; // MPI process to receive from in X1 direction + + int direction; + IdefixArray1D mapVars; + int mapNVars{0}; + + int nint[3]; //< number of internal elements of the arrays we treat + int nghost[3]; //< number of ghost zone of the arrays we treat + int ntot[3]; //< total number of cells of the arrays we treat + int beg[3]; //< begining index of the active zone + int end[3]; //< end index of the active zone + + bool haveVs{false}; + + // Requests for MPI persistent communications + MPI_Request sendRequest[2]; + MPI_Request recvRequest[2]; + + Grid *grid; +}; + + +#endif // MPI_EXCHANGER_HPP_ diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp new file mode 100644 index 000000000..36b4eb9a3 --- /dev/null +++ b/src/mpi/mpi.cpp @@ -0,0 +1,265 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + + +#include "mpi.hpp" +#include +#include +#include // NOLINT [build/c++11] +#include // NOLINT [build/c++11] +#include +#include +#include "idefix.hpp" +#include "dataBlock.hpp" + + +#if defined(OPEN_MPI) && OPEN_MPI +#include "mpi-ext.h" // Needed for CUDA-aware check */ +#endif + + + + +// init the number of instances +int Mpi::nInstances = 0; + +// MPI Routines exchange +void Mpi::ExchangeAll() { + IDEFIX_ERROR("Not Implemented"); +} + +/// +/// Initialise an instance of the MPI class. +/// @param grid: pointer to the grid object (needed to get the MPI neighbours) +/// @param inputMap: 1st indices of inputVc which are to be exchanged (i.e, the list of variables) +/// @param nghost: size of the ghost region in each direction +/// @param nint: size of the internal region in each direction +/// @param inputHaveVs: whether the instance should also treat face-centered variable +/// (optional, default false) +/// + +void Mpi::Init(Grid *grid, std::vector inputMap, + std::array nghost, std::array nint, + std::array lbound, + std::array rbound, + bool inputHaveVs) { + idfx::pushRegion("Mpi::Init"); + + // increase the number of instances + nInstances++; + thisInstance=nInstances; + + for(int dir=0; dir<3; dir++) { + std::array overWriteBXn = {true, true}; + if(lbound[dir] == BoundaryType::shearingbox) { + overWriteBXn[faceLeft] = false; + } + if(rbound[dir] == BoundaryType::shearingbox) { + overWriteBXn[faceRight] = false; + } + + exchanger[dir].Init(grid, dir, inputMap, + nghost, nint, + inputHaveVs, overWriteBXn); + } + + isInitialized = true; + idfx::popRegion(); +} + +// Destructor (clean up persistent communication channels) +Mpi::~Mpi() { + idfx::pushRegion("Mpi::~Mpi"); + if(isInitialized) { + if(thisInstance==1) { + int bytesSentOrReceived = 0; + double myTimer = 0; + for(int dir=0; dir<3; dir++) { + bytesSentOrReceived += exchanger[dir].bytesSentOrReceived; + myTimer += exchanger[dir].myTimer; + } + idfx::cout << "Mpi(" << thisInstance << "): measured throughput is " + << bytesSentOrReceived/myTimer/1024.0/1024.0 << " MB/s" << std::endl; + idfx::cout << "Mpi(" << thisInstance << "): message sizes were " << std::endl; + idfx::cout << " X1: " + << exchanger[IDIR].bufferSizeSend[0]*sizeof(real)/1024.0/1024.0 + << " MB" << std::endl; + idfx::cout << " X2: " + << exchanger[JDIR].bufferSizeSend[0]*sizeof(real)/1024.0/1024.0 + << " MB" << std::endl; + idfx::cout << " X3: " + << exchanger[KDIR].bufferSizeSend[0]*sizeof(real)/1024.0/1024.0 + << " MB" << std::endl; + } + isInitialized = false; + } + idfx::popRegion(); +} + +void Mpi::ExchangeX1(IdefixArray4D Vc, IdefixArray4D Vs) { + idfx::pushRegion("Mpi::ExchangeX1"); + + exchanger[IDIR].Exchange(Vc, Vs); + idfx::popRegion(); +} + +void Mpi::ExchangeX2(IdefixArray4D Vc, IdefixArray4D Vs) { + idfx::pushRegion("Mpi::ExchangeX2"); + exchanger[JDIR].Exchange(Vc, Vs); + idfx::popRegion(); +} + +void Mpi::ExchangeX3(IdefixArray4D Vc, IdefixArray4D Vs) { + idfx::pushRegion("Mpi::ExchangeX3"); + exchanger[KDIR].Exchange(Vc, Vs); + idfx::popRegion(); +} + + +void Mpi::CheckConfig() { + idfx::pushRegion("Mpi::CheckConfig"); + // compile time check + #ifdef KOKKOS_ENABLE_CUDA + #if defined(MPIX_CUDA_AWARE_SUPPORT) && !MPIX_CUDA_AWARE_SUPPORT + #error Your MPI library is not CUDA Aware (check Idefix requirements). + #endif + #endif /* MPIX_CUDA_AWARE_SUPPORT */ + + // Run-time check that we can do a reduce on device arrays + IdefixArray1D src("MPIChecksrc",1); + IdefixArray1D::HostMirror srcHost = Kokkos::create_mirror_view(src); + + if(idfx::prank == 0) { + srcHost(0) = 0; + Kokkos::deep_copy(src, srcHost); + } + + if(idfx::psize > 1) { + MPI_Comm_set_errhandler(MPI_COMM_WORLD, MPI_ERRORS_RETURN); + + // Capture segfaults + struct sigaction newHandler; + struct sigaction oldHandler; + memset(&newHandler, 0, sizeof(newHandler)); + newHandler.sa_flags = SA_SIGINFO; + newHandler.sa_sigaction = Mpi::SigErrorHandler; + sigaction(SIGSEGV, &newHandler, &oldHandler); + try { + // We next circulate the info round-robin accross all the nodes to check that + // MPI can exchange buffers in idefix arrays + + MPI_Status status; + int ierrSend, ierrRecv; + if(idfx::prank == 0) { + ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, idfx::prank+1, 1, MPI_COMM_WORLD); + ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::psize-1, 1, MPI_COMM_WORLD, &status); + } else { + ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::prank-1, 1, MPI_COMM_WORLD, &status); + // Add our own rank to the data + Kokkos::deep_copy(srcHost, src); + srcHost(0) += idfx::prank; + Kokkos::deep_copy(src, srcHost); + ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, (idfx::prank+1)%idfx::psize, 1, + MPI_COMM_WORLD); + } + + if(ierrSend != 0) { + char MPImsg[MPI_MAX_ERROR_STRING]; + int MPImsgLen; + MPI_Error_string(ierrSend, MPImsg, &MPImsgLen); + throw std::runtime_error(std::string(MPImsg, MPImsgLen)); + } + if(ierrRecv != 0) { + char MPImsg[MPI_MAX_ERROR_STRING]; + int MPImsgLen; + MPI_Error_string(ierrSend, MPImsg, &MPImsgLen); + throw std::runtime_error(std::string(MPImsg, MPImsgLen)); + } + } catch(std::exception &e) { + std::stringstream errmsg; + errmsg << "Your MPI library is unable to perform Send/Recv on Idefix arrays."; + errmsg << std::endl; + #ifdef KOKKOS_ENABLE_CUDA + errmsg << "Check that your MPI library is CUDA aware." << std::endl; + #elif defined(KOKKOS_ENABLE_HIP) + errmsg << "Check that your MPI library is RocM aware." << std::endl; + #else + errmsg << "Check your MPI library configuration." << std::endl; + #endif + errmsg << "Error: " << e.what() << std::endl; + IDEFIX_ERROR(errmsg); + } + // Restore old handlers + sigaction(SIGSEGV, &oldHandler, NULL ); + MPI_Comm_set_errhandler(MPI_COMM_WORLD, MPI_ERRORS_ARE_FATAL); + } + + // Check that we have the proper end result + Kokkos::deep_copy(srcHost, src); + int64_t size = static_cast(idfx::psize); + int64_t rank = static_cast(idfx::prank); + int64_t result = rank == 0 ? size*(size-1)/2 : rank*(rank+1)/2; + + if(srcHost(0) != result) { + idfx::cout << "got " << srcHost(0) << " expected " << result << std::endl; + std::stringstream errmsg; + errmsg << "Your MPI library managed to perform MPI exchanges on Idefix Arrays, but the result "; + errmsg << "is incorrect. " << std::endl; + errmsg << "Check your MPI library configuration." << std::endl; + IDEFIX_ERROR(errmsg); + } + idfx::popRegion(); +} + +void Mpi::SigErrorHandler(int nSignum, siginfo_t* si, void* vcontext) { + std::stringstream errmsg; + errmsg << "A segmentation fault was triggered while attempting to test your MPI library."; + errmsg << std::endl; + errmsg << "Your MPI library is unable to perform reductions on Idefix arrays."; + errmsg << std::endl; + #ifdef KOKKOS_ENABLE_CUDA + errmsg << "Check that your MPI library is CUDA aware." << std::endl; + #elif defined(KOKKOS_ENABLE_HIP) + errmsg << "Check that your MPI library is RocM aware." << std::endl; + #else + errmsg << "Check your MPI library configuration." << std::endl; + #endif + IDEFIX_ERROR(errmsg); +} + +// This routine check that all of the processes are synced. +// Returns true if this is the case, false otherwise + +bool Mpi::CheckSync(real timeout) { + // If no parallelism, then we're in sync! + if(idfx::psize == 1) return(true); + + int send = idfx::prank; + int recv = 0; + MPI_Request request; + + MPI_Iallreduce(&send, &recv, 1, MPI_INT, MPI_SUM, MPI_COMM_WORLD, &request); + + double start = MPI_Wtime(); + int flag = 0; + MPI_Status status; + + while((MPI_Wtime()-start < timeout) && !flag) { + MPI_Test(&request, &flag, &status); + // sleep for 10 ms + std::this_thread::sleep_for(std::chrono::milliseconds(10)); + } + if(!flag) { + // We did not managed to do an allreduce, so this is a failure. + return(false); + } + if(recv != idfx::psize*(idfx::psize-1)/2) { + IDEFIX_ERROR("wrong result for synchronisation"); + } + + return(true); +} diff --git a/src/mpi/mpi.hpp b/src/mpi/mpi.hpp new file mode 100644 index 000000000..b8f929326 --- /dev/null +++ b/src/mpi/mpi.hpp @@ -0,0 +1,74 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef MPI_MPI_HPP_ +#define MPI_MPI_HPP_ + +#include + +#include +#include +#include +#include "idefix.hpp" +#include "grid.hpp" +#include "buffer.hpp" +#include "exchanger.hpp" + + +class DataBlock; + + +class Mpi { + public: + Mpi() = default; + // MPI Exchange functions + void ExchangeAll(); ///< Exchange boundary elements in all directions (todo) + void ExchangeX1(IdefixArray4D inputVc, + IdefixArray4D inputVs = IdefixArray4D()); + ///< Exchange boundary elements in the X1 direction + void ExchangeX2(IdefixArray4D inputVc, + IdefixArray4D inputVs = IdefixArray4D()); + ///< Exchange boundary elements in the X2 direction + void ExchangeX3(IdefixArray4D inputVc, + IdefixArray4D inputVs = IdefixArray4D()); + ///< Exchange boundary elements in the X3 direction + + // Init from datablock + void Init(Grid *grid, std::vector inputMap, + std::array nghost, std::array nint, + std::array lbound, + std::array rbound, + bool inputHaveVs = false ); + + // Check that MPI will work with the designated target (in particular GPU Direct) + static void CheckConfig(); + + // Check that MPI processes are synced + static bool CheckSync(real); + + + // Destructor + ~Mpi(); + + private: + enum {faceRight, faceLeft}; + // Because the MPI class initialise internal pointers, we do not allow copies of this class + // These lines should not be removed as they constitute a safeguard + Mpi(const Mpi&); + Mpi operator=(const Mpi&); + + static int nInstances; // total number of mpi instances in the code + int thisInstance; // unique number of the current instance + int nReferences; // # of references to this instance + bool isInitialized{false}; + + std::array exchanger; ///< exchangers in each direction + // Error handler used by CheckConfig + static void SigErrorHandler(int, siginfo_t* , void* ); +}; + +#endif // MPI_MPI_HPP_ diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index c8dd8cb96..6f22de6f5 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -198,7 +198,8 @@ RKLegendre::RKLegendre(Input &input, Fluid* hydroin) { nvarRKL = varListHost.size(); #ifdef WITH_MPI - mpi.Init(data->mygrid, varListHost, data->nghost.data(), data->np_int.data(), haveVs); + mpi.Init(data->mygrid, varListHost, data->nghost, data->np_int, + data->lbound, data->rbound, haveVs); #endif diff --git a/src/utils/column.cpp b/src/utils/column.cpp index 34d55f56b..4657abc55 100644 --- a/src/utils/column.cpp +++ b/src/utils/column.cpp @@ -56,7 +56,7 @@ Column::Column(int dir, int sign, DataBlock *data) std::vector mapVars; mapVars.push_back(ntarget); - this->mpi.Init(data->mygrid, mapVars, data->nghost.data(), data->np_int.data()); + this->mpi.Init(data->mygrid, mapVars, data->nghost, data->np_int, data->lbound, data->rbound); this->nproc = data->mygrid->nproc; #endif idfx::popRegion(); diff --git a/test/MHD/AmbipolarCshock3D/idefix-rkl.ini b/test/MHD/AmbipolarCshock3D/idefix-rkl.ini index 055429557..621552b13 100644 --- a/test/MHD/AmbipolarCshock3D/idefix-rkl.ini +++ b/test/MHD/AmbipolarCshock3D/idefix-rkl.ini @@ -22,8 +22,8 @@ X1-beg userdef X1-end userdef X2-beg periodic X2-end periodic -X3-beg periodic -X3-end periodic +X3-beg userdef +X3-end userdef [Output] vtk 100.0 diff --git a/test/MHD/AmbipolarCshock3D/idefix.ini b/test/MHD/AmbipolarCshock3D/idefix.ini index 984e985ef..78c7ddd23 100644 --- a/test/MHD/AmbipolarCshock3D/idefix.ini +++ b/test/MHD/AmbipolarCshock3D/idefix.ini @@ -19,8 +19,8 @@ X1-beg userdef X1-end userdef X2-beg periodic X2-end periodic -X3-beg periodic -X3-end periodic +X3-beg userdef +X3-end userdef [Output] vtk 100.0 diff --git a/test/MHD/AmbipolarCshock3D/setup.cpp b/test/MHD/AmbipolarCshock3D/setup.cpp index 5f8ec9313..abf8a0f24 100644 --- a/test/MHD/AmbipolarCshock3D/setup.cpp +++ b/test/MHD/AmbipolarCshock3D/setup.cpp @@ -79,7 +79,48 @@ void UserdefBoundary(Hydro *hydro, int dir, BoundarySide side, real t) { }); } - + if(dir ==KDIR) { + auto Vc = hydro->Vc; + auto Vs = hydro->Vs; + int jbeg = data->beg[JDIR]; + int jend = data->end[JDIR]; + int kbeg = data->beg[KDIR]; + int kend = data->end[KDIR]; + hydro->boundary->BoundaryForAll("UserdefBoundary", dir, side, + KOKKOS_LAMBDA (int n, int k, int j, int i) { + int kref=k; + + if(side == left) { + kref = kbeg; + } else { + kref = kend -1; + } + Vc(n,k,j,i) = Vc(n,kref,j,i); + }); + + if(dir == KDIR) { + hydro->boundary->BoundaryForX1s("UserdefBoundaryX1s", dir, side, + KOKKOS_LAMBDA (int k, int j, int i) { + int kref=k; + if(side == left) { + kref = kbeg; + } else { + kref = kend -1; + } + Vs(BX1s,k,j,i) = Vs(BX1s,kref,j,i); + }); + hydro->boundary->BoundaryForX2s("UserdefBoundaryX2s", dir, side, + KOKKOS_LAMBDA (int k, int j, int i) { + int kref=k; + if(side == left) { + kref = kbeg; + } else { + kref = kend -1; + } + Vs(BX2s,k,j,i) = Vs(BX2s,kref,j,i); + }); + } + } } @@ -136,8 +177,8 @@ void Setup::InitFlow(DataBlock &data) { real z = d.x[KDIR](k); real y = d.x[JDIR](j); d.Ve(AX1e,k,j,i) = B0*sin(theta)*z; - d.Ve(AX2e,k,j,i) = ZERO_F; - d.Ve(AX3e,k,j,i) = B0*cos(theta)*y; + d.Ve(AX2e,k,j,i) = -B0*cos(theta)*z; + d.Ve(AX3e,k,j,i) = 0; #else IDEFIX_ERROR("Vector potential only valid in 3 dimensions for this setup"); #endif diff --git a/test/MHD/AmbipolarCshock3D/testme.py b/test/MHD/AmbipolarCshock3D/testme.py index f9fae6765..964224854 100755 --- a/test/MHD/AmbipolarCshock3D/testme.py +++ b/test/MHD/AmbipolarCshock3D/testme.py @@ -9,7 +9,7 @@ sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -tolerance=2e-14 +tolerance=3e-14 def testMe(test): test.configure() test.compile() diff --git a/test/MHD/OrszagTang3D/setup.cpp b/test/MHD/OrszagTang3D/setup.cpp index 8e7205c42..86766c8ee 100644 --- a/test/MHD/OrszagTang3D/setup.cpp +++ b/test/MHD/OrszagTang3D/setup.cpp @@ -19,6 +19,7 @@ void Analysis(DataBlock& data) { idfx::cout << "Analysis: Checking restart routines" << std::endl; // Trigger dump creation + // data.SetBoundaries(); myOutput->ForceWriteDump(data); // Mirror data on Host @@ -96,7 +97,8 @@ void Analysis(DataBlock& data) { errornum++; idfx::cout << "-----------------------------------------" << std::endl << " Error in Vc at (i,j,k,n) = ( " << i << ", " << j << ", " << k << ", " << n << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl + << "Original= " << myVc(n,k,j,i) << " New=" << d.Vc(n,k,j,i) << " diff=" << myVc(n,k,j,i)-d.Vc(n,k,j,i) << std::endl; } } diff --git a/test/MHD/ShearingBox/testme.py b/test/MHD/ShearingBox/testme.py index c89d24b52..364adde9b 100755 --- a/test/MHD/ShearingBox/testme.py +++ b/test/MHD/ShearingBox/testme.py @@ -41,3 +41,6 @@ def testMe(test): test.reconstruction=2 test.mpi=False testMe(test) + + test.mpi=True + testMe(test) From 0880026d777b9d894de80c5c101102c3f01c9338 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 15 Dec 2025 16:52:42 +0100 Subject: [PATCH 087/144] update changelog --- CHANGELOG.md | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 3778d514e..4447493e9 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,16 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). +## Upcoming +### Changed + +- fixed a bug that could lead to diverging results around the spherical axis in non-ideal MHD in 2.5D and 3D (#356) +- refactor of the MPI exchange routines and boundary routines to avoid buildup of roundoff errors at domain faces/edges that could lead to the sudden burst of div(B) or incoherences between MPI sub-domains (#357) + + +### Added + + ## [2.2.02] 2025-10-18 ### Changed From e28936581731f9068a78b75bb35599e3a047299e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 18 Dec 2025 08:11:24 +0100 Subject: [PATCH 088/144] fix #358 (#359) fix a compilation error on AMD APU targets (e.g. Mi 300) --- src/global.hpp | 2 +- src/output/scalarField.hpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/global.hpp b/src/global.hpp index 5a9ea70fb..c4de3926e 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -39,7 +39,7 @@ template IdefixArray1D ConvertVectorToIdefixArray(std::vector &inputVector) { IdefixArray1D outArr = IdefixArray1D("Vector",inputVector.size()); IdefixHostArray1D outArrHost; - outArrHost = Kokkos::create_mirror_view(outArr); + outArrHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), outArr); for(int i = 0; i < inputVector.size() ; i++) { outArrHost(i) = inputVector[i]; } diff --git a/src/output/scalarField.hpp b/src/output/scalarField.hpp index 9af7b1986..6cbb9dd40 100644 --- a/src/output/scalarField.hpp +++ b/src/output/scalarField.hpp @@ -33,7 +33,7 @@ class ScalarField { h4Darray, var, Kokkos::ALL, Kokkos::ALL, Kokkos::ALL); return(arr3D); } else if(type==Device3D) { - IdefixHostArray3D arr3D = Kokkos::create_mirror(d3Darray); + IdefixHostArray3D arr3D = Kokkos::create_mirror(Kokkos::HostSpace(), d3Darray); Kokkos::deep_copy(arr3D,d3Darray); return(arr3D); } else if(type==Device4D) { From 3c5586e2e5ab68d6f9ffdd74a46003f6a06ff55b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Sat, 27 Dec 2025 08:32:03 +0100 Subject: [PATCH 089/144] typo --- src/output/dump.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/output/dump.cpp b/src/output/dump.cpp index 955e06e72..96a40b548 100644 --- a/src/output/dump.cpp +++ b/src/output/dump.cpp @@ -71,7 +71,7 @@ void Dump::CreateMPIDataType(GridBox gb, bool read) { int size[3]; int subsize[3]; - // the grid is required to now the current MPÏ domain decomposition + // the grid is required to know the current MPÏ domain decomposition Grid *grid = data->mygrid; // Dimensions for cell-centered fields From 52b6c97385aae4b9a1234f3985d9bd80c2c861f5 Mon Sep 17 00:00:00 2001 From: Alankar Dutta Date: Fri, 16 Jan 2026 09:25:21 +0100 Subject: [PATCH 090/144] [FIX] compatibility with compiling on AMD Instinct MI300A APU (#360) * [FIX] compatibility with compiling on AMD Instinct MI300A APU * `pre-commit` linter fix --- src/dataBlock/dataBlockHost.cpp | 35 +++++++++++++++++---------------- src/dataBlock/dumpToFile.cpp | 14 ++++++++----- src/fluid/checkNan.hpp | 4 ++-- src/grid.hpp | 2 +- src/gridHost.cpp | 8 ++++---- src/output/dump.hpp | 4 ++-- src/utils/lookupTable.hpp | 24 +++++++++++----------- 7 files changed, 48 insertions(+), 43 deletions(-) diff --git a/src/dataBlock/dataBlockHost.cpp b/src/dataBlock/dataBlockHost.cpp index d570648fa..c7811b391 100644 --- a/src/dataBlock/dataBlockHost.cpp +++ b/src/dataBlock/dataBlockHost.cpp @@ -21,11 +21,11 @@ DataBlockHost::DataBlockHost(DataBlock& datain) { // Create mirrors (should be mirror_view) for(int dir = 0 ; dir < 3 ; dir++) { - x[dir] = Kokkos::create_mirror_view(data->x[dir]); - xr[dir] = Kokkos::create_mirror_view(data->xr[dir]); - xl[dir] = Kokkos::create_mirror_view(data->xl[dir]); - dx[dir] = Kokkos::create_mirror_view(data->dx[dir]); - A[dir] = Kokkos::create_mirror_view(data->A[dir]); + x[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->x[dir]); + xr[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->xr[dir]); + xl[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->xl[dir]); + dx[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->dx[dir]); + A[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->A[dir]); } np_tot = data->np_tot; @@ -47,30 +47,30 @@ DataBlockHost::DataBlockHost(DataBlock& datain) { // TO BE COMPLETED... - dV = Kokkos::create_mirror_view(data->dV); - Vc = Kokkos::create_mirror_view(data->hydro->Vc); - Uc = Kokkos::create_mirror_view(data->hydro->Uc); - InvDt = Kokkos::create_mirror_view(data->hydro->InvDt); + dV = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->dV); + Vc = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->Vc); + Uc = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->Uc); + InvDt = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->InvDt); #if MHD == YES - Vs = Kokkos::create_mirror_view(data->hydro->Vs); + Vs = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->Vs); this->haveCurrent = data->hydro->haveCurrent; if(data->hydro->haveCurrent) { - J = Kokkos::create_mirror_view(data->hydro->J); + J = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->J); } #ifdef EVOLVE_VECTOR_POTENTIAL - Ve = Kokkos::create_mirror_view(data->hydro->Ve); + Ve = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->Ve); #endif - D_EXPAND( Ex3 = Kokkos::create_mirror_view(data->hydro->emf->ez); , + D_EXPAND( Ex3 = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->emf->ez); , , - Ex1 = Kokkos::create_mirror_view(data->hydro->emf->ex); - Ex2 = Kokkos::create_mirror_view(data->hydro->emf->ey); ) + Ex1 = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->emf->ex); + Ex2 = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->hydro->emf->ey); ) #endif if(haveDust) { dustVc = std::vector>(data->dust.size()); for(int i = 0 ; i < data->dust.size() ; i++) { - dustVc[i] = Kokkos::create_mirror_view(data->dust[i]->Vc); + dustVc[i] = Kokkos::create_mirror_view(Kokkos::HostSpace(), data->dust[i]->Vc); } } @@ -80,7 +80,8 @@ DataBlockHost::DataBlockHost(DataBlock& datain) { this->coarseningDirection = data->coarseningDirection; for(int dir = 0 ; dir < 3 ; dir++) { if(coarseningDirection[dir]) { - coarseningLevel[dir] = Kokkos::create_mirror_view(data->coarseningLevel[dir]); + coarseningLevel[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), + data->coarseningLevel[dir]); } } } diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index 35b60b81d..51347e6ed 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -45,14 +45,15 @@ void DataBlock::DumpToFile(std::string filebase) { // TODO(lesurg) Make datablock a friend of hydro to get the Riemann flux? - //IdefixArray4D::HostMirror locFlux = Kokkos::create_mirror_view(this->hydro->FluxRiemann); + //IdefixArray4D::HostMirror locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), + // this->hydro->FluxRiemann); //Kokkos::deep_copy(locFlux, this->FluxRiemann); #if MHD == YES IdefixArray4D::HostMirror locJ; if(hydro->haveCurrent) { - locJ = Kokkos::create_mirror_view(this->hydro->J); + locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ, this->hydro->J); } #endif @@ -120,7 +121,8 @@ void DataBlock::DumpToFile(std::string filebase) { // Write Vs #if MHD == YES // Write Vs - IdefixArray4D::HostMirror locVs = Kokkos::create_mirror_view(this->hydro->Vs); + IdefixArray4D::HostMirror locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), + this->hydro->Vs); Kokkos::deep_copy(locVs,this->hydro->Vs); dims[0] = this->np_tot[IDIR]+IOFFSET; dims[1] = this->np_tot[JDIR]+JOFFSET; @@ -137,7 +139,8 @@ void DataBlock::DumpToFile(std::string filebase) { dims[2] = this->np_tot[KDIR]; std::snprintf(fieldName,NAMESIZE,"Ex3"); - IdefixArray3D::HostMirror locE = Kokkos::create_mirror_view(this->hydro->emf->ez); + IdefixArray3D::HostMirror locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), + this->hydro->emf->ez); Kokkos::deep_copy(locE,this->hydro->emf->ez); WriteVariable(fileHdl, 3, dims, fieldName, locE.data()); @@ -152,7 +155,8 @@ void DataBlock::DumpToFile(std::string filebase) { if(hydro->haveCurrent) { - IdefixArray4D::HostMirror locJ = Kokkos::create_mirror_view(this->hydro->J); + IdefixArray4D::HostMirror locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), + this->hydro->J); Kokkos::deep_copy(locJ,this->hydro->J); dims[0] = this->np_tot[IDIR]; dims[1] = this->np_tot[JDIR]; diff --git a/src/fluid/checkNan.hpp b/src/fluid/checkNan.hpp index 88e206e5e..0e8890725 100644 --- a/src/fluid/checkNan.hpp +++ b/src/fluid/checkNan.hpp @@ -67,7 +67,7 @@ int Fluid::CheckNan() { DataBlockHost dataHost(*data); - IdefixHostArray4D VcHost = Kokkos::create_mirror_view(this->Vc); + IdefixHostArray4D VcHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->Vc); Kokkos::deep_copy(VcHost,Vc); int nerrormax=10; @@ -95,7 +95,7 @@ int Fluid::CheckNan() { } if constexpr(Phys::mhd) { - IdefixHostArray4D VsHost = Kokkos::create_mirror_view(this->Vs); + IdefixHostArray4D VsHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->Vs); Kokkos::deep_copy(VsHost,Vs); for(int k = data->beg[KDIR] ; k < data->end[KDIR]+KOFFSET ; k++) { for(int j = data->beg[JDIR] ; j < data->end[JDIR]+JOFFSET ; j++) { diff --git a/src/grid.hpp b/src/grid.hpp index 0ffdb3a58..947d05d12 100644 --- a/src/grid.hpp +++ b/src/grid.hpp @@ -81,7 +81,7 @@ class SubGrid { parentGrid(grid), type(type), direction(d) { idfx::pushRegion("SubGrid::SubGrid()"); // Find the index of the current subgrid. - auto x = Kokkos::create_mirror_view(parentGrid->x[direction]); + auto x = Kokkos::create_mirror_view(Kokkos::HostSpace(), parentGrid->x[direction]); Kokkos::deep_copy(x,parentGrid->x[direction]); int iref = -1; for(int i = 0 ; i < x.extent(0) - 1 ; i++) { diff --git a/src/gridHost.cpp b/src/gridHost.cpp index ad61f0436..0c85d8e41 100644 --- a/src/gridHost.cpp +++ b/src/gridHost.cpp @@ -32,10 +32,10 @@ GridHost::GridHost(Grid &grid) { // Create mirrors on host for(int dir = 0 ; dir < 3 ; dir++) { - x[dir] = Kokkos::create_mirror_view(grid.x[dir]); - xr[dir] = Kokkos::create_mirror_view(grid.xr[dir]); - xl[dir] = Kokkos::create_mirror_view(grid.xl[dir]); - dx[dir] = Kokkos::create_mirror_view(grid.dx[dir]); + x[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), grid.x[dir]); + xr[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), grid.xr[dir]); + xl[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), grid.xl[dir]); + dx[dir] = Kokkos::create_mirror_view(Kokkos::HostSpace(), grid.dx[dir]); } idfx::popRegion(); diff --git a/src/output/dump.hpp b/src/output/dump.hpp index d823ddcaf..87cb7a3ba 100644 --- a/src/output/dump.hpp +++ b/src/output/dump.hpp @@ -88,13 +88,13 @@ class DumpField { h4Darray, var, Kokkos::ALL, Kokkos::ALL, Kokkos::ALL); return(arr3D); } else if(arrayType==Device3D) { - IdefixHostArray3D arr3D = Kokkos::create_mirror(d3Darray); + IdefixHostArray3D arr3D = Kokkos::create_mirror(Kokkos::HostSpace(), d3Darray); Kokkos::deep_copy(arr3D,d3Darray); return(arr3D); } else if(arrayType==Device4D) { IdefixArray3D arrDev3D = Kokkos::subview( d4Darray, var, Kokkos::ALL, Kokkos::ALL, Kokkos::ALL); - IdefixHostArray3D arr3D = Kokkos::create_mirror(arrDev3D); + IdefixHostArray3D arr3D = Kokkos::create_mirror(Kokkos::HostSpace(), arrDev3D); Kokkos::deep_copy(arr3D,arrDev3D); return(arr3D); } else { diff --git a/src/utils/lookupTable.hpp b/src/utils/lookupTable.hpp index c54fdb602..72d13a838 100644 --- a/src/utils/lookupTable.hpp +++ b/src/utils/lookupTable.hpp @@ -183,10 +183,10 @@ LookupTable::LookupTable(std::vector filenames, this->offsetDev = IdefixArray1D ("Table_offset", kDim); this->dataDev = IdefixArray1D ("Table_data", dataVector.size()); - this->xinHost = Kokkos::create_mirror_view(this->xinDev); - this->dimensionsHost = Kokkos::create_mirror_view(this->dimensionsDev); - this->offsetHost = Kokkos::create_mirror_view(this->offsetDev); - this->dataHost = Kokkos::create_mirror_view(this->dataDev); + this->xinHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->xinDev); + this->dimensionsHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dimensionsDev); + this->offsetHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->offsetDev); + this->dataHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dataDev); // Copy data in memory for(uint64_t i = 0 ; i < dataVector.size() ; i++) { @@ -346,10 +346,10 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB this->offsetDev = IdefixArray1D ("Table_offset", kDim); this->dataDev = IdefixArray1D ("Table_data", size[0]*size[1]); - this->xinHost = Kokkos::create_mirror_view(this->xinDev); - this->dimensionsHost = Kokkos::create_mirror_view(this->dimensionsDev); - this->offsetHost = Kokkos::create_mirror_view(this->offsetDev); - this->dataHost = Kokkos::create_mirror_view(this->dataDev); + this->xinHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->xinDev); + this->dimensionsHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dimensionsDev); + this->offsetHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->offsetDev); + this->dataHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dataDev); // Fill the arrays with the std::vector content if(idfx::prank == 0) { @@ -458,10 +458,10 @@ LookupTable::LookupTable(Kokkos::View array, this->offsetDev = IdefixArray1D ("Table_offset", kDim); this->dataDev = IdefixArray1D ("Table_data", sizeTotal); - this->xinHost = Kokkos::create_mirror_view(this->xinDev); - this->dimensionsHost = Kokkos::create_mirror_view(this->dimensionsDev); - this->offsetHost = Kokkos::create_mirror_view(this->offsetDev); - this->dataHost = Kokkos::create_mirror_view(this->dataDev); + this->xinHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->xinDev); + this->dimensionsHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dimensionsDev); + this->offsetHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->offsetDev); + this->dataHost = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->dataDev); // Copy data in memory for(uint64_t n = 0 ; n < sizeTotal ; n++) { From e53bc2061bc497550e6965720528b9a7d63a16a8 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 20 Jan 2026 16:34:14 +0100 Subject: [PATCH 091/144] Add vector potentiel to pydefix (#361) * add vector potential indices to pydefix --- src/output/dump.cpp | 2 +- src/pydefix.cpp | 5 +++++ 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/src/output/dump.cpp b/src/output/dump.cpp index 955e06e72..96a40b548 100644 --- a/src/output/dump.cpp +++ b/src/output/dump.cpp @@ -71,7 +71,7 @@ void Dump::CreateMPIDataType(GridBox gb, bool read) { int size[3]; int subsize[3]; - // the grid is required to now the current MPÏ domain decomposition + // the grid is required to know the current MPÏ domain decomposition Grid *grid = data->mygrid; // Dimensions for cell-centered fields diff --git a/src/pydefix.cpp b/src/pydefix.cpp index f0d8bc784..1f156185d 100644 --- a/src/pydefix.cpp +++ b/src/pydefix.cpp @@ -228,6 +228,11 @@ PYBIND11_EMBEDDED_MODULE(pydefix, m) { m.attr("BX1s") = BX1s; , m.attr("BX2s") = BX2s; , m.attr("BX3s") = BX3s; ) + #ifdef EVOLVE_VECTOR_POTENTIAL + m.attr("AX1e") = AX1e; + m.attr("AX2e") = AX2e; + m.attr("AX3e") = AX3e; + #endif #endif m.attr("IDIR") = IDIR; m.attr("JDIR") = JDIR; From d83d694bf2f3104c0a16cf15bdf057e71fd2cf17 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 21 Jan 2026 10:21:06 +0100 Subject: [PATCH 092/144] fix incorrect subviews when using vector_potential in 2.5D (#362) * fix incorrect subviews when using vector_potential in 2.5D --- .../enforceVectorPotentialBoundary.hpp | 34 ++++++++++++------- 1 file changed, 21 insertions(+), 13 deletions(-) diff --git a/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp index fea9b47b9..3019edfd8 100644 --- a/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp +++ b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp @@ -13,23 +13,31 @@ template void ConstrainedTransport::EnforceVectorPotentialBoundary(IdefixArray4D &Vein) { idfx::pushRegion("Emf::EnforceVectorPotentialBoundary"); - auto Ax1 = Kokkos::subview(Vein, IDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); - auto Ax2 = Kokkos::subview(Vein, JDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); - auto Ax3 = Kokkos::subview(Vein, KDIR, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); - if(this->hydro->haveAxis) { - this->hydro->boundary->axis->RegularizeEMFs(Ax1, Ax2, Ax3); - } + IdefixArray3D Ax1, Ax2, Ax3; - #ifdef ENFORCE_EMF_CONSISTENCY - #ifdef WITH_MPI - // This average the vector potential at the domain surface with immediate neighbours - // to ensure the vector potentials exactly match + #ifdef EVOLVE_VECTOR_POTENTIAL + #if DIMENSIONS == 3 + Ax1 = Kokkos::subview(Vein, AX1e, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + Ax2 = Kokkos::subview(Vein, AX2e, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + #endif + Ax3 = Kokkos::subview(Vein, AX3e, Kokkos::ALL(), Kokkos::ALL(), Kokkos::ALL()); + + + if(this->hydro->haveAxis) { + this->hydro->boundary->axis->RegularizeEMFs(Ax1, Ax2, Ax3); + } + + #ifdef ENFORCE_EMF_CONSISTENCY + #ifdef WITH_MPI + // This average the vector potential at the domain surface with immediate neighbours + // to ensure the vector potentials exactly match - this->ExchangeAll(Ax1, Ax2, Ax3); + this->ExchangeAll(Ax1, Ax2, Ax3); + #endif + EnforceEMFBoundaryPeriodic(Ax1, Ax2, Ax3); #endif - EnforceEMFBoundaryPeriodic(Ax1, Ax2, Ax3); - #endif + #endif // EVOLVE_VECTOR_POTENTIAL idfx::popRegion(); } From 56189c96ff9ffe877c9350957033a39076eb40f9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Mon, 2 Mar 2026 08:09:23 +0100 Subject: [PATCH 093/144] Usage of ccache in the test suite (#364) * test: add -cache option to the test script to accelerate the build * build: Add option -DIdefix_PROBLEM_DIR to allow using the standard out-of-source build way of cmake --------- Co-authored-by: Geoffroy Lesur --- .github/workflows/idefix-ci.yml | 4 ++-- CMakeLists.txt | 21 +++++++++++--------- doc/source/reference/makefile.rst | 6 ++++++ pytools/idfx_test.py | 32 +++++++++++++++++++++++++++---- 4 files changed, 48 insertions(+), 15 deletions(-) diff --git a/.github/workflows/idefix-ci.yml b/.github/workflows/idefix-ci.yml index cb9461431..f0050b36a 100644 --- a/.github/workflows/idefix-ci.yml +++ b/.github/workflows/idefix-ci.yml @@ -28,7 +28,7 @@ jobs: name: CPU Jobs (intel OneApi) uses: ./.github/workflows/idefix-ci-jobs.yml with: - TESTME_OPTIONS: -intel -Werror + TESTME_OPTIONS: -intel -Werror -ccache IDEFIX_COMPILER: icc gcc-jobs: @@ -36,7 +36,7 @@ jobs: name: CPU Jobs (gcc) uses: ./.github/workflows/idefix-ci-jobs.yml with: - TESTME_OPTIONS: -Werror + TESTME_OPTIONS: -Werror -ccache IDEFIX_COMPILER: gcc cuda-jobs: diff --git a/CMakeLists.txt b/CMakeLists.txt index a7c856ddd..f4a647fe8 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -16,6 +16,7 @@ option(Idefix_DEBUG "Enable Idefix debug features (makes the code very slow)" OF option(Idefix_RUNTIME_CHECKS "Enable runtime sanity checks" OFF) option(Idefix_WERROR "Treat compiler warnings as errors" OFF) option(Idefix_PYTHON "Enable python bindings (requires pybind11)" OFF) +set(Idefix_PROBLEM_DIR "${CMAKE_BINARY_DIR}" CACHE STRING "Problem directory to build for.") set(Idefix_CXX_FLAGS "" CACHE STRING "Additional compiler/linker flag") set(Idefix_DEFS "definitions.hpp" CACHE FILEPATH "Problem definition header file") option(Idefix_CUSTOM_EOS "Use custom equation of state" OFF) @@ -34,7 +35,6 @@ set_property(CACHE Idefix_PRECISION PROPERTY STRINGS Double Single) set(Idefix_LOOP_PATTERN "Default" CACHE STRING "Loop pattern for idefix_for") set_property(CACHE Idefix_LOOP_PATTERN PROPERTY STRINGS Default SIMD Range MDRange TeamPolicy TeamPolicyInnerVector) - # load git revision tools list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake/") include(GetGitRevisionDescription) @@ -51,7 +51,7 @@ if(Kokkos_ENABLE_CUDA) endif() # Add kokkos CMAKE files (required early since these set compiler options) -add_subdirectory(src/kokkos build/kokkos) +add_subdirectory(src/kokkos ${CMAKE_BINARY_DIR}/build/kokkos) include_directories(${Kokkos_INCLUDE_DIRS_RET}) # Add Idefix CXX Flags @@ -75,20 +75,22 @@ endif() add_executable(idefix) add_subdirectory(src build) -if(EXISTS ${PROJECT_BINARY_DIR}/setup.cpp) - target_sources(idefix PUBLIC ${PROJECT_BINARY_DIR}/setup.cpp) +# make absolute +get_filename_component(Idefix_PROBLEM_DIR_ABS ${Idefix_PROBLEM_DIR} ABSOLUTE BASE_DIR ${PROJECT_BINARY_DIR}) + +if(EXISTS ${Idefix_PROBLEM_DIR_ABS}/setup.cpp) + target_sources(idefix PUBLIC ${Idefix_PROBLEM_DIR_ABS}/setup.cpp) else() message(WARNING "No specific setup.cpp found in the problem directory (this message can be ignored if using python to define your problem)") endif() # If a CMakeLists.txt is in the problem dir (for problem-specific source files) # then read it -if(EXISTS ${PROJECT_BINARY_DIR}/CMakeLists.txt) - message(STATUS "Including problem-specific CMakeLists in '${PROJECT_BINARY_DIR}'") - add_subdirectory(${PROJECT_BINARY_DIR} build/setup) +if(EXISTS ${Idefix_PROBLEM_DIR_ABS}/CMakeLists.txt) + message(STATUS "Including problem-specific CMakeLists in '${Idefix_PROBLEM_DIR_ABS}'") + add_subdirectory(${Idefix_PROBLEM_DIR_ABS} build/setup) endif() - if(Idefix_MHD) add_compile_definitions("MHD=YES") else() @@ -210,7 +212,7 @@ if(${Idefix_PRECISION} STREQUAL "Single") endif() target_include_directories(idefix PUBLIC - "${PROJECT_BINARY_DIR}" + "${Idefix_PROBLEM_DIR_ABS}" ) target_include_directories(idefix PUBLIC src/kokkos/core/src @@ -249,6 +251,7 @@ message(STATUS " Python: ${Idefix_PYTHON}") message(STATUS " Reconstruction: ${Idefix_RECONSTRUCTION}") message(STATUS " Precision: ${Idefix_PRECISION}") message(STATUS " Version: ${Idefix_VERSION}") +message(STATUS " Problem directory: '${Idefix_PROBLEM_DIR}'") message(STATUS " Problem definitions: '${Idefix_DEFS}'") if(Idefix_CUSTOM_EOS) message(STATUS " EOS: Custom file '${Idefix_CUSTOM_EOS_FILE}'") diff --git a/doc/source/reference/makefile.rst b/doc/source/reference/makefile.rst index 23052d92c..8f58ceedb 100644 --- a/doc/source/reference/makefile.rst +++ b/doc/source/reference/makefile.rst @@ -59,6 +59,12 @@ Several options can be enabled from the command line (or are accessible with ``c The number of ghost cells is automatically adjusted as a function of the order of the reconstruction scheme. *Idefix* uses 2 ghost cells when ``ORDER < 4`` and 3 ghost cells when ``ORDER = 4`` +``-D Idefix_PROBLEM_DIR=.`` + Specify where to find the problem directory to build *Idefix* out of source. + Place yourself in the ``build`` directory you want to build in and call the ``cmake`` by : + + pointing the *Idefix* source directory via ``IDEFIX_DIR`` as usual. + + using ``-D Idefix_PROBLEM_DIR`` to point the problem to build. + ``-D Kokkos_ENABLE_OPENMP=ON`` Enable OpenMP parallelisation on supported compilers. Note that this can be enabled simultaneously with MPI, resulting in a hybrid MPI+OpenMP compilation. diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index 25bac76b4..fed74a22e 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -99,6 +99,9 @@ def __init__ (self): help="Consider warnings as errors", action="store_true") + parser.add_argument("-ccache", + help="Use ccache to reduce the build time over multiple run of the test suite.", + action="store_true") args, unknown=parser.parse_known_args() @@ -107,11 +110,19 @@ def __init__ (self): self.referenceDirectory = os.path.join(idefix_dir_env,"reference") # current directory relative to $IDEFIX_DIR/test (used to retrieve the path ot reference files) self.testDir=os.path.relpath(os.curdir,os.path.join(idefix_dir_env,"test")) + # build directory, currently inside the test named build-test + self.buildDir=os.path.abspath("./build-test") + # store the full path of problem directory + self.problemDir=os.path.abspath("./") def configure(self,definitionFile=""): comm=["cmake"] # add source directory comm.append(self.idefixDir) + + # we will build in ./build-test so problem dir is parent + comm.append("-DIdefix_PROBLEM_DIR="+self.problemDir) + # add specific options for opt in self.cmake: comm.append("-D"+opt) @@ -155,7 +166,7 @@ def configure(self,definitionFile=""): else: self.definitions="definitions.hpp" - comm.append("-DIdefix_DEFS="+self.definitions) + comm.append("-DIdefix_DEFS="+os.path.join(self.problemDir, self.definitions)) if(self.mpi): comm.append("-DIdefix_MPI=ON") @@ -169,9 +180,16 @@ def configure(self,definitionFile=""): elif(self.reconstruction==4): comm.append("-DIdefix_RECONSTRUCTION=Parabolic") + # export ccache env + if self.ccache: + comm.append("-DCMAKE_CXX_COMPILER_LAUNCHER=ccache") try: - cmake=subprocess.run(comm) + # clean before configuring again + self.clean() + + # call cmake + cmake=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) cmake.check_returncode() except subprocess.CalledProcessError as e: print(bcolors.FAIL+"***************************************************") @@ -179,9 +197,15 @@ def configure(self,definitionFile=""): print("***************************************************"+bcolors.ENDC) raise e + def clean(self): + # remove the build directory before re-creating it + if os.path.exists(self.buildDir): + shutil.rmtree(self.buildDir) + os.makedirs(self.buildDir, exist_ok=False) + def compile(self,jobs=8): try: - make=subprocess.run(["make","-j"+str(jobs)]) + make=subprocess.run(["make","-j"+str(jobs)], cwd=os.path.abspath(self.buildDir)) make.check_returncode() except subprocess.CalledProcessError as e: print(bcolors.FAIL+"***************************************************") @@ -190,7 +214,7 @@ def compile(self,jobs=8): raise e def run(self, inputFile="", np=2, nowrite=False, restart=-1): - comm=["./idefix"] + comm=[os.path.join(self.buildDir,"idefix")] if inputFile: comm.append("-i") comm.append(inputFile) From 8300404c1e4cd908ca125c0a896f230b98e47e3f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 10 Mar 2026 16:20:14 +0100 Subject: [PATCH 094/144] fix UCT HLLD when using DIMENSIONS &aR, const IdefixArray3D &dL, const IdefixArray3D &dR) { - EXPAND( const int Xn = DIR+MX1; , - const int Xt = (DIR == IDIR ? MX2 : MX1); , - const int Xb = (DIR == KDIR ? MX2 : MX3); ) + EXPAND( const int Xn = DIR+MX1; , + const int Xt = (DIR == IDIR ? MX2 : MX1); , + [[maybe_unused]] const int Xb = (DIR == KDIR ? MX2 : MX3); ) // Compute magnetic pressure [[maybe_unused]] real ptR, ptL; @@ -201,7 +201,7 @@ KOKKOS_FORCEINLINE_FUNCTION void K_StoreHLLD( const int i, const int j, const in } #if COMPONENTS > 1 - EXPAND( Et(k,j,i) = -st*(ar*vL[Xt] - al*vR[Xt])*scrh; , + D_EXPAND( Et(k,j,i) = -st*(ar*vL[Xt] - al*vR[Xt])*scrh; , , Eb(k,j,i) = -sb*(ar*vL[Xb] - al*vR[Xb])*scrh; ); #endif From df60d144b6fbc7f423d6fa9d4626c9567474f7a9 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 26 Mar 2026 07:05:10 +0100 Subject: [PATCH 095/144] Fix div(B) check (#369) --- src/fluid/checkDivB.hpp | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-) diff --git a/src/fluid/checkDivB.hpp b/src/fluid/checkDivB.hpp index c78f6b3e0..6e47d4c8c 100644 --- a/src/fluid/checkDivB.hpp +++ b/src/fluid/checkDivB.hpp @@ -31,12 +31,9 @@ real Fluid::CheckDivB() { KOKKOS_LAMBDA (int k, int j, int i, real &divBmax) { [[maybe_unused]] real dB1,dB2,dB3; [[maybe_unused]] real d1, d2, d3; - [[maybe_unused]] real B1,B2,B3; dB1=dB2=dB3=ZERO_F; d1=d2=d3=ZERO_F; - B1=B2=B3=ZERO_F; - D_EXPAND( dB1=(Ax1(k,j,i+1)*Vs(BX1s,k,j,i+1)-Ax1(k,j,i)*Vs(BX1s,k,j,i)); , dB2=(Ax2(k,j+1,i)*Vs(BX2s,k,j+1,i)-Ax2(k,j,i)*Vs(BX2s,k,j,i)); , @@ -46,12 +43,8 @@ real Fluid::CheckDivB() { d2=0.5*(Ax2(k,j+1,i) + Ax2(k,j,i)); , d3=0.5*(Ax3(k+1,j,i) + Ax3(k,j,i)); ) - D_EXPAND( B1=0.5*(Vs(BX1s,k,j,i+1) + Vs(BX1s,k,j,i)); , - B2=0.5*(Vs(BX2s,k,j+1,i) + Vs(BX2s,k,j,i)); , - B3=0.5*(Vs(BX3s,k+1,j,i) + Vs(BX3s,k,j,i)); ) - real amplitude = 1e-40; - amplitude += D_EXPAND( std::fabs(B1)*d1, + std::fabs(B2)*d2, + std::fabs(B3)*d3 ); + const real amplitude = D_EXPAND( d1, + d2, + d3 ); divBmax=FMAX(FABS(D_EXPAND(dB1, +dB2, +dB3))/amplitude,divBmax); }, From 8171c32eef037fca409bfeff5ed46f9498dda4bb Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 26 Mar 2026 08:58:27 +0100 Subject: [PATCH 096/144] Reorganise tests (#367) * move xdmf test in a dedicated directory * do not use xdmf in sedov test * move dump checks in a dedicated directory * add back sedov and IO tests to github actions * add back the linear wave test, and fix tolerance * Hard code pybind11 venv path from cmake --- .github/workflows/idefix-ci-jobs.yml | 27 +- CMakeLists.txt | 18 +- reference | 2 +- src/output/xdmf.cpp | 14 +- src/pydefix.cpp | 7 +- src/setup.cpp | 4 +- test/HD/SedovBlastWave/idefix.ini | 5 +- test/IO/dump/CMakeLists.txt | 1 + test/IO/dump/definitions.hpp | 5 + .../dump/idefix.ini} | 0 test/IO/dump/setup.cpp | 277 ++++++++++++++++++ test/IO/dump/testme.py | 59 ++++ test/IO/pydefix/idefix.ini | 3 +- test/IO/pydefix/python_requirements.txt | 3 +- test/IO/pydefix/testme.py | 41 +++ .../SedovBlastWave => IO/xdmf}/CMakeLists.txt | 1 + test/IO/xdmf/definitions.hpp | 5 + test/IO/xdmf/idefix.ini | 26 ++ test/IO/xdmf/setup.cpp | 75 +++++ test/IO/xdmf/testme.py | 45 +++ test/MHD/LinearWaveTest/idefix-entropy.ini | 2 +- test/MHD/LinearWaveTest/testme.py | 2 +- test/MHD/OrszagTang3D/setup.cpp | 190 ------------ test/MHD/OrszagTang3D/testme.py | 6 - 24 files changed, 602 insertions(+), 216 deletions(-) create mode 100644 test/IO/dump/CMakeLists.txt create mode 100644 test/IO/dump/definitions.hpp rename test/{MHD/OrszagTang3D/idefix-checkrestart.ini => IO/dump/idefix.ini} (100%) create mode 100644 test/IO/dump/setup.cpp create mode 100755 test/IO/dump/testme.py create mode 100755 test/IO/pydefix/testme.py rename test/{HD/SedovBlastWave => IO/xdmf}/CMakeLists.txt (50%) create mode 100644 test/IO/xdmf/definitions.hpp create mode 100644 test/IO/xdmf/idefix.ini create mode 100644 test/IO/xdmf/setup.cpp create mode 100755 test/IO/xdmf/testme.py diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index 275ea1ce2..734390db2 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -21,6 +21,7 @@ env: PYTHONPATH: ${{ github.workspace }} IDEFIX_DIR: ${{ github.workspace }} + jobs: ShocksHydro: runs-on: self-hosted @@ -35,6 +36,8 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/sod-iso -all $TESTME_OPTIONS - name: Mach reflection test run: scripts/ci/run-tests $IDEFIX_DIR/test/HD//MachReflection -all $TESTME_OPTIONS + - name: Sedov blast wave + run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/SedovBlastWave -all $TESTME_OPTIONS ParabolicHydro: runs-on: self-hosted @@ -63,8 +66,10 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/sod-iso -all $TESTME_OPTIONS - name: Orszag Tang run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/OrszagTang -all $TESTME_OPTIONS - - name: Orszag Tang 3D+restart tests + - name: Orszag Tang 3D run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/OrszagTang3D -all $TESTME_OPTIONS + - name: Linear wave test + run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/LinearWaveTest -all $TESTME_OPTIONS - name: Axis Flux tube run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/AxisFluxTube -all $TESTME_OPTIONS @@ -207,3 +212,23 @@ jobs: run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/dumpImage -all $TESTME_OPTIONS - name: Column density run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/columnDensity -all $TESTME_OPTIONS + + IOs: + needs: [Fargo, Dust, Planet, ShearingBox, SelfGravity] + runs-on: self-hosted + steps: + - name: Check out repo + uses: actions/checkout@v3 + with: + submodules: recursive + - name: Restart dumps + run: scripts/ci/run-tests $IDEFIX_DIR/test/IO/dump -all $TESTME_OPTIONS + - name: Pydefix + run: | + python3 -m venv $IDEFIX_DIR/test/IO/pydefix/env + source $IDEFIX_DIR/test/IO/pydefix/env/bin/activate + python3 -m pip install -r $IDEFIX_DIR/test/IO/pydefix/python_requirements.txt + scripts/ci/run-tests $IDEFIX_DIR/test/IO/pydefix -all $TESTME_OPTIONS + + - name: xdmf + run: scripts/ci/run-tests $IDEFIX_DIR/test/IO/xdmf -all $TESTME_OPTIONS diff --git a/CMakeLists.txt b/CMakeLists.txt index f4a647fe8..ea4a71537 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -115,7 +115,13 @@ if(Idefix_HDF5) ) find_package(HDF5 REQUIRED) target_link_libraries(idefix "${HDF5_LIBRARIES}") - target_include_directories(idefix "${HDF5_INCLUDE_DIRS}") + message(STATUS "Found HDF5 include directories: ${HDF5_INCLUDE_DIRS}") + target_include_directories(idefix PUBLIC "${HDF5_INCLUDE_DIRS}") + if(Idefix_MPI) + if(NOT HDF5_IS_PARALLEL) + message(FATAL_ERROR "Parallel HDF5 required for Idefix_MPI but the found HDF5 library does not support it") + endif() + endif() message(STATUS "XDMF (hdf5+xmf) dumps enabled") else() set(Idefix_HDF5 OFF) @@ -123,6 +129,16 @@ endif() if(Idefix_PYTHON) add_compile_definitions("WITH_PYTHON") + find_package(Python3 REQUIRED COMPONENTS Interpreter Development) + + execute_process( + COMMAND "${Python3_EXECUTABLE}" -m pybind11 --cmakedir + OUTPUT_VARIABLE PYBIND11_CMAKE_DIR + OUTPUT_STRIP_TRAILING_WHITESPACE + COMMAND_ERROR_IS_FATAL ANY + ) + + list(APPEND CMAKE_PREFIX_PATH "${PYBIND11_CMAKE_DIR}") if (NOT DEFINED Python_FIND_FRAMEWORK) set(Python_FIND_FRAMEWORK "LAST") # Use Apple's python only at last resort on Macos endif () diff --git a/reference b/reference index 1028989b3..32499c14c 160000 --- a/reference +++ b/reference @@ -1 +1 @@ -Subproject commit 1028989b3847200da9b54ed74df0d5c0b0d13045 +Subproject commit 32499c14cfacd05e1c9499bd23198a53c416c3c2 diff --git a/src/output/xdmf.cpp b/src/output/xdmf.cpp index 23ddaa03a..4e7ff6843 100644 --- a/src/output/xdmf.cpp +++ b/src/output/xdmf.cpp @@ -286,18 +286,18 @@ int Xdmf::Write() { idfx::pushRegion("Xdmf::Write"); fs::path filename; fs::path filename_xmf; - hid_t err; + [[maybe_unused]] hid_t err; idfx::cout << "Xdmf: Write file n " << xdmfFileNumber << "..." << std::flush; timer.reset(); // Create a copy of the dataBlock on Host, and sync it. #if DIMENSIONS == 1 - int tot_dim = 1; + [[maybe_unused]] int tot_dim = 1; #elif DIMENSIONS == 2 int tot_dim = 2; #elif DIMENSIONS == 3 - int tot_dim = 3; + [[maybe_unused]] int tot_dim = 3; #endif std::stringstream ssfileName, ssfileNameXmf, ssxdmfFileNum; @@ -344,7 +344,8 @@ int Xdmf::Write() { #endif // Layout of the field data in memory - hsize_t field_data_size[3], field_data_start[3], field_data_subsize[3], stride[3]; + [[maybe_unused]] hsize_t field_data_size[3], field_data_start[3]; + [[maybe_unused]] hsize_t field_data_subsize[3], stride[3]; #ifdef WITH_MPI for(int dir = 0; dir < 3 ; dir++) { field_data_size[dir] = static_cast(this->mpi_data_size[dir]); @@ -454,11 +455,10 @@ void Xdmf::WriteHeader( hid_t tspace, tattr; hid_t unit_info, unit_attr; hid_t group; - hid_t file_access = 0; #ifdef WITH_MPI hid_t plist_id_mpiio = 0; /* for collective MPI I/O */ #endif - hid_t err; + [[maybe_unused]] hid_t err; hsize_t dimstr; @@ -814,7 +814,7 @@ void Xdmf::WriteScalar( dataset_name = var_name.c_str(); std::string dataset_label = dataset_name.c_str(); std::transform(dataset_label.begin(), dataset_label.end(), dataset_label.begin(), ::tolower); - hid_t err, dataset; + [[maybe_unused]] hid_t err, dataset; // We define the dataset that contain the fields. diff --git a/src/pydefix.cpp b/src/pydefix.cpp index 1f156185d..1b8168088 100644 --- a/src/pydefix.cpp +++ b/src/pydefix.cpp @@ -68,7 +68,7 @@ py::array_t GatherIdefixArray(IdefixHostArray3D // np_int: size that should be copied into global // beg: offset in the incoming array where copy should begin // gbeg: offset in the global array where copy should be begin - std::array np_int,np_tot, beg, gbeg; + [[maybe_unused]] std::array np_int,np_tot, beg, gbeg; IdefixHostArray3D buf; if(rank==0) { @@ -127,7 +127,7 @@ py::array_t GatherIdefixArray(IdefixHostArray3D }// End loop on target rank for root process } else { // MPI prank >0 std::array np_int = dataHost.np_int; - std::array np_tot = dataHost.np_tot; + [[maybe_unused]] std::array np_tot = dataHost.np_tot; std::array gbeg = dataHost.gbeg; std::array beg = dataHost.beg; @@ -278,6 +278,9 @@ Pydefix::Pydefix(Input &input) { idfx::cout << "Pydefix: start Python interpreter." << std::endl; py::initialize_interpreter(); + py::exec("import sys; print(f'Pydefix: Python Version: {sys.version}')"); + py::exec("print(f'Pydefix: Executable Path: {sys.executable}')"); + py::exec("print(f'Pydefix: Sys Path: {sys.path}')"); } this->scriptFilename = input.Get("Python","script",0); if(scriptFilename.substr(scriptFilename.length() - 3, 3).compare(".py")==0) { diff --git a/src/setup.cpp b/src/setup.cpp index 8c64f4447..b82f118f8 100644 --- a/src/setup.cpp +++ b/src/setup.cpp @@ -12,7 +12,9 @@ // own implementation of the constructor, initflow and destructor __attribute__((weak)) Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { - IDEFIX_WARNING("Caution, this is the default Setup constructor and it does nothing!"); + #ifndef WITH_PYTHON + IDEFIX_WARNING("Caution, this is the default Setup constructor and it does nothing!"); + #endif } __attribute__((weak)) void Setup::InitFlow(DataBlock &data) { diff --git a/test/HD/SedovBlastWave/idefix.ini b/test/HD/SedovBlastWave/idefix.ini index 51122521c..107b719cd 100644 --- a/test/HD/SedovBlastWave/idefix.ini +++ b/test/HD/SedovBlastWave/idefix.ini @@ -25,6 +25,5 @@ X3-beg periodic X3-end periodic [Output] -vtk 0.1 -xdmf 0.1 -dmp 0.1 +vtk 0.1 +dmp 0.1 diff --git a/test/IO/dump/CMakeLists.txt b/test/IO/dump/CMakeLists.txt new file mode 100644 index 000000000..629aed2d1 --- /dev/null +++ b/test/IO/dump/CMakeLists.txt @@ -0,0 +1 @@ +enable_idefix_property(Idefix_MHD) diff --git a/test/IO/dump/definitions.hpp b/test/IO/dump/definitions.hpp new file mode 100644 index 000000000..a854ad9e3 --- /dev/null +++ b/test/IO/dump/definitions.hpp @@ -0,0 +1,5 @@ +#define COMPONENTS 3 +#define DIMENSIONS 3 +//#define DEBUG + +#define GEOMETRY CARTESIAN diff --git a/test/MHD/OrszagTang3D/idefix-checkrestart.ini b/test/IO/dump/idefix.ini similarity index 100% rename from test/MHD/OrszagTang3D/idefix-checkrestart.ini rename to test/IO/dump/idefix.ini diff --git a/test/IO/dump/setup.cpp b/test/IO/dump/setup.cpp new file mode 100644 index 000000000..1db56f5b0 --- /dev/null +++ b/test/IO/dump/setup.cpp @@ -0,0 +1,277 @@ +#include "idefix.hpp" +#include "setup.hpp" + +/*********************************************/ +/** +Customized random number generator +Allow one to have consistent random numbers +generators on different architectures. +**/ +/*********************************************/ + +Output* myOutput; +int outnum; +// Analysis function +// This analysis checks that the restart routines are performing as they should +void Analysis(DataBlock& data) { + + + idfx::cout << "Analysis: Checking restart routines" << std::endl; + + // Trigger dump creation + // data.SetBoundaries(); + myOutput->ForceWriteDump(data); + + // Mirror data on Host + DataBlockHost d(data); + + // Sync it + d.SyncFromDevice(); + + // Create local arrays to store the current physical state + IdefixHostArray4D myVc = IdefixHostArray4D("myVc", d.Vc.extent(0), data.np_tot[KDIR], data.np_tot[JDIR],data.np_tot[IDIR]); + IdefixHostArray4D myVs = IdefixHostArray4D("myVs", DIMENSIONS, data.np_tot[KDIR]+KOFFSET, data.np_tot[JDIR]+JOFFSET,data.np_tot[IDIR]+IOFFSET); + #ifdef EVOLVE_VECTOR_POTENTIAL + IdefixHostArray4D myVe = IdefixHostArray4D("myVe", AX3e+1, data.np_tot[KDIR]+KOFFSET, data.np_tot[JDIR]+JOFFSET,data.np_tot[IDIR]+IOFFSET); + #endif + // Transfer the datablock to myVc and myVs + for(int n = 0; n < d.Vc.extent(0) ; n++) { + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + myVc(n,k,j,i) = d.Vc(n,k,j,i); + d.Vc(n,k,j,i) = 0.0; + + } + } + } + } + + for(int n = 0; n < DIMENSIONS ; n++) { + for(int k = 0; k < d.np_tot[KDIR] + KOFFSET; k++) { + for(int j = 0; j < d.np_tot[JDIR] + JOFFSET; j++) { + for(int i = 0; i < d.np_tot[IDIR] + IOFFSET; i++) { + myVs(n,k,j,i) = d.Vs(n,k,j,i); + d.Vs(n,k,j,i) = 0.0; + } + } + } + } + #ifdef EVOLVE_VECTOR_POTENTIAL + for(int n = 0; n < AX3e+1 ; n++) { + for(int k = 0; k < d.np_tot[KDIR] + KOFFSET; k++) { + for(int j = 0; j < d.np_tot[JDIR] + JOFFSET; j++) { + for(int i = 0; i < d.np_tot[IDIR] + IOFFSET; i++) { + myVe(n,k,j,i) = d.Ve(n,k,j,i); + d.Ve(n,k,j,i) = 0.0; + } + } + } + } + #endif + + // Push our datablockHost to erase everything + d.SyncToDevice(); + // From this point, the dataBlock is full of zeros + + // Load back the restart dump + myOutput->RestartFromDump(data, outnum); + data.SetBoundaries(); + #ifdef EVOLVE_VECTOR_POTENTIAL + data.hydro->emf->ComputeMagFieldFromA(data.hydro->Ve, data.hydro->Vs); + #endif + d.SyncFromDevice(); + + // increment outnum + outnum++; + int errornum; + + errornum = 0; + idfx::cout << "Analysis: checking consistency" << std::endl; + // Check that the save/load routines have left everything unchanged. + for(int n = 0; n < d.Vc.extent(0) ; n++) { + for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { + if(myVc(n,k,j,i) != d.Vc(n,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Vc at (i,j,k,n) = ( " << i << ", " << j << ", " << k << ", " << n << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl + << "Original= " << myVc(n,k,j,i) << " New=" << d.Vc(n,k,j,i) << " diff=" << myVc(n,k,j,i)-d.Vc(n,k,j,i) << std::endl; + } + + } + } + } + } + + for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { + if(myVs(BX1s,k,j,i) != d.Vs(BX1s,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Vs(BX1s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl + << "Original= " << myVs(BX1s,k,j,i) << " New=" << d.Vs(BX1s,k,j,i) << " diff=" << myVs(BX1s,k,j,i)-d.Vs(BX1s,k,j,i) << std::endl; + + } + + } + } + } + for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { + if(myVs(BX2s,k,j,i) != d.Vs(BX2s,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Vs(BX2s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; + } + + } + } + } + for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { + if(myVs(BX3s,k,j,i) != d.Vs(BX3s,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Vs(BX3s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl + << "Original= " << myVs(BX3s,k,j,i) << " New=" << d.Vs(BX3s,k,j,i) << " diff=" << myVs(BX3s,k,j,i)-d.Vs(BX3s,k,j,i) << std::endl; + } + + } + } + } +#ifdef EVOLVE_VECTOR_POTENTIAL + for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { + if(myVe(AX1e,k,j,i) != d.Ve(AX1e,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Ve(AX1e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; + + } + + } + } + } + for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { + if(myVe(AX2e,k,j,i) != d.Ve(AX2e,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Ve(AX2e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; + } + + } + } + } + for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { + for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { + for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { + if(myVe(AX3e,k,j,i) != d.Ve(AX3e,k,j,i)) { + errornum++; + idfx::cout << "-----------------------------------------" << std::endl + << " Error in Ve(AX3e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl + << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl + << "Original= " << myVs(BX3s,k,j,i) << " New=" << d.Vs(BX3s,k,j,i) << " diff=" << myVs(BX3s,k,j,i)-d.Vs(BX3s,k,j,i) << std::endl; + } + + } + } + } +#endif + + idfx::cout << "Analysis: consistency check done with " << errornum << " errors " << std::endl; + if(errornum>0) { + IDEFIX_ERROR("Restart from dump failed validation"); + } +} + +// Initialisation routine. Can be used to allocate +// Arrays or variables which are used later on +Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { + if(input.CheckEntry("Output","analysis")>0) { + output.EnrollAnalysis(&Analysis); + myOutput = &output; + outnum=0; + } +} + +// This routine initialize the flow +// Note that data is on the device. +// One can therefore define locally +// a datahost and sync it, if needed +void Setup::InitFlow(DataBlock &data) { + // Create a host copy + DataBlockHost d(data); + real x,y,z; + IdefixHostArray4D Ve; + + #ifndef EVOLVE_VECTOR_POTENTIAL + Ve = IdefixHostArray4D("Potential vector",3, d.np_tot[KDIR]+1, d.np_tot[JDIR]+1, d.np_tot[IDIR]+1); + #else + Ve = d.Ve; + #endif + + bool haveTracer = data.hydro->haveTracer; + + real B0=1.0/sqrt(4.0*M_PI); + + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + x=d.x[IDIR](i); + y=d.x[JDIR](j); + z=d.x[KDIR](k); + + d.Vc(RHO,k,j,i) = 25.0/(36.0*M_PI); + d.Vc(PRS,k,j,i) = 5.0/(12.0*M_PI); + d.Vc(VX1,k,j,i) = -sin(2.0*M_PI*y); + d.Vc(VX2,k,j,i) = sin(2.0*M_PI*x)+cos(2.0*M_PI*z); + d.Vc(VX3,k,j,i) = cos(2.0*M_PI*x); + + real xl=d.xl[IDIR](i); + real yl=d.xl[JDIR](j); + real zl=d.xl[KDIR](k); + Ve(IDIR,k,j,i) = B0/(2.0*M_PI)*(cos(2.0*M_PI*yl)); + Ve(JDIR,k,j,i) = B0/(2.0*M_PI)*sin(2.0*M_PI*xl); + Ve(KDIR,k,j,i) = B0/(2.0*M_PI)*( + cos(2.0*M_PI*yl) + cos(4.0*M_PI*xl)/2.0); + + if(haveTracer) { + d.Vc(TRG ,k,j,i) = x>0.5? 1.0:0.0; + d.Vc(TRG+1,k,j,i) = z>0.5? 1.0:0.0; + } + } + } + } + + #ifndef EVOLVE_VECTOR_POTENTIAL + d.MakeVsFromAmag(Ve); + #endif + // Send it all, if needed + d.SyncToDevice(); +} + +// Analyse data to produce an output +void MakeAnalysis(DataBlock & data) { + +} + + + +// Do a specifically designed user step in the middle of the integration +void ComputeUserStep(DataBlock &data, real t, real dt) { + +} diff --git a/test/IO/dump/testme.py b/test/IO/dump/testme.py new file mode 100755 index 000000000..35affdba2 --- /dev/null +++ b/test/IO/dump/testme.py @@ -0,0 +1,59 @@ +#!/usr/bin/env python3 +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) + +import pytools.idfx_test as tst + +# Whether we should reset our reference run (only do that on purpose!) + +tolerance=1e-13 + +def testMe(test): + test.configure() + test.compile() + + # Check restarts + test.run("idefix.ini") + + +test=tst.idfxTest() + +# if no decomposition is specified, use that one +if not test.dec: + test.dec=["2","2","2"] + +if not test.all: + testMe(test) +else: + test.vectPot=False + test.reconstruction=2 + test.mpi=False + testMe(test) + # test in MPI mode + test.mpi=True + testMe(test) + + + # test with vector potential + test.mpi=False + test.vectPot=True + test.reconstruction=2 + testMe(test) + + test.mpi=True + testMe(test) + + # test with other precision + test.single=True + test.vectPot=False + test.reconstruction=2 + test.mpi=False + testMe(test) + # test in MPI mode + test.mpi=True + testMe(test) diff --git a/test/IO/pydefix/idefix.ini b/test/IO/pydefix/idefix.ini index 57fdcfc4a..3ee42ae3e 100644 --- a/test/IO/pydefix/idefix.ini +++ b/test/IO/pydefix/idefix.ini @@ -26,5 +26,6 @@ X3-beg outflow X3-end outflow [Output] -log 10 +log 100 python 0.02 +dmp 0.5 diff --git a/test/IO/pydefix/python_requirements.txt b/test/IO/pydefix/python_requirements.txt index 6afd3019b..9489d0889 100644 --- a/test/IO/pydefix/python_requirements.txt +++ b/test/IO/pydefix/python_requirements.txt @@ -1,6 +1,7 @@ # note: version requirements are indicative and tests # should be able to run with # older versions of our dependencies, though it is not guaranteed. +# minimally require last versions available for Python 2.7 numpy>=1.16.6 matplotlib>=2.2.5 -pybind11>=2.12.0 +pybind11>=2.10.0 diff --git a/test/IO/pydefix/testme.py b/test/IO/pydefix/testme.py new file mode 100755 index 000000000..0a3ad0432 --- /dev/null +++ b/test/IO/pydefix/testme.py @@ -0,0 +1,41 @@ +#!/usr/bin/env python3 + +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) + +import pytools.idfx_test as tst +tolerance=1e-12 +def testMe(test): + test.configure() + test.compile() + + test.run(inputFile="idefix.ini") + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + + test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tolerance) + + +test=tst.idfxTest() +if not test.dec: + test.dec=['2','2'] + +if not test.all: + if(test.check): + test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) + else: + testMe(test) +else: + test.noplot = True + test.vectPot = False + test.single=False + test.reconstruction=2 + test.mpi=False + testMe(test) + test.mpi=True + testMe(test) diff --git a/test/HD/SedovBlastWave/CMakeLists.txt b/test/IO/xdmf/CMakeLists.txt similarity index 50% rename from test/HD/SedovBlastWave/CMakeLists.txt rename to test/IO/xdmf/CMakeLists.txt index c4ae088b8..8ce9e0f4d 100644 --- a/test/HD/SedovBlastWave/CMakeLists.txt +++ b/test/IO/xdmf/CMakeLists.txt @@ -1 +1,2 @@ +enable_idefix_property(Idefix_MHD) enable_idefix_property(Idefix_HDF5) diff --git a/test/IO/xdmf/definitions.hpp b/test/IO/xdmf/definitions.hpp new file mode 100644 index 000000000..a854ad9e3 --- /dev/null +++ b/test/IO/xdmf/definitions.hpp @@ -0,0 +1,5 @@ +#define COMPONENTS 3 +#define DIMENSIONS 3 +//#define DEBUG + +#define GEOMETRY CARTESIAN diff --git a/test/IO/xdmf/idefix.ini b/test/IO/xdmf/idefix.ini new file mode 100644 index 000000000..250a24054 --- /dev/null +++ b/test/IO/xdmf/idefix.ini @@ -0,0 +1,26 @@ +[Grid] +X1-grid 1 0.0 32 u 1.0 +X2-grid 1 0.0 64 u 1.0 +X3-grid 1 0.0 32 u 1.0 + +[TimeIntegrator] +CFL 0.9 +tstop 0.2 +first_dt 1.e-4 +nstages 2 + +[Hydro] +solver hlld + +[Boundary] +X1-beg periodic +X1-end periodic +X2-beg periodic +X2-end periodic +X3-beg periodic +X3-end periodic + +[Output] +xdmf 0.2 +dmp 0.2 +log 10 diff --git a/test/IO/xdmf/setup.cpp b/test/IO/xdmf/setup.cpp new file mode 100644 index 000000000..8cc40857f --- /dev/null +++ b/test/IO/xdmf/setup.cpp @@ -0,0 +1,75 @@ +#include "idefix.hpp" +#include "setup.hpp" + +// Initialisation routine. Can be used to allocate +// Arrays or variables which are used later on +Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { +} + +// This routine initialize the flow +// Note that data is on the device. +// One can therefore define locally +// a datahost and sync it, if needed +void Setup::InitFlow(DataBlock &data) { + // Create a host copy + DataBlockHost d(data); + real x,y,z; + IdefixHostArray4D Ve; + + #ifndef EVOLVE_VECTOR_POTENTIAL + Ve = IdefixHostArray4D("Potential vector",3, d.np_tot[KDIR]+1, d.np_tot[JDIR]+1, d.np_tot[IDIR]+1); + #else + Ve = d.Ve; + #endif + + bool haveTracer = data.hydro->haveTracer; + + real B0=1.0/sqrt(4.0*M_PI); + + for(int k = 0; k < d.np_tot[KDIR] ; k++) { + for(int j = 0; j < d.np_tot[JDIR] ; j++) { + for(int i = 0; i < d.np_tot[IDIR] ; i++) { + x=d.x[IDIR](i); + y=d.x[JDIR](j); + z=d.x[KDIR](k); + + d.Vc(RHO,k,j,i) = 25.0/(36.0*M_PI); + d.Vc(PRS,k,j,i) = 5.0/(12.0*M_PI); + d.Vc(VX1,k,j,i) = -sin(2.0*M_PI*y); + d.Vc(VX2,k,j,i) = sin(2.0*M_PI*x)+cos(2.0*M_PI*z); + d.Vc(VX3,k,j,i) = cos(2.0*M_PI*x); + + real xl=d.xl[IDIR](i); + real yl=d.xl[JDIR](j); + real zl=d.xl[KDIR](k); + Ve(IDIR,k,j,i) = B0/(2.0*M_PI)*(cos(2.0*M_PI*yl)); + Ve(JDIR,k,j,i) = B0/(2.0*M_PI)*sin(2.0*M_PI*xl); + Ve(KDIR,k,j,i) = B0/(2.0*M_PI)*( + cos(2.0*M_PI*yl) + cos(4.0*M_PI*xl)/2.0); + + if(haveTracer) { + d.Vc(TRG ,k,j,i) = x>0.5? 1.0:0.0; + d.Vc(TRG+1,k,j,i) = z>0.5? 1.0:0.0; + } + } + } + } + + #ifndef EVOLVE_VECTOR_POTENTIAL + d.MakeVsFromAmag(Ve); + #endif + // Send it all, if needed + d.SyncToDevice(); +} + +// Analyse data to produce an output +void MakeAnalysis(DataBlock & data) { + +} + + + +// Do a specifically designed user step in the middle of the integration +void ComputeUserStep(DataBlock &data, real t, real dt) { + +} diff --git a/test/IO/xdmf/testme.py b/test/IO/xdmf/testme.py new file mode 100755 index 000000000..a1e333430 --- /dev/null +++ b/test/IO/xdmf/testme.py @@ -0,0 +1,45 @@ +#!/usr/bin/env python3 + +""" + +@author: glesur +""" +import os +import sys +sys.path.append(os.getenv("IDEFIX_DIR")) + +import pytools.idfx_test as tst + +name="dump.0001.dmp" + +test=tst.idfxTest() + +def check_xdmf_exists(): + # verify that the expected XDMF sidecar and data file exist. + xdmf_file = "data.0001.flt.xmf" + h5_file = "data.0001.flt.h5" + + + if not os.path.exists(xdmf_file): + print("Missing expected XDMF output file: {}".format(xdmf_file)) + sys.exit(1) + if not os.path.exists(h5_file): + print("Missing expected XDMF data file: {}".format(h5_file)) + sys.exit(1) + +if not test.dec: + test.dec=['2','2','2'] + +if test.check: + check_xdmf_exists() + +else: + test.vectPot=False + test.single=False + test.reconstruction=2 + test.mpi=False + # Only check that the test runs. + test.configure(definitionFile="definitions.hpp") + test.compile() + test.run(inputFile="idefix.ini") + check_xdmf_exists diff --git a/test/MHD/LinearWaveTest/idefix-entropy.ini b/test/MHD/LinearWaveTest/idefix-entropy.ini index 5a54d274b..805819477 100644 --- a/test/MHD/LinearWaveTest/idefix-entropy.ini +++ b/test/MHD/LinearWaveTest/idefix-entropy.ini @@ -29,4 +29,4 @@ epsilon 1.0e-6 [Output] dmp 1.0 vtk 1.0 -log 1 +log 10 diff --git a/test/MHD/LinearWaveTest/testme.py b/test/MHD/LinearWaveTest/testme.py index 8c9282862..390a5759b 100755 --- a/test/MHD/LinearWaveTest/testme.py +++ b/test/MHD/LinearWaveTest/testme.py @@ -9,7 +9,7 @@ sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -tolerance=1e-14 +tolerance=2e-13 def testMe(test): test.configure() test.compile() diff --git a/test/MHD/OrszagTang3D/setup.cpp b/test/MHD/OrszagTang3D/setup.cpp index 86766c8ee..a6927a132 100644 --- a/test/MHD/OrszagTang3D/setup.cpp +++ b/test/MHD/OrszagTang3D/setup.cpp @@ -12,200 +12,10 @@ generators on different architectures. Output* myOutput; int outnum; // Analysis function -// This analysis checks that the restart routines are performing as they should -void Analysis(DataBlock& data) { - - - idfx::cout << "Analysis: Checking restart routines" << std::endl; - - // Trigger dump creation - // data.SetBoundaries(); - myOutput->ForceWriteDump(data); - - // Mirror data on Host - DataBlockHost d(data); - - // Sync it - d.SyncFromDevice(); - - // Create local arrays to store the current physical state - IdefixHostArray4D myVc = IdefixHostArray4D("myVc", d.Vc.extent(0), data.np_tot[KDIR], data.np_tot[JDIR],data.np_tot[IDIR]); - IdefixHostArray4D myVs = IdefixHostArray4D("myVs", DIMENSIONS, data.np_tot[KDIR]+KOFFSET, data.np_tot[JDIR]+JOFFSET,data.np_tot[IDIR]+IOFFSET); - #ifdef EVOLVE_VECTOR_POTENTIAL - IdefixHostArray4D myVe = IdefixHostArray4D("myVe", AX3e+1, data.np_tot[KDIR]+KOFFSET, data.np_tot[JDIR]+JOFFSET,data.np_tot[IDIR]+IOFFSET); - #endif - // Transfer the datablock to myVc and myVs - for(int n = 0; n < d.Vc.extent(0) ; n++) { - for(int k = 0; k < d.np_tot[KDIR] ; k++) { - for(int j = 0; j < d.np_tot[JDIR] ; j++) { - for(int i = 0; i < d.np_tot[IDIR] ; i++) { - myVc(n,k,j,i) = d.Vc(n,k,j,i); - d.Vc(n,k,j,i) = 0.0; - - } - } - } - } - - for(int n = 0; n < DIMENSIONS ; n++) { - for(int k = 0; k < d.np_tot[KDIR] + KOFFSET; k++) { - for(int j = 0; j < d.np_tot[JDIR] + JOFFSET; j++) { - for(int i = 0; i < d.np_tot[IDIR] + IOFFSET; i++) { - myVs(n,k,j,i) = d.Vs(n,k,j,i); - d.Vs(n,k,j,i) = 0.0; - } - } - } - } - #ifdef EVOLVE_VECTOR_POTENTIAL - for(int n = 0; n < AX3e+1 ; n++) { - for(int k = 0; k < d.np_tot[KDIR] + KOFFSET; k++) { - for(int j = 0; j < d.np_tot[JDIR] + JOFFSET; j++) { - for(int i = 0; i < d.np_tot[IDIR] + IOFFSET; i++) { - myVe(n,k,j,i) = d.Ve(n,k,j,i); - d.Ve(n,k,j,i) = 0.0; - } - } - } - } - #endif - - // Push our datablockHost to erase everything - d.SyncToDevice(); - // From this point, the dataBlock is full of zeros - - // Load back the restart dump - myOutput->RestartFromDump(data, outnum); - data.SetBoundaries(); - #ifdef EVOLVE_VECTOR_POTENTIAL - data.hydro->emf->ComputeMagFieldFromA(data.hydro->Ve, data.hydro->Vs); - #endif - d.SyncFromDevice(); - - // increment outnum - outnum++; - int errornum; - - errornum = 0; - idfx::cout << "Analysis: checking consistency" << std::endl; - // Check that the save/load routines have left everything unchanged. - for(int n = 0; n < d.Vc.extent(0) ; n++) { - for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { - if(myVc(n,k,j,i) != d.Vc(n,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Vc at (i,j,k,n) = ( " << i << ", " << j << ", " << k << ", " << n << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl - << "Original= " << myVc(n,k,j,i) << " New=" << d.Vc(n,k,j,i) << " diff=" << myVc(n,k,j,i)-d.Vc(n,k,j,i) << std::endl; - } - - } - } - } - } - - for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { - if(myVs(BX1s,k,j,i) != d.Vs(BX1s,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Vs(BX1s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl - << "Original= " << myVs(BX1s,k,j,i) << " New=" << d.Vs(BX1s,k,j,i) << " diff=" << myVs(BX1s,k,j,i)-d.Vs(BX1s,k,j,i) << std::endl; - - } - - } - } - } - for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { - if(myVs(BX2s,k,j,i) != d.Vs(BX2s,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Vs(BX2s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; - } - - } - } - } - for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { - if(myVs(BX3s,k,j,i) != d.Vs(BX3s,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Vs(BX3s) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl - << "Original= " << myVs(BX3s,k,j,i) << " New=" << d.Vs(BX3s,k,j,i) << " diff=" << myVs(BX3s,k,j,i)-d.Vs(BX3s,k,j,i) << std::endl; - } - - } - } - } -#ifdef EVOLVE_VECTOR_POTENTIAL - for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR] ; i++) { - if(myVe(AX1e,k,j,i) != d.Ve(AX1e,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Ve(AX1e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; - - } - - } - } - } - for(int k = d.beg[KDIR]; k < d.end[KDIR]+KOFFSET ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR] ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { - if(myVe(AX2e,k,j,i) != d.Ve(AX2e,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Ve(AX2e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl; - } - - } - } - } - for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { - for(int j = d.beg[JDIR]; j < d.end[JDIR]+JOFFSET ; j++) { - for(int i = d.beg[IDIR]; i < d.end[IDIR]+IOFFSET ; i++) { - if(myVe(AX3e,k,j,i) != d.Ve(AX3e,k,j,i)) { - errornum++; - idfx::cout << "-----------------------------------------" << std::endl - << " Error in Ve(AX3e) at (i,j,k) = ( " << i << ", " << j << ", " << k << ")" << std::endl - << " Coordinates (x1,x2,x3) = ( " << d.x[IDIR](i) << ", " << d.x[JDIR](j) << ", " << d.x[KDIR](k) << ")" << std::endl - << "Original= " << myVs(BX3s,k,j,i) << " New=" << d.Vs(BX3s,k,j,i) << " diff=" << myVs(BX3s,k,j,i)-d.Vs(BX3s,k,j,i) << std::endl; - } - - } - } - } -#endif - - idfx::cout << "Analysis: consistency check done with " << errornum << " errors " << std::endl; - if(errornum>0) { - IDEFIX_ERROR("Restart from dump failed validation"); - } -} // Initialisation routine. Can be used to allocate // Arrays or variables which are used later on Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { - if(input.CheckEntry("Output","analysis")>0) { - output.EnrollAnalysis(&Analysis); - myOutput = &output; - outnum=0; - } } // This routine initialize the flow diff --git a/test/MHD/OrszagTang3D/testme.py b/test/MHD/OrszagTang3D/testme.py index 600a5ef5f..b9626f9cc 100755 --- a/test/MHD/OrszagTang3D/testme.py +++ b/test/MHD/OrszagTang3D/testme.py @@ -27,12 +27,6 @@ def testMe(test): test.makeReference(filename="dump.0001.dmp") test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tol) - # Check restarts - test.run("idefix-checkrestart.ini") - #force override the inputfile since the result should be identical - test.inifile="idefix.ini" - test.nonRegressionTest(filename="dump.0002.dmp",tolerance=tol) - test=tst.idfxTest() From 4f625afe8e36c147d410bf6328ecdcb6f2de7748 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Sat, 4 Apr 2026 15:59:42 +0200 Subject: [PATCH 097/144] MNT: upgrade inifix pre-commit hook (#372) --- .pre-commit-config.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 72360011b..080bc9ac3 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -40,7 +40,7 @@ repos: - F403 # ignore import * - repo: https://github.com/neutrinoceros/inifix - rev: v5.0.2 + rev: v6.1.2 hooks: - id: inifix-format From 24a3c3d6ad6ecc0feade619701e734fa15cba45e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Apr 2026 15:30:04 +0200 Subject: [PATCH 098/144] update pydefix for people using venv --- doc/source/modules/pydefix.rst | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/doc/source/modules/pydefix.rst b/doc/source/modules/pydefix.rst index f68284203..0a8daf753 100644 --- a/doc/source/modules/pydefix.rst +++ b/doc/source/modules/pydefix.rst @@ -23,7 +23,8 @@ Pydefix usage Idefix Configuration ++++++++++++++++++++ -In order to use Pydefix, you need to switch on ``Idefix_PYTHON`` in cmake. This will auto-detect Python and check that pybind11 can be used effectively. +In order to use Pydefix, you need to switch on ``Idefix_PYTHON`` in cmake. This will auto-detect Python and check that pybind11 can be used effectively. If you are using a python environement manager such as venv or conda, make sure to activate the right environement *before* running cmake, as idefix +now includes the full path to python and pybind11 in its executable file. Run Idefix with Pydefix From 3b26652a51d1a2943834d703849eeb6e851fe024 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Apr 2026 15:30:26 +0200 Subject: [PATCH 099/144] update changelog in prep for release 2.2.1 --- CHANGELOG.md | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4447493e9..f18371de3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,14 +4,20 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). -## Upcoming +## [2.2.1] 2026-04-21 ### Changed - fixed a bug that could lead to diverging results around the spherical axis in non-ideal MHD in 2.5D and 3D (#356) - refactor of the MPI exchange routines and boundary routines to avoid buildup of roundoff errors at domain faces/edges that could lead to the sudden burst of div(B) or incoherences between MPI sub-domains (#357) - +- fixed a bug that could lead to compilations error when targetting AMD APUs (#359) +- fixed a bug that led to the generation of incorrect subviews in 2.5D with vector_potential enabled (#362) +- fixed a bug that could lead to memory corruption when using the UCT_HLLD emf reconstruction scheme and DIMENSIONS < COMPONENTS (#363) +- reorganise the test to separate specific IO tests from physics tests (#367) ### Added +- magnetic vector potential is now accessible from pydefix when enabled (#361) +- use ccache in the test suite to reduce the runtime of continuous integration (#364) +- automatically detects pybind11 path with cmake when using pydefix (#367) ## [2.2.02] 2025-10-18 @@ -23,6 +29,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - fixed a bug that led to incorrect BX2 reconstruction when axis is not used on both sides of the domain (#345) - fixed a bug that led to incorrect reflective boundary conditions on B when DIMENSIONS < 3 (#345) - fixed a bug that led to incorrect dust stopping time when the adiabatic equation of state is used with "size" drag law (#353) +- fixed div(B) normalisation to avoid "too large div(B)" errors when this is actually due to nulls in |B| +- fixed insecure github actions settings (#373) ### Added From a6eebd135e7475c151e67f896846c450afd4a1c3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Tue, 21 Apr 2026 18:15:07 +0200 Subject: [PATCH 100/144] Test launcher based on pytest (#366) --- .gitignore | 1 + .pre-commit-config.yaml | 1 + doc/source/testing.rst | 12 +- doc/source/testing/idfxTest.rst | 3 + doc/source/testing/testLauncher.rst | 383 ++++++++++++++++++ pytest.ini | 6 + pytools/idfx_test.py | 205 +++++++++- pytools/idfx_test_gen.py | 249 ++++++++++++ pytools/idfx_test_run.py | 257 ++++++++++++ pytools/pytest.ini | 2 + pytools/tests/__init__.py | 0 pytools/tests/test/pb1/testme.json | 11 + pytools/tests/test/pb2/testme.json | 18 + pytools/tests/test_idfx_test_gen.py | 208 ++++++++++ pytools/tests/test_idfx_test_run.py | 88 ++++ test.py | 26 ++ test/Dust/DustEnergy/testme.json | 12 + test/Dust/DustEnergy/testme.py | 2 +- test/Dust/DustyShock/testme.json | 11 + test/Dust/DustyShock/testme.py | 2 +- test/Dust/DustyWave/testme.json | 12 + test/Dust/DustyWave/testme.py | 2 +- test/HD/FargoPlanet/testme.json | 25 ++ test/HD/FargoPlanet/testme.py | 2 +- test/HD/MachReflection/testme.json | 15 + test/HD/MachReflection/testme.py | 2 +- test/HD/SedovBlastWave/testme.json | 28 ++ test/HD/SedovBlastWave/testme.py | 2 +- test/HD/ShearingBox/testme.json | 15 + test/HD/ShearingBox/testme.py | 2 +- test/HD/ViscousDisk/testme.json | 15 + test/HD/ViscousDisk/testme.py | 2 +- test/HD/ViscousFlowPastCylinder/testme.json | 23 ++ test/HD/ViscousFlowPastCylinder/testme.py | 2 +- test/HD/sod-iso/testme.json | 33 ++ test/HD/sod-iso/testme.py | 2 +- test/HD/sod/testme.json | 33 ++ test/HD/sod/testme.py | 2 +- test/HD/thermalDiffusion/testme.json | 15 + test/HD/thermalDiffusion/testme.py | 2 +- test/IO/dump/testme.json | 28 ++ test/IO/dump/testme.py | 2 +- test/IO/pydefix/testme.json | 17 + test/IO/pydefix/testme.py | 2 +- test/IO/xdmf/testme.json | 17 + test/IO/xdmf/testme.py | 2 +- test/MHD/AmbipolarCshock/testme.json | 14 + test/MHD/AmbipolarCshock/testme.py | 2 +- test/MHD/AmbipolarCshock3D/testme.json | 35 ++ test/MHD/AmbipolarCshock3D/testme.py | 2 +- test/MHD/AxisFluxTube/testme.json | 16 + test/MHD/AxisFluxTube/testme.py | 2 +- test/MHD/Coarsening/testme.json | 12 + test/MHD/Coarsening/testme.py | 2 +- test/MHD/FargoMHDSpherical/testme.json | 17 + test/MHD/FargoMHDSpherical/testme.py | 2 +- test/MHD/HallWhistler/testme.json | 15 + test/MHD/HallWhistler/testme.py | 2 +- test/MHD/LinearWaveTest/testme.json | 24 ++ test/MHD/LinearWaveTest/testme.py | 2 +- test/MHD/MTI/testme.json | 15 + test/MHD/MTI/testme.py | 2 +- test/MHD/OrszagTang/testme.json | 74 ++++ test/MHD/OrszagTang/testme.py | 2 +- test/MHD/OrszagTang3D/testme.json | 34 ++ test/MHD/OrszagTang3D/testme.py | 2 +- test/MHD/ResistiveAlfvenWave/testme.json | 22 + test/MHD/ResistiveAlfvenWave/testme.py | 2 +- test/MHD/ShearingBox/testme.json | 15 + test/MHD/ShearingBox/testme.py | 2 +- test/MHD/clessTDiffusion/testme.json | 15 + test/MHD/clessTDiffusion/testme.py | 2 +- test/MHD/sod-iso/testme.json | 43 ++ test/MHD/sod-iso/testme.py | 2 +- test/MHD/sod/testme.json | 33 ++ test/MHD/sod/testme.py | 2 +- test/MHD/sphBragTDiffusion/testme.json | 15 + test/MHD/sphBragTDiffusion/testme.py | 2 +- test/MHD/sphBragViscosity/testme.json | 16 + test/MHD/sphBragViscosity/testme.py | 2 +- test/Planet/Planet3Body/testme.json | 15 + test/Planet/Planet3Body/testme.py | 2 +- test/Planet/PlanetMigration2D/testme.json | 16 + test/Planet/PlanetMigration2D/testme.py | 2 +- test/Planet/PlanetPlanetRK42D/testme.json | 25 ++ test/Planet/PlanetPlanetRK42D/testme.py | 2 +- test/Planet/PlanetSpiral2D/testme.json | 16 + test/Planet/PlanetSpiral2D/testme.py | 2 +- test/Planet/PlanetTorque3D/testme.json | 16 + test/Planet/PlanetTorque3D/testme.py | 2 +- test/Planet/PlanetsIsActiveRK52D/testme.json | 17 + test/Planet/PlanetsIsActiveRK52D/testme.py | 2 +- test/SelfGravity/DustyCollapse/testme.json | 16 + test/SelfGravity/DustyCollapse/testme.py | 2 +- test/SelfGravity/JeansInstability/testme.json | 17 + test/SelfGravity/JeansInstability/testme.py | 2 +- test/SelfGravity/RandomSphere/testme.json | 14 + test/SelfGravity/RandomSphere/testme.py | 2 +- .../RandomSphereCartesian/testme.json | 12 + .../RandomSphereCartesian/testme.py | 2 +- test/SelfGravity/UniformCollapse/testme.json | 16 + test/SelfGravity/UniformCollapse/testme.py | 2 +- test/python_requirements.txt | 4 + test/utils/columnDensity/testme.json | 13 + test/utils/columnDensity/testme.py | 2 +- test/utils/dumpImage/testme.json | 13 + test/utils/dumpImage/testme.py | 2 +- test/utils/lookupTable/testme.json | 12 + test/utils/lookupTable/testme.py | 2 +- 109 files changed, 2434 insertions(+), 64 deletions(-) create mode 100644 doc/source/testing/testLauncher.rst create mode 100644 pytest.ini create mode 100644 pytools/idfx_test_gen.py create mode 100644 pytools/idfx_test_run.py create mode 100644 pytools/pytest.ini create mode 100644 pytools/tests/__init__.py create mode 100644 pytools/tests/test/pb1/testme.json create mode 100644 pytools/tests/test/pb2/testme.json create mode 100644 pytools/tests/test_idfx_test_gen.py create mode 100644 pytools/tests/test_idfx_test_run.py create mode 100755 test.py create mode 100644 test/Dust/DustEnergy/testme.json create mode 100644 test/Dust/DustyShock/testme.json create mode 100644 test/Dust/DustyWave/testme.json create mode 100644 test/HD/FargoPlanet/testme.json create mode 100644 test/HD/MachReflection/testme.json create mode 100644 test/HD/SedovBlastWave/testme.json create mode 100644 test/HD/ShearingBox/testme.json create mode 100644 test/HD/ViscousDisk/testme.json create mode 100644 test/HD/ViscousFlowPastCylinder/testme.json create mode 100644 test/HD/sod-iso/testme.json create mode 100644 test/HD/sod/testme.json create mode 100644 test/HD/thermalDiffusion/testme.json create mode 100644 test/IO/dump/testme.json create mode 100644 test/IO/pydefix/testme.json create mode 100644 test/IO/xdmf/testme.json create mode 100644 test/MHD/AmbipolarCshock/testme.json create mode 100644 test/MHD/AmbipolarCshock3D/testme.json create mode 100644 test/MHD/AxisFluxTube/testme.json create mode 100644 test/MHD/Coarsening/testme.json create mode 100644 test/MHD/FargoMHDSpherical/testme.json create mode 100644 test/MHD/HallWhistler/testme.json create mode 100644 test/MHD/LinearWaveTest/testme.json create mode 100644 test/MHD/MTI/testme.json create mode 100644 test/MHD/OrszagTang/testme.json create mode 100644 test/MHD/OrszagTang3D/testme.json create mode 100644 test/MHD/ResistiveAlfvenWave/testme.json create mode 100644 test/MHD/ShearingBox/testme.json create mode 100644 test/MHD/clessTDiffusion/testme.json create mode 100644 test/MHD/sod-iso/testme.json create mode 100644 test/MHD/sod/testme.json create mode 100644 test/MHD/sphBragTDiffusion/testme.json create mode 100644 test/MHD/sphBragViscosity/testme.json create mode 100644 test/Planet/Planet3Body/testme.json create mode 100644 test/Planet/PlanetMigration2D/testme.json create mode 100644 test/Planet/PlanetPlanetRK42D/testme.json create mode 100644 test/Planet/PlanetSpiral2D/testme.json create mode 100644 test/Planet/PlanetTorque3D/testme.json create mode 100644 test/Planet/PlanetsIsActiveRK52D/testme.json create mode 100644 test/SelfGravity/DustyCollapse/testme.json create mode 100644 test/SelfGravity/JeansInstability/testme.json create mode 100644 test/SelfGravity/RandomSphere/testme.json create mode 100644 test/SelfGravity/RandomSphereCartesian/testme.json create mode 100644 test/SelfGravity/UniformCollapse/testme.json create mode 100644 test/utils/columnDensity/testme.json create mode 100644 test/utils/dumpImage/testme.json create mode 100644 test/utils/lookupTable/testme.json diff --git a/.gitignore b/.gitignore index 88b83a749..e3bf696a2 100644 --- a/.gitignore +++ b/.gitignore @@ -41,6 +41,7 @@ test/**/*.pyc test/**/*.dat test/**/cmake_packages* test/**/ +idefix-tests.junit.xml # machine specific cache and hidden files .* diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 080bc9ac3..522249fed 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -43,6 +43,7 @@ repos: rev: v6.1.2 hooks: - id: inifix-format + files: ^(test/).*\.(ini)$ # want to skip pytest.ini - repo: https://github.com/Lucas-C/pre-commit-hooks rev: v1.5.5 diff --git a/doc/source/testing.rst b/doc/source/testing.rst index 888ac2057..59bd2177a 100644 --- a/doc/source/testing.rst +++ b/doc/source/testing.rst @@ -71,9 +71,17 @@ How tests are driven (testme scripts) Each test directory contains a small Python "testMe" driver that uses the helper Python class documented in the repository: +- See the test launcher documentation: :doc:`test.py ` - See the test helper documentation: :doc:`idfxTest ` -That helper (idfxTest) is responsible for: +The test launcher (test.py) is responsible for: + +- Loading all the test definitions by search all the ``testme.json`` files in the ``test`` + directory. +- Calling the :doc:`idfxTest ` helper to run the particular test. +- Generate reports about success and failures. + +The helper (idfxTest) is responsible for: - parsing TESTME_OPTIONS-like flags (precision, MPI, CUDA, reconstruction, vector potential, etc.), - calling configure / compile / run, @@ -108,10 +116,12 @@ Relevant files - Workflow entry point: .github/workflows/idefix-ci.yml - Reusable jobs: .github/workflows/idefix-ci-jobs.yml +- Test launcher documentation: :doc:`test launcher ` - Test helper documentation: :doc:`idfxTest ` .. toctree:: :maxdepth: 2 :caption: Contents: + testing/testLauncher.rst testing/idfxTest.rst diff --git a/doc/source/testing/idfxTest.rst b/doc/source/testing/idfxTest.rst index b425d3fe2..96e364465 100644 --- a/doc/source/testing/idfxTest.rst +++ b/doc/source/testing/idfxTest.rst @@ -74,6 +74,9 @@ The constructor parses command-line arguments using ``argparse``. These options * - ``-Werror`` - ``Werror`` - Treat compiler warnings as errors. + * - ``-ccache`` + - ``ccache`` + - Enable usage of ccache to build the tests and reduce the build time. Main Methods ------------ diff --git a/doc/source/testing/testLauncher.rst b/doc/source/testing/testLauncher.rst new file mode 100644 index 000000000..aea7f5c3d --- /dev/null +++ b/doc/source/testing/testLauncher.rst @@ -0,0 +1,383 @@ +========================== +Test launcher and reporter +========================== + +Overview +-------- + +The class :doc:`idfxTest ` provides the toolbox to implement an *Idefix* integration test for validation. +In order to ease launching all the tests, the user might prefer to use directly the ``./test.py`` command at the +root of the *Idefix* sources. + +This script will run all the listed variants of *Idefix* and build a report in the terminal. At the +end of the run a standard ``junit.xml`` file is produced. This one can be translated into a browsable +HTML file. + +Depencencies +------------ + +Before using :doc:`idfxTest ` you need to install some Python depencencies (possibly in a ``virtual env``): + +.. code-block:: shell + + pip install -r test/python_requirements.txt + +Running +------- + +To run the test you can basically : + +.. code-block:: shell + + # Run all tests + ./test.py + + # Run all tests in ./tests/HD + ./test.py -subdir=./tests/HD + + # Select in more details the tests containing the "single" keyword + # See pytest documentation for the exact advanced semantic + ./test.py -subdir=./tests/HD -k single + + # Run in verbose + ./test.py -v + +The result of the execution will be an output like : + +.. code-block:: text + + ============================================ test session starts ============================================= + collected 52 items / 44 deselected / 8 selected + + test.py::test_idefix_build_run_check[HD/sod-iso-idefix.ini-single-reconstruction-2] PASSED [ 12%] + test.py::test_idefix_build_run_check[HD/sod-iso-idefix-hll.ini-single-reconstruction-2] PASSED [ 25%] + test.py::test_idefix_build_run_check[HD/sod-iso-idefix-hllc.ini-single-reconstruction-2] PASSED [ 37%] + test.py::test_idefix_build_run_check[HD/sod-iso-idefix-tvdlf.ini-single-reconstruction-2] PASSED [ 50%] + test.py::test_idefix_build_run_check[HD/sod-idefix.ini-single-reconstruction-2] PASSED [ 62%] + test.py::test_idefix_build_run_check[HD/sod-idefix-hll.ini-single-reconstruction-2] PASSED [ 75%] + test.py::test_idefix_build_run_check[HD/sod-idefix-hllc.ini-single-reconstruction-2] PASSED [ 87%] + test.py::test_idefix_build_run_check[HD/sod-idefix-tvdlf.ini-single-reconstruction-2] PASSED [100%] + + ---------- generated xml file: idefix-tests.junit.xml --------------------------------------------------------- + =============================== 8 passed, 44 deselected in 73.03s (0:01:13) =================================== + +When an error is detected, the output of the command will be printed at the end. + +HTML report +----------- + +If you want to to generate an HTML page from the report you can proceed by using the Python package ``junit2html`` : + +.. code-block:: shell + + # install junit2html + pip install junit2html + + # convert the report + junit2html ./idefix-tests.junit.xml ./idefix-tests.junit.html + +Advanced usage of the command +----------------------------- + +Here the options supported by the test script : + +.. code-block:: text + + usage: test.py [-h] [-noplot] [-ploterr] [-cmake CMAKE [CMAKE ...]] [-definitions DEFINITIONS] + [-dec DEC [DEC ...]] [-check] [-cuda] [-intel] [-hip] [-single] [-vectPot] + [-reconstruction RECONSTRUCTION] [-idefixDir IDEFIXDIR] [-mpi] [-all] [-init] + [-Werror] [-ccache] [-restart] [-v] [--help-pytest] [-fake] [-subdir SUBDIR] + + options: + -h, --help show this help message and exit + -noplot disable plotting in standard tests + -ploterr Enable plotting on error in regression tests + -cmake CMAKE [CMAKE ...] + CMake options + -definitions DEFINITIONS + definitions.hpp file + -dec DEC [DEC ...] MPI domain decomposition + -check Only perform regression tests without compilation + -cuda Test on Nvidia GPU using CUDA + -intel Test compiling with Intel OneAPI + -hip Test on AMD GPU using HIP + -single Enable single precision + -vectPot Enable vector potential formulation + -reconstruction RECONSTRUCTION + set reconstruction scheme (2=PLM, 3=LimO3, 4=PPM) + -idefixDir IDEFIXDIR Set directory for idefix source files (default $IDEFIX_DIR) + -mpi Enable MPI + -all Do all test suite (otherwise, just do the test with the current configuration) + -init Reinit reference files for non-regression tests (dangerous!) + -Werror Consider warnings as errors + -ccache Use ccache to reduce the build time over multiple run of the test suite. + -restart Enable creating a restart from a checkpoint. + -v, --verbose Enable verbose mode, by not capturing the output. + --help-pytest Display the options you can transmit directly to pytest in addition to the specific to idefix tests. + -fake Make a fake run by just logging the actions to validate that we generate same command over refactoring. + -subdir SUBDIR Select the test in the given subdir not to run all. + +The script is built on top of the ``pytest`` command so you automatically get access +to all the advanced option this command provide. Here a few examples : + +.. code-block:: shell + + # get the pytest help + ./test.py --help-pytest + + # let pytest filtering the tests + ./test.py -k "single and mpi" + + # stop on first failure + ./test.py -x + + # re-run only the last failed tests + ./test.py --lf + +Definition of the tests +----------------------- + +The script looks for all the files named ``testme.json`` in the ``test`` directory and all its sub-directories. +This file describes the combination of parameters used to produce the list of *Idefix* runs to check. +For a single basic configuration one can use : + +.. code-block:: json + + { + "variants": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 0 + } + } + +Available parameters +-------------------- + +The parameters in the ``variants`` dictionnary correspond to the options supported by the +:doc:`idfxTest ` script to configure the build and run of *Idefix*. + +In addition there is some extra keys which are dedicated to the json interpretation layer : + +.. list-table:: + :header-rows: 1 + + * - Option + - Default + - Description + * - ``dumname`` + - ``dump.0001.dmp`` + - Dump file to use to check the results after the run. + * - ``ini`` + - ``idefix.ini`` + - The configuration file to use. + * - ``tolerance`` + - ``0`` + - The margins to allow when checking the results. + * - ``standardTest`` + - ``true`` + - Runs any Python-based standard tests (e.g., ``testidefix.py``) present in the test directory for additional validation. + * - ``nonRegressionTest`` + - ``true`` + - Compares the output dump file to a reference file using RMSE; fails if the error exceeds the tolerance. + * - ``nonRegressionTestIni`` + - Same than ``ini`` + - When making restart you might want to make the check using the inirial configuration file. + * - ``multirun`` + - ``{}`` + - See the multi-run section below. + +Looping over parameters +----------------------- + +You might want to explore running Idefix within parameter ranges (configuration files, modes). +For this simply list the values you want as a list. The test script will automatically +generate all combinations. + +.. code-block:: json + + { + "variants": { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini"], + "vectPot": [false, true], + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "standardTest": false, + "tolerance": 0 + } + } + +It will automatically produce the tests : + +* HD/sod-iso-idefix.ini +* HD/sod-iso-idefix.ini-vectPot +* HD/sod-iso-idefix.ini-mpi +* HD/sod-iso-idefix.ini-vectPot-mpi +* HD/sod-iso-idefix-hll.ini +* HD/sod-iso-idefix-hll.ini-vectPot +* HD/sod-iso-idefix-hll.ini-mpi +* HD/sod-iso-idefix-hll.ini-vectPot-mpi + +Specific keys +------------- + +There is some keys which are by default some arrays, they will not be considered +as combination rules : + +* ``dec`` +* ``multirun`` +* ``restart_no_overwrite`` +* ``tolerance`` + +Reduce the combinations +----------------------- + +You might not want to see all the combinations but just a few, for this, you +can list several sets as a list. Here using single only on half of the modes. + +.. code-block:: json + + { + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-hll.ini"], + "vectPot": true, + "single": true, + "reconstruction": 2, + "mpi": [false, true], + "standardTest": false, + "tolerance": 0 + } + ] + } + +* HD/sod-iso-idefix.ini +* HD/sod-iso-idefix.ini-mpi +* HD/sod-iso-idefix-hll.ini-single-vectPot +* HD/sod-iso-idefix-hll.ini-single-vectPot-mpi + +Naming the test +--------------- + +If you prefer to see the options appearing in a specific order in the generated test name, +you can provide the key ``namings`` listing as a comma separated list the variables in +the order you want to see them composing the test name. + +.. code-block:: json + + { + "namings": "ini,single,mpi", + "variants": { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini"], + "vectPot": false, + "single": [false, true], + "reconstruction": 2, + "mpi": [false, true], + "standardTest": false, + "tolerance": 0 + } + } + + +By default, the alphabetical order is used. + +When clauses +------------ + +You can also dynamically override a specific value when a parameter value is selected. +It is just like if you used and IF statement. + +.. code-block:: json + + { + "namings": "ini,single,mpi", + "variants": { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini"], + "vectPot": false, + "single": [false, true], + "reconstruction": 2, + "mpi": [false, true], + "standardTest": false, + "tolerance": 0 + }, + "when": { + "conditions": { + "single": true + }, + "apply": { + "reconstruction": 1 + } + } + } + +In this case, ``reconstruction`` will be set to 1 when ``single`` is equal to ``true``. + +Note that the ``conditions`` field can contains several values which will be treaded +as and AND logical operator. + +You can provide several ``when`` clauses by using a list of them instead of directly +the dictionnary. + +Making multi-run steps +---------------------- + +In order to validate checkpoint restart, or continuing a simulation with dirfferent +tunnings the script supports decribing multi-run configurations. + +They are described like : + +.. code-block:: json + + { + "variants": { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 0, + "dec": [2,2,2], + "multirun": [ + { + },{ + "mpi": true, + "restart": true, + "restart_no_overwrite": ["dump.0001.dmp", "data.0005.vtk"] + } + ] + }, + } + +Using the idfxTest options +-------------------------- + +As the ``test.py`` uses the class described in :doc:`idfxTest ` it also supports all the +command line options it offers. + +Most usefull might be the enabling of ``ccache`` to reduce the compilation time from one +run to another. + +.. code-block:: shell + + ./test.py -ccache diff --git a/pytest.ini b/pytest.ini new file mode 100644 index 000000000..b3482664f --- /dev/null +++ b/pytest.ini @@ -0,0 +1,6 @@ +[pytest] +markers= + default: Test to run by default. +python_files="test_*.py" +junit_logging="system-out" +junit_log_passing_tests=false diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index fed74a22e..fd28ccb61 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -4,6 +4,7 @@ import subprocess import sys import re +import json import numpy as np import matplotlib.pyplot as plt @@ -22,7 +23,7 @@ class bcolors: UNDERLINE = '\033[4m' class idfxTest: - def __init__ (self): + def __init__ (self, current_test_file, name=""): parser = argparse.ArgumentParser() idefix_dir_env = os.getenv("IDEFIX_DIR") @@ -103,19 +104,83 @@ def __init__ (self): help="Use ccache to reduce the build time over multiple run of the test suite.", action="store_true") + parser.add_argument("-restart", + help="Enable creating a restart from a checkpoint.", + action='store_true') + + parser.add_argument("-v", "--verbose", + help="Enable verbose mode, by not capturing the output.", + action="store_true") + + parser.add_argument("--help-pytest", + help="Display the options you can transmit directly to pytest in addition to the specific to idefix tests.", + action="store_true") + + parser.add_argument("-fake", + help="Make a fake run by just logging the actions to validate that we generate same command over refactoring.", + action="store_true") + + # this option is not used directly by direct users of idfxTest but by idx_test_gen + parser.add_argument("-subdir", + default="./test", + help="Select the test in the given subdir not to run all.", + type=str) + args, unknown=parser.parse_known_args() # transform all arguments from args into attributes of this instance self.__dict__.update(vars(args)) + # store the full path of problem directory + self.currentTestFile = current_test_file + self.currentTestName = name + self.problemDir=os.path.dirname(current_test_file) self.referenceDirectory = os.path.join(idefix_dir_env,"reference") # current directory relative to $IDEFIX_DIR/test (used to retrieve the path ot reference files) - self.testDir=os.path.relpath(os.curdir,os.path.join(idefix_dir_env,"test")) + self.testDir=os.path.relpath(self.problemDir,os.path.join(idefix_dir_env,"test")) # build directory, currently inside the test named build-test - self.buildDir=os.path.abspath("./build-test") - # store the full path of problem directory - self.problemDir=os.path.abspath("./") - - def configure(self,definitionFile=""): + self.buildDir=os.path.join(self.problemDir,"build-test") + # remind what build we dit last + self.lastCmakeCmd="" + # subdir + self.filterSubdir=args.subdir + # save + self.cmdArgs = vars(args) + self.cmdArgs.update({ + "restart_no_overwrite": [], + }) + self.log=[] + # when making a restart we should not overrite those files (will be checked) + self.restart_no_overwrite=[] + + # forward args for pytest + if args.verbose: + unknown.append("--capture=no") + if args.help_pytest: + unknown.append("--help") + # remaining args + self.remainingArgs=unknown + + def addLog(self, entry): + if self.fake: + self.log.append(entry) + with open(os.path.join(self.problemDir,"testsuite.log.json"), "w+") as fp: + json.dump(self.log, fp, indent='\t') + + def applyConfig(self, config: dict={}): + # check args + for key, value in config.items(): + if key not in ['ini', 'testfile', 'testname', 'dumpname']: + assert key in self.cmdArgs, f"The given configuration overriding try to set an invalid paramater : {key}={value}" + + # override options + newArgs = {} + newArgs.update(self.cmdArgs) + newArgs.update(config) + + # replace in dict + self.__dict__.update(newArgs) + + def _genCmakeCommand(self,definitionFile=""): comm=["cmake"] # add source directory comm.append(self.idefixDir) @@ -184,29 +249,84 @@ def configure(self,definitionFile=""): if self.ccache: comm.append("-DCMAKE_CXX_COMPILER_LAUNCHER=ccache") + # ok + return comm + + + def configure(self,definitionFile="", reuse_last_same_build=True, override: dict={}): + # log + self.addLog({"call": "configure", "args":{ + 'definitionFile': definitionFile, + 'reuse_last_same_build': reuse_last_same_build, + 'override': override + }}) + + # gen command + comm = self._genCmakeCommand(definitionFile) + + # log + print("***************** CALLING CMAKE *******************") + print(f"mkdir -p {self.buildDir}") + print(f"cd {self.buildDir}") + print(' '.join(comm)) + print("***************************************************") + + # not action needed if same command or force no rebuild + if reuse_last_same_build == True and self.lastCmakeCmd == ' '.join(comm): + print("SKIP ALREADY DONE") + return + + # run try: - # clean before configuring again + # do cleanup self.clean() + # log and in fake mode we do not execute + self.addLog({"command": comm}) + # call cmake - cmake=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) - cmake.check_returncode() + if not self.fake: + cmake=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) + cmake.check_returncode() except subprocess.CalledProcessError as e: print(bcolors.FAIL+"***************************************************") print("Cmake failed") print("***************************************************"+bcolors.ENDC) raise e + finally: + # remind for next time + self.lastCmakeCmd = ' '.join(comm) def clean(self): + # log and in fake mode we do not execute + self.addLog({"call": "clean", "args":{}}) + if self.fake: + return + # remove the build directory before re-creating it if os.path.exists(self.buildDir): shutil.rmtree(self.buildDir) + + # recreate os.makedirs(self.buildDir, exist_ok=False) def compile(self,jobs=8): + self.addLog({"call": "compile", "args":{ + 'jobs': jobs, + }}) + try: - make=subprocess.run(["make","-j"+str(jobs)], cwd=os.path.abspath(self.buildDir)) - make.check_returncode() + comm = ["make","-j"+str(jobs)] + self.addLog({"command": comm}) + + print("***************************************************") + print(f"cd {os.getcwd()}") + print(' '.join(comm)) + print("***************************************************") + + if not self.fake: + make=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) + make.check_returncode() except subprocess.CalledProcessError as e: print(bcolors.FAIL+"***************************************************") print("Compilation failed") @@ -214,6 +334,13 @@ def compile(self,jobs=8): raise e def run(self, inputFile="", np=2, nowrite=False, restart=-1): + # log + self.addLog({"call": "run", "args":{ + 'np': np, + 'nowrite': nowrite, + 'restart': restart, + }}) + comm=[os.path.join(self.buildDir,"idefix")] if inputFile: comm.append("-i") @@ -242,9 +369,16 @@ def run(self, inputFile="", np=2, nowrite=False, restart=-1): comm.append("-restart") comm.append(str(restart)) + print("***************************************************") + print(f"cd {os.getcwd()}") + print(' '.join(comm)) + print("***************************************************") + try: - make=subprocess.run(comm) - make.check_returncode() + self.addLog({"command": comm}) + if not self.fake: + make=subprocess.run(comm, cwd=self.problemDir) + make.check_returncode() except subprocess.CalledProcessError as e: print(bcolors.FAIL+"***************************************************") print("Execution failed") @@ -254,6 +388,9 @@ def run(self, inputFile="", np=2, nowrite=False, restart=-1): self._readLog() def _readLog(self): + if self.fake: + return + if not os.path.exists('./idefix.0.log'): # When no idefix file is produced, we leave return @@ -298,6 +435,12 @@ def _readLog(self): self.perf=float(line.group(1)) def checkOnly(self, filename, tolerance=0): + # log + self.addLog({"call": "checkOnly", "args":{ + 'filename': filename, + 'tolerance': tolerance, + }}) + # Assumes the code has been run manually using some configuration, so we simply # do the test suite witout configure/compile/run self._readLog() @@ -312,8 +455,14 @@ def checkOnly(self, filename, tolerance=0): self.nonRegressionTest(filename, tolerance) def standardTest(self): - if os.path.exists(os.path.join('python', 'testidefix.py')): - os.chdir("python") + # log and in fake mode do not execute. + self.addLog({"call": "standardTest", "args":{}}) + if self.fake: + return + + if os.path.exists(os.path.join(self.problemDir, 'python', 'testidefix.py')): + oldPwd = os.getcwd() + os.chdir(os.path.join(self.problemDir, "python")) comm = [sys.executable, "testidefix.py"] if self.noplot: comm.append("-noplot") @@ -328,12 +477,19 @@ def standardTest(self): print("***************************************************"+bcolors.ENDC) raise e print(bcolors.OKCYAN+"Standard test succeeded"+bcolors.ENDC) - os.chdir("..") + os.chdir(oldPwd) else: print(bcolors.WARNING+"No standard testidefix.py for this test"+bcolors.ENDC) sys.stdout.flush() def nonRegressionTest(self, filename,tolerance=0): + # log and in fake mode do not execute. + self.addLog({"call": "nonRegressionTest", "args":{ + "filename": filename, + "tolerance": tolerance + }}) + if self.fake: + return fileref=os.path.join(self.referenceDirectory, self.testDir, self._getReferenceFilename()) if not(os.path.exists(fileref)): @@ -357,6 +513,14 @@ def nonRegressionTest(self, filename,tolerance=0): sys.stdout.flush() def compareDump(self, file1, file2,tolerance=0): + self.addLog({"call": "compareDump", "args":{ + "file1": file1, + "file2": file2, + "tolerance": tolerance, + }}) + if self.fake: + return + Vref=readDump(file1) Vtest=readDump(file2) error=self._computeError(Vref,Vtest) @@ -371,6 +535,13 @@ def compareDump(self, file1, file2,tolerance=0): def makeReference(self,filename): + # log and in fake mode do not execute. + self.addLog({"call": "compareDump", "args":{ + "filename": filename, + }}) + if self.fake: + return + self._readLog() targetDir = os.path.join(self.referenceDirectory,self.testDir) if not os.path.exists(targetDir): diff --git a/pytools/idfx_test_gen.py b/pytools/idfx_test_gen.py new file mode 100644 index 000000000..e552c321d --- /dev/null +++ b/pytools/idfx_test_gen.py @@ -0,0 +1,249 @@ +##################################################################################### +# Idefix MHD astrophysical code +# Copyright(C) Sébastien Valat +# and other code contributors +# Licensed under CeCILL 2.1 License, see COPYING for more information +##################################################################################### + +import copy +import pytest + +DO_NOT_LOOP_ON = ['restart_no_overwrite', "dec", "multirun", "check_file_produced"] + +class IdefixDirTestGenerator: + ''' + Class used to generate the various configuration to run by parsing the + files `testme.py` found in the hierarchy of the /test directory of Idefix. + ''' + + def __init__(self, currentTestFile: str, name: str = ""): + ''' + Constructor or the class. + + Args: + currentTestFile (str): + Path the the current python file. Normally you + simply pass __file__ to this parameter. + name (str): + Define a name for the test, can be empty. + ''' + + self.currentTestFile = currentTestFile + self.currentTestName = name + + # generate the list of configs to run + def genTestConfigs(self, names:str, params, whenClauses = {}) -> list: + ''' + Generate the the list of configurations as pytest parameters. + It will unpack the configuration set by looping on all combinations defined + by the given sets. + + Args: + names (str): + Comma separated list of variables do consider to build the + name of the file. + params (dict|list): + A configuration set as a dictionnary or a list of + configuration set. + whenCaluses (dict|list): + Provide a set of clauses to apply after unpacking + the configuration so we can patch some values depending on some others. + + Returns: + A list of pytest.param() ready to be fiven to parametrized pytest functions. + ''' + # get name ordering list + nameList = names.split(',') + + # gen list of complete configs + all_configs = [] + if isinstance(params, dict): + all_configs += self._genOneConfigSeries(names, params) + elif isinstance(params, list): + for p in params: + all_configs += self._genOneConfigSeries(names, p) + else: + raise Exception("Should never be called !") + + # convert as parametrize with nice name + result = [] + for config in all_configs: + # append the file + config['testfile'] = self.currentTestFile + config['testname'] = self.currentTestName + # gen name + nameParts = [self.currentTestName] + for name in nameList: + if isinstance(config[name], bool): + if config[name]: + nameParts.append(name) + elif isinstance(config[name], str): + nameParts.append(str(config[name])) + else: + nameParts.append(f"{name}-{config[name]}") + confName = "-".join(nameParts) + + # apply when clause + config = self._applyWhen(config, whenClauses) + + result.append(pytest.param(config, id=confName)) + + # ok + return result + + def extractNamingParameters(self, params) -> list: + ''' + Loop on the parameters and check automatically what are the list of variable parameters. + + Args: + params (list|dict): + The list of configuration sets to scan or a single set. + + Returns: + The list of names of the variable parameters. + ''' + + # if not a list make a list + if not isinstance(params, list): + params = [params] + + # see params + seen = {} + variables = [] + + # loop + for param_set in params: + for key, value in param_set.items(): + if key in variables: + pass + elif key in DO_NOT_LOOP_ON: + pass + elif isinstance(value, list): + variables.append(key) + elif key in seen and seen[key] != value: + variables.append(key) + elif key not in seen: + seen[key] = value + + # by default sort by alphabetic order about var names + # TODO make something better by assigning a priority to vars + variables.sort() + + # ok + return ','.join(variables) + + def _genNextLevelCombinations(self, input: list, paramName: str, paramValues: list) -> list: + ''' + Take an input case list and unpack the given parameter to build the new combinations. + + Args: + input (list): + The incoming list of combinations already unpacked before this call. + paramName (str): + Name of the parameter to unpack. + paramValues (list): + The list of values to unpack and to build combinations for. + + Returns: + The updated list of run sets. + ''' + result = [] + for entry in input: + for value in paramValues: + v = copy.deepcopy(entry) + v[paramName] = value + result.append(v) + return result + + def _genOneConfigSeries(self, names: str, config: dict) -> list: + ''' + Generate the the list of configurations as pytest parameters. + It will unpack the configuration set by looping on all combinations defined + by the given sets. + + Args: + names (str): + Comma separated list of variables do consider to build the + name of the file. + config (dict): + A configuration set as a dictionnary. + + Returns: + A list of pytest.param() ready to be fiven to parametrized pytest functions. + ''' + # get name ordering list + nameList = names.split(',') + + # if there is ini in the list we put it at the end + loopOrder = nameList.copy() + if 'ini' in loopOrder: + loopOrder.remove('ini') + loopOrder.append('ini') + + # init core with everything not a list + core = {} + for key, value in config.items(): + if isinstance(value, list) and key not in DO_NOT_LOOP_ON: + assert key in nameList, f"All variable parameteres should be ordered in the names list, '{key}' is not." + else: + core[key] = copy.deepcopy(value) + + # at start we have only default core + result = [core] + + # loop + for key in loopOrder: + value = config[key] + assert isinstance(value, list), f"This parameter is marked as a list but is not a list : {key}={value} !" + result = self._genNextLevelCombinations(result, key, value) + + # ok + return result + + def _matchWhenClause(self, config: dict, when_clause: dict) -> bool: + ''' + Check the matching of a given when clause on the given configuration. + + Args: + config (dict): The configuration. + when_clause (dict): The when clause to check. + + Returns: + True if the clause, match, False otherwise. + ''' + for key, value in when_clause.items(): + if config[key] != value: + return False + return True + + def _applyWhen(self, config: dict, when: dict) -> dict: + ''' + Check if the when clause applies and apply if if any. + + Args: + config (dict): The configuration. + when_clause (dict): The when clause to check and apply. + + Returns: + The fixed config. + ''' + # nothing to do + if when == {}: + return config + + # clone + result = copy.deepcopy(config) + + # loop on when + if isinstance(when, list): + for clause in when: + if self._matchWhenClause(config, clause['conditions']): + result.update(clause['apply']) + elif isinstance(when, dict): + if self._matchWhenClause(config, when['conditions']): + result.update(when['apply']) + else: + raise Exception(f"Invalid type for 'when' : {when}") + + # ok + return result diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py new file mode 100644 index 000000000..d14de0b41 --- /dev/null +++ b/pytools/idfx_test_run.py @@ -0,0 +1,257 @@ +##################################################################################### +# Idefix MHD astrophysical code +# Copyright(C) Sébastien Valat +# and other code contributors +# Licensed under CeCILL 2.1 License, see COPYING for more information +##################################################################################### + +import os +import sys +import json +import glob +import copy +import pytest +# idefix test class +import pytools.idfx_test as tst +from pytools.idfx_test_gen import IdefixDirTestGenerator +from contextlib import contextmanager + +@contextmanager +def moveInDir(path): + ''' + Change current working dir for the given directoy for what is inside the + with statement. + ''' + oldpwd = os.getcwd() + os.chdir(path) + try: + yield + finally: + os.chdir(oldpwd) + +class IdexPytestRunner: + ''' + Implement the Idefix pytest runner to scan and run all the tests described by the files + testme.json into the /test directory of Idefix sources. + ''' + + def __init__(self, parentScriptFile: str): + self.currentTestFile="" + self.currentTestRunner: tst.idfxTest=None + self.parentScritFile=parentScriptFile + self.filterSubdir = os.environ.get("IDEFIX_TEST_FILTER_SUBDIR", "./test/") + + def _validateNaming(self, namings: str, autoExtracted: str, file: str): + names = namings.split(',') + for n in autoExtracted.split(','): + if not n in names: + raise Exception(f"Naming parameter list not match the auto-detectection, some are missinge. You gave : '{names}', detected '{autoExtracted}' into {file}") + + def _makeVariableArgAsList(self, namings: str, variants) -> list: + # make as a list + if isinstance(variants, list) == False: + variants = [variants] + + # split namings + namings = namings.split(",") + + # loop on each + for variant in variants: + for name in namings: + if name in variant and isinstance(variant[name], list) == False: + variant[name] = [variant[name]] + + def genTests(self) -> list: + sourceDir = os.path.dirname(self.parentScritFile) + + # loop over all tests + result = [] + with moveInDir(sourceDir): + # if missing / + if self.filterSubdir != "" and self.filterSubdir[-1] != "/": + self.filterSubdir += "/" + + # walk in test dir to find the tests & sort by name + testfiles = glob.glob(self.filterSubdir + "**/testme.json", recursive=True) + testfiles.sort() + + # loop over each + for testfile in testfiles: + try: + # calc some paths + testfileRelPath = os.path.relpath(testfile, os.path.join(sourceDir, 'test')) + testfilePath = os.path.abspath(os.path.join('test',testfileRelPath)) + testfileDir = os.path.dirname(testfileRelPath) + + # load json & build the inner test combinations + with open(testfilePath, 'r') as fp: + test = json.load(fp) + idefixTestGenerator=IdefixDirTestGenerator(testfilePath, testfileDir) + if 'namings' in test: + namings = test['namings'] + autoExtracted = idefixTestGenerator.extractNamingParameters(test['variants']) + self._validateNaming(namings, autoExtracted, testfilePath) + else: + namings = idefixTestGenerator.extractNamingParameters(test['variants']) + + # required to simplify the algos later, if var is listed as variable, we need to loop over it. + self._makeVariableArgAsList(namings, test['variants']) + + # gen + result += idefixTestGenerator.genTestConfigs(namings, test['variants'], test.get('when', {})) + except Exception as e: + raise Exception(f"Fail to generate tests from {testfileRelPath} : {e}") + + # ok + return result + + def run(self, config: dict) -> None: + # clone before modify to not modity for caller + config = copy.deepcopy(config) + + # print config + print("***************************************************") + print(json.dumps(config, indent='\t')) + print("***************************************************") + + # extract some infos for local usage + testfile = config["testfile"] + dumpname = config['dumpname'] + testname = config["testname"] + tolerance = config.get("tolerance", 0) + definitionFile = config.get("definitionFile", "") + standardTest = config.get("standardTest", True) + nonRegressionTest = config.get("nonRegressionTest", True) + nonRegressionTestIni = config.get("nonRegressionTestIni", None) + check_file_produced = config.get("check_file_produced", []) + problemDir = os.path.dirname(testfile) + + # cleanup some keyword not handled at the + # level of idx_test so we don't perturbate it + del config['dumpname'] + if 'definitionFile' in config: + del config['definitionFile'] + if 'tolerance' in config: + del config['tolerance'] + if 'standardTest' in config: + del config['standardTest'] + if 'nonRegressionTest' in config: + del config['nonRegressionTest'] + if 'nonRegressionTestIni' in config: + del config['nonRegressionTestIni'] + + # if switch from test, rebuild the runner (a runner make for one dir) + if self.currentTestFile != testfile: + self.currentTestRunner = tst.idfxTest(testfile, name=testname) + self.currentTestFile = testfile + + # run + with moveInDir(problemDir): + self._runNonRegression(dumpname, config['ini'], config, tolerance=tolerance, definitionFile=definitionFile, standardTest=standardTest, nonReg=nonRegressionTest, nonRegIni=nonRegressionTestIni) + + # check produced + for file in check_file_produced: + if not os.path.exists(file): + raise Exception(f"Don't find expected file to be produced by the run : {file} !") + + def _runNonRegression(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): + if 'multirun' in config_override: + self._runNonRegMultirun(dumpname, ini, config_override, tolerance=tolerance, nonReg=nonReg, nonRegIni=nonRegIni, standardTest=standardTest, configure_and_compile=configure_and_compile, definitionFile=definitionFile, first_run_ini=first_run_ini, first_run_dumpname=first_run_dumpname) + else: + # single basic run + self._runNonRegSingleRun(dumpname, ini, config_override, tolerance=tolerance, nonReg=nonReg, standardTest=standardTest, configure_and_compile=configure_and_compile, definitionFile=definitionFile, first_run_ini=first_run_ini, first_run_dumpname=first_run_dumpname) + + def _runNonRegMultirun(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): + # check + assert 'multirun' in config_override + + # loop over runs + for run in config_override['multirun']: + # copy config + run_config = copy.deepcopy(config_override) + + # patch a bit + del run_config['multirun'] + run_config.update(run) + nonReg=run_config.get('nonRegressionTest', nonReg) + dumpname=run_config.get('dumpname', dumpname) + if 'nonRegressionTest' in run_config: + del run_config['nonRegressionTest'] + standardTest=run_config.get('standardTest', standardTest) + if 'standardTest' in run_config: + del run_config['standardTest'] + + # make single run + self._runNonRegSingleRun(dumpname, run_config['ini'], run_config, definitionFile=definitionFile, tolerance=tolerance, nonReg=nonReg, nonRegIni=nonRegIni, standardTest=standardTest) + + def _runNonRegSingleRun(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): + # build the runner + idefixTest = self.currentTestRunner + + # handle special override which should not go into + # idefixTest because it is not supported by the idfx_test layer. + config_override = copy.deepcopy(config_override) + nonRegIni = config_override.get("nonRegressionTestIni", nonRegIni) + if 'nonRegressionTestIni' in config_override: + del config_override['nonRegressionTestIni'] + + # apply config + idefixTest.applyConfig(config_override) + + # recompile if needed + if configure_and_compile: + idefixTest.configure(override=config_override, definitionFile=definitionFile) + idefixTest.compile() + + if first_run_ini: + idefixTest.run(inputFile=first_run_ini) + if nonReg: + idefixTest.nonRegressionTest(filename=first_run_dumpname, tolerance=tolerance) + + # Test the restart option + file_mtime={} + if not idefixTest.fake: + for file in idefixTest.restart_no_overwrite: + file_mtime[file] = os.path.getmtime(file) + + # restart + if idefixTest.restart: + restart = 1 + else: + restart = -1 + + # run + idefixTest.run(inputFile=ini, restart=restart) + + # regen ref if needed + if idefixTest.init: + idefixTest.makeReference(filename=dumpname) + + # check outputs + if standardTest: + idefixTest.standardTest() + if nonReg: + if nonRegIni: + idefixTest.inifile = nonRegIni + idefixTest.nonRegressionTest(filename=dumpname, tolerance=tolerance) + + # check that we didn't overrite the file during the restart + if not idefixTest.fake: + for file in idefixTest.restart_no_overwrite: + assert file_mtime[file] == os.path.getmtime(file), f"Dump file {file} was overwritten on restart" + + def main(self, all: bool = False): + if all: + sys.argv.append("-all") + idefixTest = tst.idfxTest(self.parentScritFile, name="main") + os.environ["IDEFIX_TEST_FILTER_SUBDIR"] = idefixTest.filterSubdir + + if idefixTest.all: + pytest.main(['-v', '--no-header', '--junit-xml=idefix-tests.junit.xml', '--tb=short'] + idefixTest.remainingArgs + [self.parentScritFile]) + else: + assert False, "Not yet supported !" + #elif self.check: + # idefixTest.checkOnly(filename=dumpname, tolerance=tolerance) + #else: + # for ini in ini_list: + # self.runNonRegression(dumpname, ini, {}, tolerance=tolerance) diff --git a/pytools/pytest.ini b/pytools/pytest.ini new file mode 100644 index 000000000..d1f826516 --- /dev/null +++ b/pytools/pytest.ini @@ -0,0 +1,2 @@ +[pytest] +python_files="test_*.py" diff --git a/pytools/tests/__init__.py b/pytools/tests/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/pytools/tests/test/pb1/testme.json b/pytools/tests/test/pb1/testme.json new file mode 100644 index 000000000..d8ddad44f --- /dev/null +++ b/pytools/tests/test/pb1/testme.json @@ -0,0 +1,11 @@ +{ + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + } + ] +} diff --git a/pytools/tests/test/pb2/testme.json b/pytools/tests/test/pb2/testme.json new file mode 100644 index 000000000..96c1753ab --- /dev/null +++ b/pytools/tests/test/pb2/testme.json @@ -0,0 +1,18 @@ +{ + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + }, + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": false, + "reconstruction": 2, + "tolerance": 1e-14 + } + ] +} diff --git a/pytools/tests/test_idfx_test_gen.py b/pytools/tests/test_idfx_test_gen.py new file mode 100644 index 000000000..fc4f6261e --- /dev/null +++ b/pytools/tests/test_idfx_test_gen.py @@ -0,0 +1,208 @@ +##################################################################################### +# Idefix MHD astrophysical code +# Copyright(C) Sébastien Valat +# and other code contributors +# Licensed under CeCILL 2.1 License, see COPYING for more information +##################################################################################### + +from ..idfx_test_gen import IdefixDirTestGenerator +import pytest + +def test_extractNamingParameters(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + lst = gen.extractNamingParameters([ + { + "dec": [1,2,3], + "a": 10, + "b": 11, + "c": [True, False] + }, + { + "dec": [1,2,4], + "a": 10, + "b": 12, + "d": [True, False] + }, + ]) + + # valid + assert lst == 'b,c,d' + +def test_genNextLevelCombinations(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # init with single element + core = {} + init = [core] + + # gen first set of combinations + lst1 = gen._genNextLevelCombinations(init, "mpi", [True, False]) + assert lst1 == [ + {"mpi": True}, + {"mpi": False}, + ] + + # gen first second set of combinations + lst3 = gen._genNextLevelCombinations(lst1, "name", ["a", "b"]) + assert lst3 == [ + {"mpi": True, "name": "a"}, + {"mpi": True, "name": "b"}, + {"mpi": False, "name": "a"}, + {"mpi": False, "name": "b"}, + ] + +def test_genOneConfigSeries(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # gen + result = gen._genOneConfigSeries("mpi,name", { + "mpi": [True, False], + "name": ["a", "b"] + }) + + # check + assert result == [ + { + 'mpi': True, + 'name': 'a', + },{ + 'mpi': True, + 'name': 'b', + },{ + 'mpi': False, + 'name': 'a', + },{ + 'mpi': False, + 'name': 'b', + }, + ] + +def test_matchWhenClause_single(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # calls + assert gen._matchWhenClause({"a":10, "b": 11}, {"a":10}) == True + assert gen._matchWhenClause({"a":10, "b": 11}, {"a":11}) == False + assert gen._matchWhenClause({"a":10, "b": 11}, {"b":11}) == True + assert gen._matchWhenClause({"a":10, "b": 11}, {"b":10}) == False + +def test_matchWhenClause_and(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # calls + assert gen._matchWhenClause({"a":10, "b": 11}, {"a":10, "b":11}) == True + assert gen._matchWhenClause({"a":10, "b": 11}, {"a":11, "b":11}) == False + +def test_applyWhen_none(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen({ + "a": 10, + "b": 11 + }, when={}) + + # check result + assert res == {"a": 10, "b": 11} + +def test_applyWhen_single_apply_yes(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen({ + "a": 10, + "b": 11 + }, when={ + "conditions": { + "a": 10, + }, + "apply": { + "b": 12 + } + }) + + # check result + assert res == {"a": 10, "b": 12} + +def test_applyWhen_single_apply_no(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen({ + "a": 10, + "b": 11 + }, when={ + "conditions": { + "a": 9, + }, + "apply": { + "b": 12 + } + }) + + # check result + assert res == {"a": 10, "b": 11} + +def test_applyWhen_list_apply_yes(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen({ + "a": 10, + "b": 11 + }, when=[ + { + "conditions": { + "a": 10, + }, + "apply": { + "b": 12 + } + }, + { + "conditions": { + "a": 13, + }, + "apply": { + "b": 13 + } + } + ]) + + # check result + assert res == {"a": 10, "b": 12} + +def test_gen_full(): + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # gen + result = gen.genTestConfigs("mpi,name", { + "mpi": [True, False], + "name": ["a", "b"] + }, { + "conditions": { + "mpi": True + }, + "apply": { + "extra": 10, + } + }) + + # check + assert result == [ + pytest.param({'mpi': True, 'name': 'a', 'testfile': __file__, 'testname': 'unit-test', 'extra': 10}, id='unit-test-mpi-a'), + pytest.param({'mpi': True, 'name': 'b', 'testfile': __file__, 'testname': 'unit-test', 'extra': 10}, id='unit-test-mpi-b'), + pytest.param({'mpi': False, 'name': 'a', 'testfile': __file__, 'testname': 'unit-test'}, id='unit-test-a'), + pytest.param({'mpi': False, 'name': 'b', 'testfile': __file__, 'testname': 'unit-test'}, id='unit-test-b'), + ] diff --git a/pytools/tests/test_idfx_test_run.py b/pytools/tests/test_idfx_test_run.py new file mode 100644 index 000000000..8843705ee --- /dev/null +++ b/pytools/tests/test_idfx_test_run.py @@ -0,0 +1,88 @@ +##################################################################################### +# Idefix MHD astrophysical code +# Copyright(C) Sébastien Valat +# and other code contributors +# Licensed under CeCILL 2.1 License, see COPYING for more information +##################################################################################### + +from ..idfx_test_run import IdexPytestRunner +import pytest +import os + +def test_genTests(): + # build runner + runner = IdexPytestRunner(__file__) + + # dir + dir = os.path.dirname(__file__) + + # generate + result = runner.genTests() + assert result == [ + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': True, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix.ini', + 'testfile': dir + '/test/pb1/testme.json', + 'testname': 'pb1' + }, marks=(), id='pb1-idefix.ini' + ), + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': True, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix-implicit.ini', + 'testfile': dir + '/test/pb1/testme.json', + 'testname': 'pb1' + }, marks=(), id='pb1-idefix-implicit.ini' + ), + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': True, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix.ini', + 'testfile': dir + '/test/pb2/testme.json', + 'testname': 'pb2' + }, marks=(), id='pb2-idefix.ini-noplot' + ), + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': True, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix-implicit.ini', + 'testfile': dir + '/test/pb2/testme.json', + 'testname': 'pb2' + }, marks=(), id='pb2-idefix-implicit.ini-noplot' + ), + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': False, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix.ini', + 'testfile': dir + '/test/pb2/testme.json', + 'testname': 'pb2' + }, marks=(), id='pb2-idefix.ini' + ), + pytest.param( + { + 'dumpname': 'dump.0001.dmp', + 'noplot': False, + 'reconstruction': 2, + 'tolerance': 1e-14, + 'ini': 'idefix-implicit.ini', + 'testfile': dir + '/test/pb2/testme.json', + 'testname': 'pb2' + }, marks=(), id='pb2-idefix-implicit.ini' + ), + ] diff --git a/test.py b/test.py new file mode 100755 index 000000000..6ded87fa0 --- /dev/null +++ b/test.py @@ -0,0 +1,26 @@ +#!/usr/bin/env python3 + +import os +import sys +import pytest + +# set IDEFIX_DIR +source_dir = os.path.dirname(__file__) +os.environ["IDEFIX_DIR"] = source_dir + +# idefix test class +sys.path.append(source_dir) +from pytools.idfx_test_run import IdexPytestRunner + +# should be global so it remember state (last build) and avoids +# to build for each run if we just changed the ini file and run options. +gblIdefixPytestRunner = IdexPytestRunner(__file__) + +# define the pytest test +@pytest.mark.parametrize("config", gblIdefixPytestRunner.genTests()) +def test_idefix_build_run_check(config): + gblIdefixPytestRunner.run(config) + +# if called directly as a script +if __name__ == "__main__": + gblIdefixPytestRunner.main(all=True) diff --git a/test/Dust/DustEnergy/testme.json b/test/Dust/DustEnergy/testme.json new file mode 100644 index 000000000..9a78834b9 --- /dev/null +++ b/test/Dust/DustEnergy/testme.json @@ -0,0 +1,12 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": true, + "reconstruction": 2, + "tolerance": 0 + } + ] +} diff --git a/test/Dust/DustEnergy/testme.py b/test/Dust/DustEnergy/testme.py index 7187d299b..12d476b66 100755 --- a/test/Dust/DustEnergy/testme.py +++ b/test/Dust/DustEnergy/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/Dust/DustyShock/testme.json b/test/Dust/DustyShock/testme.json new file mode 100644 index 000000000..d8ddad44f --- /dev/null +++ b/test/Dust/DustyShock/testme.json @@ -0,0 +1,11 @@ +{ + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + } + ] +} diff --git a/test/Dust/DustyShock/testme.py b/test/Dust/DustyShock/testme.py index 2b03d1636..622f34772 100755 --- a/test/Dust/DustyShock/testme.py +++ b/test/Dust/DustyShock/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=1e-14) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/Dust/DustyWave/testme.json b/test/Dust/DustyWave/testme.json new file mode 100644 index 000000000..0050f364e --- /dev/null +++ b/test/Dust/DustyWave/testme.json @@ -0,0 +1,12 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-implicit.ini"], + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + } + ] +} diff --git a/test/Dust/DustyWave/testme.py b/test/Dust/DustyWave/testme.py index 2b03d1636..622f34772 100755 --- a/test/Dust/DustyWave/testme.py +++ b/test/Dust/DustyWave/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=1e-14) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/HD/FargoPlanet/testme.json b/test/HD/FargoPlanet/testme.json new file mode 100644 index 000000000..e1d735828 --- /dev/null +++ b/test/HD/FargoPlanet/testme.json @@ -0,0 +1,25 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini", "idefix-rkl.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": [false, true], + "dec": [2, 2], + "tolerance": 1e-13 + } + ], + "when": [ + { + "conditions": { + "ini": "idefix-rkl.ini" + }, + "apply": { + "tolerance": 1e-12 + } + } + ] +} diff --git a/test/HD/FargoPlanet/testme.py b/test/HD/FargoPlanet/testme.py index 5890d010f..b25a74bb0 100755 --- a/test/HD/FargoPlanet/testme.py +++ b/test/HD/FargoPlanet/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/HD/MachReflection/testme.json b/test/HD/MachReflection/testme.json new file mode 100644 index 000000000..be2d8d950 --- /dev/null +++ b/test/HD/MachReflection/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": [false, true], + "dec": [2, 2], + "tolerance": 0 + } + ] +} diff --git a/test/HD/MachReflection/testme.py b/test/HD/MachReflection/testme.py index ce87f3923..7e6121815 100755 --- a/test/HD/MachReflection/testme.py +++ b/test/HD/MachReflection/testme.py @@ -23,7 +23,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp") -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/HD/SedovBlastWave/testme.json b/test/HD/SedovBlastWave/testme.json new file mode 100644 index 000000000..11327598b --- /dev/null +++ b/test/HD/SedovBlastWave/testme.json @@ -0,0 +1,28 @@ +{ + "namings": "definitionFile,ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "definitionFile": "definitions.hpp", + "ini": ["idefix.ini"], + "vectPot": false, + "reconstruction": 2, + "single": false, + "mpi": true, + "dec": [2, 2, 2 ], + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "definitionFile": "definitions-spherical.hpp", + "ini": ["idefix-spherical.ini"], + "vectPot": false, + "reconstruction": 2, + "single": false, + "mpi": true, + "dec": [2, 2, 2 ], + "standardTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/HD/SedovBlastWave/testme.py b/test/HD/SedovBlastWave/testme.py index 95fdd030a..c3ef7025f 100755 --- a/test/HD/SedovBlastWave/testme.py +++ b/test/HD/SedovBlastWave/testme.py @@ -12,7 +12,7 @@ name="dump.0001.dmp" -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2','2'] diff --git a/test/HD/ShearingBox/testme.json b/test/HD/ShearingBox/testme.json new file mode 100644 index 000000000..3e473d0ba --- /dev/null +++ b/test/HD/ShearingBox/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-fargo.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 1e-15 + } + ] +} diff --git a/test/HD/ShearingBox/testme.py b/test/HD/ShearingBox/testme.py index 3739910a0..18c792656 100755 --- a/test/HD/ShearingBox/testme.py +++ b/test/HD/ShearingBox/testme.py @@ -23,7 +23,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','1','2'] diff --git a/test/HD/ViscousDisk/testme.json b/test/HD/ViscousDisk/testme.json new file mode 100644 index 000000000..df8c19d86 --- /dev/null +++ b/test/HD/ViscousDisk/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 3e-15 + } + ] +} diff --git a/test/HD/ViscousDisk/testme.py b/test/HD/ViscousDisk/testme.py index 1e8ad742b..34628fd80 100755 --- a/test/HD/ViscousDisk/testme.py +++ b/test/HD/ViscousDisk/testme.py @@ -24,7 +24,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/HD/ViscousFlowPastCylinder/testme.json b/test/HD/ViscousFlowPastCylinder/testme.json new file mode 100644 index 000000000..7b3763436 --- /dev/null +++ b/test/HD/ViscousFlowPastCylinder/testme.json @@ -0,0 +1,23 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": [false, true], + "dec": ["2","2"], + "tolerance": 3e-14 + } + ], + "when": { + "conditions": { + "ini": "idefix-rkl.ini" + }, + "apply": { + "tolerance": 1e-8 + } + } +} diff --git a/test/HD/ViscousFlowPastCylinder/testme.py b/test/HD/ViscousFlowPastCylinder/testme.py index c831e8093..832a80e56 100755 --- a/test/HD/ViscousFlowPastCylinder/testme.py +++ b/test/HD/ViscousFlowPastCylinder/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/HD/sod-iso/testme.json b/test/HD/sod-iso/testme.json new file mode 100644 index 000000000..5016415d6 --- /dev/null +++ b/test/HD/sod-iso/testme.json @@ -0,0 +1,33 @@ +{ + "namings": "ini,single,reconstruction", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "vectPot": false, + "noplot": true, + "reconstruction": [2, 3], + "single": [false], + "mpi": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], + "vectPot": false, + "noplot": true, + "reconstruction": [4], + "single": [false], + "mpi": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "vectPot": false, + "noplot": true, + "reconstruction": [2], + "single": [true], + "mpi": false, + "tolerance": 0 + } + ] +} diff --git a/test/HD/sod-iso/testme.py b/test/HD/sod-iso/testme.py index e8f0f9ae2..109109baf 100755 --- a/test/HD/sod-iso/testme.py +++ b/test/HD/sod-iso/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/HD/sod/testme.json b/test/HD/sod/testme.json new file mode 100644 index 000000000..9128c08d4 --- /dev/null +++ b/test/HD/sod/testme.json @@ -0,0 +1,33 @@ +{ + "namings": "ini,single,reconstruction", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "noplot": true, + "vectPot": false, + "single": [false], + "reconstruction": [2,3], + "mpi": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], + "noplot": true, + "vectPot": false, + "single": [false], + "reconstruction": [4], + "mpi": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "noplot": true, + "vectPot": false, + "reconstruction": [2], + "mpi": false, + "single": [true], + "tolerance": 0 + } + ] +} diff --git a/test/HD/sod/testme.py b/test/HD/sod/testme.py index e8f0f9ae2..109109baf 100755 --- a/test/HD/sod/testme.py +++ b/test/HD/sod/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/HD/thermalDiffusion/testme.json b/test/HD/thermalDiffusion/testme.json new file mode 100644 index 000000000..2e89ad747 --- /dev/null +++ b/test/HD/thermalDiffusion/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 0 + } + ] +} diff --git a/test/HD/thermalDiffusion/testme.py b/test/HD/thermalDiffusion/testme.py index 3806293d0..1d1a181b0 100755 --- a/test/HD/thermalDiffusion/testme.py +++ b/test/HD/thermalDiffusion/testme.py @@ -23,7 +23,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp") -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/IO/dump/testme.json b/test/IO/dump/testme.json new file mode 100644 index 000000000..cb69f946f --- /dev/null +++ b/test/IO/dump/testme.json @@ -0,0 +1,28 @@ +{ + "namings": "ini,single,vectPot,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": [false, true], + "reconstruction": 2, + "single": [false], + "mpi": [false, true], + "dec": ["2","2","2"], + "standardTest": false, + "nonRegressionTest": false, + "tolerance": 1e-13 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": [false], + "reconstruction": 2, + "mpi": [false, true], + "single": [true], + "dec": ["2","2","2"], + "standardTest": false, + "nonRegressionTest": false, + "tolerance": 1e-13 + } + ] +} diff --git a/test/IO/dump/testme.py b/test/IO/dump/testme.py index 35affdba2..25e84433b 100755 --- a/test/IO/dump/testme.py +++ b/test/IO/dump/testme.py @@ -21,7 +21,7 @@ def testMe(test): test.run("idefix.ini") -test=tst.idfxTest() +test=tst.idfxTest(__file__) # if no decomposition is specified, use that one if not test.dec: diff --git a/test/IO/pydefix/testme.json b/test/IO/pydefix/testme.json new file mode 100644 index 000000000..78760f724 --- /dev/null +++ b/test/IO/pydefix/testme.json @@ -0,0 +1,17 @@ +{ + "namings": "ini,single,vectPot,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "reconstruction": 2, + "single": false, + "mpi": [false, true], + "dec": ["2","2"], + "standardTest": false, + "tolerance": 1e-12 + } + ] +} diff --git a/test/IO/pydefix/testme.py b/test/IO/pydefix/testme.py index 0a3ad0432..2940e56dd 100755 --- a/test/IO/pydefix/testme.py +++ b/test/IO/pydefix/testme.py @@ -21,7 +21,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/IO/xdmf/testme.json b/test/IO/xdmf/testme.json new file mode 100644 index 000000000..8198bb7bb --- /dev/null +++ b/test/IO/xdmf/testme.json @@ -0,0 +1,17 @@ +{ + "namings": "ini,single,vectPot,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": false, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","2","2"], + "standardTest": false, + "nonRegressionTest": false, + "check_file_produced": [ "data.0001.flt.xmf", "data.0001.flt.h5" ] + } + ] +} diff --git a/test/IO/xdmf/testme.py b/test/IO/xdmf/testme.py index a1e333430..6273bbe0e 100755 --- a/test/IO/xdmf/testme.py +++ b/test/IO/xdmf/testme.py @@ -12,7 +12,7 @@ name="dump.0001.dmp" -test=tst.idfxTest() +test=tst.idfxTest(__file__) def check_xdmf_exists(): # verify that the expected XDMF sidecar and data file exist. diff --git a/test/MHD/AmbipolarCshock/testme.json b/test/MHD/AmbipolarCshock/testme.json new file mode 100644 index 000000000..2eb2ac51f --- /dev/null +++ b/test/MHD/AmbipolarCshock/testme.json @@ -0,0 +1,14 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 0 + } + ] +} diff --git a/test/MHD/AmbipolarCshock/testme.py b/test/MHD/AmbipolarCshock/testme.py index 675958a7b..0e2f0815e 100755 --- a/test/MHD/AmbipolarCshock/testme.py +++ b/test/MHD/AmbipolarCshock/testme.py @@ -23,7 +23,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/AmbipolarCshock3D/testme.json b/test/MHD/AmbipolarCshock3D/testme.json new file mode 100644 index 000000000..fdcb11a76 --- /dev/null +++ b/test/MHD/AmbipolarCshock3D/testme.json @@ -0,0 +1,35 @@ +{ + "namings": "ini,mpi,vectPot", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": [false], + "vectPot": [false, true], + "dec": ["2","1","1"], + "tolerance": 3e-14 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": [true], + "vectPot": [false], + "dec": ["2","1","1"], + "tolerance": 3e-14 + } + ], + "when": { + "conditions": { + "ini": "idefix-rkl.ini", + "mpi": true + }, + "apply": { + "tolerance": 2e-10 + } + } +} diff --git a/test/MHD/AmbipolarCshock3D/testme.py b/test/MHD/AmbipolarCshock3D/testme.py index 964224854..94a8b0f4c 100755 --- a/test/MHD/AmbipolarCshock3D/testme.py +++ b/test/MHD/AmbipolarCshock3D/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','1','1'] diff --git a/test/MHD/AxisFluxTube/testme.json b/test/MHD/AxisFluxTube/testme.json new file mode 100644 index 000000000..781d4f7b3 --- /dev/null +++ b/test/MHD/AxisFluxTube/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-coarsening.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "vectPot": false, + "standardTest": false, + "tolerance": 1e-14 + } + ] +} diff --git a/test/MHD/AxisFluxTube/testme.py b/test/MHD/AxisFluxTube/testme.py index 44a53dc28..5abb46568 100755 --- a/test/MHD/AxisFluxTube/testme.py +++ b/test/MHD/AxisFluxTube/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/Coarsening/testme.json b/test/MHD/Coarsening/testme.json new file mode 100644 index 000000000..5b38ffebb --- /dev/null +++ b/test/MHD/Coarsening/testme.json @@ -0,0 +1,12 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini","idefix-x2.ini","idefix-x3.ini"], + "noplot": true, + "mpi": [false,true], + "tolerance": 0 + } + ] +} diff --git a/test/MHD/Coarsening/testme.py b/test/MHD/Coarsening/testme.py index 52a083bd2..50d13c926 100755 --- a/test/MHD/Coarsening/testme.py +++ b/test/MHD/Coarsening/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/FargoMHDSpherical/testme.json b/test/MHD/FargoMHDSpherical/testme.json new file mode 100644 index 000000000..72d93f493 --- /dev/null +++ b/test/MHD/FargoMHDSpherical/testme.json @@ -0,0 +1,17 @@ +{ + "namings": "ini,mpi,vectPot", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "vectPot": [false, true], + "mpi": [false, true], + "dec": ["2","2","2"], + "standardTest": false, + "tolerance": 1e-14 + } + ] +} diff --git a/test/MHD/FargoMHDSpherical/testme.py b/test/MHD/FargoMHDSpherical/testme.py index 7ee3100b2..1a3b28adb 100755 --- a/test/MHD/FargoMHDSpherical/testme.py +++ b/test/MHD/FargoMHDSpherical/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2','2'] diff --git a/test/MHD/HallWhistler/testme.json b/test/MHD/HallWhistler/testme.json new file mode 100644 index 000000000..cc71c4bf7 --- /dev/null +++ b/test/MHD/HallWhistler/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 1e-15 + } + ] +} diff --git a/test/MHD/HallWhistler/testme.py b/test/MHD/HallWhistler/testme.py index f8d633840..f8ba0a258 100755 --- a/test/MHD/HallWhistler/testme.py +++ b/test/MHD/HallWhistler/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/LinearWaveTest/testme.json b/test/MHD/LinearWaveTest/testme.json new file mode 100644 index 000000000..a3f997e34 --- /dev/null +++ b/test/MHD/LinearWaveTest/testme.json @@ -0,0 +1,24 @@ +{ + "namings": "ini,reconstruction,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], + "noplot": true, + "single": false, + "reconstruction": [2], + "mpi": [false,true], + "dec": ["2","2","2"], + "tolerance": 2e-13 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], + "noplot": true, + "single": false, + "reconstruction": [3, 4], + "mpi": [false], + "dec": ["2","2","2"], + "tolerance": 2e-13 + } + ] +} diff --git a/test/MHD/LinearWaveTest/testme.py b/test/MHD/LinearWaveTest/testme.py index 390a5759b..eeaaab0fe 100755 --- a/test/MHD/LinearWaveTest/testme.py +++ b/test/MHD/LinearWaveTest/testme.py @@ -24,7 +24,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2','2'] diff --git a/test/MHD/MTI/testme.json b/test/MHD/MTI/testme.json new file mode 100644 index 000000000..3bd669cca --- /dev/null +++ b/test/MHD/MTI/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini","idefix-sl.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 0 + } + ] +} diff --git a/test/MHD/MTI/testme.py b/test/MHD/MTI/testme.py index 7975c8075..0e2c9e317 100755 --- a/test/MHD/MTI/testme.py +++ b/test/MHD/MTI/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/OrszagTang/testme.json b/test/MHD/OrszagTang/testme.json new file mode 100644 index 000000000..3128b3239 --- /dev/null +++ b/test/MHD/OrszagTang/testme.json @@ -0,0 +1,74 @@ +{ + "namings": "ini,reconstruction,mpi,single,vectPot", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "noplot": true, + "vectPot": [false], + "single": false, + "reconstruction": [2,3,4], + "mpi": [false, true], + "dec": ["2","2"], + "tolerance": 1e-12, + "standardTest": false + },{ + "dumpname": "dump.0001.dmp", + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "noplot": true, + "vectPot": [false], + "single": true, + "reconstruction": [2], + "mpi": [false], + "dec": ["2","2"], + "tolerance": 1e-12, + "standardTest": false + },{ + "dumpname": "dump.0001.dmp", + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "noplot": true, + "vectPot": [true], + "single": false, + "reconstruction": [2], + "mpi": [false], + "dec": ["2","2"], + "tolerance": 1e-12, + "standardTest": false + } + ], + "when": { + "conditions": { + "single": true + }, + "apply" : { + "tolerance": 1e-5 + } + } +} diff --git a/test/MHD/OrszagTang/testme.py b/test/MHD/OrszagTang/testme.py index 761505caa..41f33aba6 100755 --- a/test/MHD/OrszagTang/testme.py +++ b/test/MHD/OrszagTang/testme.py @@ -33,7 +33,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/MHD/OrszagTang3D/testme.json b/test/MHD/OrszagTang3D/testme.json new file mode 100644 index 000000000..a37b54164 --- /dev/null +++ b/test/MHD/OrszagTang3D/testme.json @@ -0,0 +1,34 @@ +{ + "namings": "ini,single,vectPot,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": [false, true], + "reconstruction": 2, + "single": [false], + "mpi": [false, true], + "dec": ["2","2","2"], + "standardTest": false, + "tolerance": 1e-13 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "vectPot": [false], + "reconstruction": 2, + "mpi": [false, true], + "single": [true], + "dec": ["2","2","2"], + "standardTest": false, + "tolerance": 1e-13 + } + ], + "when": { + "conditions": { + "single": true + }, + "apply" : { + "tolerance": 1e-6 + } + } +} diff --git a/test/MHD/OrszagTang3D/testme.py b/test/MHD/OrszagTang3D/testme.py index b9626f9cc..7a66150c5 100755 --- a/test/MHD/OrszagTang3D/testme.py +++ b/test/MHD/OrszagTang3D/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) # if no decomposition is specified, use that one if not test.dec: diff --git a/test/MHD/ResistiveAlfvenWave/testme.json b/test/MHD/ResistiveAlfvenWave/testme.json new file mode 100644 index 000000000..56ae122ec --- /dev/null +++ b/test/MHD/ResistiveAlfvenWave/testme.json @@ -0,0 +1,22 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-rkl.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "tolerance": 1e-14 + } + ], + "when": { + "conditions": { + "ini": "idefix-rkl.ini" + }, + "apply" : { + "tolerance": 1e-10 + } + } +} diff --git a/test/MHD/ResistiveAlfvenWave/testme.py b/test/MHD/ResistiveAlfvenWave/testme.py index f9b8ae56f..ebc29ab57 100755 --- a/test/MHD/ResistiveAlfvenWave/testme.py +++ b/test/MHD/ResistiveAlfvenWave/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/ShearingBox/testme.json b/test/MHD/ShearingBox/testme.json new file mode 100644 index 000000000..71ae0ab0d --- /dev/null +++ b/test/MHD/ShearingBox/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-fargo.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","1","2"], + "tolerance": 1e-14 + } + ] +} diff --git a/test/MHD/ShearingBox/testme.py b/test/MHD/ShearingBox/testme.py index 364adde9b..ccee1a69c 100755 --- a/test/MHD/ShearingBox/testme.py +++ b/test/MHD/ShearingBox/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','1','2'] diff --git a/test/MHD/clessTDiffusion/testme.json b/test/MHD/clessTDiffusion/testme.json new file mode 100644 index 000000000..d615696f5 --- /dev/null +++ b/test/MHD/clessTDiffusion/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "vectPot": false, + "tolerance": 2e-15 + } + ] +} diff --git a/test/MHD/clessTDiffusion/testme.py b/test/MHD/clessTDiffusion/testme.py index 6ed5b1648..41193e141 100755 --- a/test/MHD/clessTDiffusion/testme.py +++ b/test/MHD/clessTDiffusion/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name, tolerance=2e-15) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/sod-iso/testme.json b/test/MHD/sod-iso/testme.json new file mode 100644 index 000000000..9f5534fbc --- /dev/null +++ b/test/MHD/sod-iso/testme.json @@ -0,0 +1,43 @@ +{ + "namings": "ini,reconstruction,single", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], + "vectPot": false, + "single": false, + "reconstruction": [2,3], + "mpi": false, + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-rk3.ini","idefix-hlld-rk3.ini"], + "vectPot": false, + "single": false, + "reconstruction": [4], + "mpi": false, + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], + "vectPot": false, + "reconstruction": [2], + "mpi": false, + "single": true, + "standardTest": false, + "tolerance": 0 + } + ], + "when": [ + { + "conditions": { + "ini": "idefix-rkl.ini" + }, + "apply": { + "tolerance": 1e-10 + } + } + ] +} diff --git a/test/MHD/sod-iso/testme.py b/test/MHD/sod-iso/testme.py index 798aace57..c85cc4ce7 100755 --- a/test/MHD/sod-iso/testme.py +++ b/test/MHD/sod-iso/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/sod/testme.json b/test/MHD/sod/testme.json new file mode 100644 index 000000000..1501e3049 --- /dev/null +++ b/test/MHD/sod/testme.json @@ -0,0 +1,33 @@ +{ + "namings": "ini,reconstruction,single", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], + "vectPot": false, + "single": false, + "reconstruction": [2,3], + "mpi": false, + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix-rk3.ini","idefix-hlld-rk3.ini"], + "vectPot": false, + "single": false, + "reconstruction": 4, + "mpi": false, + "standardTest": false, + "tolerance": 0 + },{ + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], + "vectPot": false, + "reconstruction": 2, + "mpi": false, + "single": true, + "standardTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/MHD/sod/testme.py b/test/MHD/sod/testme.py index 798aace57..c85cc4ce7 100755 --- a/test/MHD/sod/testme.py +++ b/test/MHD/sod/testme.py @@ -27,7 +27,7 @@ def testMe(test): test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/sphBragTDiffusion/testme.json b/test/MHD/sphBragTDiffusion/testme.json new file mode 100644 index 000000000..c4cb9a334 --- /dev/null +++ b/test/MHD/sphBragTDiffusion/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 2e-15 + } + ] +} diff --git a/test/MHD/sphBragTDiffusion/testme.py b/test/MHD/sphBragTDiffusion/testme.py index 6ed5b1648..41193e141 100755 --- a/test/MHD/sphBragTDiffusion/testme.py +++ b/test/MHD/sphBragTDiffusion/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.nonRegressionTest(filename=name, tolerance=2e-15) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/MHD/sphBragViscosity/testme.json b/test/MHD/sphBragViscosity/testme.json new file mode 100644 index 000000000..900a34a77 --- /dev/null +++ b/test/MHD/sphBragViscosity/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 1e-15 + } + ] +} diff --git a/test/MHD/sphBragViscosity/testme.py b/test/MHD/sphBragViscosity/testme.py index 254417f44..b6c3467ea 100755 --- a/test/MHD/sphBragViscosity/testme.py +++ b/test/MHD/sphBragViscosity/testme.py @@ -29,7 +29,7 @@ def testMe(test): test.nonRegressionTest(filename=name, tolerance=1e-15) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/Planet/Planet3Body/testme.json b/test/Planet/Planet3Body/testme.json new file mode 100644 index 000000000..2b2fad202 --- /dev/null +++ b/test/Planet/Planet3Body/testme.json @@ -0,0 +1,15 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "tolerance": 2e-11 + } + ] +} diff --git a/test/Planet/Planet3Body/testme.py b/test/Planet/Planet3Body/testme.py index c11d08963..6edac53ee 100755 --- a/test/Planet/Planet3Body/testme.py +++ b/test/Planet/Planet3Body/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/Planet/PlanetMigration2D/testme.json b/test/Planet/PlanetMigration2D/testme.json new file mode 100644 index 000000000..6e1e08537 --- /dev/null +++ b/test/Planet/PlanetMigration2D/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","2"], + "tolerance": 1e-13 + } + ] +} diff --git a/test/Planet/PlanetMigration2D/testme.py b/test/Planet/PlanetMigration2D/testme.py index 0921d4e62..6c435cbd3 100755 --- a/test/Planet/PlanetMigration2D/testme.py +++ b/test/Planet/PlanetMigration2D/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/Planet/PlanetPlanetRK42D/testme.json b/test/Planet/PlanetPlanetRK42D/testme.json new file mode 100644 index 000000000..0181b072f --- /dev/null +++ b/test/Planet/PlanetPlanetRK42D/testme.json @@ -0,0 +1,25 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0002.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","2"], + "tolerance": 1e-13, + "multirun": [ + { + "nonRegressionTest": true, + "standardTest": true + },{ + "restart": true, + "restart_no_overwrite": ["dump.0001.dmp", "data.0005.vtk"] + } + ] + } + ] +} diff --git a/test/Planet/PlanetPlanetRK42D/testme.py b/test/Planet/PlanetPlanetRK42D/testme.py index 26cb8ee21..9521aabac 100755 --- a/test/Planet/PlanetPlanetRK42D/testme.py +++ b/test/Planet/PlanetPlanetRK42D/testme.py @@ -38,7 +38,7 @@ def testMe(test): assert dump_mtime == os.path.getmtime("dump.0001.dmp"), "Dump was overwritten on restart" assert vtk_mtime == os.path.getmtime("data.0005.vtk"), "VTK file was overwritten on restart" -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/Planet/PlanetSpiral2D/testme.json b/test/Planet/PlanetSpiral2D/testme.json new file mode 100644 index 000000000..6e1e08537 --- /dev/null +++ b/test/Planet/PlanetSpiral2D/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","2"], + "tolerance": 1e-13 + } + ] +} diff --git a/test/Planet/PlanetSpiral2D/testme.py b/test/Planet/PlanetSpiral2D/testme.py index 0921d4e62..6c435cbd3 100755 --- a/test/Planet/PlanetSpiral2D/testme.py +++ b/test/Planet/PlanetSpiral2D/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/Planet/PlanetTorque3D/testme.json b/test/Planet/PlanetTorque3D/testme.json new file mode 100644 index 000000000..085fb6c0f --- /dev/null +++ b/test/Planet/PlanetTorque3D/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","2","2"], + "tolerance": 1e-13 + } + ] +} diff --git a/test/Planet/PlanetTorque3D/testme.py b/test/Planet/PlanetTorque3D/testme.py index b4f04a507..4393636ea 100755 --- a/test/Planet/PlanetTorque3D/testme.py +++ b/test/Planet/PlanetTorque3D/testme.py @@ -28,7 +28,7 @@ def testMe(test): test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2','2'] diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.json b/test/Planet/PlanetsIsActiveRK52D/testme.json new file mode 100644 index 000000000..30848aecd --- /dev/null +++ b/test/Planet/PlanetsIsActiveRK52D/testme.json @@ -0,0 +1,17 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix-rk4.ini", "idefix-rk5.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2","2"], + "nonRegressionTest": false, + "tolerance": 1e-13 + } + ] +} diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.py b/test/Planet/PlanetsIsActiveRK52D/testme.py index ce0d405c0..aca39ae53 100755 --- a/test/Planet/PlanetsIsActiveRK52D/testme.py +++ b/test/Planet/PlanetsIsActiveRK52D/testme.py @@ -26,7 +26,7 @@ def testMe(test): # test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2'] diff --git a/test/SelfGravity/DustyCollapse/testme.json b/test/SelfGravity/DustyCollapse/testme.json new file mode 100644 index 000000000..8afbcdb6d --- /dev/null +++ b/test/SelfGravity/DustyCollapse/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "nonRegressionTest": false, + "tolerance": 1e-13 + } + ] +} diff --git a/test/SelfGravity/DustyCollapse/testme.py b/test/SelfGravity/DustyCollapse/testme.py index 689038265..2df3893ab 100755 --- a/test/SelfGravity/DustyCollapse/testme.py +++ b/test/SelfGravity/DustyCollapse/testme.py @@ -25,7 +25,7 @@ def testMe(test): test.standardTest() -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/SelfGravity/JeansInstability/testme.json b/test/SelfGravity/JeansInstability/testme.json new file mode 100644 index 000000000..bf4819389 --- /dev/null +++ b/test/SelfGravity/JeansInstability/testme.json @@ -0,0 +1,17 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-cg.ini"], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": [false, true], + "dec": ["2"], + "nonRegressionTest": false, + "tolerance": 1e-13 + } + ] +} diff --git a/test/SelfGravity/JeansInstability/testme.py b/test/SelfGravity/JeansInstability/testme.py index ff2f39a83..833feb262 100755 --- a/test/SelfGravity/JeansInstability/testme.py +++ b/test/SelfGravity/JeansInstability/testme.py @@ -26,7 +26,7 @@ def testMe(test): test.standardTest() -test=tst.idfxTest() +test=tst.idfxTest(__file__) # if no decomposition is specified, use that one if not test.dec: diff --git a/test/SelfGravity/RandomSphere/testme.json b/test/SelfGravity/RandomSphere/testme.json new file mode 100644 index 000000000..d5cda3135 --- /dev/null +++ b/test/SelfGravity/RandomSphere/testme.json @@ -0,0 +1,14 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-cg.ini","idefix-minres.ini"], + "noplot": true, + "mpi": [false, true], + "dec": ["2","2","1"], + "nonRegressionTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/SelfGravity/RandomSphere/testme.py b/test/SelfGravity/RandomSphere/testme.py index 38fc30d92..65123498b 100755 --- a/test/SelfGravity/RandomSphere/testme.py +++ b/test/SelfGravity/RandomSphere/testme.py @@ -26,7 +26,7 @@ def testMe(test): #test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.dec: test.dec=['2','2','1'] diff --git a/test/SelfGravity/RandomSphereCartesian/testme.json b/test/SelfGravity/RandomSphereCartesian/testme.json new file mode 100644 index 000000000..85f0f3889 --- /dev/null +++ b/test/SelfGravity/RandomSphereCartesian/testme.json @@ -0,0 +1,12 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini","idefix-cg.ini","idefix-minres.ini","idefix-jacobi.ini"], + "noplot": true, + "nonRegressionTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/SelfGravity/RandomSphereCartesian/testme.py b/test/SelfGravity/RandomSphereCartesian/testme.py index 64b4a9ba5..598aa3f21 100755 --- a/test/SelfGravity/RandomSphereCartesian/testme.py +++ b/test/SelfGravity/RandomSphereCartesian/testme.py @@ -26,7 +26,7 @@ def testMe(test): #test.nonRegressionTest(filename=name) -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: testMe(test) else: diff --git a/test/SelfGravity/UniformCollapse/testme.json b/test/SelfGravity/UniformCollapse/testme.json new file mode 100644 index 000000000..3de00c4df --- /dev/null +++ b/test/SelfGravity/UniformCollapse/testme.json @@ -0,0 +1,16 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 0, + "nonRegressionTest": false + } + ] +} diff --git a/test/SelfGravity/UniformCollapse/testme.py b/test/SelfGravity/UniformCollapse/testme.py index 21debc0e0..69918896b 100755 --- a/test/SelfGravity/UniformCollapse/testme.py +++ b/test/SelfGravity/UniformCollapse/testme.py @@ -25,7 +25,7 @@ def testMe(test): test.standardTest() -test=tst.idfxTest() +test=tst.idfxTest(__file__) if not test.all: if(test.check): diff --git a/test/python_requirements.txt b/test/python_requirements.txt index 77ce6e9c2..9cf2383a2 100644 --- a/test/python_requirements.txt +++ b/test/python_requirements.txt @@ -8,3 +8,7 @@ scipy>=1.2.3 # note that no version of inifix supports Python older than 3.6 inifix>=0.11.2 + +# To run the test suite, we can use pytest, mostly any version +# 6.0 is the one available on system available on debian-11 +pytest >= 6.0 diff --git a/test/utils/columnDensity/testme.json b/test/utils/columnDensity/testme.json new file mode 100644 index 000000000..718413c4d --- /dev/null +++ b/test/utils/columnDensity/testme.json @@ -0,0 +1,13 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "mpi": [false,true], + "nonRegressionTest": false, + "standardTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/utils/columnDensity/testme.py b/test/utils/columnDensity/testme.py index 6f017d7d8..cd94eb4ef 100755 --- a/test/utils/columnDensity/testme.py +++ b/test/utils/columnDensity/testme.py @@ -9,7 +9,7 @@ sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -test=tst.idfxTest() +test=tst.idfxTest(__file__) test.configure() test.compile() diff --git a/test/utils/dumpImage/testme.json b/test/utils/dumpImage/testme.json new file mode 100644 index 000000000..718413c4d --- /dev/null +++ b/test/utils/dumpImage/testme.json @@ -0,0 +1,13 @@ +{ + "namings": "ini,mpi", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini": ["idefix.ini"], + "mpi": [false,true], + "nonRegressionTest": false, + "standardTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/utils/dumpImage/testme.py b/test/utils/dumpImage/testme.py index 6f017d7d8..cd94eb4ef 100755 --- a/test/utils/dumpImage/testme.py +++ b/test/utils/dumpImage/testme.py @@ -9,7 +9,7 @@ sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -test=tst.idfxTest() +test=tst.idfxTest(__file__) test.configure() test.compile() diff --git a/test/utils/lookupTable/testme.json b/test/utils/lookupTable/testme.json new file mode 100644 index 000000000..8ea6f6961 --- /dev/null +++ b/test/utils/lookupTable/testme.json @@ -0,0 +1,12 @@ +{ + "namings": "ini", + "variants": [ + { + "dumpname": "dump.0001.dmp", + "ini":["idefix.ini"], + "nonRegressionTest": false, + "standardTest": false, + "tolerance": 0 + } + ] +} diff --git a/test/utils/lookupTable/testme.py b/test/utils/lookupTable/testme.py index d40884652..53f6607f2 100755 --- a/test/utils/lookupTable/testme.py +++ b/test/utils/lookupTable/testme.py @@ -30,7 +30,7 @@ def MakeNumpyFile(): -test=tst.idfxTest() +test=tst.idfxTest(__file__) MakeNumpyFile() test.configure() From 3c69e4515c73153b6a072d2872c3f120d1380fe2 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Apr 2026 18:15:47 +0200 Subject: [PATCH 101/144] update version number --- CHANGELOG.md | 2 +- CMakeLists.txt | 6 +++--- doc/source/conf.py | 2 +- src/main.cpp | 2 +- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f18371de3..10ae74f6e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,7 +4,7 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). -## [2.2.1] 2026-04-21 +## [2.3.0] 2026-04-21 ### Changed - fixed a bug that could lead to diverging results around the spherical axis in non-ideal MHD in 2.5D and 3D (#356) diff --git a/CMakeLists.txt b/CMakeLists.txt index ea4a71537..6698aaec6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -5,10 +5,10 @@ endif() set (CMAKE_CXX_STANDARD 17) set(Idefix_VERSION_MAJOR 2) -set(Idefix_VERSION_MINOR 2) -set(Idefix_VERSION_PATCH 02) +set(Idefix_VERSION_MINOR 3) +set(Idefix_VERSION_PATCH 0) -project (idefix VERSION 2.2.02) +project (idefix VERSION 2.3.0) option(Idefix_MHD "enable MHD" OFF) option(Idefix_MPI "enable Message Passing Interface parallelisation" OFF) option(Idefix_HIGH_ORDER_FARGO "Force Fargo to use a PPM reconstruction scheme" OFF) diff --git a/doc/source/conf.py b/doc/source/conf.py index 595672c25..f47f6659c 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -23,7 +23,7 @@ author = 'Geoffroy Lesur' # The full version, including alpha/beta/rc tags -release = '2.2.02' +release = '2.3.0' diff --git a/src/main.cpp b/src/main.cpp index 7b2c00c85..a2dcd630a 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -9,7 +9,7 @@ //@HEADER // ************************************************************************ // -// IDEFIX v 2.2.01 +// IDEFIX v 2.3.0 // // ************************************************************************ //@HEADER From 5be7d71d99282e1f84853b2350b5cae4411b0ac9 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 21 Apr 2026 21:01:02 +0200 Subject: [PATCH 102/144] fix security in ci-jobs --- .github/workflows/idefix-ci-jobs.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index 7c9333092..847ba3cbe 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -231,9 +231,10 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@v3 + uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 with: submodules: recursive + persist-credentials: false - name: Restart dumps run: scripts/ci/run-tests $IDEFIX_DIR/test/IO/dump -all $TESTME_OPTIONS - name: Pydefix From 62c32562d4a842de5472959cbec5affda9c56d81 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 22 Apr 2026 09:49:07 +0200 Subject: [PATCH 103/144] add pytest PR to changelog --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 10ae74f6e..6bb7f979e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -18,6 +18,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - magnetic vector potential is now accessible from pydefix when enabled (#361) - use ccache in the test suite to reduce the runtime of continuous integration (#364) - automatically detects pybind11 path with cmake when using pydefix (#367) +- skeleton to run the test suite with pytest (#366) ## [2.2.02] 2025-10-18 From b6bdd5acf60184c2a8da8a11cc30e119fd86f800 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 22 Apr 2026 09:49:33 +0200 Subject: [PATCH 104/144] bump up sphinx package requirements for readthedocs --- doc/python_requirements.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/doc/python_requirements.txt b/doc/python_requirements.txt index c75fa02b7..28715fb71 100644 --- a/doc/python_requirements.txt +++ b/doc/python_requirements.txt @@ -6,12 +6,12 @@ # python -m pip install -r python_requirements.txt wheel>=0.38.4 # help forward compatibility for pip with old sphinx plugins -sphinx==5.3.0 -sphinx_rtd_theme==1.3.0 +sphinx==9.1.0 +sphinx_rtd_theme==3.1.0 sphinx_git==11.0.0 -breathe==4.34.0 +breathe==4.36.0 exhale==0.3.7 -m2r2==0.3.2 +m2r2==0.3.4 sphinx-copybutton==0.5.2 #sphinxcontrib-applehelp==1.0.7 matplotlib==3.10.0 From 0ef3886d16aec0e8791e1032aa2836e5682939b0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Thu, 4 Jun 2026 15:56:05 +0200 Subject: [PATCH 105/144] test: add "default" semantic to testme.json files (#378) * test: add the "default" keyword for testme.json and port all testme.json to it * test: update doc to document de "default" behavior * test: fix missing disabling nonRegressionTest for test/HD/SedovBlastWave in testme.json * test: enable logging all streams (log, stdout, sterr) in junit file (to prepare following patches for CI) --- doc/source/testing/testLauncher.rst | 63 ++++---- pytest.ini | 2 +- pytools/idfx_test.py | 2 +- pytools/idfx_test_gen.py | 18 ++- pytools/idfx_test_run.py | 17 ++- pytools/tests/test/pb1/testme.json | 12 +- pytools/tests/test/pb2/testme.json | 14 +- test/Dust/DustEnergy/testme.json | 12 +- test/Dust/DustyShock/testme.json | 12 +- test/Dust/DustyWave/testme.json | 12 +- test/HD/FargoPlanet/testme.json | 16 ++- test/HD/MachReflection/testme.json | 16 ++- test/HD/SedovBlastWave/testme.json | 31 ++-- test/HD/ShearingBox/testme.json | 28 ++-- test/HD/ViscousDisk/testme.json | 28 ++-- test/HD/ViscousFlowPastCylinder/testme.json | 42 +++--- test/HD/sod-iso/testme.json | 54 +++---- test/HD/sod/testme.json | 54 +++---- test/HD/thermalDiffusion/testme.json | 28 ++-- test/IO/dump/testme.json | 47 +++--- test/IO/pydefix/testme.json | 30 ++-- test/IO/xdmf/testme.json | 25 ++-- test/MHD/AmbipolarCshock/testme.json | 26 ++-- test/MHD/AmbipolarCshock3D/testme.json | 62 ++++---- test/MHD/AxisFluxTube/testme.json | 30 ++-- test/MHD/Coarsening/testme.json | 22 +-- test/MHD/FargoMHDSpherical/testme.json | 32 +++-- test/MHD/HallWhistler/testme.json | 23 ++- test/MHD/LinearWaveTest/testme.json | 42 +++--- test/MHD/MTI/testme.json | 28 ++-- test/MHD/OrszagTang/testme.json | 134 ++++++++---------- test/MHD/OrszagTang3D/testme.json | 59 ++++---- test/MHD/ResistiveAlfvenWave/testme.json | 14 +- test/MHD/ShearingBox/testme.json | 16 ++- test/MHD/clessTDiffusion/testme.json | 23 ++- test/MHD/sod-iso/testme.json | 28 ++-- test/MHD/sod/testme.json | 23 ++- test/MHD/sphBragTDiffusion/testme.json | 23 ++- test/MHD/sphBragViscosity/testme.json | 25 ++-- test/Planet/PlanetMigration2D/testme.json | 22 +-- test/Planet/PlanetPlanetRK42D/testme.json | 20 +-- test/Planet/PlanetSpiral2D/testme.json | 22 +-- test/Planet/PlanetTorque3D/testme.json | 18 +-- test/Planet/PlanetsIsActiveRK52D/testme.json | 20 +-- test/SelfGravity/DustyCollapse/testme.json | 22 +-- test/SelfGravity/JeansInstability/testme.json | 20 +-- test/SelfGravity/RandomSphere/testme.json | 14 +- .../RandomSphereCartesian/testme.json | 12 +- test/SelfGravity/UniformCollapse/testme.json | 25 ++-- test/utils/columnDensity/testme.json | 16 ++- test/utils/lookupTable/testme.json | 17 +-- 51 files changed, 699 insertions(+), 702 deletions(-) diff --git a/doc/source/testing/testLauncher.rst b/doc/source/testing/testLauncher.rst index aea7f5c3d..ffb80ef9f 100644 --- a/doc/source/testing/testLauncher.rst +++ b/doc/source/testing/testLauncher.rst @@ -144,7 +144,7 @@ For a single basic configuration one can use : .. code-block:: json { - "variants": { + "default": { "dumpname": "dump.0001.dmp", "ini": "idefix.ini", "vectPot": false, @@ -159,7 +159,7 @@ For a single basic configuration one can use : Available parameters -------------------- -The parameters in the ``variants`` dictionnary correspond to the options supported by the +The parameters in the ``default`` dictionnary correspond to the options supported by the :doc:`idfxTest ` script to configure the build and run of *Idefix*. In addition there is some extra keys which are dedicated to the json interpretation layer : @@ -195,22 +195,24 @@ In addition there is some extra keys which are dedicated to the json interpretat Looping over parameters ----------------------- -You might want to explore running Idefix within parameter ranges (configuration files, modes). -For this simply list the values you want as a list. The test script will automatically -generate all combinations. +You might want to explore running *Idefix* within parameter ranges (configuration files, modes). +For this simply list the values you want as a list in tha ``variants`` dictionnary. The test script +will automatically generate all combinations. .. code-block:: json { - "variants": { + "default": { "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini"], - "vectPot": [false, true], "single": false, "reconstruction": 2, - "mpi": [false, true], "standardTest": false, "tolerance": 0 + }, + "variants": { + "ini": ["idefix.ini","idefix-hll.ini"], + "vectPot": [false, true], + "mpi": [false, true] } } @@ -245,25 +247,24 @@ can list several sets as a list. Here using single only on half of the modes. .. code-block:: json { + "default": { + "dumpname": "dump.0001.dmp", + "tolerance": 0 + "standardTest": false, + "reconstruction": 2 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], + "ini": "idefix.ini", "vectPot": false, "single": false, - "reconstruction": 2, "mpi": [false, true], - "standardTest": false, - "tolerance": 0 },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix-hll.ini"], + "ini": "idefix-hll.ini", "vectPot": true, "single": true, - "reconstruction": 2, "mpi": [false, true], - "standardTest": false, - "tolerance": 0 + } ] } @@ -284,15 +285,17 @@ the order you want to see them composing the test name. { "namings": "ini,single,mpi", - "variants": { + "default": { "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini"], "vectPot": false, - "single": [false, true], "reconstruction": 2, - "mpi": [false, true], "standardTest": false, "tolerance": 0 + }, + "variants": { + "ini": ["idefix.ini","idefix-hll.ini"], + "single": [false, true], + "mpi": [false, true], } } @@ -309,16 +312,18 @@ It is just like if you used and IF statement. { "namings": "ini,single,mpi", - "variants": { + "default": { "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini"], "vectPot": false, - "single": [false, true], "reconstruction": 2, - "mpi": [false, true], "standardTest": false, "tolerance": 0 }, + "variants": { + "ini": ["idefix.ini","idefix-hll.ini"], + "single": [false, true], + "mpi": [false, true], + }, "when": { "conditions": { "single": true @@ -348,9 +353,9 @@ They are described like : .. code-block:: json { - "variants": { + "default": { "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], + "ini": "idefix.ini", "vectPot": false, "single": false, "reconstruction": 2, diff --git a/pytest.ini b/pytest.ini index b3482664f..33a7f2a95 100644 --- a/pytest.ini +++ b/pytest.ini @@ -2,5 +2,5 @@ markers= default: Test to run by default. python_files="test_*.py" -junit_logging="system-out" +junit_logging="all" junit_log_passing_tests=false diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index fd28ccb61..be35e78e5 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -169,7 +169,7 @@ def addLog(self, entry): def applyConfig(self, config: dict={}): # check args for key, value in config.items(): - if key not in ['ini', 'testfile', 'testname', 'dumpname']: + if key not in ['ini', 'testfile', 'testname', 'dumpname', 'check_file_produced']: assert key in self.cmdArgs, f"The given configuration overriding try to set an invalid paramater : {key}={value}" # override options diff --git a/pytools/idfx_test_gen.py b/pytools/idfx_test_gen.py index e552c321d..e45f927d0 100644 --- a/pytools/idfx_test_gen.py +++ b/pytools/idfx_test_gen.py @@ -32,7 +32,7 @@ def __init__(self, currentTestFile: str, name: str = ""): self.currentTestName = name # generate the list of configs to run - def genTestConfigs(self, names:str, params, whenClauses = {}) -> list: + def genTestConfigs(self, names:str, params, whenClauses = {}, defaultConfig: dict = {}) -> list: ''' Generate the the list of configurations as pytest parameters. It will unpack the configuration set by looping on all combinations defined @@ -48,20 +48,24 @@ def genTestConfigs(self, names:str, params, whenClauses = {}) -> list: whenCaluses (dict|list): Provide a set of clauses to apply after unpacking the configuration so we can patch some values depending on some others. + defaultConfig (dict): + The default configuration on top of which to apply the variants. Returns: A list of pytest.param() ready to be fiven to parametrized pytest functions. ''' # get name ordering list nameList = names.split(',') + if '' in nameList: + nameList.remove('') # gen list of complete configs all_configs = [] if isinstance(params, dict): - all_configs += self._genOneConfigSeries(names, params) + all_configs += self._genOneConfigSeries(names, params, defaultConfig=defaultConfig) elif isinstance(params, list): for p in params: - all_configs += self._genOneConfigSeries(names, p) + all_configs += self._genOneConfigSeries(names, p, defaultConfig=defaultConfig) else: raise Exception("Should never be called !") @@ -155,7 +159,7 @@ def _genNextLevelCombinations(self, input: list, paramName: str, paramValues: li result.append(v) return result - def _genOneConfigSeries(self, names: str, config: dict) -> list: + def _genOneConfigSeries(self, names: str, config: dict, defaultConfig: dict={}) -> list: ''' Generate the the list of configurations as pytest parameters. It will unpack the configuration set by looping on all combinations defined @@ -167,6 +171,8 @@ def _genOneConfigSeries(self, names: str, config: dict) -> list: name of the file. config (dict): A configuration set as a dictionnary. + defaultConfig (dict): + The default configuration to overload with the variant part. Returns: A list of pytest.param() ready to be fiven to parametrized pytest functions. @@ -179,9 +185,11 @@ def _genOneConfigSeries(self, names: str, config: dict) -> list: if 'ini' in loopOrder: loopOrder.remove('ini') loopOrder.append('ini') + if '' in loopOrder: + loopOrder.remove('') # init core with everything not a list - core = {} + core = copy.deepcopy(defaultConfig) for key, value in config.items(): if isinstance(value, list) and key not in DO_NOT_LOOP_ON: assert key in nameList, f"All variable parameteres should be ordered in the names list, '{key}' is not." diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index d14de0b41..a4ad268da 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -85,20 +85,27 @@ def genTests(self) -> list: # load json & build the inner test combinations with open(testfilePath, 'r') as fp: + # load test = json.load(fp) idefixTestGenerator=IdefixDirTestGenerator(testfilePath, testfileDir) + + # extract default config & when & variants + defaultConfig = test.get('default', {}) + whenClauses = test.get('when', {}) + variants = test.get('variants', {}) + if 'namings' in test: namings = test['namings'] - autoExtracted = idefixTestGenerator.extractNamingParameters(test['variants']) + autoExtracted = idefixTestGenerator.extractNamingParameters(variants) self._validateNaming(namings, autoExtracted, testfilePath) else: - namings = idefixTestGenerator.extractNamingParameters(test['variants']) + namings = idefixTestGenerator.extractNamingParameters(variants) # required to simplify the algos later, if var is listed as variable, we need to loop over it. - self._makeVariableArgAsList(namings, test['variants']) + self._makeVariableArgAsList(namings, variants) # gen - result += idefixTestGenerator.genTestConfigs(namings, test['variants'], test.get('when', {})) + result += idefixTestGenerator.genTestConfigs(namings, variants, whenClauses=whenClauses, defaultConfig=defaultConfig) except Exception as e: raise Exception(f"Fail to generate tests from {testfileRelPath} : {e}") @@ -151,7 +158,7 @@ def run(self, config: dict) -> None: # check produced for file in check_file_produced: - if not os.path.exists(file): + if not os.path.exists(file) and not self.currentTestRunner.fake: raise Exception(f"Don't find expected file to be produced by the run : {file} !") def _runNonRegression(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): diff --git a/pytools/tests/test/pb1/testme.json b/pytools/tests/test/pb1/testme.json index d8ddad44f..25e225f93 100644 --- a/pytools/tests/test/pb1/testme.json +++ b/pytools/tests/test/pb1/testme.json @@ -1,11 +1,13 @@ { + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": true, - "reconstruction": 2, - "tolerance": 1e-14 + "ini": ["idefix.ini","idefix-implicit.ini"] } ] } diff --git a/pytools/tests/test/pb2/testme.json b/pytools/tests/test/pb2/testme.json index 96c1753ab..6401a69cd 100644 --- a/pytools/tests/test/pb2/testme.json +++ b/pytools/tests/test/pb2/testme.json @@ -1,18 +1,18 @@ { + "default": { + "dumpname": "dump.0001.dmp", + "reconstruction": 2, + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": true, - "reconstruction": 2, - "tolerance": 1e-14 + "noplot": true }, { "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": false, - "reconstruction": 2, - "tolerance": 1e-14 + "noplot": false } ] } diff --git a/test/Dust/DustEnergy/testme.json b/test/Dust/DustEnergy/testme.json index 9a78834b9..3465b5fdb 100644 --- a/test/Dust/DustEnergy/testme.json +++ b/test/Dust/DustEnergy/testme.json @@ -1,12 +1,14 @@ { "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": true, - "reconstruction": 2, - "tolerance": 0 + "ini": ["idefix.ini","idefix-implicit.ini"] } ] } diff --git a/test/Dust/DustyShock/testme.json b/test/Dust/DustyShock/testme.json index d8ddad44f..25e225f93 100644 --- a/test/Dust/DustyShock/testme.json +++ b/test/Dust/DustyShock/testme.json @@ -1,11 +1,13 @@ { + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": true, - "reconstruction": 2, - "tolerance": 1e-14 + "ini": ["idefix.ini","idefix-implicit.ini"] } ] } diff --git a/test/Dust/DustyWave/testme.json b/test/Dust/DustyWave/testme.json index 0050f364e..13309e266 100644 --- a/test/Dust/DustyWave/testme.json +++ b/test/Dust/DustyWave/testme.json @@ -1,12 +1,14 @@ { "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-implicit.ini"], - "noplot": true, - "reconstruction": 2, - "tolerance": 1e-14 + "ini": ["idefix.ini","idefix-implicit.ini"] } ] } diff --git a/test/HD/FargoPlanet/testme.json b/test/HD/FargoPlanet/testme.json index e1d735828..4753035c3 100644 --- a/test/HD/FargoPlanet/testme.json +++ b/test/HD/FargoPlanet/testme.json @@ -1,15 +1,17 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "dec": [2, 2], + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini", "idefix-rkl.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": [false, true], - "dec": [2, 2], - "tolerance": 1e-13 + "mpi": [false, true] } ], "when": [ diff --git a/test/HD/MachReflection/testme.json b/test/HD/MachReflection/testme.json index be2d8d950..c701471f3 100644 --- a/test/HD/MachReflection/testme.json +++ b/test/HD/MachReflection/testme.json @@ -1,15 +1,17 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "dec": [2, 2], + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": [false, true], - "dec": [2, 2], - "tolerance": 0 + "mpi": [false, true] } ] } diff --git a/test/HD/SedovBlastWave/testme.json b/test/HD/SedovBlastWave/testme.json index 11327598b..ba77c4b7e 100644 --- a/test/HD/SedovBlastWave/testme.json +++ b/test/HD/SedovBlastWave/testme.json @@ -1,28 +1,23 @@ { "namings": "definitionFile,ini", + "default": { + "dumpname": "dump.0001.dmp", + "vectPot": false, + "reconstruction": 2, + "single": false, + "mpi": true, + "dec": [2, 2, 2 ], + "standardTest": false, + "nonRegressionTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "definitionFile": "definitions.hpp", - "ini": ["idefix.ini"], - "vectPot": false, - "reconstruction": 2, - "single": false, - "mpi": true, - "dec": [2, 2, 2 ], - "standardTest": false, - "tolerance": 0 + "ini": ["idefix.ini"] },{ - "dumpname": "dump.0001.dmp", "definitionFile": "definitions-spherical.hpp", - "ini": ["idefix-spherical.ini"], - "vectPot": false, - "reconstruction": 2, - "single": false, - "mpi": true, - "dec": [2, 2, 2 ], - "standardTest": false, - "tolerance": 0 + "ini": ["idefix-spherical.ini"] } ] } diff --git a/test/HD/ShearingBox/testme.json b/test/HD/ShearingBox/testme.json index 3e473d0ba..802c6ce33 100644 --- a/test/HD/ShearingBox/testme.json +++ b/test/HD/ShearingBox/testme.json @@ -1,15 +1,17 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-fargo.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": false, - "dec": ["2","1","2"], - "tolerance": 1e-15 - } - ] + "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 1e-15 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-fargo.ini"] + } + ] } diff --git a/test/HD/ViscousDisk/testme.json b/test/HD/ViscousDisk/testme.json index df8c19d86..a25a09e4b 100644 --- a/test/HD/ViscousDisk/testme.json +++ b/test/HD/ViscousDisk/testme.json @@ -1,15 +1,17 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": false, - "dec": ["2","1","2"], - "tolerance": 3e-15 - } - ] + "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 3e-15 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini"] + } + ] } diff --git a/test/HD/ViscousFlowPastCylinder/testme.json b/test/HD/ViscousFlowPastCylinder/testme.json index 7b3763436..519a01ca4 100644 --- a/test/HD/ViscousFlowPastCylinder/testme.json +++ b/test/HD/ViscousFlowPastCylinder/testme.json @@ -1,23 +1,25 @@ { - "namings": "ini,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": [false, true], - "dec": ["2","2"], - "tolerance": 3e-14 - } - ], - "when": { - "conditions": { - "ini": "idefix-rkl.ini" - }, - "apply": { - "tolerance": 1e-8 - } + "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "dec": ["2","2"], + "tolerance": 3e-14 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini"], + "mpi": [false, true] } + ], + "when": { + "conditions": { + "ini": "idefix-rkl.ini" + }, + "apply": { + "tolerance": 1e-8 + } + } } diff --git a/test/HD/sod-iso/testme.json b/test/HD/sod-iso/testme.json index 5016415d6..480bc50d3 100644 --- a/test/HD/sod-iso/testme.json +++ b/test/HD/sod-iso/testme.json @@ -1,33 +1,25 @@ { - "namings": "ini,single,reconstruction", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], - "vectPot": false, - "noplot": true, - "reconstruction": [2, 3], - "single": [false], - "mpi": false, - "tolerance": 0 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], - "vectPot": false, - "noplot": true, - "reconstruction": [4], - "single": [false], - "mpi": false, - "tolerance": 0 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], - "vectPot": false, - "noplot": true, - "reconstruction": [2], - "single": [true], - "mpi": false, - "tolerance": 0 - } - ] + "namings": "ini,single,reconstruction", + "default": { + "dumpname": "dump.0001.dmp", + "mpi": false, + "vectPot": false, + "noplot": true, + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "reconstruction": [2, 3], + "single": [false] + },{ + "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], + "reconstruction": [4], + "single": [false] + },{ + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "reconstruction": [2], + "single": [true] + } + ] } diff --git a/test/HD/sod/testme.json b/test/HD/sod/testme.json index 9128c08d4..d5d287c46 100644 --- a/test/HD/sod/testme.json +++ b/test/HD/sod/testme.json @@ -1,33 +1,25 @@ { - "namings": "ini,single,reconstruction", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], - "noplot": true, - "vectPot": false, - "single": [false], - "reconstruction": [2,3], - "mpi": false, - "tolerance": 0 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], - "noplot": true, - "vectPot": false, - "single": [false], - "reconstruction": [4], - "mpi": false, - "tolerance": 0 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], - "noplot": true, - "vectPot": false, - "reconstruction": [2], - "mpi": false, - "single": [true], - "tolerance": 0 - } - ] + "namings": "ini,single,reconstruction", + "default": { + "dumpname": "dump.0001.dmp", + "mpi": false, + "noplot": true, + "vectPot": false, + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "single": [false], + "reconstruction": [2,3] + },{ + "ini": ["idefix-rk3.ini","idefix-hllc-rk3.ini"], + "single": [false], + "reconstruction": [4] + },{ + "ini": ["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"], + "reconstruction": [2], + "single": [true] + } + ] } diff --git a/test/HD/thermalDiffusion/testme.json b/test/HD/thermalDiffusion/testme.json index 2e89ad747..8fd07a94a 100644 --- a/test/HD/thermalDiffusion/testme.json +++ b/test/HD/thermalDiffusion/testme.json @@ -1,15 +1,17 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "reconstruction": 2, - "single": false, - "mpi": false, - "dec": ["2","1","2"], - "tolerance": 0 - } - ] + "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "reconstruction": 2, + "single": false, + "mpi": false, + "dec": ["2","1","2"], + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini"] + } + ] } diff --git a/test/IO/dump/testme.json b/test/IO/dump/testme.json index cb69f946f..39c575662 100644 --- a/test/IO/dump/testme.json +++ b/test/IO/dump/testme.json @@ -1,28 +1,23 @@ { - "namings": "ini,single,vectPot,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "vectPot": [false, true], - "reconstruction": 2, - "single": [false], - "mpi": [false, true], - "dec": ["2","2","2"], - "standardTest": false, - "nonRegressionTest": false, - "tolerance": 1e-13 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "vectPot": [false], - "reconstruction": 2, - "mpi": [false, true], - "single": [true], - "dec": ["2","2","2"], - "standardTest": false, - "nonRegressionTest": false, - "tolerance": 1e-13 - } - ] + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0001.dmp", + "tolerance": 1e-13, + "nonRegressionTest": false, + "standardTest": false, + "reconstruction": 2, + "dec": [2, 2, 2] + }, + "variants": [ + { + "single": false, + "vectPot": [false, true], + "mpi": [false, true] + }, { + + "vectPot": false, + "single": true, + "mpi": [false, true] + } + ] } diff --git a/test/IO/pydefix/testme.json b/test/IO/pydefix/testme.json index 78760f724..d228245c0 100644 --- a/test/IO/pydefix/testme.json +++ b/test/IO/pydefix/testme.json @@ -1,17 +1,17 @@ { - "namings": "ini,single,vectPot,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "reconstruction": 2, - "single": false, - "mpi": [false, true], - "dec": ["2","2"], - "standardTest": false, - "tolerance": 1e-12 - } - ] + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0001.dmp", + "tolerance": 1e-12, + "dec": [2, 2], + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2 + }, + "variants": [ + { + "mpi": [false, true] + } + ] } diff --git a/test/IO/xdmf/testme.json b/test/IO/xdmf/testme.json index 8198bb7bb..42628d6d6 100644 --- a/test/IO/xdmf/testme.json +++ b/test/IO/xdmf/testme.json @@ -1,17 +1,12 @@ { - "namings": "ini,single,vectPot,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "vectPot": false, - "reconstruction": 2, - "single": false, - "mpi": false, - "dec": ["2","2","2"], - "standardTest": false, - "nonRegressionTest": false, - "check_file_produced": [ "data.0001.flt.xmf", "data.0001.flt.h5" ] - } - ] + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0001.dmp", + "vectPot": false, + "single": false, + "mpi": false, + "nonRegressionTest": false, + "standardTest": false, + "check_file_produced": [ "data.0001.flt.xmf", "data.0001.flt.h5" ] + } } diff --git a/test/MHD/AmbipolarCshock/testme.json b/test/MHD/AmbipolarCshock/testme.json index 2eb2ac51f..4ce0ace6d 100644 --- a/test/MHD/AmbipolarCshock/testme.json +++ b/test/MHD/AmbipolarCshock/testme.json @@ -1,14 +1,16 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": false, - "tolerance": 0 - } - ] + "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini"] + } + ] } diff --git a/test/MHD/AmbipolarCshock3D/testme.json b/test/MHD/AmbipolarCshock3D/testme.json index fdcb11a76..96c8bff2a 100644 --- a/test/MHD/AmbipolarCshock3D/testme.json +++ b/test/MHD/AmbipolarCshock3D/testme.json @@ -1,35 +1,33 @@ { - "namings": "ini,mpi,vectPot", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": [false], - "vectPot": [false, true], - "dec": ["2","1","1"], - "tolerance": 3e-14 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": [true], - "vectPot": [false], - "dec": ["2","1","1"], - "tolerance": 3e-14 - } - ], - "when": { - "conditions": { - "ini": "idefix-rkl.ini", - "mpi": true - }, - "apply": { - "tolerance": 2e-10 - } + "namings": "ini,mpi,vectPot", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "tolerance": 3e-14 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini"], + "mpi": [false], + "vectPot": [false, true], + "dec": ["2","1","1"] + },{ + "ini": ["idefix.ini","idefix-rkl.ini"], + "mpi": [true], + "vectPot": [false], + "dec": ["2","1","1"], + "tolerance": 3e-14 } + ], + "when": { + "conditions": { + "ini": "idefix-rkl.ini", + "mpi": true + }, + "apply": { + "tolerance": 2e-10 + } + } } diff --git a/test/MHD/AxisFluxTube/testme.json b/test/MHD/AxisFluxTube/testme.json index 781d4f7b3..f5d074770 100644 --- a/test/MHD/AxisFluxTube/testme.json +++ b/test/MHD/AxisFluxTube/testme.json @@ -1,16 +1,18 @@ { - "namings": "ini,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-coarsening.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "vectPot": false, - "standardTest": false, - "tolerance": 1e-14 - } - ] + "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "vectPot": false, + "standardTest": false, + "tolerance": 1e-14 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-coarsening.ini"], + "mpi": [false, true] + } + ] } diff --git a/test/MHD/Coarsening/testme.json b/test/MHD/Coarsening/testme.json index 5b38ffebb..b631c5ec7 100644 --- a/test/MHD/Coarsening/testme.json +++ b/test/MHD/Coarsening/testme.json @@ -1,12 +1,14 @@ { - "namings": "ini,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini","idefix-x2.ini","idefix-x3.ini"], - "noplot": true, - "mpi": [false,true], - "tolerance": 0 - } - ] + "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini","idefix-x2.ini","idefix-x3.ini"], + "mpi": [false,true] + } + ] } diff --git a/test/MHD/FargoMHDSpherical/testme.json b/test/MHD/FargoMHDSpherical/testme.json index 72d93f493..8943f0ce5 100644 --- a/test/MHD/FargoMHDSpherical/testme.json +++ b/test/MHD/FargoMHDSpherical/testme.json @@ -1,17 +1,19 @@ { - "namings": "ini,mpi,vectPot", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "vectPot": [false, true], - "mpi": [false, true], - "dec": ["2","2","2"], - "standardTest": false, - "tolerance": 1e-14 - } - ] + "namings": "ini,mpi,vectPot", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "dec": ["2","2","2"], + "standardTest": false, + "tolerance": 1e-14 + }, + "variants": [ + { + "ini": ["idefix.ini"], + "vectPot": [false, true], + "mpi": [false, true] + } + ] } diff --git a/test/MHD/HallWhistler/testme.json b/test/MHD/HallWhistler/testme.json index cc71c4bf7..b08340cbe 100644 --- a/test/MHD/HallWhistler/testme.json +++ b/test/MHD/HallWhistler/testme.json @@ -1,15 +1,12 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": false, - "tolerance": 1e-15 - } - ] + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 1e-15 + } } diff --git a/test/MHD/LinearWaveTest/testme.json b/test/MHD/LinearWaveTest/testme.json index a3f997e34..dd56af87f 100644 --- a/test/MHD/LinearWaveTest/testme.json +++ b/test/MHD/LinearWaveTest/testme.json @@ -1,24 +1,22 @@ { - "namings": "ini,reconstruction,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], - "noplot": true, - "single": false, - "reconstruction": [2], - "mpi": [false,true], - "dec": ["2","2","2"], - "tolerance": 2e-13 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], - "noplot": true, - "single": false, - "reconstruction": [3, 4], - "mpi": [false], - "dec": ["2","2","2"], - "tolerance": 2e-13 - } - ] + "namings": "ini,reconstruction,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "dec": ["2","2","2"], + "tolerance": 2e-13 + }, + "variants": [ + { + "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], + "single": false, + "reconstruction": [2], + "mpi": [false,true] + },{ + "ini": ["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"], + "single": false, + "reconstruction": [3, 4], + "mpi": [false] + } + ] } diff --git a/test/MHD/MTI/testme.json b/test/MHD/MTI/testme.json index 3bd669cca..1adf7c6f7 100644 --- a/test/MHD/MTI/testme.json +++ b/test/MHD/MTI/testme.json @@ -1,15 +1,17 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-rkl.ini","idefix-sl.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": false, - "tolerance": 0 - } - ] + "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 0 + }, + "variants": [ + { + "ini": ["idefix.ini","idefix-rkl.ini","idefix-sl.ini"] + } + ] } diff --git a/test/MHD/OrszagTang/testme.json b/test/MHD/OrszagTang/testme.json index 3128b3239..b455db40d 100644 --- a/test/MHD/OrszagTang/testme.json +++ b/test/MHD/OrszagTang/testme.json @@ -1,74 +1,66 @@ { - "namings": "ini,reconstruction,mpi,single,vectPot", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": [ - "idefix.ini", - "idefix-hll.ini", - "idefix-hlld-arithmetic.ini", - "idefix-hlld-hll.ini", - "idefix-hlld-hlld.ini", - "idefix-hlld-uct0.ini", - "idefix-hlld.ini", - "idefix-tvdlf.ini" - ], - "noplot": true, - "vectPot": [false], - "single": false, - "reconstruction": [2,3,4], - "mpi": [false, true], - "dec": ["2","2"], - "tolerance": 1e-12, - "standardTest": false - },{ - "dumpname": "dump.0001.dmp", - "ini": [ - "idefix.ini", - "idefix-hll.ini", - "idefix-hlld-arithmetic.ini", - "idefix-hlld-hll.ini", - "idefix-hlld-hlld.ini", - "idefix-hlld-uct0.ini", - "idefix-hlld.ini", - "idefix-tvdlf.ini" - ], - "noplot": true, - "vectPot": [false], - "single": true, - "reconstruction": [2], - "mpi": [false], - "dec": ["2","2"], - "tolerance": 1e-12, - "standardTest": false - },{ - "dumpname": "dump.0001.dmp", - "ini": [ - "idefix.ini", - "idefix-hll.ini", - "idefix-hlld-arithmetic.ini", - "idefix-hlld-hll.ini", - "idefix-hlld-hlld.ini", - "idefix-hlld-uct0.ini", - "idefix-hlld.ini", - "idefix-tvdlf.ini" - ], - "noplot": true, - "vectPot": [true], - "single": false, - "reconstruction": [2], - "mpi": [false], - "dec": ["2","2"], - "tolerance": 1e-12, - "standardTest": false - } - ], - "when": { - "conditions": { - "single": true - }, - "apply" : { - "tolerance": 1e-5 - } + "namings": "ini,reconstruction,mpi,single,vectPot", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "dec": ["2","2"], + "tolerance": 1e-12, + "standardTest": false + }, + "variants": [ + { + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "vectPot": [false], + "single": false, + "reconstruction": [2,3,4], + "mpi": [false, true] + },{ + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "vectPot": [false], + "single": true, + "reconstruction": [2], + "mpi": [false] + },{ + "ini": [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini" + ], + "vectPot": [true], + "single": false, + "reconstruction": [2], + "mpi": [false] } + ], + "when": { + "conditions": { + "single": true + }, + "apply" : { + "tolerance": 1e-5 + } + } } diff --git a/test/MHD/OrszagTang3D/testme.json b/test/MHD/OrszagTang3D/testme.json index a37b54164..8bebdb77e 100644 --- a/test/MHD/OrszagTang3D/testme.json +++ b/test/MHD/OrszagTang3D/testme.json @@ -1,34 +1,31 @@ { - "namings": "ini,single,vectPot,mpi", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "vectPot": [false, true], - "reconstruction": 2, - "single": [false], - "mpi": [false, true], - "dec": ["2","2","2"], - "standardTest": false, - "tolerance": 1e-13 - },{ - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "vectPot": [false], - "reconstruction": 2, - "mpi": [false, true], - "single": [true], - "dec": ["2","2","2"], - "standardTest": false, - "tolerance": 1e-13 - } - ], - "when": { - "conditions": { - "single": true - }, - "apply" : { - "tolerance": 1e-6 - } + "namings": "ini,single,vectPot,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "reconstruction": 2, + "dec": ["2","2","2"], + "standardTest": false, + "tolerance": 1e-13 + }, + "variants": [ + { + "ini": ["idefix.ini"], + "vectPot": [false, true], + "single": [false], + "mpi": [false, true] + },{ + "ini": ["idefix.ini"], + "vectPot": [false], + "mpi": [false, true], + "single": [true] } + ], + "when": { + "conditions": { + "single": true + }, + "apply" : { + "tolerance": 1e-6 + } + } } diff --git a/test/MHD/ResistiveAlfvenWave/testme.json b/test/MHD/ResistiveAlfvenWave/testme.json index 56ae122ec..fc5d9bc71 100644 --- a/test/MHD/ResistiveAlfvenWave/testme.json +++ b/test/MHD/ResistiveAlfvenWave/testme.json @@ -1,14 +1,16 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-rkl.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "tolerance": 1e-14 + "mpi": [false, true] } ], "when": { diff --git a/test/MHD/ShearingBox/testme.json b/test/MHD/ShearingBox/testme.json index 71ae0ab0d..7166c3e86 100644 --- a/test/MHD/ShearingBox/testme.json +++ b/test/MHD/ShearingBox/testme.json @@ -1,15 +1,17 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "dec": ["2","1","2"], + "tolerance": 1e-14 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-fargo.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2","1","2"], - "tolerance": 1e-14 + "mpi": [false, true] } ] } diff --git a/test/MHD/clessTDiffusion/testme.json b/test/MHD/clessTDiffusion/testme.json index d615696f5..a6ca18745 100644 --- a/test/MHD/clessTDiffusion/testme.json +++ b/test/MHD/clessTDiffusion/testme.json @@ -1,15 +1,12 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": false, - "vectPot": false, - "tolerance": 2e-15 - } - ] + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0001.dmp", + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "vectPot": false, + "tolerance": 2e-15 + } } diff --git a/test/MHD/sod-iso/testme.json b/test/MHD/sod-iso/testme.json index 9f5534fbc..459744862 100644 --- a/test/MHD/sod-iso/testme.json +++ b/test/MHD/sod-iso/testme.json @@ -1,33 +1,25 @@ { "namings": "ini,reconstruction,single", + "default": { + "dumpname": "dump.0001.dmp", + "vectPot": false, + "mpi": false, + "standardTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], - "vectPot": false, "single": false, - "reconstruction": [2,3], - "mpi": false, - "standardTest": false, - "tolerance": 0 + "reconstruction": [2,3] },{ - "dumpname": "dump.0001.dmp", "ini": ["idefix-rk3.ini","idefix-hlld-rk3.ini"], - "vectPot": false, "single": false, - "reconstruction": [4], - "mpi": false, - "standardTest": false, - "tolerance": 0 + "reconstruction": [4] },{ - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], - "vectPot": false, "reconstruction": [2], - "mpi": false, - "single": true, - "standardTest": false, - "tolerance": 0 + "single": true } ], "when": [ diff --git a/test/MHD/sod/testme.json b/test/MHD/sod/testme.json index 1501e3049..b0f6f927b 100644 --- a/test/MHD/sod/testme.json +++ b/test/MHD/sod/testme.json @@ -1,33 +1,28 @@ { "namings": "ini,reconstruction,single", + "default": { + "dumpname": "dump.0001.dmp", + "vectPot": false, + "mpi": false, + "standardTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], - "vectPot": false, "single": false, "reconstruction": [2,3], - "mpi": false, - "standardTest": false, - "tolerance": 0 + "standardTest": false },{ - "dumpname": "dump.0001.dmp", "ini": ["idefix-rk3.ini","idefix-hlld-rk3.ini"], - "vectPot": false, "single": false, "reconstruction": 4, - "mpi": false, "standardTest": false, "tolerance": 0 },{ - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"], - "vectPot": false, "reconstruction": 2, - "mpi": false, - "single": true, - "standardTest": false, - "tolerance": 0 + "single": true } ] } diff --git a/test/MHD/sphBragTDiffusion/testme.json b/test/MHD/sphBragTDiffusion/testme.json index c4cb9a334..79d2ac668 100644 --- a/test/MHD/sphBragTDiffusion/testme.json +++ b/test/MHD/sphBragTDiffusion/testme.json @@ -1,15 +1,12 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": false, - "tolerance": 2e-15 - } - ] + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "tolerance": 2e-15 + } } diff --git a/test/MHD/sphBragViscosity/testme.json b/test/MHD/sphBragViscosity/testme.json index 900a34a77..017a9b625 100644 --- a/test/MHD/sphBragViscosity/testme.json +++ b/test/MHD/sphBragViscosity/testme.json @@ -1,16 +1,13 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": false, - "standardTest": false, - "tolerance": 1e-15 - } - ] + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 1e-15 + } } diff --git a/test/Planet/PlanetMigration2D/testme.json b/test/Planet/PlanetMigration2D/testme.json index 6e1e08537..fa0c71fbc 100644 --- a/test/Planet/PlanetMigration2D/testme.json +++ b/test/Planet/PlanetMigration2D/testme.json @@ -1,16 +1,18 @@ { - "namings": "ini,mpi", + "namings": "mpi", + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2","2"], + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2","2"], - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/Planet/PlanetPlanetRK42D/testme.json b/test/Planet/PlanetPlanetRK42D/testme.json index 0181b072f..458fecd6b 100644 --- a/test/Planet/PlanetPlanetRK42D/testme.json +++ b/test/Planet/PlanetPlanetRK42D/testme.json @@ -1,16 +1,18 @@ { - "namings": "ini,mpi", + "namings": "mpi", + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0002.dmp", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2","2"], + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0002.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, "mpi": [false, true], - "dec": ["2","2"], - "tolerance": 1e-13, "multirun": [ { "nonRegressionTest": true, diff --git a/test/Planet/PlanetSpiral2D/testme.json b/test/Planet/PlanetSpiral2D/testme.json index 6e1e08537..fa0c71fbc 100644 --- a/test/Planet/PlanetSpiral2D/testme.json +++ b/test/Planet/PlanetSpiral2D/testme.json @@ -1,16 +1,18 @@ { - "namings": "ini,mpi", + "namings": "mpi", + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2","2"], + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2","2"], - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/Planet/PlanetTorque3D/testme.json b/test/Planet/PlanetTorque3D/testme.json index 085fb6c0f..5ef1ba03f 100644 --- a/test/Planet/PlanetTorque3D/testme.json +++ b/test/Planet/PlanetTorque3D/testme.json @@ -1,16 +1,18 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2","2","2"], + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2","2","2"], - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.json b/test/Planet/PlanetsIsActiveRK52D/testme.json index 30848aecd..1f7e49ebf 100644 --- a/test/Planet/PlanetsIsActiveRK52D/testme.json +++ b/test/Planet/PlanetsIsActiveRK52D/testme.json @@ -1,17 +1,19 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2","2"], + "nonRegressionTest": false, + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix-rk4.ini", "idefix-rk5.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2","2"], - "nonRegressionTest": false, - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/SelfGravity/DustyCollapse/testme.json b/test/SelfGravity/DustyCollapse/testme.json index 8afbcdb6d..208d8a307 100644 --- a/test/SelfGravity/DustyCollapse/testme.json +++ b/test/SelfGravity/DustyCollapse/testme.json @@ -1,16 +1,18 @@ { - "namings": "ini,mpi", + "namings": "mpi", + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "nonRegressionTest": false, + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "nonRegressionTest": false, - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/SelfGravity/JeansInstability/testme.json b/test/SelfGravity/JeansInstability/testme.json index bf4819389..cdcfaa60c 100644 --- a/test/SelfGravity/JeansInstability/testme.json +++ b/test/SelfGravity/JeansInstability/testme.json @@ -1,17 +1,19 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "vectPot": false, + "single": false, + "reconstruction": 2, + "dec": ["2"], + "nonRegressionTest": false, + "tolerance": 1e-13 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-cg.ini"], - "noplot": true, - "vectPot": false, - "single": false, - "reconstruction": 2, - "mpi": [false, true], - "dec": ["2"], - "nonRegressionTest": false, - "tolerance": 1e-13 + "mpi": [false, true] } ] } diff --git a/test/SelfGravity/RandomSphere/testme.json b/test/SelfGravity/RandomSphere/testme.json index d5cda3135..a3b2fbe94 100644 --- a/test/SelfGravity/RandomSphere/testme.json +++ b/test/SelfGravity/RandomSphere/testme.json @@ -1,14 +1,16 @@ { "namings": "ini,mpi", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "dec": ["2","2","1"], + "nonRegressionTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", "ini": ["idefix.ini","idefix-cg.ini","idefix-minres.ini"], - "noplot": true, - "mpi": [false, true], - "dec": ["2","2","1"], - "nonRegressionTest": false, - "tolerance": 0 + "mpi": [false, true] } ] } diff --git a/test/SelfGravity/RandomSphereCartesian/testme.json b/test/SelfGravity/RandomSphereCartesian/testme.json index 85f0f3889..0cf3294a9 100644 --- a/test/SelfGravity/RandomSphereCartesian/testme.json +++ b/test/SelfGravity/RandomSphereCartesian/testme.json @@ -1,12 +1,14 @@ { "namings": "ini", + "default": { + "dumpname": "dump.0001.dmp", + "noplot": true, + "nonRegressionTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini","idefix-cg.ini","idefix-minres.ini","idefix-jacobi.ini"], - "noplot": true, - "nonRegressionTest": false, - "tolerance": 0 + "ini": ["idefix.ini","idefix-cg.ini","idefix-minres.ini","idefix-jacobi.ini"] } ] } diff --git a/test/SelfGravity/UniformCollapse/testme.json b/test/SelfGravity/UniformCollapse/testme.json index 3de00c4df..50e6e9e3d 100644 --- a/test/SelfGravity/UniformCollapse/testme.json +++ b/test/SelfGravity/UniformCollapse/testme.json @@ -1,16 +1,13 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "noplot": true, - "single": false, - "reconstruction": 2, - "mpi": false, - "standardTest": false, - "tolerance": 0, - "nonRegressionTest": false - } - ] + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "noplot": true, + "single": false, + "reconstruction": 2, + "mpi": false, + "standardTest": false, + "tolerance": 0, + "nonRegressionTest": false + } } diff --git a/test/utils/columnDensity/testme.json b/test/utils/columnDensity/testme.json index 718413c4d..4163c0327 100644 --- a/test/utils/columnDensity/testme.json +++ b/test/utils/columnDensity/testme.json @@ -1,13 +1,15 @@ { - "namings": "ini,mpi", + "namings": "mpi", + "default": { + "ini": "idefix.ini", + "dumpname": "dump.0001.dmp", + "nonRegressionTest": false, + "standardTest": false, + "tolerance": 0 + }, "variants": [ { - "dumpname": "dump.0001.dmp", - "ini": ["idefix.ini"], - "mpi": [false,true], - "nonRegressionTest": false, - "standardTest": false, - "tolerance": 0 + "mpi": [false,true] } ] } diff --git a/test/utils/lookupTable/testme.json b/test/utils/lookupTable/testme.json index 8ea6f6961..100e561d8 100644 --- a/test/utils/lookupTable/testme.json +++ b/test/utils/lookupTable/testme.json @@ -1,12 +1,9 @@ { - "namings": "ini", - "variants": [ - { - "dumpname": "dump.0001.dmp", - "ini":["idefix.ini"], - "nonRegressionTest": false, - "standardTest": false, - "tolerance": 0 - } - ] + "default": { + "dumpname": "dump.0001.dmp", + "ini": "idefix.ini", + "nonRegressionTest": false, + "standardTest": false, + "tolerance": 0 + } } From 273abf10ffee7e56bb83c30e15cd4036295aac95 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 4 Jun 2026 16:36:28 +0200 Subject: [PATCH 106/144] Bump up to Kokkos 5.1 (#375) --- CMakeLists.txt | 2 +- doc/source/index.rst | 9 ++++++--- doc/source/programmingguide.rst | 30 +++++++++++++++--------------- src/dataBlock/dumpToFile.cpp | 14 +++++++------- src/fluid/boundary/axis.hpp | 4 ++-- src/gravity/laplacian.cpp | 2 +- src/kokkos | 2 +- src/mpi/mpi.cpp | 2 +- 8 files changed, 34 insertions(+), 31 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 6698aaec6..fad0058ba 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.16) if (NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release" CACHE STRING "" FORCE) endif() -set (CMAKE_CXX_STANDARD 17) +set (CMAKE_CXX_STANDARD 20) set(Idefix_VERSION_MAJOR 2) set(Idefix_VERSION_MINOR 3) diff --git a/doc/source/index.rst b/doc/source/index.rst index d36ab39be..2871f7953 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -20,11 +20,11 @@ algorithm is essentially the same (but with some major modification to its struc ================ Requirements ================ -*Idefix* is written is standard C++17 and does not rely on any external library in serial (non MPI). +*Idefix* is written is standard C++20 and does not rely on any external library in serial (non MPI). Compiler - *Idefix* requires a C++17 compatible compiler. It has been tested successfully with GCC (>8), Intel compiler suite (>2018) and - Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>10) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250) using the hipcc compiler. + *Idefix* requires a C++20 compatible compiler. It has been tested successfully with GCC (>11), Intel compiler suite (>2022) and + Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>12) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250, Mi300) using the hipcc compiler. Kokkos library *Idefix* relies internally on the `Kokkos `_ library, which is bundled with *Idefix* as a git submodule and compiled on the fly, hence no external installation is required. @@ -90,6 +90,9 @@ Jean Kempf, Victor Reville, François Rincon Marc Coiffier Continuous integration, automatic benchmarking +Sébastien Valat + Continuous integration + ======================== About this documentation ======================== diff --git a/doc/source/programmingguide.rst b/doc/source/programmingguide.rst index 4bd7c69f7..6f65742bc 100644 --- a/doc/source/programmingguide.rst +++ b/doc/source/programmingguide.rst @@ -355,13 +355,13 @@ fills the following arrays (essentially grid information) with data from its par .. code-block:: c++ - IdefixArray1D::HostMirror x[3]; // geometrical central points - IdefixArray1D::HostMirror xr[3]; // cell right interface - IdefixArray1D::HostMirror xl[3]; // cell left interface - IdefixArray1D::HostMirror dx[3]; // cell width + IdefixArray1D::host_mirror_type x[3]; // geometrical central points + IdefixArray1D::host_mirror_type xr[3]; // cell right interface + IdefixArray1D::host_mirror_type xl[3]; // cell left interface + IdefixArray1D::host_mirror_type dx[3]; // cell width - IdefixArray3D::HostMirror dV; // cell volume - IdefixArray3D::HostMirror A[3]; // cell right interface area + IdefixArray3D::host_mirror_type dV; // cell volume + IdefixArray3D::host_mirror_type A[3]; // cell right interface area Note however that the physics arrays are not automatically synchronized when ``DataBlockHost`` is @@ -369,17 +369,17 @@ created, that is: .. code-block:: c++ - IdefixArray4D::HostMirror Vc; // Main cell-centered primitive variables index - IdefixArray4D::HostMirror Vs; // Main face-centered primitive variables index - IdefixArray4D::HostMirror J; // Current (only when haveCurrent is enabled) - IdefixArray4D::HostMirror Uc; // Main cell-centered conservative variables - IdefixArray3D::HostMirror InvDt; + IdefixArray4D::host_mirror_type Vc; // Main cell-centered primitive variables index + IdefixArray4D::host_mirror_type Vs; // Main face-centered primitive variables index + IdefixArray4D::host_mirror_type J; // Current (only when haveCurrent is enabled) + IdefixArray4D::host_mirror_type Uc; // Main cell-centered conservative variables + IdefixArray3D::host_mirror_type InvDt; - IdefixArray3D::HostMirror Ex1; // x1 electric field - IdefixArray3D::HostMirror Ex2; // x2 electric field - IdefixArray3D::HostMirror Ex3; // x3 electric field + IdefixArray3D::host_mirror_type Ex1; // x1 electric field + IdefixArray3D::host_mirror_type Ex2; // x2 electric field + IdefixArray3D::host_mirror_type Ex3; // x3 electric field -need to be synchronized *manually*. These IdefixArrays are all defined as ``HostMirror``, implying that they are accessible +need to be synchronized *manually*. These IdefixArrays are all defined as ``host_mirror_type``, implying that they are accessible from the host only. If modifications are performed on the arrays of the parent ``DataBlock``, one can call ``DataBlockHost::SyncFromDevice()`` to refresh the host arrays, and inversely one can call ``DataBlockHost::SyncToDevice()`` to send data from ``DataBlockHost`` diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index 51347e6ed..f20dde838 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -45,13 +45,13 @@ void DataBlock::DumpToFile(std::string filebase) { // TODO(lesurg) Make datablock a friend of hydro to get the Riemann flux? - //IdefixArray4D::HostMirror locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), + //IdefixArray4D::host_mirror_type locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), // this->hydro->FluxRiemann); //Kokkos::deep_copy(locFlux, this->FluxRiemann); #if MHD == YES - IdefixArray4D::HostMirror locJ; + IdefixArray4D::host_mirror_type locJ; if(hydro->haveCurrent) { locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ, this->hydro->J); @@ -82,7 +82,7 @@ void DataBlock::DumpToFile(std::string filebase) { fwrite (header, sizeof(char), HEADERSIZE, fileHdl); // Write Vc - IdefixArray4D::HostMirror locVc = Kokkos::create_mirror_view(this->hydro->Vc); + IdefixArray4D::host_mirror_type locVc = Kokkos::create_mirror_view(this->hydro->Vc); Kokkos::deep_copy(locVc,this->hydro->Vc); dims[0] = this->np_tot[IDIR]; dims[1] = this->np_tot[JDIR]; @@ -94,7 +94,7 @@ void DataBlock::DumpToFile(std::string filebase) { WriteVariable(fileHdl, 4, dims, fieldName, locVc.data()); if (this->gravity->haveSelfGravityPotential) { - IdefixArray3D::HostMirror locPot = Kokkos::create_mirror_view(this->gravity->phiP); + IdefixArray3D::host_mirror_type locPot = Kokkos::create_mirror_view(this->gravity->phiP); Kokkos::deep_copy(locPot, this->gravity->phiP); dims[3] = 1; @@ -121,7 +121,7 @@ void DataBlock::DumpToFile(std::string filebase) { // Write Vs #if MHD == YES // Write Vs - IdefixArray4D::HostMirror locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::host_mirror_type locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->Vs); Kokkos::deep_copy(locVs,this->hydro->Vs); dims[0] = this->np_tot[IDIR]+IOFFSET; @@ -139,7 +139,7 @@ void DataBlock::DumpToFile(std::string filebase) { dims[2] = this->np_tot[KDIR]; std::snprintf(fieldName,NAMESIZE,"Ex3"); - IdefixArray3D::HostMirror locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray3D::host_mirror_type locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->emf->ez); Kokkos::deep_copy(locE,this->hydro->emf->ez); WriteVariable(fileHdl, 3, dims, fieldName, locE.data()); @@ -155,7 +155,7 @@ void DataBlock::DumpToFile(std::string filebase) { if(hydro->haveCurrent) { - IdefixArray4D::HostMirror locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::host_mirror_type locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ,this->hydro->J); dims[0] = this->np_tot[IDIR]; diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index 1a1227b61..229c772f6 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -126,7 +126,7 @@ Axis::Axis(Boundary *boundary) { // Init the symmetry array (used to flip the signs of arrays accross the axis) symmetryVc = IdefixArray1D("Axis:SymmetryVc",nVar); - IdefixArray1D::HostMirror symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); + IdefixArray1D::host_mirror_type symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); // Init the array for (int nv = 0; nv < nVar; nv++) { symmetryVcHost(nv) = 1; @@ -143,7 +143,7 @@ Axis::Axis(Boundary *boundary) { if constexpr(Phys::mhd) { symmetryVs = IdefixArray1D("Axis:SymmetryVs",DIMENSIONS); - IdefixArray1D::HostMirror symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); + IdefixArray1D::host_mirror_type symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); // Init the array for(int nv = 0; nv < DIMENSIONS; nv++) { symmetryVsHost(nv) = 1; diff --git a/src/gravity/laplacian.cpp b/src/gravity/laplacian.cpp index 7ac329ea3..127299548 100644 --- a/src/gravity/laplacian.cpp +++ b/src/gravity/laplacian.cpp @@ -170,7 +170,7 @@ void Laplacian::InitInternalGrid() { }); // Check that all is well - IdefixArray1D::HostMirror xH = Kokkos::create_mirror_view(x1l); + IdefixArray1D::host_mirror_type xH = Kokkos::create_mirror_view(x1l); Kokkos::deep_copy(xH, x1l); if(xH(0)<0.0) { diff --git a/src/kokkos b/src/kokkos index 09e775bfc..3ec81abe1 160000 --- a/src/kokkos +++ b/src/kokkos @@ -1 +1 @@ -Subproject commit 09e775bfc585840bb9ab1156cbd8d7d1c9e0cc6d +Subproject commit 3ec81abe1816109f6f62ac48cef41921f91a4d00 diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp index 36b4eb9a3..d0759199a 100644 --- a/src/mpi/mpi.cpp +++ b/src/mpi/mpi.cpp @@ -131,7 +131,7 @@ void Mpi::CheckConfig() { // Run-time check that we can do a reduce on device arrays IdefixArray1D src("MPIChecksrc",1); - IdefixArray1D::HostMirror srcHost = Kokkos::create_mirror_view(src); + IdefixArray1D::host_mirror_type srcHost = Kokkos::create_mirror_view(src); if(idfx::prank == 0) { srcHost(0) = 0; From b3c330bffeb236cfa6c53e0cdb9725483b6f1fec Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 4 Jun 2026 17:19:17 +0200 Subject: [PATCH 107/144] Revert "Bump up to Kokkos 5.1 (#375)" This reverts commit 273abf10ffee7e56bb83c30e15cd4036295aac95. --- CMakeLists.txt | 2 +- doc/source/index.rst | 9 +++------ doc/source/programmingguide.rst | 30 +++++++++++++++--------------- src/dataBlock/dumpToFile.cpp | 14 +++++++------- src/fluid/boundary/axis.hpp | 4 ++-- src/gravity/laplacian.cpp | 2 +- src/kokkos | 2 +- src/mpi/mpi.cpp | 2 +- 8 files changed, 31 insertions(+), 34 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index fad0058ba..6698aaec6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.16) if (NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release" CACHE STRING "" FORCE) endif() -set (CMAKE_CXX_STANDARD 20) +set (CMAKE_CXX_STANDARD 17) set(Idefix_VERSION_MAJOR 2) set(Idefix_VERSION_MINOR 3) diff --git a/doc/source/index.rst b/doc/source/index.rst index 2871f7953..d36ab39be 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -20,11 +20,11 @@ algorithm is essentially the same (but with some major modification to its struc ================ Requirements ================ -*Idefix* is written is standard C++20 and does not rely on any external library in serial (non MPI). +*Idefix* is written is standard C++17 and does not rely on any external library in serial (non MPI). Compiler - *Idefix* requires a C++20 compatible compiler. It has been tested successfully with GCC (>11), Intel compiler suite (>2022) and - Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>12) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250, Mi300) using the hipcc compiler. + *Idefix* requires a C++17 compatible compiler. It has been tested successfully with GCC (>8), Intel compiler suite (>2018) and + Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>10) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250) using the hipcc compiler. Kokkos library *Idefix* relies internally on the `Kokkos `_ library, which is bundled with *Idefix* as a git submodule and compiled on the fly, hence no external installation is required. @@ -90,9 +90,6 @@ Jean Kempf, Victor Reville, François Rincon Marc Coiffier Continuous integration, automatic benchmarking -Sébastien Valat - Continuous integration - ======================== About this documentation ======================== diff --git a/doc/source/programmingguide.rst b/doc/source/programmingguide.rst index 6f65742bc..4bd7c69f7 100644 --- a/doc/source/programmingguide.rst +++ b/doc/source/programmingguide.rst @@ -355,13 +355,13 @@ fills the following arrays (essentially grid information) with data from its par .. code-block:: c++ - IdefixArray1D::host_mirror_type x[3]; // geometrical central points - IdefixArray1D::host_mirror_type xr[3]; // cell right interface - IdefixArray1D::host_mirror_type xl[3]; // cell left interface - IdefixArray1D::host_mirror_type dx[3]; // cell width + IdefixArray1D::HostMirror x[3]; // geometrical central points + IdefixArray1D::HostMirror xr[3]; // cell right interface + IdefixArray1D::HostMirror xl[3]; // cell left interface + IdefixArray1D::HostMirror dx[3]; // cell width - IdefixArray3D::host_mirror_type dV; // cell volume - IdefixArray3D::host_mirror_type A[3]; // cell right interface area + IdefixArray3D::HostMirror dV; // cell volume + IdefixArray3D::HostMirror A[3]; // cell right interface area Note however that the physics arrays are not automatically synchronized when ``DataBlockHost`` is @@ -369,17 +369,17 @@ created, that is: .. code-block:: c++ - IdefixArray4D::host_mirror_type Vc; // Main cell-centered primitive variables index - IdefixArray4D::host_mirror_type Vs; // Main face-centered primitive variables index - IdefixArray4D::host_mirror_type J; // Current (only when haveCurrent is enabled) - IdefixArray4D::host_mirror_type Uc; // Main cell-centered conservative variables - IdefixArray3D::host_mirror_type InvDt; + IdefixArray4D::HostMirror Vc; // Main cell-centered primitive variables index + IdefixArray4D::HostMirror Vs; // Main face-centered primitive variables index + IdefixArray4D::HostMirror J; // Current (only when haveCurrent is enabled) + IdefixArray4D::HostMirror Uc; // Main cell-centered conservative variables + IdefixArray3D::HostMirror InvDt; - IdefixArray3D::host_mirror_type Ex1; // x1 electric field - IdefixArray3D::host_mirror_type Ex2; // x2 electric field - IdefixArray3D::host_mirror_type Ex3; // x3 electric field + IdefixArray3D::HostMirror Ex1; // x1 electric field + IdefixArray3D::HostMirror Ex2; // x2 electric field + IdefixArray3D::HostMirror Ex3; // x3 electric field -need to be synchronized *manually*. These IdefixArrays are all defined as ``host_mirror_type``, implying that they are accessible +need to be synchronized *manually*. These IdefixArrays are all defined as ``HostMirror``, implying that they are accessible from the host only. If modifications are performed on the arrays of the parent ``DataBlock``, one can call ``DataBlockHost::SyncFromDevice()`` to refresh the host arrays, and inversely one can call ``DataBlockHost::SyncToDevice()`` to send data from ``DataBlockHost`` diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index f20dde838..51347e6ed 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -45,13 +45,13 @@ void DataBlock::DumpToFile(std::string filebase) { // TODO(lesurg) Make datablock a friend of hydro to get the Riemann flux? - //IdefixArray4D::host_mirror_type locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), + //IdefixArray4D::HostMirror locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), // this->hydro->FluxRiemann); //Kokkos::deep_copy(locFlux, this->FluxRiemann); #if MHD == YES - IdefixArray4D::host_mirror_type locJ; + IdefixArray4D::HostMirror locJ; if(hydro->haveCurrent) { locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ, this->hydro->J); @@ -82,7 +82,7 @@ void DataBlock::DumpToFile(std::string filebase) { fwrite (header, sizeof(char), HEADERSIZE, fileHdl); // Write Vc - IdefixArray4D::host_mirror_type locVc = Kokkos::create_mirror_view(this->hydro->Vc); + IdefixArray4D::HostMirror locVc = Kokkos::create_mirror_view(this->hydro->Vc); Kokkos::deep_copy(locVc,this->hydro->Vc); dims[0] = this->np_tot[IDIR]; dims[1] = this->np_tot[JDIR]; @@ -94,7 +94,7 @@ void DataBlock::DumpToFile(std::string filebase) { WriteVariable(fileHdl, 4, dims, fieldName, locVc.data()); if (this->gravity->haveSelfGravityPotential) { - IdefixArray3D::host_mirror_type locPot = Kokkos::create_mirror_view(this->gravity->phiP); + IdefixArray3D::HostMirror locPot = Kokkos::create_mirror_view(this->gravity->phiP); Kokkos::deep_copy(locPot, this->gravity->phiP); dims[3] = 1; @@ -121,7 +121,7 @@ void DataBlock::DumpToFile(std::string filebase) { // Write Vs #if MHD == YES // Write Vs - IdefixArray4D::host_mirror_type locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::HostMirror locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->Vs); Kokkos::deep_copy(locVs,this->hydro->Vs); dims[0] = this->np_tot[IDIR]+IOFFSET; @@ -139,7 +139,7 @@ void DataBlock::DumpToFile(std::string filebase) { dims[2] = this->np_tot[KDIR]; std::snprintf(fieldName,NAMESIZE,"Ex3"); - IdefixArray3D::host_mirror_type locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray3D::HostMirror locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->emf->ez); Kokkos::deep_copy(locE,this->hydro->emf->ez); WriteVariable(fileHdl, 3, dims, fieldName, locE.data()); @@ -155,7 +155,7 @@ void DataBlock::DumpToFile(std::string filebase) { if(hydro->haveCurrent) { - IdefixArray4D::host_mirror_type locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::HostMirror locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ,this->hydro->J); dims[0] = this->np_tot[IDIR]; diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index 229c772f6..1a1227b61 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -126,7 +126,7 @@ Axis::Axis(Boundary *boundary) { // Init the symmetry array (used to flip the signs of arrays accross the axis) symmetryVc = IdefixArray1D("Axis:SymmetryVc",nVar); - IdefixArray1D::host_mirror_type symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); + IdefixArray1D::HostMirror symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); // Init the array for (int nv = 0; nv < nVar; nv++) { symmetryVcHost(nv) = 1; @@ -143,7 +143,7 @@ Axis::Axis(Boundary *boundary) { if constexpr(Phys::mhd) { symmetryVs = IdefixArray1D("Axis:SymmetryVs",DIMENSIONS); - IdefixArray1D::host_mirror_type symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); + IdefixArray1D::HostMirror symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); // Init the array for(int nv = 0; nv < DIMENSIONS; nv++) { symmetryVsHost(nv) = 1; diff --git a/src/gravity/laplacian.cpp b/src/gravity/laplacian.cpp index 127299548..7ac329ea3 100644 --- a/src/gravity/laplacian.cpp +++ b/src/gravity/laplacian.cpp @@ -170,7 +170,7 @@ void Laplacian::InitInternalGrid() { }); // Check that all is well - IdefixArray1D::host_mirror_type xH = Kokkos::create_mirror_view(x1l); + IdefixArray1D::HostMirror xH = Kokkos::create_mirror_view(x1l); Kokkos::deep_copy(xH, x1l); if(xH(0)<0.0) { diff --git a/src/kokkos b/src/kokkos index 3ec81abe1..09e775bfc 160000 --- a/src/kokkos +++ b/src/kokkos @@ -1 +1 @@ -Subproject commit 3ec81abe1816109f6f62ac48cef41921f91a4d00 +Subproject commit 09e775bfc585840bb9ab1156cbd8d7d1c9e0cc6d diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp index d0759199a..36b4eb9a3 100644 --- a/src/mpi/mpi.cpp +++ b/src/mpi/mpi.cpp @@ -131,7 +131,7 @@ void Mpi::CheckConfig() { // Run-time check that we can do a reduce on device arrays IdefixArray1D src("MPIChecksrc",1); - IdefixArray1D::host_mirror_type srcHost = Kokkos::create_mirror_view(src); + IdefixArray1D::HostMirror srcHost = Kokkos::create_mirror_view(src); if(idfx::prank == 0) { srcHost(0) = 0; From e5899791a789a8a0750150aae93569a04bc3e1fb Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 4 Jun 2026 23:00:58 +0200 Subject: [PATCH 108/144] Bump up to Kokkos 5.1 (#384) --- .../pre-install-py-packages/action.yml | 15 ++++++++++ .github/workflows/idefix-ci-jobs.yml | 26 ++++++++++++++++ CMakeLists.txt | 2 +- doc/source/index.rst | 9 ++++-- doc/source/programmingguide.rst | 30 +++++++++---------- scripts/ci/run-tests | 13 ++++++++ src/dataBlock/dumpToFile.cpp | 14 ++++----- .../planetarySystem/planetStructs.hpp | 2 +- src/fluid/boundary/axis.hpp | 4 +-- src/gravity/laplacian.cpp | 2 +- src/kokkos | 2 +- src/mpi/mpi.cpp | 2 +- test/MHD/AmbipolarWind/setup.cpp | 2 +- test/python_requirements.txt | 2 +- test/skeleton/main.cpp | 2 +- test/utils/columnDensity/setup.cpp | 2 +- test/utils/lookupTable/main.cpp | 2 +- 17 files changed, 94 insertions(+), 37 deletions(-) create mode 100644 .github/workflows/actions/pre-install-py-packages/action.yml diff --git a/.github/workflows/actions/pre-install-py-packages/action.yml b/.github/workflows/actions/pre-install-py-packages/action.yml new file mode 100644 index 000000000..2be0d7afd --- /dev/null +++ b/.github/workflows/actions/pre-install-py-packages/action.yml @@ -0,0 +1,15 @@ +name: Install python packages + +description: "Action installing the Idefix python packages before running the tests." + +inputs: {} + +runs: + using: "composite" + steps: + - name: Create venv + shell: bash + run: | + python3 -m venv .venv + source .venv/bin/activate + python3 -m pip install -r ./test/python_requirements.txt diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index 847ba3cbe..05b42568e 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -32,6 +32,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Sod test run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/sod -all $TESTME_OPTIONS - name: Isothermal Sod test @@ -49,6 +51,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Viscous flow past cylinder run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/ViscousFlowPastCylinder -all $TESTME_OPTIONS - name: Viscous disk @@ -64,6 +68,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: MHD Sod test run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/sod -all $TESTME_OPTIONS - name: MHD Isothermal Sod test @@ -85,6 +91,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Ambipolar C Shock run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/AmbipolarCshock -all $TESTME_OPTIONS - name: Ambipolar C Shock 3D @@ -105,6 +113,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Fargo + planet run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/FargoPlanet -all $TESTME_OPTIONS - name: Fargo MHD spherical @@ -119,6 +129,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Hydro shearing box run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/ShearingBox -all $TESTME_OPTIONS - name: MHD shearing box @@ -133,6 +145,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Jeans Instability run: scripts/ci/run-tests $IDEFIX_DIR/test/SelfGravity/JeansInstability -all $TESTME_OPTIONS - name: Random sphere spherical @@ -153,6 +167,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: 3 body run: scripts/ci/run-tests $IDEFIX_DIR/test/Planet/Planet3Body -all $TESTME_OPTIONS - name: migration @@ -175,6 +191,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Energy conservation run: scripts/ci/run-tests $IDEFIX_DIR/test/Dust/DustEnergy -all $TESTME_OPTIONS - name: Dusty wave @@ -189,6 +207,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: MTI run: scripts/ci/run-tests $IDEFIX_DIR/test/MHD/MTI -all $TESTME_OPTIONS - name: Spherical anisotropic diffusion @@ -207,6 +227,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Run examples test run: cd test && ./checks_examples.sh $TEST_OPTIONS @@ -219,6 +241,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Lookup table run: scripts/ci/run-tests $IDEFIX_DIR/test/utils/lookupTable -all $TESTME_OPTIONS - name: Dump Image @@ -235,6 +259,8 @@ jobs: with: submodules: recursive persist-credentials: false + - name: Prep python + uses: ./.github/workflows/actions/pre-install-py-packages - name: Restart dumps run: scripts/ci/run-tests $IDEFIX_DIR/test/IO/dump -all $TESTME_OPTIONS - name: Pydefix diff --git a/CMakeLists.txt b/CMakeLists.txt index 6698aaec6..fad0058ba 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -2,7 +2,7 @@ cmake_minimum_required(VERSION 3.16) if (NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release" CACHE STRING "" FORCE) endif() -set (CMAKE_CXX_STANDARD 17) +set (CMAKE_CXX_STANDARD 20) set(Idefix_VERSION_MAJOR 2) set(Idefix_VERSION_MINOR 3) diff --git a/doc/source/index.rst b/doc/source/index.rst index d36ab39be..2871f7953 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -20,11 +20,11 @@ algorithm is essentially the same (but with some major modification to its struc ================ Requirements ================ -*Idefix* is written is standard C++17 and does not rely on any external library in serial (non MPI). +*Idefix* is written is standard C++20 and does not rely on any external library in serial (non MPI). Compiler - *Idefix* requires a C++17 compatible compiler. It has been tested successfully with GCC (>8), Intel compiler suite (>2018) and - Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>10) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250) using the hipcc compiler. + *Idefix* requires a C++20 compatible compiler. It has been tested successfully with GCC (>11), Intel compiler suite (>2022) and + Clang on both Intel and AMD CPUs. *Idefix* has also been tested on NVIDIA GPUs (Pascal, Volta and Ampere architectures) using the nvcc (>12) compiler, and on AMD GPUs (Radeon Mi50, Mi210, Mi250, Mi300) using the hipcc compiler. Kokkos library *Idefix* relies internally on the `Kokkos `_ library, which is bundled with *Idefix* as a git submodule and compiled on the fly, hence no external installation is required. @@ -90,6 +90,9 @@ Jean Kempf, Victor Reville, François Rincon Marc Coiffier Continuous integration, automatic benchmarking +Sébastien Valat + Continuous integration + ======================== About this documentation ======================== diff --git a/doc/source/programmingguide.rst b/doc/source/programmingguide.rst index 4bd7c69f7..6f65742bc 100644 --- a/doc/source/programmingguide.rst +++ b/doc/source/programmingguide.rst @@ -355,13 +355,13 @@ fills the following arrays (essentially grid information) with data from its par .. code-block:: c++ - IdefixArray1D::HostMirror x[3]; // geometrical central points - IdefixArray1D::HostMirror xr[3]; // cell right interface - IdefixArray1D::HostMirror xl[3]; // cell left interface - IdefixArray1D::HostMirror dx[3]; // cell width + IdefixArray1D::host_mirror_type x[3]; // geometrical central points + IdefixArray1D::host_mirror_type xr[3]; // cell right interface + IdefixArray1D::host_mirror_type xl[3]; // cell left interface + IdefixArray1D::host_mirror_type dx[3]; // cell width - IdefixArray3D::HostMirror dV; // cell volume - IdefixArray3D::HostMirror A[3]; // cell right interface area + IdefixArray3D::host_mirror_type dV; // cell volume + IdefixArray3D::host_mirror_type A[3]; // cell right interface area Note however that the physics arrays are not automatically synchronized when ``DataBlockHost`` is @@ -369,17 +369,17 @@ created, that is: .. code-block:: c++ - IdefixArray4D::HostMirror Vc; // Main cell-centered primitive variables index - IdefixArray4D::HostMirror Vs; // Main face-centered primitive variables index - IdefixArray4D::HostMirror J; // Current (only when haveCurrent is enabled) - IdefixArray4D::HostMirror Uc; // Main cell-centered conservative variables - IdefixArray3D::HostMirror InvDt; + IdefixArray4D::host_mirror_type Vc; // Main cell-centered primitive variables index + IdefixArray4D::host_mirror_type Vs; // Main face-centered primitive variables index + IdefixArray4D::host_mirror_type J; // Current (only when haveCurrent is enabled) + IdefixArray4D::host_mirror_type Uc; // Main cell-centered conservative variables + IdefixArray3D::host_mirror_type InvDt; - IdefixArray3D::HostMirror Ex1; // x1 electric field - IdefixArray3D::HostMirror Ex2; // x2 electric field - IdefixArray3D::HostMirror Ex3; // x3 electric field + IdefixArray3D::host_mirror_type Ex1; // x1 electric field + IdefixArray3D::host_mirror_type Ex2; // x2 electric field + IdefixArray3D::host_mirror_type Ex3; // x3 electric field -need to be synchronized *manually*. These IdefixArrays are all defined as ``HostMirror``, implying that they are accessible +need to be synchronized *manually*. These IdefixArrays are all defined as ``host_mirror_type``, implying that they are accessible from the host only. If modifications are performed on the arrays of the parent ``DataBlock``, one can call ``DataBlockHost::SyncFromDevice()`` to refresh the host arrays, and inversely one can call ``DataBlockHost::SyncToDevice()`` to send data from ``DataBlockHost`` diff --git a/scripts/ci/run-tests b/scripts/ci/run-tests index 329831029..359e1eb14 100755 --- a/scripts/ci/run-tests +++ b/scripts/ci/run-tests @@ -1,7 +1,20 @@ #!/usr/bin/env bash + +# load ICC compiler env if [ "$IDEFIX_COMPILER" == icc ]; then source /opt/intel/oneapi/setvars.sh fi + +# enable bash features set -ue + +# load python venv if present +if [ -d .venv ]; then + source .venv/bin/activate +fi + +# jump in test directory cd "$1" + +# run the test ./testme.py "${@:2}" diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index 51347e6ed..f20dde838 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -45,13 +45,13 @@ void DataBlock::DumpToFile(std::string filebase) { // TODO(lesurg) Make datablock a friend of hydro to get the Riemann flux? - //IdefixArray4D::HostMirror locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), + //IdefixArray4D::host_mirror_type locFlux = Kokkos::create_mirror_view(Kokkos::HostSpace(), // this->hydro->FluxRiemann); //Kokkos::deep_copy(locFlux, this->FluxRiemann); #if MHD == YES - IdefixArray4D::HostMirror locJ; + IdefixArray4D::host_mirror_type locJ; if(hydro->haveCurrent) { locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ, this->hydro->J); @@ -82,7 +82,7 @@ void DataBlock::DumpToFile(std::string filebase) { fwrite (header, sizeof(char), HEADERSIZE, fileHdl); // Write Vc - IdefixArray4D::HostMirror locVc = Kokkos::create_mirror_view(this->hydro->Vc); + IdefixArray4D::host_mirror_type locVc = Kokkos::create_mirror_view(this->hydro->Vc); Kokkos::deep_copy(locVc,this->hydro->Vc); dims[0] = this->np_tot[IDIR]; dims[1] = this->np_tot[JDIR]; @@ -94,7 +94,7 @@ void DataBlock::DumpToFile(std::string filebase) { WriteVariable(fileHdl, 4, dims, fieldName, locVc.data()); if (this->gravity->haveSelfGravityPotential) { - IdefixArray3D::HostMirror locPot = Kokkos::create_mirror_view(this->gravity->phiP); + IdefixArray3D::host_mirror_type locPot = Kokkos::create_mirror_view(this->gravity->phiP); Kokkos::deep_copy(locPot, this->gravity->phiP); dims[3] = 1; @@ -121,7 +121,7 @@ void DataBlock::DumpToFile(std::string filebase) { // Write Vs #if MHD == YES // Write Vs - IdefixArray4D::HostMirror locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::host_mirror_type locVs = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->Vs); Kokkos::deep_copy(locVs,this->hydro->Vs); dims[0] = this->np_tot[IDIR]+IOFFSET; @@ -139,7 +139,7 @@ void DataBlock::DumpToFile(std::string filebase) { dims[2] = this->np_tot[KDIR]; std::snprintf(fieldName,NAMESIZE,"Ex3"); - IdefixArray3D::HostMirror locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray3D::host_mirror_type locE = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->emf->ez); Kokkos::deep_copy(locE,this->hydro->emf->ez); WriteVariable(fileHdl, 3, dims, fieldName, locE.data()); @@ -155,7 +155,7 @@ void DataBlock::DumpToFile(std::string filebase) { if(hydro->haveCurrent) { - IdefixArray4D::HostMirror locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), + IdefixArray4D::host_mirror_type locJ = Kokkos::create_mirror_view(Kokkos::HostSpace(), this->hydro->J); Kokkos::deep_copy(locJ,this->hydro->J); dims[0] = this->np_tot[IDIR]; diff --git a/src/dataBlock/planetarySystem/planetStructs.hpp b/src/dataBlock/planetarySystem/planetStructs.hpp index 3749a34d2..6440daf8f 100644 --- a/src/dataBlock/planetarySystem/planetStructs.hpp +++ b/src/dataBlock/planetarySystem/planetStructs.hpp @@ -19,7 +19,7 @@ struct Force { real f_ex_inner[3]; real f_outer[3]; real f_ex_outer[3]; - KOKKOS_FUNCTION void operator+=(Force const volatile& f) volatile { + KOKKOS_FUNCTION void operator+=(const Force & f) { for (int i = 0; i < 3; ++i) { f_inner[i] += f.f_inner[i]; f_ex_inner[i] += f.f_ex_inner[i]; diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index 1a1227b61..229c772f6 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -126,7 +126,7 @@ Axis::Axis(Boundary *boundary) { // Init the symmetry array (used to flip the signs of arrays accross the axis) symmetryVc = IdefixArray1D("Axis:SymmetryVc",nVar); - IdefixArray1D::HostMirror symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); + IdefixArray1D::host_mirror_type symmetryVcHost = Kokkos::create_mirror_view(symmetryVc); // Init the array for (int nv = 0; nv < nVar; nv++) { symmetryVcHost(nv) = 1; @@ -143,7 +143,7 @@ Axis::Axis(Boundary *boundary) { if constexpr(Phys::mhd) { symmetryVs = IdefixArray1D("Axis:SymmetryVs",DIMENSIONS); - IdefixArray1D::HostMirror symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); + IdefixArray1D::host_mirror_type symmetryVsHost = Kokkos::create_mirror_view(symmetryVs); // Init the array for(int nv = 0; nv < DIMENSIONS; nv++) { symmetryVsHost(nv) = 1; diff --git a/src/gravity/laplacian.cpp b/src/gravity/laplacian.cpp index 7ac329ea3..127299548 100644 --- a/src/gravity/laplacian.cpp +++ b/src/gravity/laplacian.cpp @@ -170,7 +170,7 @@ void Laplacian::InitInternalGrid() { }); // Check that all is well - IdefixArray1D::HostMirror xH = Kokkos::create_mirror_view(x1l); + IdefixArray1D::host_mirror_type xH = Kokkos::create_mirror_view(x1l); Kokkos::deep_copy(xH, x1l); if(xH(0)<0.0) { diff --git a/src/kokkos b/src/kokkos index 09e775bfc..3ec81abe1 160000 --- a/src/kokkos +++ b/src/kokkos @@ -1 +1 @@ -Subproject commit 09e775bfc585840bb9ab1156cbd8d7d1c9e0cc6d +Subproject commit 3ec81abe1816109f6f62ac48cef41921f91a4d00 diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp index 36b4eb9a3..d0759199a 100644 --- a/src/mpi/mpi.cpp +++ b/src/mpi/mpi.cpp @@ -131,7 +131,7 @@ void Mpi::CheckConfig() { // Run-time check that we can do a reduce on device arrays IdefixArray1D src("MPIChecksrc",1); - IdefixArray1D::HostMirror srcHost = Kokkos::create_mirror_view(src); + IdefixArray1D::host_mirror_type srcHost = Kokkos::create_mirror_view(src); if(idfx::prank == 0) { srcHost(0) = 0; diff --git a/test/MHD/AmbipolarWind/setup.cpp b/test/MHD/AmbipolarWind/setup.cpp index 78620f6e2..892eeea27 100644 --- a/test/MHD/AmbipolarWind/setup.cpp +++ b/test/MHD/AmbipolarWind/setup.cpp @@ -373,7 +373,7 @@ void ComputeUserVars(DataBlock & data, UserDefVariablesContainer &variables) { IdefixHostArray1D x1=d.x[IDIR]; IdefixHostArray1D x2=d.x[JDIR]; IdefixHostArray4D Vc=d.Vc; - IdefixArray3D::HostMirror scrhHost = Kokkos::create_mirror_view(scrh); + IdefixArray3D::host_mirror_type scrhHost = Kokkos::create_mirror_view(scrh); Kokkos::deep_copy(scrhHost,scrh); for(int k = d.beg[KDIR]; k < d.end[KDIR] ; k++) { diff --git a/test/python_requirements.txt b/test/python_requirements.txt index 9cf2383a2..6419c74af 100644 --- a/test/python_requirements.txt +++ b/test/python_requirements.txt @@ -8,7 +8,7 @@ scipy>=1.2.3 # note that no version of inifix supports Python older than 3.6 inifix>=0.11.2 - +pybind11 >= 3.0.4 # To run the test suite, we can use pytest, mostly any version # 6.0 is the one available on system available on debian-11 pytest >= 6.0 diff --git a/test/skeleton/main.cpp b/test/skeleton/main.cpp index 4930ecb15..aecadc962 100644 --- a/test/skeleton/main.cpp +++ b/test/skeleton/main.cpp @@ -37,7 +37,7 @@ void testReduction() { // Init an array on device, and image on host IdefixArray3D rho = IdefixArray3D("rho",nx3,nx2,nx1); - IdefixArray3D::HostMirror rhoHost = Kokkos::create_mirror_view(rho); + IdefixArray3D::host_mirror_type rhoHost = Kokkos::create_mirror_view(rho); // Fill the host array, and compute the theoretical results real theoreticalResult = 0; diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp index fe7c57e69..090024abc 100644 --- a/test/utils/columnDensity/setup.cpp +++ b/test/utils/columnDensity/setup.cpp @@ -33,7 +33,7 @@ void Analysis(DataBlock & data) { columnX3Right->ComputeColumn(rho); IdefixArray3D columnDensityLeft, columnDensityRight; - IdefixArray3D::HostMirror columnDensityLeftHost, columnDensityRightHost; + IdefixArray3D::host_mirror_type columnDensityLeftHost, columnDensityRightHost; // IDIR columnDensityLeft = columnX1Left->GetColumn(); columnDensityRight = columnX1Right->GetColumn(); diff --git a/test/utils/lookupTable/main.cpp b/test/utils/lookupTable/main.cpp index 619cae6d2..1fc660cd6 100644 --- a/test/utils/lookupTable/main.cpp +++ b/test/utils/lookupTable/main.cpp @@ -38,7 +38,7 @@ int main( int argc, char* argv[] ) idfx::cout << "--------------------------------------" << std::endl; idfx::cout << "Testing 2D CSV file on device." << std::endl; IdefixArray1D arr = IdefixArray1D("Test",1); - IdefixArray1D::HostMirror arrHost = Kokkos::create_mirror_view(arr); + IdefixArray1D::host_mirror_type arrHost = Kokkos::create_mirror_view(arr); LookupTable<2> csv("toto.csv",','); From cd5650666bdae554da9cdf53d98ba2d2fb213012 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Fri, 5 Jun 2026 17:55:43 +0200 Subject: [PATCH 109/144] ci: run the test via the new way (test.py && **/testme.json) (#377) --- .github/workflows/idefix-ci-jobs.yml | 2 +- scripts/ci/run-tests | 16 ++++++++++++---- 2 files changed, 13 insertions(+), 5 deletions(-) diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index 05b42568e..ab2b73247 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -39,7 +39,7 @@ jobs: - name: Isothermal Sod test run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/sod-iso -all $TESTME_OPTIONS - name: Mach reflection test - run: scripts/ci/run-tests $IDEFIX_DIR/test/HD//MachReflection -all $TESTME_OPTIONS + run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/MachReflection -all $TESTME_OPTIONS - name: Sedov blast wave run: scripts/ci/run-tests $IDEFIX_DIR/test/HD/SedovBlastWave -all $TESTME_OPTIONS diff --git a/scripts/ci/run-tests b/scripts/ci/run-tests index 359e1eb14..ebf895035 100755 --- a/scripts/ci/run-tests +++ b/scripts/ci/run-tests @@ -13,8 +13,16 @@ if [ -d .venv ]; then source .venv/bin/activate fi -# jump in test directory -cd "$1" +# to get access to idefix ./pytools/ module in python code +if [[ -v PYTHONPATH ]]; then + export PYTHONPATH="${PWD}:${PYTHONPATH}" +else + export PYTHONPATH="${PWD}" +fi + +# run the test the old way (still possible up to now) +#cd "$1" +#./testme.py "${@:2}" -# run the test -./testme.py "${@:2}" +# run the test the new way (via pytest) +./test.py -subdir "$@" From 70f53185f61772c47999eff631e3a85dad0a335e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 3 Jul 2026 00:30:26 +0200 Subject: [PATCH 110/144] fix segfault when using UCT_HLL with dimensions <3 (#386) --- src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp index 921a312ac..b376befe0 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp @@ -62,8 +62,8 @@ KOKKOS_FORCEINLINE_FUNCTION void K_StoreHLL( const int i, const int j, const int real al = std::fmin(ZERO_F, sl); real scrh = ONE_F/(ar - al); - #if COMPONENTS > 1 - EXPAND( Et(k,j,i) = -st*(ar*vL[Xt] - al*vR[Xt])*scrh; , + #if DIMENSIONS > 1 + D_EXPAND( Et(k,j,i) = -st*(ar*vL[Xt] - al*vR[Xt])*scrh; , , Eb(k,j,i) = -sb*(ar*vL[Xb] - al*vR[Xb])*scrh; ); #endif From 39ff4679e265ef3806eb8f5b80de44d59e3df0d5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Wed, 8 Jul 2026 09:36:13 +0200 Subject: [PATCH 111/144] refactor: use the Buffer and BoundingBox types to perform the communication packing / unpacking in Axis & ConstrainedTransport classes (#385) * refactor: axis communication by using Buffer and BoundingBox * refactor: use Buffer and BoundingBox for the MPI communications of ConstrainedTransport * refactor: Remove some none used varaibles following the previous patches in axis.cpp * refactor: Remove some temporary includes --- src/fluid/boundary/axis.cpp | 180 +++++++------- src/fluid/boundary/axis.hpp | 5 +- .../constrainedTransport/EMFexchange.hpp | 231 +++++++++--------- .../constrainedTransport.hpp | 37 +-- src/mpi/buffer.hpp | 61 +++++ 5 files changed, 287 insertions(+), 227 deletions(-) diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index 47f0c2954..45ea49ea5 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -393,12 +393,15 @@ void Axis::ExchangeMPI(int side) { #ifdef WITH_MPI // Load the buffers with data int ibeg,iend,jbeg,jend,kbeg,kend,offset; - int nx,ny,nz; - auto bufferSend = this->bufferSend; + int ny; + Buffer bufferSend = this->bufferSend; IdefixArray1D map = this->mapVars; IdefixArray4D Vc = this->Vc; IdefixArray4D Vs = this->Vs; + //reset pointer + bufferSend.ResetPointer(); + // If MPI Persistent, start receiving even before the buffers are filled MPI_Status sendStatus; @@ -409,64 +412,58 @@ void Axis::ExchangeMPI(int side) { idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Coordinates of the ghost region which needs to be transfered - ibeg = 0; - iend = data->np_tot[IDIR]; - nx = data->np_tot[IDIR]; // Number of points in x - jbeg = 0; - jend = data->nghost[JDIR]; offset = data->end[JDIR]; // Distance between beginning of left and right ghosts ny = data->nghost[JDIR]; - kbeg = data->beg[KDIR]; - kend = data->end[KDIR]; - nz = kend - kbeg; + + // Create the base box to be patched by the ops + BoundingBox baseBox; + baseBox[IDIR][0] = 0; + baseBox[IDIR][1] = data->np_tot[IDIR]; + baseBox[JDIR][0] = 0; + baseBox[JDIR][1] = data->nghost[JDIR]; + baseBox[KDIR][0] = data->beg[KDIR]; + baseBox[KDIR][1] = data->end[KDIR]; + if(side==left) { - idefix_for("LoadBufferX2Vc",0,mapNVars,kbeg,kend,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - bufferSend(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + n*nx*ny*nz ) = - Vc(map(n),k,j+ny,i); - } - ); + //shift by NY + BoundingBox sendBoxVc = baseBox; + sendBoxVc[JDIR][0] += ny; + sendBoxVc[JDIR][1] += ny; + bufferSend.Pack(Vc, map, sendBoxVc); + if (haveMHD) { - int VsIndex = mapNVars*nx*ny*nz; - idefix_for("LoadBufferX2IDIR",kbeg,kend,jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int j, int i) { - bufferSend(i + (j-jbeg)*(nx+1) + (k-kbeg)*(nx+1)*ny + VsIndex ) = - Vs(IDIR,k,j+ny,i); - } - ); - VsIndex = mapNVars*nx*ny*nz + (nx+1)*ny*nz; - idefix_for("LoadBufferX2KDIR",kbeg,kend+1,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int k, int j, int i) { - bufferSend(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + VsIndex ) = - Vs(KDIR,k,j+ny,i); - } - ); + //extend by one the end on idir + BoundingBox sendBoxVsIdir = sendBoxVc; + sendBoxVsIdir[IDIR][1] += 1; + bufferSend.Pack(Vs, IDIR, sendBoxVsIdir); + + //extend by one the end on kdir + BoundingBox sendBoxVsKdir = sendBoxVc; + sendBoxVsKdir[KDIR][1] += 1; + bufferSend.Pack(Vs, KDIR, sendBoxVsKdir); } // MHD } else if(side==right) { - idefix_for("LoadBufferX2Vc",0,mapNVars,kbeg,kend,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - bufferSend(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + n*nx*ny*nz ) = - Vc(map(n),k,j+offset-ny,i); - } - ); + //shift by offset - NY (to select the right part) + BoundingBox sendBoxVc = baseBox; + sendBoxVc[JDIR][0] += offset - ny; + sendBoxVc[JDIR][1] += offset - ny; + bufferSend.Pack(Vc, map, sendBoxVc); // Load face-centered field in the buffer if (haveMHD) { - int VsIndex = mapNVars*nx*ny*nz; - idefix_for("LoadBufferX2IDIR",kbeg,kend,jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int j, int i) { - bufferSend(i + (j-jbeg)*(nx+1) + (k-kbeg)*(nx+1)*ny + VsIndex ) = - Vs(IDIR,k,j+offset-ny,i); - } - ); - VsIndex = mapNVars*nx*ny*nz + (nx+1)*ny*nz; - - idefix_for("LoadBufferX2KDIR",kbeg,kend+1,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int k, int j, int i) { - bufferSend(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + VsIndex ) = - Vs(KDIR,k,j+offset-ny,i); - } - ); + //extend by one the end on idir + take the right part or the mesh on jdir + BoundingBox sendBoxVsIdir = baseBox; + sendBoxVsIdir[IDIR][1] += 1; + sendBoxVsIdir[JDIR][0] += offset - ny; + sendBoxVsIdir[JDIR][1] += offset - ny; + bufferSend.Pack(Vs, IDIR, sendBoxVsIdir); + + //extend by one the end on kdir + take the right part or the mesh on jdir + BoundingBox sendBoxVsKdir = baseBox; + sendBoxVsKdir[KDIR][1] += 1; + sendBoxVsKdir[JDIR][0] += offset - ny; + sendBoxVsKdir[JDIR][1] += offset - ny; + bufferSend.Pack(Vs, KDIR, sendBoxVsKdir); } // MHD } // side==right @@ -478,63 +475,53 @@ void Axis::ExchangeMPI(int side) { idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Unpack - auto bufferRecv=this->bufferRecv; + Buffer bufferRecv=this->bufferRecv; + bufferRecv.ResetPointer(); auto sVc = this->symmetryVc; if(side==left) { - idefix_for("StoreBufferAxis",0,mapNVars,kbeg,kend,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - Vc(map(n),k,jend-(j-jbeg)-1,i) = - sVc(map(n))*bufferRecv(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + n*nx*ny*nz ); - } - ); + //unpack Vc + BoundingBox recvBoxVc = baseBox; + bufferRecv.UnpackJDirSymetric(Vc, map, sVc, recvBoxVc); // Load face-centered field in the buffer if (haveMHD) { - int VsIndex = mapNVars*nx*ny*nz; auto sVs = this->symmetryVs; - idefix_for("StoreBufferX2IDIR",kbeg,kend,jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int j, int i) { - Vs(IDIR,k,jend-(j-jbeg)-1,i) = - sVs(IDIR)*bufferRecv(i + (j-jbeg)*(nx+1) + (k-kbeg)*(nx+1)*ny + VsIndex ); - } - ); - VsIndex = mapNVars*nx*ny*nz + (nx+1)*ny*nz; + //unpack Vs face-centered + BoundingBox recvBoxVsIdir = baseBox; + recvBoxVsIdir[IDIR][1] += 1; + bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs(IDIR), recvBoxVsIdir); - idefix_for("StoreBufferX2KDIR",kbeg,kend+1,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA ( int k, int j, int i) { - Vs(KDIR,k,jend-(j-jbeg)-1,i) = - sVs(KDIR)*bufferRecv(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + VsIndex ); - } - ); + //unpack Vs face-centered + BoundingBox recvBoxVsKdir = baseBox; + recvBoxVsKdir[KDIR][1] += 1; + bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs(KDIR), recvBoxVsKdir); } } else if(side==right) { - idefix_for("StoreBufferAxis",0,mapNVars,kbeg,kend,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA (int n, int k, int j, int i) { - Vc(map(n),k,jend-(j-jbeg)-1+offset,i) = - sVc(map(n))*bufferRecv(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + n*nx*ny*nz ); - } - ); + //unpack Vc on right part + BoundingBox recvBoxVc = baseBox; + recvBoxVc[JDIR][0] += offset; + recvBoxVc[JDIR][1] += offset; + bufferRecv.UnpackJDirSymetric(Vc, map, sVc, recvBoxVc); // Load face-centered field in the buffer if (haveMHD) { - int VsIndex = mapNVars*nx*ny*nz; auto sVs = this->symmetryVs; - idefix_for("StoreBufferX2IDIR",kbeg,kend,jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int j, int i) { - Vs(IDIR,k,jend-(j-jbeg)-1+offset,i) = - sVs(IDIR)*bufferRecv(i + (j-jbeg)*(nx+1) + (k-kbeg)*(nx+1)*ny + VsIndex ); - } - ); - VsIndex = mapNVars*nx*ny*nz + (nx+1)*ny*nz; - idefix_for("StoreBufferX2KDIR",kbeg,kend+1,jbeg,jend,ibeg,iend, - KOKKOS_LAMBDA ( int k, int j, int i) { - Vs(KDIR,k,jend-(j-jbeg)-1+offset,i) = - sVs(KDIR)*bufferRecv(i + (j-jbeg)*nx + (k-kbeg)*nx*ny + VsIndex ); - } - ); + //unpack Vs face-centered on right part + BoundingBox recvBoxVsIdir = baseBox; + recvBoxVsIdir[IDIR][1] += 1; + recvBoxVsIdir[JDIR][0] += offset; + recvBoxVsIdir[JDIR][1] += offset; + bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs(IDIR), recvBoxVsIdir); + + //unpack Vs face-centered on right part + BoundingBox recvBoxVsKdir = baseBox; + recvBoxVsKdir[KDIR][1] += 1; + recvBoxVsKdir[JDIR][0] += offset; + recvBoxVsKdir[JDIR][1] += offset; + bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs(KDIR), recvBoxVsKdir); } // MHD } @@ -594,8 +581,9 @@ void Axis::InitMPI() { #endif // DIMENSIONS } - this->bufferRecv = IdefixArray1D("bufferRecvAxis", bufferSize); - this->bufferSend = IdefixArray1D("bufferSendAxis", bufferSize); + //build buffers + this->bufferRecv = Buffer(bufferSize); + this->bufferSend = Buffer(bufferSize); // init persistent communications // We receive from procRecv, and we send to procSend @@ -605,10 +593,10 @@ void Axis::InitMPI() { MPI_SAFE_CALL(MPI_Cart_shift(data->mygrid->AxisComm,0,data->mygrid->nproc[KDIR]/2, &procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(bufferSend.data(), bufferSize, realMPI, procSend, + MPI_SAFE_CALL(MPI_Send_init(bufferSend.data(), bufferSend.Size(), realMPI, procSend, 650, data->mygrid->AxisComm, &sendRequest)); - MPI_SAFE_CALL(MPI_Recv_init(bufferRecv.data(), bufferSize, realMPI, procRecv, + MPI_SAFE_CALL(MPI_Recv_init(bufferRecv.data(), bufferRecv.Size(), realMPI, procRecv, 650, data->mygrid->AxisComm, &recvRequest)); #endif diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index 229c772f6..390a628ce 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -11,6 +11,7 @@ #include #include "idefix.hpp" #include "grid.hpp" +#include "buffer.hpp" // Forward class hydro declaration #include "physics.hpp" @@ -59,8 +60,8 @@ class Axis { MPI_Request sendRequest; MPI_Request recvRequest; - IdefixArray1D bufferSend; - IdefixArray1D bufferRecv; + Buffer bufferSend; + Buffer bufferRecv; int bufferSize; diff --git a/src/fluid/constrainedTransport/EMFexchange.hpp b/src/fluid/constrainedTransport/EMFexchange.hpp index f6e90f75a..aad123346 100644 --- a/src/fluid/constrainedTransport/EMFexchange.hpp +++ b/src/fluid/constrainedTransport/EMFexchange.hpp @@ -30,12 +30,10 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 // Load the buffers with data - int ileft,iright,jbeg,jend,kbeg,kend; - int ny; - [[maybe_unused]] int nz; + int ileft,iright,jbeg,jend; - IdefixArray1D BufferLeft=BufferSendX1[faceLeft]; - IdefixArray1D BufferRight=BufferSendX1[faceRight]; + Buffer BufferLeft=BufferSendX1[faceLeft]; + Buffer BufferRight=BufferSendX1[faceRight]; // If MPI Persistent, start receiving even before the buffers are filled @@ -54,24 +52,30 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 iright = data->end[IDIR]; jbeg = data->beg[JDIR]; jend = data->end[JDIR]; - ny = jend - jbeg; - kbeg = data->beg[KDIR]; - kend = data->end[KDIR]; - nz = kend - kbeg; - - idefix_for("LoadBufferX1Emfz",kbeg,kend,jbeg,jend+1, - KOKKOS_LAMBDA (int k, int j) { - BufferRight( (j-jbeg) + (k-kbeg)*(ny+1) ) = ez(k,j,iright); - } - ); + + // Create the base box to be patched by the ops + BoundingBox baseBox; + baseBox[IDIR][0] = data->beg[IDIR]; + baseBox[IDIR][1] = data->end[IDIR]; + baseBox[JDIR][0] = data->beg[JDIR]; + baseBox[JDIR][1] = data->end[JDIR]; + baseBox[KDIR][0] = data->beg[KDIR]; + baseBox[KDIR][1] = data->end[KDIR]; + + //extend by one the end on jdir && take the ghost on i + BoundingBox sendBoxEz = baseBox; + sendBoxEz[JDIR][1] += 1; + sendBoxEz[IDIR][0] = iright; + sendBoxEz[IDIR][1] = iright + 1; + BufferRight.Pack(ez, sendBoxEz); #if DIMENSIONS == 3 - int Vsindex = (ny+1)*nz; - idefix_for("LoadBufferX1Emfy",kbeg,kend+1,jbeg,jend, - KOKKOS_LAMBDA (int k, int j) { - BufferRight( (j-jbeg) + (k-kbeg)*ny + Vsindex ) = ey(k,j,iright); - } - ); + //extend by one the end on kdir && take the ghost on i + BoundingBox sendBoxEy = baseBox; + sendBoxEy[KDIR][1] += 1; + sendBoxEy[IDIR][0] = iright; + sendBoxEy[IDIR][1] = iright + 1; + BufferRight.Pack(ez, sendBoxEy); #endif // Wait for completion before sending out everything @@ -90,22 +94,22 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 BufferRight=BufferRecvX1[faceRight]; // Erase the emf with the one coming from the left process - - idefix_for("StoreBufferX1Emfz",kbeg,kend,jbeg,jend+1, - KOKKOS_LAMBDA (int k, int j) { - if(lbound == internal || lbound == periodic) { - ez(k,j,ileft) = BufferLeft( (j-jbeg) + (k-kbeg)*(ny+1)); - } - }); + //extend by one the end on jdir && take the ghost revc zone on i + BoundingBox recvBoxEz = baseBox; + recvBoxEz[JDIR][1] += 1; + recvBoxEz[IDIR][0] = ileft; + recvBoxEz[IDIR][1] = ileft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ez, recvBoxEz); #if DIMENSIONS == 3 - Vsindex = (ny+1)*nz; - idefix_for("StoreBufferX1Emfy",kbeg,kend+1,jbeg,jend, - KOKKOS_LAMBDA (int k, int j) { - if(lbound == internal || lbound == periodic) { - ey(k,j,ileft) = BufferLeft( (j-jbeg) + (k-kbeg)*ny +Vsindex); - } - }); + //extend by one the end on kdir && take the ghost revc zone on i + BoundingBox recvBoxEy = baseBox; + recvBoxEy[KDIR][1] += 1; + recvBoxEy[IDIR][0] = ileft; + recvBoxEy[IDIR][1] = ileft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ey, recvBoxEy); #endif @@ -118,11 +122,9 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 idfx::pushRegion("Emf::ExchangeX2"); // Load the buffers with data - int jleft,jright,ibeg,iend,kbeg,kend; - int nx; - [[maybe_unused]] int nz; - IdefixArray1D BufferLeft=BufferSendX2[faceLeft]; - IdefixArray1D BufferRight=BufferSendX2[faceRight]; + int jleft,jright; + Buffer BufferLeft=BufferSendX2[faceLeft]; + Buffer BufferRight=BufferSendX2[faceRight]; // If MPI Persistent, start receiving even before the buffers are filled double tStart = MPI_Wtime(); @@ -135,28 +137,32 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 BoundaryType rbound = data->rbound[JDIR]; // Coordinates of the ghost region which needs to be transfered - ibeg = data->beg[IDIR]; - iend = data->end[IDIR]; - nx = iend - ibeg; jleft = data->beg[JDIR]; jright = data->end[JDIR]; - kbeg = data->beg[KDIR]; - kend = data->end[KDIR]; - nz = kend - kbeg; - - idefix_for("LoadBufferX2Emfz",kbeg,kend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int i) { - BufferRight( (i-ibeg) + (k-kbeg)*(nx+1) ) = ez(k,jright,i); - } - ); + + // Create the base box to be patched by the ops + BoundingBox baseBox; + baseBox[IDIR][0] = data->beg[IDIR]; + baseBox[IDIR][1] = data->end[IDIR]; + baseBox[JDIR][0] = data->beg[JDIR]; + baseBox[JDIR][1] = data->end[JDIR]; + baseBox[KDIR][0] = data->beg[KDIR]; + baseBox[KDIR][1] = data->end[KDIR]; + + //extend by one the end on idir && take the ghost on j + BoundingBox sendBoxEz = baseBox; + sendBoxEz[IDIR][1] += 1; + sendBoxEz[JDIR][0] = jright; + sendBoxEz[JDIR][1] = jright + 1; + BufferRight.Pack(ez, sendBoxEz); #if DIMENSIONS == 3 - int Vsindex = (nx+1)*nz; - idefix_for("LoadBufferX1Emfx",kbeg,kend+1,ibeg,iend, - KOKKOS_LAMBDA (int k, int i) { - BufferRight( (i-ibeg) + (k-kbeg)*nx + Vsindex ) = ex(k,jright,i); - } - ); + //extend by one the end on idir && take the ghost on j + BoundingBox sendBoxEx = baseBox; + sendBoxEx[KDIR][1] += 1; + sendBoxEx[JDIR][0] = jright; + sendBoxEx[JDIR][1] = jright + 1; + BufferRight.Pack(ex, sendBoxEx); #endif // Wait for completion before sending out everything @@ -165,7 +171,7 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 tStart = MPI_Wtime(); MPI_SAFE_CALL(MPI_Startall(2, sendRequestX2)); // Wait for buffers to be received - MPI_Waitall(2,recvRequestX2,recvStatus); + MPI_Waitall(2, recvRequestX2, recvStatus); MPI_Waitall(2, sendRequestX2, sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; @@ -174,20 +180,21 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 BufferRight=BufferRecvX2[faceRight]; // We average the edge emfs zones - idefix_for("StoreBufferX2Emfz",kbeg,kend,ibeg,iend+1, - KOKKOS_LAMBDA (int k, int i) { - if(lbound == internal || lbound == periodic) { - ez(k,jleft,i) = BufferLeft( (i-ibeg) + (k-kbeg)*(nx+1) ); - } - }); + //extend by one the end on idir && take the ghost revc zone on j + BoundingBox recvBoxEz = baseBox; + recvBoxEz[IDIR][1] += 1; + recvBoxEz[JDIR][0] = jleft; + recvBoxEz[JDIR][1] = jleft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ez, recvBoxEz); #if DIMENSIONS == 3 - Vsindex = (nx+1)*nz; - idefix_for("StoreBufferX1Emfy",kbeg,kend+1,ibeg,iend, - KOKKOS_LAMBDA (int k, int i) { - if(lbound == internal || lbound == periodic) { - ex(k,jleft,i) = BufferLeft( (i-ibeg) + (k-kbeg)*nx +Vsindex); - } - }); + //extend by one the end on kdir && take the ghost revc zone on j + BoundingBox recvBoxEx = baseBox; + recvBoxEx[KDIR][1] += 1; + recvBoxEx[JDIR][0] = jleft; + recvBoxEx[JDIR][1] = jleft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ex, recvBoxEx); #endif @@ -201,13 +208,9 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 // Load the buffers with data - int kleft,kright,ibeg,iend,jbeg,jend; - int nx,ny; - IdefixArray1D BufferLeft=BufferSendX3[faceLeft]; - IdefixArray1D BufferRight=BufferSendX3[faceRight]; - - int Vsindex = 0; - + int kleft,kright,jbeg,jend; + Buffer BufferLeft=BufferSendX3[faceLeft]; + Buffer BufferRight=BufferSendX3[faceRight]; // If MPI Persistent, start receiving even before the buffers are filled double tStart = MPI_Wtime(); @@ -220,29 +223,34 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 BoundaryType rbound = data->rbound[KDIR]; // Coordinates of the ghost region which needs to be transfered - ibeg = data->beg[IDIR]; - iend = data->end[IDIR]; - nx = iend - ibeg; - jbeg = data->beg[JDIR]; jend = data->end[JDIR]; - ny = jend - jbeg; kleft = data->beg[KDIR]; kright = data->end[KDIR]; - idefix_for("LoadBufferX3Emfx",jbeg,jend+1,ibeg,iend, - KOKKOS_LAMBDA (int j, int i) { - BufferRight( (i-ibeg) + (j-jbeg)*nx ) = ex(kright,j,i); - } - ); - Vsindex = nx*(ny+1); - - idefix_for("LoadBufferX3Emfy",jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int j, int i) { - BufferRight( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ) = ey(kright,j,i); - } - ); + // Create the base box to be patched by the ops + BoundingBox baseBox; + baseBox[IDIR][0] = data->beg[IDIR]; + baseBox[IDIR][1] = data->end[IDIR]; + baseBox[JDIR][0] = data->beg[JDIR]; + baseBox[JDIR][1] = data->end[JDIR]; + baseBox[KDIR][0] = data->beg[KDIR]; + baseBox[KDIR][1] = data->end[KDIR]; + + //extend by one the end on jdir && take the ghost on k + BoundingBox sendBoxEz = baseBox; + sendBoxEz[JDIR][1] += 1; + sendBoxEz[KDIR][0] = kright; + sendBoxEz[KDIR][1] = kright + 1; + BufferRight.Pack(ez, sendBoxEz); + + //extend by one the end on idir && take the ghost on k + BoundingBox sendBoxEy = baseBox; + sendBoxEy[IDIR][1] += 1; + sendBoxEy[KDIR][0] = kright; + sendBoxEy[KDIR][1] = kright + 1; + BufferRight.Pack(ey, sendBoxEy); // Wait for completion before sending out everything Kokkos::fence(); @@ -250,7 +258,7 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 tStart = MPI_Wtime(); MPI_SAFE_CALL(MPI_Startall(2, sendRequestX3)); // Wait for buffers to be received - MPI_Waitall(2,recvRequestX3,recvStatus); + MPI_Waitall(2, recvRequestX3, recvStatus); MPI_Waitall(2, sendRequestX3, sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; @@ -259,20 +267,21 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 BufferRight=BufferRecvX3[faceRight]; // We average the edge emfs zones - idefix_for("StoreBufferX3Emfx",jbeg,jend+1,ibeg,iend, - KOKKOS_LAMBDA (int j, int i) { - if(lbound == internal || lbound == periodic) { - ex(kleft,j,i) = BufferLeft( (i-ibeg) + (j-jbeg)*nx ); - } - }); - - Vsindex = nx*(ny+1); - idefix_for("StoreBufferX3Emfy",jbeg,jend,ibeg,iend+1, - KOKKOS_LAMBDA (int j, int i) { - if(lbound == internal || lbound == periodic) { - ey(kleft,j,i) = BufferLeft( (i-ibeg) + (j-jbeg)*(nx+1) + Vsindex ); - } - }); + //extend by one the end on jdir && take the ghost revc zone on k + BoundingBox recvBoxEx = baseBox; + recvBoxEx[JDIR][1] += 1; + recvBoxEx[KDIR][0] = kleft; + recvBoxEx[KDIR][1] = kleft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ex, recvBoxEx); + + //extend by one the end on idir && take the ghost revc zone on k + BoundingBox recvBoxEy = baseBox; + recvBoxEy[IDIR][1] += 1; + recvBoxEy[KDIR][0] = kleft; + recvBoxEy[KDIR][1] = kleft + 1; + if(lbound == internal || lbound == periodic) + BufferLeft.Unpack(ey, recvBoxEy); idfx::popRegion(); } diff --git a/src/fluid/constrainedTransport/constrainedTransport.hpp b/src/fluid/constrainedTransport/constrainedTransport.hpp index 24c317c09..ab83b23bc 100644 --- a/src/fluid/constrainedTransport/constrainedTransport.hpp +++ b/src/fluid/constrainedTransport/constrainedTransport.hpp @@ -11,6 +11,7 @@ #include "idefix.hpp" #include "input.hpp" #include "riemannSolver.hpp" +#include "buffer.hpp" // Forward declarations #include "physics.hpp" @@ -122,12 +123,12 @@ class ConstrainedTransport { enum {faceRight, faceLeft}; // Buffers for MPI calls - IdefixArray1D BufferSendX1[2]; - IdefixArray1D BufferSendX2[2]; - IdefixArray1D BufferSendX3[2]; - IdefixArray1D BufferRecvX1[2]; - IdefixArray1D BufferRecvX2[2]; - IdefixArray1D BufferRecvX3[2]; + Buffer BufferSendX1[2]; + Buffer BufferSendX2[2]; + Buffer BufferSendX3[2]; + Buffer BufferRecvX1[2]; + Buffer BufferRecvX2[2]; + Buffer BufferRecvX3[2]; IdefixArray1D mapVars; @@ -286,10 +287,10 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr bufferSizeX1 += data->np_int[JDIR] * (data->np_int[KDIR]+KOFFSET); #endif - BufferRecvX1[faceLeft ] = IdefixArray1D("EmfRecvX1Left", bufferSizeX1); - BufferRecvX1[faceRight] = IdefixArray1D("EmfRecvX1Right",bufferSizeX1); - BufferSendX1[faceLeft ] = IdefixArray1D("EmfSendX1Left", bufferSizeX1); - BufferSendX1[faceRight] = IdefixArray1D("EmfSendX1Right",bufferSizeX1); + BufferRecvX1[faceLeft ] = Buffer(bufferSizeX1); + BufferRecvX1[faceRight] = Buffer(bufferSizeX1); + BufferSendX1[faceLeft ] = Buffer(bufferSizeX1); + BufferSendX1[faceRight] = Buffer(bufferSizeX1); // Number of cells in X2 boundary condition (only required when problem >2D): #if DIMENSIONS >= 2 @@ -301,10 +302,10 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr bufferSizeX2 += data->np_int[IDIR] * (data->np_int[KDIR]+KOFFSET); #endif - BufferRecvX2[faceLeft ] = IdefixArray1D("EmfRecvX2Left", bufferSizeX2); - BufferRecvX2[faceRight] = IdefixArray1D("EmfRecvX2Right",bufferSizeX2); - BufferSendX2[faceLeft ] = IdefixArray1D("EmfSendX2Left", bufferSizeX2); - BufferSendX2[faceRight] = IdefixArray1D("EmfSendX2Right",bufferSizeX2); + BufferRecvX2[faceLeft ] = Buffer(bufferSizeX2); + BufferRecvX2[faceRight] = Buffer(bufferSizeX2); + BufferSendX2[faceLeft ] = Buffer(bufferSizeX2); + BufferSendX2[faceRight] = Buffer(bufferSizeX2); #endif // Number of cells in X3 boundary condition (only required when problem is 3D): @@ -314,10 +315,10 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr // ey bufferSizeX3 += (data->np_int[IDIR]+IOFFSET) * data->np_int[JDIR]; - BufferRecvX3[faceLeft ] = IdefixArray1D("EmfRecvX3Left", bufferSizeX3); - BufferRecvX3[faceRight] = IdefixArray1D("EmfRecvX3Right",bufferSizeX3); - BufferSendX3[faceLeft ] = IdefixArray1D("EmfSendX3Left", bufferSizeX3); - BufferSendX3[faceRight] = IdefixArray1D("EmfSendX3Right",bufferSizeX3); + BufferRecvX3[faceLeft ] = Buffer(bufferSizeX3); + BufferRecvX3[faceRight] = Buffer(bufferSizeX3); + BufferSendX3[faceLeft ] = Buffer(bufferSizeX3); + BufferSendX3[faceRight] = Buffer(bufferSizeX3); #endif // DIMENSIONS // Init persistent MPI communications diff --git a/src/mpi/buffer.hpp b/src/mpi/buffer.hpp index ff4dff146..35164355b 100644 --- a/src/mpi/buffer.hpp +++ b/src/mpi/buffer.hpp @@ -31,6 +31,10 @@ class Buffer { return(array.data()); } + const IdefixArray1D & getArray(void) const { + return this->array; + } + int Size() { return(array.size()); } @@ -159,6 +163,33 @@ class Buffer { this->pointer += ninjnk; } + void UnpackJDirSymetric(IdefixArray4D& out, + const int var, + const int symMultiplier, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("UnLoadBuffer4D_var_sym",kbeg,kend,jbeg,jend,ibeg,iend, + KOKKOS_LAMBDA (int k, int j, int i) { + const int jinverted = jend-(j-jbeg)-1; + const int arrIndex = i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset; + out(var,k,jinverted,i) = symMultiplier * arr(arrIndex); + }); + + // Update pointer + this->pointer += ninjnk; + } + void Unpack(IdefixArray4D& out, IdefixArray1D& map, BoundingBox box) { @@ -186,6 +217,36 @@ class Buffer { this->pointer += ninjnk*map.size(); } + void UnpackJDirSymetric(IdefixArray4D& out, + IdefixArray1D& map, + IdefixArray1D& SymMap, + BoundingBox box) { + const int ni = box[IDIR][1]-box[IDIR][0]; + const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; + const int ninjnk = (box[KDIR][1]-box[KDIR][0])*ninj; + const int ibeg = box[IDIR][0]; + const int jbeg = box[JDIR][0]; + const int kbeg = box[KDIR][0]; + const int iend = box[IDIR][1]; + const int jend = box[JDIR][1]; + const int kend = box[KDIR][1]; + const int offset = this->pointer; + + auto arr = this->array; + idefix_for("UnLoadBuffer4D_map_sym",0,map.size(), + kbeg,kend, + jbeg,jend, + ibeg,iend, + KOKKOS_LAMBDA (int n, int k, int j, int i) { + const int jinverted = jend-(j-jbeg)-1; + const int arrIndex = i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + n*ninjnk + offset; + out(map(n),k,jinverted,i) = SymMap(map(n)) * arr(arrIndex); + }); + + // Update pointer + this->pointer += ninjnk*map.size(); + } + private: size_t pointer; From 85004d863c1f74d685165b0dcc903d9f947f603f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 8 Jul 2026 09:36:56 +0200 Subject: [PATCH 112/144] restore ctrl-c in pydefix (#388) --- src/pydefix.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/pydefix.cpp b/src/pydefix.cpp index 1b8168088..f7044af71 100644 --- a/src/pydefix.cpp +++ b/src/pydefix.cpp @@ -13,6 +13,7 @@ #include // For STL vectors and containers #include #include +#include #include "idefix.hpp" #include "dataBlock.hpp" #include "dataBlockHost.hpp" @@ -278,6 +279,7 @@ Pydefix::Pydefix(Input &input) { idfx::cout << "Pydefix: start Python interpreter." << std::endl; py::initialize_interpreter(); + std::signal(SIGINT, SIG_DFL); // restore "terminate on Ctrl-C" signal handler py::exec("import sys; print(f'Pydefix: Python Version: {sys.version}')"); py::exec("print(f'Pydefix: Executable Path: {sys.executable}')"); py::exec("print(f'Pydefix: Sys Path: {sys.path}')"); From 3a12a5cf48b713b26dc19b4163353745b13b5816 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Thu, 9 Jul 2026 19:09:17 +0200 Subject: [PATCH 113/144] MNT: migrate inifix-pre-commit hooks (#383) --- .pre-commit-config.yaml | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 8249b7b03..534106d85 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -44,11 +44,10 @@ repos: - --ignore - F403 # ignore import * - - repo: https://github.com/neutrinoceros/inifix - rev: v6.1.2 + - repo: https://github.com/la-niche/inifix-pre-commit + rev: v1.0.0 hooks: - id: inifix-format - files: ^(test/).*\.(ini)$ # want to skip pytest.ini - repo: https://github.com/Lucas-C/pre-commit-hooks rev: v1.5.5 From a1033893125d087407089312c5abd62dd9c06409 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 10 Jul 2026 11:07:45 +0200 Subject: [PATCH 114/144] do not show warning for balance issues on cpus (#387) * do not show warning for balance issues on cpus --- src/timeIntegrator.cpp | 37 +++++++++++++++++++++---------------- 1 file changed, 21 insertions(+), 16 deletions(-) diff --git a/src/timeIntegrator.cpp b/src/timeIntegrator.cpp index 6ffb6acfb..7079700d9 100644 --- a/src/timeIntegrator.cpp +++ b/src/timeIntegrator.cpp @@ -219,24 +219,29 @@ double TimeIntegrator::ComputeBalance() { } computeMean /= idfx::psize; imbalance = (computeMax-computeMin)/computeMean*100; - - if(imbalance>allowedImbalance ) { - idfx::cout << "-------------------------------------------------------------"<< std::endl; - idfx::cout << "Warning: MPI imbalance found in this run " << std::endl; - idfx::cout << std::fixed; - for(int i = 0 ; i < idfx::psize ; i++) { - if(computeLogPerCore[i]/computeMean - 1> allowedImbalance/2/100) { - idfx::cout << "+" << 100*(computeLogPerCore[i]/computeMean-1) - << "% (proc " << i << ")" << std::endl; - } - if(1-computeLogPerCore[i]/computeMean > allowedImbalance/2/100) { - idfx::cout << "-" << 100*(1-computeLogPerCore[i]/computeMean) - << "% (proc " << i << ")" << std::endl; + // only show warnings if the imbalance is higher than 20%on GPUs + #if defined(KOKKOS_ENABLE_CUDA) || defined(KOKKOS_ENABLE_HIP) || defined(KOKKOS_ENABLE_SYCL) + if(imbalance>allowedImbalance ) { + idfx::cout << "-------------------------------------------------------------" + << std::endl; + idfx::cout << "Warning: MPI imbalance found in this run " << std::endl; + idfx::cout << std::fixed; + for(int i = 0 ; i < idfx::psize ; i++) { + if(computeLogPerCore[i]/computeMean - 1> allowedImbalance/2/100) { + idfx::cout << "+" << 100*(computeLogPerCore[i]/computeMean-1) + << "% (proc " << i << ")" << std::endl; + } + if(1-computeLogPerCore[i]/computeMean > allowedImbalance/2/100) { + idfx::cout << "-" << 100*(1-computeLogPerCore[i]/computeMean) + << "% (proc " << i << ")" << std::endl; + } } + idfx::cout << "You should probably check these nodes are running properly." + << std::endl; + idfx::cout << "-------------------------------------------------------------" + << std::endl; } - idfx::cout << "You should probably check these nodes are running properly." << std::endl; - idfx::cout << "-------------------------------------------------------------"<< std::endl; - } + #endif } #endif return(imbalance); From 4f0ff746cb38accee32ab33e395b34956a7de95f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Wed, 15 Jul 2026 09:37:47 +0200 Subject: [PATCH 115/144] MNT: upgrade ruff pre-commit hook, move its configuration out of pre-commit-config.yaml and fix lints (#371) * MNT: move ruff config to ruff.toml * STY: apply ruff autofixes * STY: semi-manual fixes for Python lints: - add missing stacklevel in a Python warning - use conventional naming for unused loop variables in Python - Fix violations to rules, B011, B006 and B904 * fix indentation Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --------- Co-authored-by: Geoffroy Lesur Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --- .pre-commit-config.yaml | 17 +++-------------- doc/source/plot_idefix_bench.py | 4 +++- pytools/dump_io.py | 2 +- pytools/idfx_io.py | 3 +-- pytools/idfx_test.py | 15 ++++++++++----- pytools/idfx_test_gen.py | 11 +++++++++-- pytools/idfx_test_run.py | 17 ++++++++++------- pytools/sod.py | 2 +- pytools/tests/test_idfx_test_gen.py | 4 +++- pytools/tests/test_idfx_test_run.py | 7 +++++-- pytools/vtk_io.py | 7 ++++--- ruff.toml | 14 ++++++++++++++ test.py | 1 + test/Dust/DustEnergy/python/testidefix.py | 5 +++-- test/Dust/DustEnergy/testme.py | 1 + test/Dust/DustyShock/python/testidefix.py | 7 +++++-- test/Dust/DustyShock/testme.py | 1 + test/Dust/DustyWave/python/testidefix.py | 5 +++-- test/Dust/DustyWave/testme.py | 1 + test/HD/FargoPlanet/testme.py | 2 ++ test/HD/MachReflection/testme.py | 2 ++ test/HD/SedovBlastWave/python/testidefix.py | 7 +++++-- test/HD/SedovBlastWave/testme.py | 1 + test/HD/ShearingBox/python/testidefix.py | 6 ++++-- test/HD/ShearingBox/testme.py | 2 ++ test/HD/ViscousDisk/python/testidefix.py | 7 +++++-- test/HD/ViscousDisk/testme.py | 2 ++ test/HD/ViscousFlowPastCylinder/testme.py | 2 ++ test/HD/sod-iso/python/testidefix.py | 9 ++++++--- test/HD/sod-iso/testme.py | 1 + test/HD/sod/pydefix_example.py | 5 +++-- test/HD/sod/python/testidefix.py | 9 ++++++--- test/HD/sod/testme.py | 1 + test/HD/thermalDiffusion/python/testidefix.py | 5 +++-- test/HD/thermalDiffusion/testme.py | 2 ++ test/IO/dump/testme.py | 1 + test/IO/pydefix/pydefix_example.py | 5 +++-- test/IO/pydefix/testme.py | 2 ++ test/IO/xdmf/testme.py | 9 ++++----- test/MHD/AmbipolarCshock/python/testidefix.py | 11 +++++++---- test/MHD/AmbipolarCshock/testme.py | 2 ++ test/MHD/AmbipolarCshock3D/python/testidefix.py | 11 +++++++---- test/MHD/AmbipolarCshock3D/testme.py | 2 ++ .../AmbipolarShearingBox/python/testidefix.py | 6 ++++-- test/MHD/AxisFluxTube/python/checkAxisBounds.py | 4 +++- test/MHD/AxisFluxTube/testme.py | 1 + test/MHD/Coarsening/python/testidefix.py | 9 ++++++--- test/MHD/Coarsening/testme.py | 1 + test/MHD/FargoMHDSpherical/testme.py | 1 + test/MHD/HallWhistler/python/testidefix.py | 5 +++-- test/MHD/HallWhistler/testme.py | 1 + test/MHD/LinearWaveTest/python/testidefix.py | 12 ++++++++---- test/MHD/LinearWaveTest/testme.py | 2 ++ test/MHD/MTI/python/testidefix.py | 3 ++- test/MHD/MTI/testme.py | 1 + test/MHD/OrszagTang/testme.py | 2 ++ test/MHD/OrszagTang3D/testme.py | 1 + .../ResistiveAlfvenWave/python/testidefix.py | 5 +++-- test/MHD/ResistiveAlfvenWave/testme.py | 2 ++ test/MHD/ShearingBox/python/testidefix.py | 6 ++++-- test/MHD/ShearingBox/testme.py | 2 ++ test/MHD/clessTDiffusion/python/testidefix.py | 6 ++++-- test/MHD/clessTDiffusion/testme.py | 1 + test/MHD/sod-iso/testme.py | 1 + test/MHD/sod/testme.py | 1 + test/MHD/sphBragTDiffusion/python/testidefix.py | 6 ++++-- test/MHD/sphBragTDiffusion/testme.py | 1 + test/MHD/sphBragViscosity/python/testidefix.py | 6 ++++-- test/MHD/sphBragViscosity/testme.py | 1 + test/Planet/Planet3Body/python/testidefix.py | 2 ++ test/Planet/Planet3Body/testme.py | 1 + .../PlanetMigration2D/python/testidefix.py | 2 ++ test/Planet/PlanetMigration2D/testme.py | 1 + .../PlanetPlanetRK42D/python/testidefix.py | 4 +++- test/Planet/PlanetPlanetRK42D/testme.py | 1 + test/Planet/PlanetSpiral2D/python/testidefix.py | 9 +++++---- test/Planet/PlanetSpiral2D/testme.py | 1 + test/Planet/PlanetTorque3D/python/testidefix.py | 2 ++ test/Planet/PlanetTorque3D/testme.py | 1 + .../PlanetsIsActiveRK52D/python/testidefix.py | 2 ++ test/Planet/PlanetsIsActiveRK52D/testme.py | 1 + test/Pluto/HD/sod/python/idefixTools.py | 2 ++ test/Pluto/HD/sod/python/sod.py | 2 +- test/Pluto/HD/sod/python/testidefix.py | 9 +++++---- .../DustyCollapse/python/testidefix.py | 3 ++- test/SelfGravity/DustyCollapse/testme.py | 1 + .../JeansInstability/python/testidefix.py | 4 +++- test/SelfGravity/JeansInstability/testme.py | 1 + .../RandomSphere/python/testidefix.py | 5 +++-- test/SelfGravity/RandomSphere/testme.py | 2 ++ .../RandomSphereCartesian/python/testidefix.py | 5 +++-- .../SelfGravity/RandomSphereCartesian/testme.py | 2 ++ .../UniformCollapse/python/testidefix.py | 4 +++- test/SelfGravity/UniformCollapse/testme.py | 1 + test/utils/columnDensity/testme.py | 1 + test/utils/dumpImage/testme.py | 1 + test/utils/lookupTable/testme.py | 3 +++ 97 files changed, 274 insertions(+), 116 deletions(-) create mode 100644 ruff.toml diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 534106d85..9df5af9d9 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -28,21 +28,10 @@ repos: - repo: https://github.com/astral-sh/ruff-pre-commit - rev: v0.6.9 + rev: v0.15.8 hooks: - - id: ruff - args: - - --quiet - - --fix - - --select - - F # pyflakes - - B # flake8-bugbear - - I # isort - - NPY # numpy-specific rules - - --ignore - - F405 - - --ignore - - F403 # ignore import * + - id: ruff-check + args: [--quiet, --fix, --show-fixes] - repo: https://github.com/la-niche/inifix-pre-commit rev: v1.0.0 diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py index 43482eb04..baa74ac89 100644 --- a/doc/source/plot_idefix_bench.py +++ b/doc/source/plot_idefix_bench.py @@ -1,6 +1,8 @@ -import matplotlib.pyplot as plt import json +import matplotlib.pyplot as plt + + def do_plot(title, bench_file, gpumodels): with open(bench_file, 'r') as f: benches = json.load(f) diff --git a/pytools/dump_io.py b/pytools/dump_io.py index 4b258336f..7d0ec580b 100644 --- a/pytools/dump_io.py +++ b/pytools/dump_io.py @@ -59,7 +59,7 @@ def __init__(self, fh, byteorder="little"): self.ndims = int.from_bytes(fh.read(INT_SIZE), byteorder) dims = [] ntot = 1 - for dim in range(self.ndims): + for _ in range(self.ndims): dims.append(int.from_bytes(fh.read(INT_SIZE), byteorder)) ntot = ntot * dims[-1] raw = struct.unpack(str(ntot) + stringchar, fh.read(mysize * ntot)) diff --git a/pytools/idfx_io.py b/pytools/idfx_io.py index 17dc62725..0e53a39aa 100644 --- a/pytools/idfx_io.py +++ b/pytools/idfx_io.py @@ -2,7 +2,6 @@ import numpy as np - __all__ = ["readIdfxFile"] # Read .idfx files which are created # for debug purposes by DataBlock.DumpToFile(std::string&) @@ -27,7 +26,7 @@ def __init__(self, fh, byteorder="little"): return self.ndims = int.from_bytes(fh.read(INT_SIZE), byteorder) dims = [] - for dim in range(self.ndims): + for _ in range(self.ndims): dims.append(int.from_bytes(fh.read(INT_SIZE), byteorder)) ntot = int(np.prod(dims)) raw = struct.unpack(str(ntot) + "d", fh.read(DOUBLE_SIZE * ntot)) diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index be35e78e5..ee3fbee36 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -1,16 +1,17 @@ import argparse +import json import os +import re import shutil import subprocess import sys -import re -import json -import numpy as np import matplotlib.pyplot as plt +import numpy as np from .dump_io import readDump + class bcolors: HEADER = '\033[95m' OKBLUE = '\033[94m' @@ -166,8 +167,10 @@ def addLog(self, entry): with open(os.path.join(self.problemDir,"testsuite.log.json"), "w+") as fp: json.dump(self.log, fp, indent='\t') - def applyConfig(self, config: dict={}): + def applyConfig(self, config: dict | None = None): # check args + if config is None: + config = {} for key, value in config.items(): if key not in ['ini', 'testfile', 'testname', 'dumpname', 'check_file_produced']: assert key in self.cmdArgs, f"The given configuration overriding try to set an invalid paramater : {key}={value}" @@ -253,7 +256,9 @@ def _genCmakeCommand(self,definitionFile=""): return comm - def configure(self,definitionFile="", reuse_last_same_build=True, override: dict={}): + def configure(self,definitionFile="", reuse_last_same_build=True, override: dict | None = None): + if override is None: + override = {} # log self.addLog({"call": "configure", "args":{ 'definitionFile': definitionFile, diff --git a/pytools/idfx_test_gen.py b/pytools/idfx_test_gen.py index e45f927d0..ada8b962a 100644 --- a/pytools/idfx_test_gen.py +++ b/pytools/idfx_test_gen.py @@ -6,6 +6,7 @@ ##################################################################################### import copy + import pytest DO_NOT_LOOP_ON = ['restart_no_overwrite', "dec", "multirun", "check_file_produced"] @@ -32,7 +33,7 @@ def __init__(self, currentTestFile: str, name: str = ""): self.currentTestName = name # generate the list of configs to run - def genTestConfigs(self, names:str, params, whenClauses = {}, defaultConfig: dict = {}) -> list: + def genTestConfigs(self, names:str, params, whenClauses = None, defaultConfig: dict | None = None) -> list: ''' Generate the the list of configurations as pytest parameters. It will unpack the configuration set by looping on all combinations defined @@ -54,6 +55,10 @@ def genTestConfigs(self, names:str, params, whenClauses = {}, defaultConfig: dic Returns: A list of pytest.param() ready to be fiven to parametrized pytest functions. ''' + if defaultConfig is None: + defaultConfig = {} + if whenClauses is None: + whenClauses = {} # get name ordering list nameList = names.split(',') if '' in nameList: @@ -159,7 +164,7 @@ def _genNextLevelCombinations(self, input: list, paramName: str, paramValues: li result.append(v) return result - def _genOneConfigSeries(self, names: str, config: dict, defaultConfig: dict={}) -> list: + def _genOneConfigSeries(self, names: str, config: dict, defaultConfig: dict | None = None) -> list: ''' Generate the the list of configurations as pytest parameters. It will unpack the configuration set by looping on all combinations defined @@ -177,6 +182,8 @@ def _genOneConfigSeries(self, names: str, config: dict, defaultConfig: dict={}) Returns: A list of pytest.param() ready to be fiven to parametrized pytest functions. ''' + if defaultConfig is None: + defaultConfig = {} # get name ordering list nameList = names.split(',') diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index a4ad268da..b96ce8408 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -5,16 +5,19 @@ # Licensed under CeCILL 2.1 License, see COPYING for more information ##################################################################################### +import copy +import glob +import json import os import sys -import json -import glob -import copy +from contextlib import contextmanager + import pytest + # idefix test class import pytools.idfx_test as tst -from pytools.idfx_test_gen import IdefixDirTestGenerator -from contextlib import contextmanager +from pytools.idfx_test_gen import IdefixDirTestGenerator + @contextmanager def moveInDir(path): @@ -107,7 +110,7 @@ def genTests(self) -> list: # gen result += idefixTestGenerator.genTestConfigs(namings, variants, whenClauses=whenClauses, defaultConfig=defaultConfig) except Exception as e: - raise Exception(f"Fail to generate tests from {testfileRelPath} : {e}") + raise Exception(f"Fail to generate tests from {testfileRelPath}") from e # ok return result @@ -256,7 +259,7 @@ def main(self, all: bool = False): if idefixTest.all: pytest.main(['-v', '--no-header', '--junit-xml=idefix-tests.junit.xml', '--tb=short'] + idefixTest.remainingArgs + [self.parentScritFile]) else: - assert False, "Not yet supported !" + raise NotImplementedError("Not yet supported !") #elif self.check: # idefixTest.checkOnly(filename=dumpname, tolerance=tolerance) #else: diff --git a/pytools/sod.py b/pytools/sod.py index 07a60d2cc..ba0e16314 100644 --- a/pytools/sod.py +++ b/pytools/sod.py @@ -264,7 +264,7 @@ def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, pos_description = ('Head of Rarefaction', 'Foot of Rarefaction', 'Contact Discontinuity', 'Shock') - positions = dict(zip(pos_description, x_positions)) + positions = dict(zip(pos_description, x_positions, strict=True)) # create arrays x, p, rho, u = create_arrays(pl, pr, xl, xr, x_positions, diff --git a/pytools/tests/test_idfx_test_gen.py b/pytools/tests/test_idfx_test_gen.py index fc4f6261e..d92a7d486 100644 --- a/pytools/tests/test_idfx_test_gen.py +++ b/pytools/tests/test_idfx_test_gen.py @@ -5,9 +5,11 @@ # Licensed under CeCILL 2.1 License, see COPYING for more information ##################################################################################### -from ..idfx_test_gen import IdefixDirTestGenerator import pytest +from ..idfx_test_gen import IdefixDirTestGenerator + + def test_extractNamingParameters(): # build generator gen = IdefixDirTestGenerator(__file__, "unit-test") diff --git a/pytools/tests/test_idfx_test_run.py b/pytools/tests/test_idfx_test_run.py index 8843705ee..58dc31ebe 100644 --- a/pytools/tests/test_idfx_test_run.py +++ b/pytools/tests/test_idfx_test_run.py @@ -5,10 +5,13 @@ # Licensed under CeCILL 2.1 License, see COPYING for more information ##################################################################################### -from ..idfx_test_run import IdexPytestRunner -import pytest import os +import pytest + +from ..idfx_test_run import IdexPytestRunner + + def test_genTests(): # build runner runner = IdexPytestRunner(__file__) diff --git a/pytools/vtk_io.py b/pytools/vtk_io.py index eb5cf4125..ac4551b2f 100644 --- a/pytools/vtk_io.py +++ b/pytools/vtk_io.py @@ -4,10 +4,11 @@ @author: glesur """ -import warnings -import numpy as np import os import re +import warnings + +import numpy as np # restrict what's included with `import *` to public API __all__ = [ @@ -98,7 +99,7 @@ def _load_header(self, fh, geometry=None): native_name, _ncomp, native_dim, _dtype = d.split() self.native_coordinates[native_name] = np.fromfile(fh, dtype=dt, count=int(native_dim)) else: - warnings.warn("Found unknown field %s" % d) + warnings.warn("Found unknown field %s" % d, stacklevel=3) fh.readline() # skip extra linefeed (empty line) if self.geometry is None: diff --git a/ruff.toml b/ruff.toml new file mode 100644 index 000000000..9b6b6c620 --- /dev/null +++ b/ruff.toml @@ -0,0 +1,14 @@ +target-version = "py310" + +[lint] +select = [ + "F", # pyflakes + "B", # flake8-bugbear + "I", # isort + "NPY", # numpy-specific rules +] +ignore = [ + # allow `import *` + "F403", # undefined-local-with-import-star + "F405", # undefined-local-with-import-star-usage +] diff --git a/test.py b/test.py index 6ded87fa0..081d31664 100755 --- a/test.py +++ b/test.py @@ -2,6 +2,7 @@ import os import sys + import pytest # set IDEFIX_DIR diff --git a/test/Dust/DustEnergy/python/testidefix.py b/test/Dust/DustEnergy/python/testidefix.py index d7d766a15..14b64e002 100755 --- a/test/Dust/DustEnergy/python/testidefix.py +++ b/test/Dust/DustEnergy/python/testidefix.py @@ -5,10 +5,11 @@ @author: lesurg """ -import sys -import numpy as np import argparse +import sys + import matplotlib.pyplot as plt +import numpy as np parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/Dust/DustEnergy/testme.py b/test/Dust/DustEnergy/testme.py index 12d476b66..1d997a4ba 100755 --- a/test/Dust/DustEnergy/testme.py +++ b/test/Dust/DustEnergy/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Dust/DustyShock/python/testidefix.py b/test/Dust/DustyShock/python/testidefix.py index 8fca15a3f..df575bfe2 100755 --- a/test/Dust/DustyShock/python/testidefix.py +++ b/test/Dust/DustyShock/python/testidefix.py @@ -8,13 +8,16 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import argparse -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.integrate import solve_ivp +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/Dust/DustyShock/testme.py b/test/Dust/DustyShock/testme.py index 622f34772..b3cfab716 100755 --- a/test/Dust/DustyShock/testme.py +++ b/test/Dust/DustyShock/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Dust/DustyWave/python/testidefix.py b/test/Dust/DustyWave/python/testidefix.py index ad52d3306..1c386e6bf 100755 --- a/test/Dust/DustyWave/python/testidefix.py +++ b/test/Dust/DustyWave/python/testidefix.py @@ -5,10 +5,11 @@ @author: lesurg """ -import sys -import numpy as np import argparse +import sys + import matplotlib.pyplot as plt +import numpy as np parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/Dust/DustyWave/testme.py b/test/Dust/DustyWave/testme.py index 622f34772..b3cfab716 100755 --- a/test/Dust/DustyWave/testme.py +++ b/test/Dust/DustyWave/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/HD/FargoPlanet/testme.py b/test/HD/FargoPlanet/testme.py index b25a74bb0..5a0364443 100755 --- a/test/HD/FargoPlanet/testme.py +++ b/test/HD/FargoPlanet/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-13 def testMe(test): test.configure() diff --git a/test/HD/MachReflection/testme.py b/test/HD/MachReflection/testme.py index 7e6121815..cc8cf72e6 100755 --- a/test/HD/MachReflection/testme.py +++ b/test/HD/MachReflection/testme.py @@ -6,10 +6,12 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + def testMe(test): test.configure() test.compile() diff --git a/test/HD/SedovBlastWave/python/testidefix.py b/test/HD/SedovBlastWave/python/testidefix.py index a78bc88e5..40d39a79a 100755 --- a/test/HD/SedovBlastWave/python/testidefix.py +++ b/test/HD/SedovBlastWave/python/testidefix.py @@ -8,13 +8,16 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import argparse -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.interpolate import interp1d +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/HD/SedovBlastWave/testme.py b/test/HD/SedovBlastWave/testme.py index c3ef7025f..b75c7c6ea 100755 --- a/test/HD/SedovBlastWave/testme.py +++ b/test/HD/SedovBlastWave/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/HD/ShearingBox/python/testidefix.py b/test/HD/ShearingBox/python/testidefix.py index 1a0c2509a..d76561875 100755 --- a/test/HD/ShearingBox/python/testidefix.py +++ b/test/HD/ShearingBox/python/testidefix.py @@ -5,11 +5,13 @@ @author: lesurg """ +import argparse import sys -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.integrate import solve_ivp -import argparse + #compute theoretical solution (from Balbus & Hawley 2006, using notations from Lesur 2021) def rhs(t, y, Omega, q, k0x, k0y, k0z): diff --git a/test/HD/ShearingBox/testme.py b/test/HD/ShearingBox/testme.py index 18c792656..c69954af9 100755 --- a/test/HD/ShearingBox/testme.py +++ b/test/HD/ShearingBox/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-15 def testMe(test): test.configure() diff --git a/test/HD/ViscousDisk/python/testidefix.py b/test/HD/ViscousDisk/python/testidefix.py index 39e3666e1..8ee0d3491 100755 --- a/test/HD/ViscousDisk/python/testidefix.py +++ b/test/HD/ViscousDisk/python/testidefix.py @@ -8,11 +8,14 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -import numpy as np import argparse + import matplotlib.pyplot as plt +import numpy as np + +from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/HD/ViscousDisk/testme.py b/test/HD/ViscousDisk/testme.py index 34628fd80..0c74c78e4 100755 --- a/test/HD/ViscousDisk/testme.py +++ b/test/HD/ViscousDisk/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=3e-15 def testMe(test): test.configure() diff --git a/test/HD/ViscousFlowPastCylinder/testme.py b/test/HD/ViscousFlowPastCylinder/testme.py index 832a80e56..7033ae829 100755 --- a/test/HD/ViscousFlowPastCylinder/testme.py +++ b/test/HD/ViscousFlowPastCylinder/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=3e-14 def testMe(test): test.configure() diff --git a/test/HD/sod-iso/python/testidefix.py b/test/HD/sod-iso/python/testidefix.py index ec91c63eb..94b06c0f4 100755 --- a/test/HD/sod-iso/python/testidefix.py +++ b/test/HD/sod-iso/python/testidefix.py @@ -8,14 +8,17 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -from pytools import sod import argparse -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.interpolate import interp1d +from pytools import sod +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/HD/sod-iso/testme.py b/test/HD/sod-iso/testme.py index 109109baf..2a0257caf 100755 --- a/test/HD/sod-iso/testme.py +++ b/test/HD/sod-iso/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/HD/sod/pydefix_example.py b/test/HD/sod/pydefix_example.py index 58d73642b..937159f80 100644 --- a/test/HD/sod/pydefix_example.py +++ b/test/HD/sod/pydefix_example.py @@ -1,6 +1,7 @@ -import pydefix as pdfx -import numpy as np import matplotlib.pyplot as plt +import numpy as np +import pydefix as pdfx + def output(data): diff --git a/test/HD/sod/python/testidefix.py b/test/HD/sod/python/testidefix.py index 899218b17..3ba7a000c 100755 --- a/test/HD/sod/python/testidefix.py +++ b/test/HD/sod/python/testidefix.py @@ -8,14 +8,17 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -from pytools import sod import argparse -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.interpolate import interp1d +from pytools import sod +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/HD/sod/testme.py b/test/HD/sod/testme.py index 109109baf..2a0257caf 100755 --- a/test/HD/sod/testme.py +++ b/test/HD/sod/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/HD/thermalDiffusion/python/testidefix.py b/test/HD/thermalDiffusion/python/testidefix.py index 126c0be06..e032a5327 100755 --- a/test/HD/thermalDiffusion/python/testidefix.py +++ b/test/HD/thermalDiffusion/python/testidefix.py @@ -1,10 +1,11 @@ #!/usr/bin/env python3 # -*- coding: utf-8 -*- -import sys -import numpy as np import argparse +import sys + import matplotlib.pyplot as plt +import numpy as np parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/HD/thermalDiffusion/testme.py b/test/HD/thermalDiffusion/testme.py index 1d1a181b0..ead248b0e 100755 --- a/test/HD/thermalDiffusion/testme.py +++ b/test/HD/thermalDiffusion/testme.py @@ -6,10 +6,12 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + def testMe(test): test.configure() test.compile() diff --git a/test/IO/dump/testme.py b/test/IO/dump/testme.py index 25e84433b..41b0f277b 100755 --- a/test/IO/dump/testme.py +++ b/test/IO/dump/testme.py @@ -5,6 +5,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/IO/pydefix/pydefix_example.py b/test/IO/pydefix/pydefix_example.py index a08e86464..788518b26 100644 --- a/test/IO/pydefix/pydefix_example.py +++ b/test/IO/pydefix/pydefix_example.py @@ -1,6 +1,7 @@ -from pydefix import * -import numpy as np import matplotlib.pyplot as plt +import numpy as np +from pydefix import * + # The output function # the only argument is dataBlockHost python object, wrapping a dataBlockHost Idefix object diff --git a/test/IO/pydefix/testme.py b/test/IO/pydefix/testme.py index 2940e56dd..1e280af53 100755 --- a/test/IO/pydefix/testme.py +++ b/test/IO/pydefix/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-12 def testMe(test): test.configure() diff --git a/test/IO/xdmf/testme.py b/test/IO/xdmf/testme.py index 6273bbe0e..4f6b458f5 100755 --- a/test/IO/xdmf/testme.py +++ b/test/IO/xdmf/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst @@ -30,10 +31,7 @@ def check_xdmf_exists(): if not test.dec: test.dec=['2','2','2'] -if test.check: - check_xdmf_exists() - -else: +if not test.check: test.vectPot=False test.single=False test.reconstruction=2 @@ -42,4 +40,5 @@ def check_xdmf_exists(): test.configure(definitionFile="definitions.hpp") test.compile() test.run(inputFile="idefix.ini") - check_xdmf_exists + +check_xdmf_exists() diff --git a/test/MHD/AmbipolarCshock/python/testidefix.py b/test/MHD/AmbipolarCshock/python/testidefix.py index 8c95dbb1a..fe780c816 100755 --- a/test/MHD/AmbipolarCshock/python/testidefix.py +++ b/test/MHD/AmbipolarCshock/python/testidefix.py @@ -5,15 +5,18 @@ @author: lesurg """ -import numpy as np -from scipy.integrate import ode -import matplotlib.pyplot as plt import os import sys + +import matplotlib.pyplot as plt +import numpy as np +from scipy.integrate import ode + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import argparse +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/MHD/AmbipolarCshock/testme.py b/test/MHD/AmbipolarCshock/testme.py index 0e2f0815e..b8bd69459 100755 --- a/test/MHD/AmbipolarCshock/testme.py +++ b/test/MHD/AmbipolarCshock/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=0 def testMe(test): diff --git a/test/MHD/AmbipolarCshock3D/python/testidefix.py b/test/MHD/AmbipolarCshock3D/python/testidefix.py index a7354fbaa..c151dd789 100755 --- a/test/MHD/AmbipolarCshock3D/python/testidefix.py +++ b/test/MHD/AmbipolarCshock3D/python/testidefix.py @@ -5,15 +5,18 @@ @author: lesurg """ -import numpy as np -from scipy.integrate import ode -import matplotlib.pyplot as plt import os import sys + +import matplotlib.pyplot as plt +import numpy as np +from scipy.integrate import ode + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import argparse +from pytools.vtk_io import readVTK + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/MHD/AmbipolarCshock3D/testme.py b/test/MHD/AmbipolarCshock3D/testme.py index 94a8b0f4c..981fbff38 100755 --- a/test/MHD/AmbipolarCshock3D/testme.py +++ b/test/MHD/AmbipolarCshock3D/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=3e-14 def testMe(test): test.configure() diff --git a/test/MHD/AmbipolarShearingBox/python/testidefix.py b/test/MHD/AmbipolarShearingBox/python/testidefix.py index 1d1ccb281..6aec86a64 100755 --- a/test/MHD/AmbipolarShearingBox/python/testidefix.py +++ b/test/MHD/AmbipolarShearingBox/python/testidefix.py @@ -5,10 +5,12 @@ @author: lesurg """ -import numpy as np -import matplotlib.pyplot as plt import os import sys + +import matplotlib.pyplot as plt +import numpy as np + sys.path.append(os.getenv("IDEFIX_DIR")) from pytools.vtk_io import readVTK diff --git a/test/MHD/AxisFluxTube/python/checkAxisBounds.py b/test/MHD/AxisFluxTube/python/checkAxisBounds.py index 44eec58e2..774069886 100755 --- a/test/MHD/AxisFluxTube/python/checkAxisBounds.py +++ b/test/MHD/AxisFluxTube/python/checkAxisBounds.py @@ -7,10 +7,12 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.idfx_io import readIdfxFile import matplotlib.pyplot as plt +from pytools.idfx_io import readIdfxFile + rep="../" idfx=readIdfxFile(rep+"analysis.99.0.idfx") diff --git a/test/MHD/AxisFluxTube/testme.py b/test/MHD/AxisFluxTube/testme.py index 5abb46568..c5db6cfac 100755 --- a/test/MHD/AxisFluxTube/testme.py +++ b/test/MHD/AxisFluxTube/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/Coarsening/python/testidefix.py b/test/MHD/Coarsening/python/testidefix.py index e3ea0cd0a..206c01600 100755 --- a/test/MHD/Coarsening/python/testidefix.py +++ b/test/MHD/Coarsening/python/testidefix.py @@ -8,12 +8,15 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import argparse -import numpy as np -import matplotlib.pyplot as plt + import inifix +import matplotlib.pyplot as plt +import numpy as np + +from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/MHD/Coarsening/testme.py b/test/MHD/Coarsening/testme.py index 50d13c926..e82277ee6 100755 --- a/test/MHD/Coarsening/testme.py +++ b/test/MHD/Coarsening/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/FargoMHDSpherical/testme.py b/test/MHD/FargoMHDSpherical/testme.py index 1a3b28adb..ee74c24db 100755 --- a/test/MHD/FargoMHDSpherical/testme.py +++ b/test/MHD/FargoMHDSpherical/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/HallWhistler/python/testidefix.py b/test/MHD/HallWhistler/python/testidefix.py index 3d3eab2d3..2ca5d6bf8 100755 --- a/test/MHD/HallWhistler/python/testidefix.py +++ b/test/MHD/HallWhistler/python/testidefix.py @@ -12,10 +12,11 @@ @author: lesurg """ -import sys -import numpy as np import argparse +import sys + import matplotlib.pyplot as plt +import numpy as np from scipy.signal import argrelextrema parser = argparse.ArgumentParser() diff --git a/test/MHD/HallWhistler/testme.py b/test/MHD/HallWhistler/testme.py index f8ba0a258..ce50a7ae6 100755 --- a/test/MHD/HallWhistler/testme.py +++ b/test/MHD/HallWhistler/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/LinearWaveTest/python/testidefix.py b/test/MHD/LinearWaveTest/python/testidefix.py index be82269a6..8603ee8ed 100755 --- a/test/MHD/LinearWaveTest/python/testidefix.py +++ b/test/MHD/LinearWaveTest/python/testidefix.py @@ -1,15 +1,19 @@ #!/usr/bin/env python3 # -*- coding: utf-8 -*- -import numpy as np +import math import os import sys -import math + +import numpy as np + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.dump_io import readDump -import matplotlib.pyplot as plt import argparse +import matplotlib.pyplot as plt + +from pytools.dump_io import readDump + parser = argparse.ArgumentParser() parser.add_argument("-noplot", default=False, diff --git a/test/MHD/LinearWaveTest/testme.py b/test/MHD/LinearWaveTest/testme.py index eeaaab0fe..5b4aed87f 100755 --- a/test/MHD/LinearWaveTest/testme.py +++ b/test/MHD/LinearWaveTest/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=2e-13 def testMe(test): test.configure() diff --git a/test/MHD/MTI/python/testidefix.py b/test/MHD/MTI/python/testidefix.py index 4b60cc8bd..18481692d 100644 --- a/test/MHD/MTI/python/testidefix.py +++ b/test/MHD/MTI/python/testidefix.py @@ -9,9 +9,10 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -import numpy as np import inifix +import numpy as np n = 1 # fondamental mode diff --git a/test/MHD/MTI/testme.py b/test/MHD/MTI/testme.py index 0e2c9e317..baaed6302 100755 --- a/test/MHD/MTI/testme.py +++ b/test/MHD/MTI/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/OrszagTang/testme.py b/test/MHD/OrszagTang/testme.py index 41f33aba6..7f9688eb0 100755 --- a/test/MHD/OrszagTang/testme.py +++ b/test/MHD/OrszagTang/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-12 def testMe(test): test.configure() diff --git a/test/MHD/OrszagTang3D/testme.py b/test/MHD/OrszagTang3D/testme.py index 7a66150c5..662ba4066 100755 --- a/test/MHD/OrszagTang3D/testme.py +++ b/test/MHD/OrszagTang3D/testme.py @@ -5,6 +5,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/ResistiveAlfvenWave/python/testidefix.py b/test/MHD/ResistiveAlfvenWave/python/testidefix.py index 89b0f136c..52b11c8c8 100644 --- a/test/MHD/ResistiveAlfvenWave/python/testidefix.py +++ b/test/MHD/ResistiveAlfvenWave/python/testidefix.py @@ -1,7 +1,8 @@ -import sys -import numpy as np import argparse +import sys + import matplotlib.pyplot as plt +import numpy as np parser = argparse.ArgumentParser() parser.add_argument("-noplot", diff --git a/test/MHD/ResistiveAlfvenWave/testme.py b/test/MHD/ResistiveAlfvenWave/testme.py index ebc29ab57..72014c7cc 100755 --- a/test/MHD/ResistiveAlfvenWave/testme.py +++ b/test/MHD/ResistiveAlfvenWave/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-14 def testMe(test): diff --git a/test/MHD/ShearingBox/python/testidefix.py b/test/MHD/ShearingBox/python/testidefix.py index e1a882229..1ab5b2935 100755 --- a/test/MHD/ShearingBox/python/testidefix.py +++ b/test/MHD/ShearingBox/python/testidefix.py @@ -5,11 +5,13 @@ @author: lesurg """ +import argparse import sys -import numpy as np + import matplotlib.pyplot as plt +import numpy as np from scipy.integrate import solve_ivp -import argparse + #compute theoretical solution (from Balbus & Hawley 2006, using notations from Lesur 2021) def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): diff --git a/test/MHD/ShearingBox/testme.py b/test/MHD/ShearingBox/testme.py index ccee1a69c..1e30e1745 100755 --- a/test/MHD/ShearingBox/testme.py +++ b/test/MHD/ShearingBox/testme.py @@ -6,9 +6,11 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + tolerance=1e-14 def testMe(test): diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py index 9427aca82..f37cf5032 100644 --- a/test/MHD/clessTDiffusion/python/testidefix.py +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -1,9 +1,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -import numpy as np import inifix +import numpy as np + +from pytools.vtk_io import readVTK conf = inifix.load("../idefix.ini") gamma = conf["Hydro"]["gamma"] diff --git a/test/MHD/clessTDiffusion/testme.py b/test/MHD/clessTDiffusion/testme.py index 41193e141..98e3def92 100755 --- a/test/MHD/clessTDiffusion/testme.py +++ b/test/MHD/clessTDiffusion/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/sod-iso/testme.py b/test/MHD/sod-iso/testme.py index c85cc4ce7..70c7daaad 100755 --- a/test/MHD/sod-iso/testme.py +++ b/test/MHD/sod-iso/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/sod/testme.py b/test/MHD/sod/testme.py index c85cc4ce7..70c7daaad 100755 --- a/test/MHD/sod/testme.py +++ b/test/MHD/sod/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/sphBragTDiffusion/python/testidefix.py b/test/MHD/sphBragTDiffusion/python/testidefix.py index 8bf639cb4..d42c8bc92 100644 --- a/test/MHD/sphBragTDiffusion/python/testidefix.py +++ b/test/MHD/sphBragTDiffusion/python/testidefix.py @@ -1,9 +1,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -import numpy as np import inifix +import numpy as np + +from pytools.vtk_io import readVTK conf = inifix.load("../idefix.ini") amplitude = conf["Setup"]["amplitude"] diff --git a/test/MHD/sphBragTDiffusion/testme.py b/test/MHD/sphBragTDiffusion/testme.py index 41193e141..98e3def92 100755 --- a/test/MHD/sphBragTDiffusion/testme.py +++ b/test/MHD/sphBragTDiffusion/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/MHD/sphBragViscosity/python/testidefix.py b/test/MHD/sphBragViscosity/python/testidefix.py index c016242d6..7369f636e 100644 --- a/test/MHD/sphBragViscosity/python/testidefix.py +++ b/test/MHD/sphBragViscosity/python/testidefix.py @@ -1,11 +1,13 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK -import numpy as np import inifix +import numpy as np from scipy.special import jn +from pytools.vtk_io import readVTK + conf = inifix.load("../idefix.ini") amplitude = conf["Setup"]["amplitude"] time_step = conf["Output"]["vtk"] diff --git a/test/MHD/sphBragViscosity/testme.py b/test/MHD/sphBragViscosity/testme.py index b6c3467ea..0ad8ef254 100755 --- a/test/MHD/sphBragViscosity/testme.py +++ b/test/MHD/sphBragViscosity/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/Planet3Body/python/testidefix.py b/test/Planet/Planet3Body/python/testidefix.py index a3b7f64d5..91a680d63 100755 --- a/test/Planet/Planet3Body/python/testidefix.py +++ b/test/Planet/Planet3Body/python/testidefix.py @@ -8,9 +8,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + def separation(resonance): a = int(resonance[-1]) b = int(resonance[0]) diff --git a/test/Planet/Planet3Body/testme.py b/test/Planet/Planet3Body/testme.py index 6edac53ee..bdb0e193b 100755 --- a/test/Planet/Planet3Body/testme.py +++ b/test/Planet/Planet3Body/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/PlanetMigration2D/python/testidefix.py b/test/Planet/PlanetMigration2D/python/testidefix.py index 897d7b53f..0a47d24f7 100755 --- a/test/Planet/PlanetMigration2D/python/testidefix.py +++ b/test/Planet/PlanetMigration2D/python/testidefix.py @@ -8,9 +8,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + def datafile(filename): return np.loadtxt(filename, dtype="float64").T diff --git a/test/Planet/PlanetMigration2D/testme.py b/test/Planet/PlanetMigration2D/testme.py index 6c435cbd3..7aff376d0 100755 --- a/test/Planet/PlanetMigration2D/testme.py +++ b/test/Planet/PlanetMigration2D/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/PlanetPlanetRK42D/python/testidefix.py b/test/Planet/PlanetPlanetRK42D/python/testidefix.py index c3d4aa9b6..656e55c28 100755 --- a/test/Planet/PlanetPlanetRK42D/python/testidefix.py +++ b/test/Planet/PlanetPlanetRK42D/python/testidefix.py @@ -7,11 +7,13 @@ """ import os -import sys import re +import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + def filter_index(t): # get read of data previously generated (when the code was restarted) tref=t[-1] diff --git a/test/Planet/PlanetPlanetRK42D/testme.py b/test/Planet/PlanetPlanetRK42D/testme.py index 9521aabac..96dc08970 100755 --- a/test/Planet/PlanetPlanetRK42D/testme.py +++ b/test/Planet/PlanetPlanetRK42D/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/PlanetSpiral2D/python/testidefix.py b/test/Planet/PlanetSpiral2D/python/testidefix.py index ee9f5acc2..0b7fafe59 100755 --- a/test/Planet/PlanetSpiral2D/python/testidefix.py +++ b/test/Planet/PlanetSpiral2D/python/testidefix.py @@ -1,13 +1,14 @@ #!/usr/bin/env python # coding: utf-8 -import sys import os -sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK +import sys -import numpy as np +sys.path.append(os.getenv("IDEFIX_DIR")) import matplotlib.pyplot as plt +import numpy as np + +from pytools.vtk_io import readVTK on = 3 ds = readVTK(f"../data.{on:04d}.vtk", geometry="polar") diff --git a/test/Planet/PlanetSpiral2D/testme.py b/test/Planet/PlanetSpiral2D/testme.py index 6c435cbd3..7aff376d0 100755 --- a/test/Planet/PlanetSpiral2D/testme.py +++ b/test/Planet/PlanetSpiral2D/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/PlanetTorque3D/python/testidefix.py b/test/Planet/PlanetTorque3D/python/testidefix.py index 47477f64b..f51b4974b 100755 --- a/test/Planet/PlanetTorque3D/python/testidefix.py +++ b/test/Planet/PlanetTorque3D/python/testidefix.py @@ -8,9 +8,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + def datafile(filename): return np.loadtxt(filename, dtype="float64").T diff --git a/test/Planet/PlanetTorque3D/testme.py b/test/Planet/PlanetTorque3D/testme.py index 4393636ea..d68987dfa 100755 --- a/test/Planet/PlanetTorque3D/testme.py +++ b/test/Planet/PlanetTorque3D/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py index 0a5f91499..c39f51784 100755 --- a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py +++ b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py @@ -8,9 +8,11 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + def find_nearest(array, value): array = np.asarray(array) idx = (np.abs(array - value)).argmin() diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.py b/test/Planet/PlanetsIsActiveRK52D/testme.py index aca39ae53..562334d58 100755 --- a/test/Planet/PlanetsIsActiveRK52D/testme.py +++ b/test/Planet/PlanetsIsActiveRK52D/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/Pluto/HD/sod/python/idefixTools.py b/test/Pluto/HD/sod/python/idefixTools.py index a8d2dc86f..06e63afa8 100644 --- a/test/Pluto/HD/sod/python/idefixTools.py +++ b/test/Pluto/HD/sod/python/idefixTools.py @@ -7,6 +7,8 @@ import numpy as np + + class DataStructure: pass diff --git a/test/Pluto/HD/sod/python/sod.py b/test/Pluto/HD/sod/python/sod.py index 717c27ca6..90ad62fe0 100755 --- a/test/Pluto/HD/sod/python/sod.py +++ b/test/Pluto/HD/sod/python/sod.py @@ -266,7 +266,7 @@ def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, pos_description = ('Head of Rarefaction', 'Foot of Rarefaction', 'Contact Discontinuity', 'Shock') - positions = dict(zip(pos_description, x_positions)) + positions = dict(zip(pos_description, x_positions, strict=True)) # create arrays x, p, rho, u = create_arrays(pl, pr, xl, xr, x_positions, diff --git a/test/Pluto/HD/sod/python/testidefix.py b/test/Pluto/HD/sod/python/testidefix.py index d01db7bca..239bb1c86 100755 --- a/test/Pluto/HD/sod/python/testidefix.py +++ b/test/Pluto/HD/sod/python/testidefix.py @@ -6,12 +6,13 @@ @author: glesur """ -import idefixTools as idfx -import sod -import sys import argparse -import numpy as np +import sys + +import idefixTools as idfx import matplotlib.pyplot as plt +import numpy as np +import sod from scipy.interpolate import interp1d parser = argparse.ArgumentParser() diff --git a/test/SelfGravity/DustyCollapse/python/testidefix.py b/test/SelfGravity/DustyCollapse/python/testidefix.py index 370d89e77..83ec380ac 100644 --- a/test/SelfGravity/DustyCollapse/python/testidefix.py +++ b/test/SelfGravity/DustyCollapse/python/testidefix.py @@ -1,7 +1,8 @@ -import numpy as np import os import sys +import numpy as np + sys.path.append(os.getenv("IDEFIX_DIR")) from pytools.vtk_io import readVTK diff --git a/test/SelfGravity/DustyCollapse/testme.py b/test/SelfGravity/DustyCollapse/testme.py index 2df3893ab..bc9842e70 100755 --- a/test/SelfGravity/DustyCollapse/testme.py +++ b/test/SelfGravity/DustyCollapse/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/SelfGravity/JeansInstability/python/testidefix.py b/test/SelfGravity/JeansInstability/python/testidefix.py index 80d6ee620..34c52975c 100755 --- a/test/SelfGravity/JeansInstability/python/testidefix.py +++ b/test/SelfGravity/JeansInstability/python/testidefix.py @@ -8,11 +8,13 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import numpy as np from scipy.fftpack import fft, fftfreq +from pytools.vtk_io import readVTK + # Arguments gravCst = np.pi # grav cst G=pi gamma = 5/3 diff --git a/test/SelfGravity/JeansInstability/testme.py b/test/SelfGravity/JeansInstability/testme.py index 833feb262..0bb1d5188 100755 --- a/test/SelfGravity/JeansInstability/testme.py +++ b/test/SelfGravity/JeansInstability/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/SelfGravity/RandomSphere/python/testidefix.py b/test/SelfGravity/RandomSphere/python/testidefix.py index 444c3034d..65f3b8045 100755 --- a/test/SelfGravity/RandomSphere/python/testidefix.py +++ b/test/SelfGravity/RandomSphere/python/testidefix.py @@ -6,11 +6,12 @@ @author: glesur """ +import argparse import os import sys -import numpy as np + import matplotlib.pyplot as plt -import argparse +import numpy as np sys.path.append(os.getenv("IDEFIX_DIR")) diff --git a/test/SelfGravity/RandomSphere/testme.py b/test/SelfGravity/RandomSphere/testme.py index 65123498b..320cf5c59 100755 --- a/test/SelfGravity/RandomSphere/testme.py +++ b/test/SelfGravity/RandomSphere/testme.py @@ -6,10 +6,12 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + def testMe(test): test.configure() test.compile() diff --git a/test/SelfGravity/RandomSphereCartesian/python/testidefix.py b/test/SelfGravity/RandomSphereCartesian/python/testidefix.py index 7367b3d9a..3f8983843 100755 --- a/test/SelfGravity/RandomSphereCartesian/python/testidefix.py +++ b/test/SelfGravity/RandomSphereCartesian/python/testidefix.py @@ -6,12 +6,13 @@ @author: glesur """ +import argparse import os import sys -import numpy as np + import matplotlib.pyplot as plt +import numpy as np import numpy.fft as fft -import argparse sys.path.append(os.getenv("IDEFIX_DIR")) diff --git a/test/SelfGravity/RandomSphereCartesian/testme.py b/test/SelfGravity/RandomSphereCartesian/testme.py index 598aa3f21..507674665 100755 --- a/test/SelfGravity/RandomSphereCartesian/testme.py +++ b/test/SelfGravity/RandomSphereCartesian/testme.py @@ -6,10 +6,12 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst + def testMe(test): test.configure() test.compile() diff --git a/test/SelfGravity/UniformCollapse/python/testidefix.py b/test/SelfGravity/UniformCollapse/python/testidefix.py index e89a296a0..90dfacdac 100755 --- a/test/SelfGravity/UniformCollapse/python/testidefix.py +++ b/test/SelfGravity/UniformCollapse/python/testidefix.py @@ -8,10 +8,12 @@ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) -from pytools.vtk_io import readVTK import numpy as np +from pytools.vtk_io import readVTK + # Arguments gravCst = 1./(4.*np.pi) # grav cst 4piG rho0 = 1e-3 # initial density diff --git a/test/SelfGravity/UniformCollapse/testme.py b/test/SelfGravity/UniformCollapse/testme.py index 69918896b..f011cd211 100755 --- a/test/SelfGravity/UniformCollapse/testme.py +++ b/test/SelfGravity/UniformCollapse/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/utils/columnDensity/testme.py b/test/utils/columnDensity/testme.py index cd94eb4ef..4197a936e 100755 --- a/test/utils/columnDensity/testme.py +++ b/test/utils/columnDensity/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/utils/dumpImage/testme.py b/test/utils/dumpImage/testme.py index cd94eb4ef..4197a936e 100755 --- a/test/utils/dumpImage/testme.py +++ b/test/utils/dumpImage/testme.py @@ -6,6 +6,7 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst diff --git a/test/utils/lookupTable/testme.py b/test/utils/lookupTable/testme.py index 53f6607f2..1bc69a8f2 100755 --- a/test/utils/lookupTable/testme.py +++ b/test/utils/lookupTable/testme.py @@ -6,11 +6,14 @@ """ import os import sys + sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np + #from scipy.interpolate import RegularGridInterpolator import pytools.idfx_test as tst + def MakeNumpyFile(): x=np.arange(1,10,1.0) y=np.arange(5,10,1.0) From 0822bdf4e8546bb937ca8e47d5e3e15667cdac8e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 15 Jul 2026 09:42:54 +0200 Subject: [PATCH 116/144] update python req to 3.10 consistently (#390) * update python req to 3.10 consistently Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --------- Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --- doc/python_requirements.txt | 2 +- doc/source/index.rst | 2 +- doc/source/modules/pydefix.rst | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/doc/python_requirements.txt b/doc/python_requirements.txt index 28715fb71..991631e87 100644 --- a/doc/python_requirements.txt +++ b/doc/python_requirements.txt @@ -1,5 +1,5 @@ # Other requirements -# Python >= 3.7 +# Python >= 3.10 # Doxygen https://www.doxygen.nl/download.html # # Install Sphinx and required plugins with the following command diff --git a/doc/source/index.rst b/doc/source/index.rst index 2871f7953..2cea98cdb 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -34,7 +34,7 @@ MPI library the MPI library is GPU-Aware. If unsure, check this last point with your system administrator. Python - When using *Idefix* with its python interface through the module `Pydefix`, *Idefix* relies on an external python>=3.8 interpreter with the module `pybind11 `_ + When using *Idefix* with its python interface through the module `Pydefix`, *Idefix* relies on an external python>=3.10 interpreter with the module `pybind11 `_ installed. ================ diff --git a/doc/source/modules/pydefix.rst b/doc/source/modules/pydefix.rst index 0a8daf753..d359810e7 100644 --- a/doc/source/modules/pydefix.rst +++ b/doc/source/modules/pydefix.rst @@ -16,7 +16,7 @@ Before you start Pybind11 installation +++++++++++++++++++++ -In order to use pydefix, you need to be working in a python>=3.8 environement that includes `pybind11 `_. Follow the instruction of your package manager to install pybind11>=2.12. +In order to use pydefix, you need to be working in a python>=3.10 environment that includes `pybind11 `_. Follow the instructions of your package manager to install pybind11>=2.12. Pydefix usage ------------- From 392d89dac8d9d843f836ec27cbb06b907b9d72fb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Thu, 16 Jul 2026 22:33:03 +0200 Subject: [PATCH 117/144] STY: setup python formatting with ruff (#392) --- .git-blame-ignore-revs | 3 + .pre-commit-config.yaml | 4 +- doc/source/conf.py | 51 +- doc/source/plot_idefix_bench.py | 22 +- make_tarballs.py | 2 +- pytools/dump_io.py | 2 + pytools/idfx_io.py | 8 +- pytools/idfx_test.py | 1368 +++++++++-------- pytools/idfx_test_gen.py | 515 ++++--- pytools/idfx_test_run.py | 585 ++++--- pytools/sod.py | 161 +- pytools/tests/test_idfx_test_gen.py | 350 ++--- pytools/tests/test_idfx_test_run.py | 160 +- pytools/vtk_io.py | 6 +- test.py | 6 +- test/Dust/DustEnergy/python/testidefix.py | 61 +- test/Dust/DustEnergy/testme.py | 40 +- test/Dust/DustyShock/python/testidefix.py | 109 +- test/Dust/DustyShock/testme.py | 40 +- test/Dust/DustyWave/python/testidefix.py | 74 +- test/Dust/DustyWave/testme.py | 40 +- test/HD/FargoPlanet/testme.py | 63 +- test/HD/MachReflection/testme.py | 47 +- test/HD/SedovBlastWave/python/testidefix.py | 64 +- test/HD/SedovBlastWave/testme.py | 39 +- test/HD/ShearingBox/python/testidefix.py | 141 +- test/HD/ShearingBox/testme.py | 45 +- test/HD/ViscousDisk/python/testidefix.py | 97 +- test/HD/ViscousDisk/testme.py | 47 +- test/HD/ViscousFlowPastCylinder/testme.py | 57 +- test/HD/sod-iso/python/testidefix.py | 53 +- test/HD/sod-iso/testme.py | 60 +- test/HD/sod/pydefix_example.py | 21 +- test/HD/sod/python/testidefix.py | 57 +- test/HD/sod/testme.py | 60 +- test/HD/thermalDiffusion/python/testidefix.py | 44 +- test/HD/thermalDiffusion/testme.py | 39 +- test/IO/dump/testme.py | 69 +- test/IO/pydefix/pydefix_example.py | 52 +- test/IO/pydefix/testme.py | 45 +- test/IO/xdmf/testme.py | 42 +- test/MHD/AmbipolarCshock/python/testidefix.py | 128 +- test/MHD/AmbipolarCshock/testme.py | 42 +- .../AmbipolarCshock3D/python/testidefix.py | 134 +- test/MHD/AmbipolarCshock3D/testme.py | 73 +- .../AmbipolarShearingBox/python/testidefix.py | 27 +- .../AxisFluxTube/python/checkAxisBounds.py | 51 +- test/MHD/AxisFluxTube/testme.py | 52 +- test/MHD/Coarsening/python/testidefix.py | 91 +- test/MHD/Coarsening/testme.py | 44 +- test/MHD/FargoMHDSpherical/testme.py | 76 +- test/MHD/HallWhistler/python/testidefix.py | 73 +- test/MHD/HallWhistler/testme.py | 49 +- test/MHD/LinearWaveTest/python/testidefix.py | 70 +- test/MHD/LinearWaveTest/testme.py | 70 +- test/MHD/MTI/python/testidefix.py | 73 +- test/MHD/MTI/testme.py | 47 +- test/MHD/OrszagTang/testme.py | 91 +- test/MHD/OrszagTang3D/testme.py | 91 +- .../ResistiveAlfvenWave/python/testidefix.py | 38 +- test/MHD/ResistiveAlfvenWave/testme.py | 56 +- test/MHD/ShearingBox/python/testidefix.py | 155 +- test/MHD/ShearingBox/testme.py | 54 +- test/MHD/clessTDiffusion/python/testidefix.py | 22 +- test/MHD/clessTDiffusion/testme.py | 45 +- test/MHD/sod-iso/testme.py | 58 +- test/MHD/sod/testme.py | 58 +- .../sphBragTDiffusion/python/testidefix.py | 60 +- test/MHD/sphBragTDiffusion/testme.py | 45 +- .../MHD/sphBragViscosity/python/testidefix.py | 33 +- test/MHD/sphBragViscosity/testme.py | 49 +- test/Planet/Planet3Body/python/testidefix.py | 82 +- test/Planet/Planet3Body/testme.py | 54 +- .../PlanetMigration2D/python/testidefix.py | 26 +- test/Planet/PlanetMigration2D/testme.py | 56 +- .../PlanetPlanetRK42D/python/testidefix.py | 68 +- test/Planet/PlanetPlanetRK42D/testme.py | 87 +- .../PlanetSpiral2D/python/testidefix.py | 98 +- test/Planet/PlanetSpiral2D/testme.py | 56 +- .../PlanetTorque3D/python/testidefix.py | 26 +- test/Planet/PlanetTorque3D/testme.py | 56 +- .../PlanetsIsActiveRK52D/python/testidefix.py | 32 +- test/Planet/PlanetsIsActiveRK52D/testme.py | 52 +- test/Pluto/HD/sod/python/idefixTools.py | 432 +++--- test/Pluto/HD/sod/python/sod.py | 161 +- test/Pluto/HD/sod/python/testidefix.py | 57 +- .../DustyCollapse/python/testidefix.py | 22 +- test/SelfGravity/DustyCollapse/testme.py | 46 +- .../JeansInstability/python/testidefix.py | 34 +- test/SelfGravity/JeansInstability/testme.py | 48 +- .../RandomSphere/python/testidefix.py | 63 +- test/SelfGravity/RandomSphere/testme.py | 41 +- .../python/testidefix.py | 86 +- .../RandomSphereCartesian/testme.py | 39 +- .../UniformCollapse/python/testidefix.py | 30 +- test/SelfGravity/UniformCollapse/testme.py | 42 +- test/utils/columnDensity/testme.py | 3 +- test/utils/dumpImage/testme.py | 3 +- test/utils/lookupTable/testme.py | 30 +- 99 files changed, 4569 insertions(+), 3965 deletions(-) diff --git a/.git-blame-ignore-revs b/.git-blame-ignore-revs index 107cb9efb..0c984a957 100644 --- a/.git-blame-ignore-revs +++ b/.git-blame-ignore-revs @@ -9,3 +9,6 @@ # apply inifix-format to all .ini files ac260f4af48221229aef4fc1f93ffbf9df450739 1ca7676fee7a578bd64e64ec9b6bdfbceb921775 + +# apply ruff format to all .py files +8d0437bf23d7d8007355fa35b9f094287f7de987 diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 9df5af9d9..ddd79ae61 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -30,8 +30,10 @@ repos: - repo: https://github.com/astral-sh/ruff-pre-commit rev: v0.15.8 hooks: + - id: ruff-format + args: [--target-version=py310] - id: ruff-check - args: [--quiet, --fix, --show-fixes] + args: [--target-version=py310, --quiet, --fix, --show-fixes] - repo: https://github.com/la-niche/inifix-pre-commit rev: v1.0.0 diff --git a/doc/source/conf.py b/doc/source/conf.py index f47f6659c..1c772f493 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -18,13 +18,12 @@ # -- Project information ----------------------------------------------------- -project = 'Idefix' -copyright = 'Geoffroy Lesur et al.' -author = 'Geoffroy Lesur' +project = "Idefix" +copyright = "Geoffroy Lesur et al." +author = "Geoffroy Lesur" # The full version, including alpha/beta/rc tags -release = '2.3.0' - +release = "2.3.0" # -- General configuration --------------------------------------------------- @@ -34,20 +33,24 @@ # ones. extensions = [ "sphinx_rtd_theme", - 'sphinx_git', - 'matplotlib.sphinxext.plot_directive', + "sphinx_git", + "matplotlib.sphinxext.plot_directive", "breathe", "exhale", "m2r2", - "sphinx_copybutton" - ] + "sphinx_copybutton", +] source_suffix = [".rst", ".md"] -cpp_id_attributes=["KOKKOS_FORCEINLINE_FUNCTION","KOKKOS_INLINE_FUNCTION","KOKKOS_RESTRICT"] +cpp_id_attributes = [ + "KOKKOS_FORCEINLINE_FUNCTION", + "KOKKOS_INLINE_FUNCTION", + "KOKKOS_RESTRICT", +] # Add any paths that contain templates here, relative to this directory. -templates_path = ['_templates'] +templates_path = ["_templates"] # List of patterns, relative to source directory, that match files and # directories to ignore when looking for source files. @@ -60,45 +63,47 @@ # The theme to use for HTML and HTML Help pages. See the documentation for # a list of builtin themes. # -html_theme = 'sphinx_rtd_theme' +html_theme = "sphinx_rtd_theme" # Add any paths that contain custom static files (such as style sheets) here, # relative to this directory. They are copied after the builtin static files, # so a file named "default.css" will overwrite the builtin "default.css". -html_static_path = ['_static'] +html_static_path = ["_static"] + def setup(app): - app.add_css_file('my_theme.css') + app.add_css_file("my_theme.css") + ############## # Breathe/Exhale options # Setup the breathe extension breathe_projects = { - "Idefix": "./xml" + "Idefix": "./xml", } breathe_default_project = "Idefix" # Setup the exhale extension exhale_args = { # These arguments are required - "containmentFolder": "./api", - "rootFileName": "library_root.rst", - "rootFileTitle": "Idefix API", + "containmentFolder": "./api", + "rootFileName": "library_root.rst", + "rootFileTitle": "Idefix API", # Suggested optional arguments - "createTreeView": False, + "createTreeView": False, # TIP: if using the sphinx-bootstrap-theme, you need # "treeViewIsBootstrap": True, "doxygenStripFromPath": "../../src", "exhaleExecutesDoxygen": True, - "exhaleDoxygenStdin": textwrap.dedent(''' + "exhaleDoxygenStdin": textwrap.dedent(""" INPUT = ../../src EXCLUDE = ../../src/kokkos - ''') + """), } # Tell sphinx what the primary language being documented is. -primary_domain = 'cpp' +primary_domain = "cpp" # Tell sphinx what the pygments highlight language should be. -highlight_language = 'cpp' +highlight_language = "cpp" diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py index baa74ac89..7810751ef 100644 --- a/doc/source/plot_idefix_bench.py +++ b/doc/source/plot_idefix_bench.py @@ -4,24 +4,24 @@ def do_plot(title, bench_file, gpumodels): - with open(bench_file, 'r') as f: + with open(bench_file, "r") as f: benches = json.load(f) plt.figure() - xmax=0 - ymax=0 + xmax = 0 + ymax = 0 for gpumodel in gpumodels: - select = [bench for bench in benches if bench['gpumodel'] == gpumodel][-1] + select = [bench for bench in benches if bench["gpumodel"] == gpumodel][-1] - xs = [r['nbgpu'] for r in select['results']] - ys = [r['cell_updates'] for r in select['results']] - plt.plot(xs, ys,'o-',label=gpumodel) - xmax=max(xmax,max(xs)) - ymax=max(ymax,max(ys)) + xs = [r["nbgpu"] for r in select["results"]] + ys = [r["cell_updates"] for r in select["results"]] + plt.plot(xs, ys, "o-", label=gpumodel) + xmax = max(xmax, max(xs)) + ymax = max(ymax, max(ys)) plt.xscale("log", base=2) - plt.ylim(0,ymax*1.1) - plt.xlim(1,xmax*1.1) + plt.ylim(0, ymax * 1.1) + plt.xlim(1, xmax * 1.1) plt.legend() plt.xlabel("Number of GPUs/GCDs") plt.ylabel("Performance (cells / second / GPU)") diff --git a/make_tarballs.py b/make_tarballs.py index dfc1b55fa..df57b94bc 100644 --- a/make_tarballs.py +++ b/make_tarballs.py @@ -89,7 +89,7 @@ def _make_self_contained_tarball(output_dir, *, suffix="", exclude_list=None): os.replace(os.path.join(work_dir, tarball), final_tarfile) filesize = os.path.getsize(final_tarfile) - print("Done ! Final file size is %.1f MB" % (filesize / 1024 ** 2)) + print("Done ! Final file size is %.1f MB" % (filesize / 1024**2)) def main(argv=None): diff --git a/pytools/dump_io.py b/pytools/dump_io.py index 7d0ec580b..6c8338428 100644 --- a/pytools/dump_io.py +++ b/pytools/dump_io.py @@ -4,6 +4,7 @@ @author: lesurg """ + import os import re import struct @@ -119,6 +120,7 @@ def _read_fields(self, fh): def __repr__(self): return "DumpDataset('%s')" % self.filename + # public API def readDump(filename): return DumpDataset(filename) diff --git a/pytools/idfx_io.py b/pytools/idfx_io.py index 0e53a39aa..e530117a6 100644 --- a/pytools/idfx_io.py +++ b/pytools/idfx_io.py @@ -13,9 +13,9 @@ HEADER_SIZE = 128 + # There is one .idfx file per processor class IdfxFileField(object): - def __init__(self, fh, byteorder="little"): # read entry name q = fh.read(NAME_SIZE) @@ -32,6 +32,7 @@ def __init__(self, fh, byteorder="little"): raw = struct.unpack(str(ntot) + "d", fh.read(DOUBLE_SIZE * ntot)) self.array = np.asarray(raw).reshape(dims[::-1]) + class IdfxFileDataset(object): def __init__(self, filename): # identical to DumpDataset @@ -45,12 +46,11 @@ def _read_header(self, fh): # could easily be identical to DumpDataset headerSize = 128 q = fh.read(headerSize) - n = q.index(b'\x00') - self.header = q[:n].decode('utf-8') + n = q.index(b"\x00") + self.header = q[:n].decode("utf-8") self.metadata["byteorder"] = "little" - def _read_field(self, fh): # identical to DumpDataset if self.metadata["byteorder"] is None: diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index ee3fbee36..ac72d6dde 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -13,648 +13,744 @@ class bcolors: - HEADER = '\033[95m' - OKBLUE = '\033[94m' - OKCYAN = '\033[96m' - OKGREEN = '\033[92m' - WARNING = '\033[93m' - FAIL = '\033[91m' - ENDC = '\033[0m' - BOLD = '\033[1m' - UNDERLINE = '\033[4m' + HEADER = "\033[95m" + OKBLUE = "\033[94m" + OKCYAN = "\033[96m" + OKGREEN = "\033[92m" + WARNING = "\033[93m" + FAIL = "\033[91m" + ENDC = "\033[0m" + BOLD = "\033[1m" + UNDERLINE = "\033[4m" -class idfxTest: - def __init__ (self, current_test_file, name=""): - parser = argparse.ArgumentParser() - - idefix_dir_env = os.getenv("IDEFIX_DIR") - parser.add_argument("-noplot", - dest="noplot", - help="disable plotting in standard tests", - action="store_false") - - parser.add_argument("-ploterr", - help="Enable plotting on error in regression tests", - action="store_true") - - parser.add_argument("-cmake", - default=[], - help="CMake options", - nargs='+') - - parser.add_argument("-definitions", - default="", - help="definitions.hpp file") - - parser.add_argument("-dec", - default="", - help="MPI domain decomposition", - nargs='+') - - parser.add_argument("-check", - help="Only perform regression tests without compilation", - action="store_true") - - parser.add_argument("-cuda", - help="Test on Nvidia GPU using CUDA", - action="store_true") - - parser.add_argument("-intel", - help="Test compiling with Intel OneAPI", - action="store_true") - - parser.add_argument("-hip", - help="Test on AMD GPU using HIP", - action="store_true") - - parser.add_argument("-single", - help="Enable single precision", - action="store_true") - - parser.add_argument("-vectPot", - help="Enable vector potential formulation", - action="store_true") - - parser.add_argument("-reconstruction", - type=int, - default=2, - help="set reconstruction scheme (2=PLM, 3=LimO3, 4=PPM)") - - parser.add_argument("-idefixDir", - default=idefix_dir_env, - help="Set directory for idefix source files (default $IDEFIX_DIR)") - - parser.add_argument("-mpi", - help="Enable MPI", - action="store_true") - - parser.add_argument("-all", - help="Do all test suite (otherwise, just do the test with the current configuration)", - action="store_true") - - parser.add_argument("-init", - help="Reinit reference files for non-regression tests (dangerous!)", - action="store_true") - - parser.add_argument("-Werror", - help="Consider warnings as errors", - action="store_true") - - parser.add_argument("-ccache", - help="Use ccache to reduce the build time over multiple run of the test suite.", - action="store_true") - - parser.add_argument("-restart", - help="Enable creating a restart from a checkpoint.", - action='store_true') - - parser.add_argument("-v", "--verbose", - help="Enable verbose mode, by not capturing the output.", - action="store_true") - - parser.add_argument("--help-pytest", - help="Display the options you can transmit directly to pytest in addition to the specific to idefix tests.", - action="store_true") - - parser.add_argument("-fake", - help="Make a fake run by just logging the actions to validate that we generate same command over refactoring.", - action="store_true") - - # this option is not used directly by direct users of idfxTest but by idx_test_gen - parser.add_argument("-subdir", - default="./test", - help="Select the test in the given subdir not to run all.", - type=str) - - args, unknown=parser.parse_known_args() - - # transform all arguments from args into attributes of this instance - self.__dict__.update(vars(args)) - # store the full path of problem directory - self.currentTestFile = current_test_file - self.currentTestName = name - self.problemDir=os.path.dirname(current_test_file) - self.referenceDirectory = os.path.join(idefix_dir_env,"reference") - # current directory relative to $IDEFIX_DIR/test (used to retrieve the path ot reference files) - self.testDir=os.path.relpath(self.problemDir,os.path.join(idefix_dir_env,"test")) - # build directory, currently inside the test named build-test - self.buildDir=os.path.join(self.problemDir,"build-test") - # remind what build we dit last - self.lastCmakeCmd="" - # subdir - self.filterSubdir=args.subdir - # save - self.cmdArgs = vars(args) - self.cmdArgs.update({ - "restart_no_overwrite": [], - }) - self.log=[] - # when making a restart we should not overrite those files (will be checked) - self.restart_no_overwrite=[] - - # forward args for pytest - if args.verbose: - unknown.append("--capture=no") - if args.help_pytest: - unknown.append("--help") - # remaining args - self.remainingArgs=unknown - - def addLog(self, entry): - if self.fake: - self.log.append(entry) - with open(os.path.join(self.problemDir,"testsuite.log.json"), "w+") as fp: - json.dump(self.log, fp, indent='\t') - - def applyConfig(self, config: dict | None = None): - # check args - if config is None: - config = {} - for key, value in config.items(): - if key not in ['ini', 'testfile', 'testname', 'dumpname', 'check_file_produced']: - assert key in self.cmdArgs, f"The given configuration overriding try to set an invalid paramater : {key}={value}" - - # override options - newArgs = {} - newArgs.update(self.cmdArgs) - newArgs.update(config) - - # replace in dict - self.__dict__.update(newArgs) - - def _genCmakeCommand(self,definitionFile=""): - comm=["cmake"] - # add source directory - comm.append(self.idefixDir) - - # we will build in ./build-test so problem dir is parent - comm.append("-DIdefix_PROBLEM_DIR="+self.problemDir) - - # add specific options - for opt in self.cmake: - comm.append("-D"+opt) - - if self.cuda: - comm.append("-DKokkos_ENABLE_CUDA=ON") - # disable fmad operations on Cuda to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=--fmad=false") - # disable Async cuda malloc for tests performed on old UCX implementations - comm.append("-DKokkos_ENABLE_IMPL_CUDA_MALLOC_ASYNC=OFF") - - if self.intel: - # disable fmad operations on Cuda to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=-fp-model=strict") - comm.append("-DCMAKE_CXX_COMPILER=icpx") - comm.append("-DCMAKE_C_COMPILER=icx") - - if self.hip: - comm.append("-DKokkos_ENABLE_HIP=ON") - # disable fmad operations on HIP to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=-ffp-contract=off") - - #if we use single precision - if(self.single): - comm.append("-DIdefix_PRECISION=Single") - else: - comm.append("-DIdefix_PRECISION=Double") - - - if(self.vectPot): - comm.append("-DIdefix_EVOLVE_VECTOR_POTENTIAL=ON") - else: - comm.append("-DIdefix_EVOLVE_VECTOR_POTENTIAL=OFF") - - if(self.Werror): - comm.append("-DIdefix_WERROR=ON") - - # add a definition file if provided - if(definitionFile): - self.definitions=definitionFile - else: - self.definitions="definitions.hpp" - - comm.append("-DIdefix_DEFS="+os.path.join(self.problemDir, self.definitions)) - - if(self.mpi): - comm.append("-DIdefix_MPI=ON") - else: - comm.append("-DIdefix_MPI=OFF") - - if(self.reconstruction == 2): - comm.append("-DIdefix_RECONSTRUCTION=Linear") - elif(self.reconstruction==3): - comm.append("-DIdefix_RECONSTRUCTION=LimO3") - elif(self.reconstruction==4): - comm.append("-DIdefix_RECONSTRUCTION=Parabolic") - - # export ccache env - if self.ccache: - comm.append("-DCMAKE_CXX_COMPILER_LAUNCHER=ccache") - - # ok - return comm - - - def configure(self,definitionFile="", reuse_last_same_build=True, override: dict | None = None): - if override is None: - override = {} - # log - self.addLog({"call": "configure", "args":{ - 'definitionFile': definitionFile, - 'reuse_last_same_build': reuse_last_same_build, - 'override': override - }}) - - # gen command - comm = self._genCmakeCommand(definitionFile) - - # log - print("***************** CALLING CMAKE *******************") - print(f"mkdir -p {self.buildDir}") - print(f"cd {self.buildDir}") - print(' '.join(comm)) - print("***************************************************") - - # not action needed if same command or force no rebuild - if reuse_last_same_build == True and self.lastCmakeCmd == ' '.join(comm): - print("SKIP ALREADY DONE") - return - - # run - try: - # do cleanup - self.clean() +class idfxTest: + def __init__(self, current_test_file, name=""): + parser = argparse.ArgumentParser() + + idefix_dir_env = os.getenv("IDEFIX_DIR") + + parser.add_argument( + "-noplot", + dest="noplot", + help="disable plotting in standard tests", + action="store_false", + ) + + parser.add_argument( + "-ploterr", + help="Enable plotting on error in regression tests", + action="store_true", + ) + + parser.add_argument("-cmake", default=[], help="CMake options", nargs="+") + + parser.add_argument("-definitions", default="", help="definitions.hpp file") + + parser.add_argument( + "-dec", default="", help="MPI domain decomposition", nargs="+" + ) + + parser.add_argument( + "-check", + help="Only perform regression tests without compilation", + action="store_true", + ) + + parser.add_argument( + "-cuda", help="Test on Nvidia GPU using CUDA", action="store_true" + ) + + parser.add_argument( + "-intel", help="Test compiling with Intel OneAPI", action="store_true" + ) + + parser.add_argument( + "-hip", help="Test on AMD GPU using HIP", action="store_true" + ) + + parser.add_argument( + "-single", help="Enable single precision", action="store_true" + ) + + parser.add_argument( + "-vectPot", help="Enable vector potential formulation", action="store_true" + ) + + parser.add_argument( + "-reconstruction", + type=int, + default=2, + help="set reconstruction scheme (2=PLM, 3=LimO3, 4=PPM)", + ) + + parser.add_argument( + "-idefixDir", + default=idefix_dir_env, + help="Set directory for idefix source files (default $IDEFIX_DIR)", + ) + + parser.add_argument("-mpi", help="Enable MPI", action="store_true") + + parser.add_argument( + "-all", + help="Do all test suite (otherwise, just do the test with the current configuration)", + action="store_true", + ) + + parser.add_argument( + "-init", + help="Reinit reference files for non-regression tests (dangerous!)", + action="store_true", + ) + + parser.add_argument( + "-Werror", help="Consider warnings as errors", action="store_true" + ) + + parser.add_argument( + "-ccache", + help="Use ccache to reduce the build time over multiple run of the test suite.", + action="store_true", + ) + + parser.add_argument( + "-restart", + help="Enable creating a restart from a checkpoint.", + action="store_true", + ) + + parser.add_argument( + "-v", + "--verbose", + help="Enable verbose mode, by not capturing the output.", + action="store_true", + ) + + parser.add_argument( + "--help-pytest", + help="Display the options you can transmit directly to pytest in addition to the specific to idefix tests.", + action="store_true", + ) + + parser.add_argument( + "-fake", + help="Make a fake run by just logging the actions to validate that we generate same command over refactoring.", + action="store_true", + ) + + # this option is not used directly by direct users of idfxTest but by idx_test_gen + parser.add_argument( + "-subdir", + default="./test", + help="Select the test in the given subdir not to run all.", + type=str, + ) + + args, unknown = parser.parse_known_args() + + # transform all arguments from args into attributes of this instance + self.__dict__.update(vars(args)) + # store the full path of problem directory + self.currentTestFile = current_test_file + self.currentTestName = name + self.problemDir = os.path.dirname(current_test_file) + self.referenceDirectory = os.path.join(idefix_dir_env, "reference") + # current directory relative to $IDEFIX_DIR/test (used to retrieve the path ot reference files) + self.testDir = os.path.relpath( + self.problemDir, os.path.join(idefix_dir_env, "test") + ) + # build directory, currently inside the test named build-test + self.buildDir = os.path.join(self.problemDir, "build-test") + # remind what build we dit last + self.lastCmakeCmd = "" + # subdir + self.filterSubdir = args.subdir + # save + self.cmdArgs = vars(args) + self.cmdArgs.update({"restart_no_overwrite": []}) + self.log = [] + # when making a restart we should not overrite those files (will be checked) + self.restart_no_overwrite = [] + + # forward args for pytest + if args.verbose: + unknown.append("--capture=no") + if args.help_pytest: + unknown.append("--help") + # remaining args + self.remainingArgs = unknown + + def addLog(self, entry): + if self.fake: + self.log.append(entry) + with open(os.path.join(self.problemDir, "testsuite.log.json"), "w+") as fp: + json.dump(self.log, fp, indent="\t") + + def applyConfig(self, config: dict | None = None): + # check args + if config is None: + config = {} + for key, value in config.items(): + if key not in [ + "ini", + "testfile", + "testname", + "dumpname", + "check_file_produced", + ]: + assert key in self.cmdArgs, ( + f"The given configuration overriding try to set an invalid paramater : {key}={value}" + ) + + # override options + newArgs = {} + newArgs.update(self.cmdArgs) + newArgs.update(config) + + # replace in dict + self.__dict__.update(newArgs) + + def _genCmakeCommand(self, definitionFile=""): + comm = ["cmake"] + # add source directory + comm.append(self.idefixDir) + + # we will build in ./build-test so problem dir is parent + comm.append("-DIdefix_PROBLEM_DIR=" + self.problemDir) + + # add specific options + for opt in self.cmake: + comm.append("-D" + opt) + + if self.cuda: + comm.append("-DKokkos_ENABLE_CUDA=ON") + # disable fmad operations on Cuda to make it compatible with CPU arithmetics + comm.append("-DIdefix_CXX_FLAGS=--fmad=false") + # disable Async cuda malloc for tests performed on old UCX implementations + comm.append("-DKokkos_ENABLE_IMPL_CUDA_MALLOC_ASYNC=OFF") + + if self.intel: + # disable fmad operations on Cuda to make it compatible with CPU arithmetics + comm.append("-DIdefix_CXX_FLAGS=-fp-model=strict") + comm.append("-DCMAKE_CXX_COMPILER=icpx") + comm.append("-DCMAKE_C_COMPILER=icx") + + if self.hip: + comm.append("-DKokkos_ENABLE_HIP=ON") + # disable fmad operations on HIP to make it compatible with CPU arithmetics + comm.append("-DIdefix_CXX_FLAGS=-ffp-contract=off") + + # if we use single precision + if self.single: + comm.append("-DIdefix_PRECISION=Single") + else: + comm.append("-DIdefix_PRECISION=Double") + + if self.vectPot: + comm.append("-DIdefix_EVOLVE_VECTOR_POTENTIAL=ON") + else: + comm.append("-DIdefix_EVOLVE_VECTOR_POTENTIAL=OFF") + + if self.Werror: + comm.append("-DIdefix_WERROR=ON") + + # add a definition file if provided + if definitionFile: + self.definitions = definitionFile + else: + self.definitions = "definitions.hpp" + + comm.append("-DIdefix_DEFS=" + os.path.join(self.problemDir, self.definitions)) + + if self.mpi: + comm.append("-DIdefix_MPI=ON") + else: + comm.append("-DIdefix_MPI=OFF") + + if self.reconstruction == 2: + comm.append("-DIdefix_RECONSTRUCTION=Linear") + elif self.reconstruction == 3: + comm.append("-DIdefix_RECONSTRUCTION=LimO3") + elif self.reconstruction == 4: + comm.append("-DIdefix_RECONSTRUCTION=Parabolic") + + # export ccache env + if self.ccache: + comm.append("-DCMAKE_CXX_COMPILER_LAUNCHER=ccache") + + # ok + return comm + + def configure( + self, + definitionFile="", + reuse_last_same_build=True, + override: dict | None = None, + ): + if override is None: + override = {} + # log + self.addLog( + { + "call": "configure", + "args": { + "definitionFile": definitionFile, + "reuse_last_same_build": reuse_last_same_build, + "override": override, + }, + } + ) + + # gen command + comm = self._genCmakeCommand(definitionFile) + + # log + print("***************** CALLING CMAKE *******************") + print(f"mkdir -p {self.buildDir}") + print(f"cd {self.buildDir}") + print(" ".join(comm)) + print("***************************************************") + # not action needed if same command or force no rebuild + if reuse_last_same_build == True and self.lastCmakeCmd == " ".join(comm): + print("SKIP ALREADY DONE") + return + + # run + try: + # do cleanup + self.clean() + + # log and in fake mode we do not execute + self.addLog({"command": comm}) + + # call cmake + if not self.fake: + cmake = subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) + cmake.check_returncode() + except subprocess.CalledProcessError as e: + print(bcolors.FAIL + "***************************************************") + print("Cmake failed") + print("***************************************************" + bcolors.ENDC) + raise e + finally: + # remind for next time + self.lastCmakeCmd = " ".join(comm) + + def clean(self): # log and in fake mode we do not execute - self.addLog({"command": comm}) - - # call cmake - if not self.fake: - cmake=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) - cmake.check_returncode() - except subprocess.CalledProcessError as e: - print(bcolors.FAIL+"***************************************************") - print("Cmake failed") - print("***************************************************"+bcolors.ENDC) - raise e - finally: - # remind for next time - self.lastCmakeCmd = ' '.join(comm) - - def clean(self): - # log and in fake mode we do not execute - self.addLog({"call": "clean", "args":{}}) - if self.fake: - return - - # remove the build directory before re-creating it - if os.path.exists(self.buildDir): - shutil.rmtree(self.buildDir) - - # recreate - os.makedirs(self.buildDir, exist_ok=False) - - def compile(self,jobs=8): - self.addLog({"call": "compile", "args":{ - 'jobs': jobs, - }}) - - try: - comm = ["make","-j"+str(jobs)] - self.addLog({"command": comm}) + self.addLog({"call": "clean", "args": {}}) + if self.fake: + return + + # remove the build directory before re-creating it + if os.path.exists(self.buildDir): + shutil.rmtree(self.buildDir) + + # recreate + os.makedirs(self.buildDir, exist_ok=False) + + def compile(self, jobs=8): + self.addLog({"call": "compile", "args": {"jobs": jobs}}) + + try: + comm = ["make", "-j" + str(jobs)] + self.addLog({"command": comm}) + + print("***************************************************") + print(f"cd {os.getcwd()}") + print(" ".join(comm)) + print("***************************************************") + + if not self.fake: + make = subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) + make.check_returncode() + except subprocess.CalledProcessError as e: + print(bcolors.FAIL + "***************************************************") + print("Compilation failed") + print("***************************************************" + bcolors.ENDC) + raise e + + def run(self, inputFile="", np=2, nowrite=False, restart=-1): + # log + self.addLog( + { + "call": "run", + "args": { + "np": np, + "nowrite": nowrite, + "restart": restart, + }, + } + ) + + comm = [os.path.join(self.buildDir, "idefix")] + if inputFile: + comm.append("-i") + comm.append(inputFile) + if self.mpi: + if self.dec: + np = 1 + for n in range(len(self.dec)): + np = np * int(self.dec[n]) + + comm.insert(0, "mpirun") + comm.insert(1, "-np") + comm.insert(2, str(np)) + if self.dec: + comm.append("-dec") + for n in range(len(self.dec)): + comm.append(str(self.dec[n])) + + if nowrite: + comm.append("-nowrite") + + if self.Werror: + comm.append("-Werror") + + if restart >= 0: + comm.append("-restart") + comm.append(str(restart)) print("***************************************************") print(f"cd {os.getcwd()}") - print(' '.join(comm)) + print(" ".join(comm)) print("***************************************************") - if not self.fake: - make=subprocess.run(comm, cwd=os.path.abspath(self.buildDir)) - make.check_returncode() - except subprocess.CalledProcessError as e: - print(bcolors.FAIL+"***************************************************") - print("Compilation failed") - print("***************************************************"+bcolors.ENDC) - raise e - - def run(self, inputFile="", np=2, nowrite=False, restart=-1): - # log - self.addLog({"call": "run", "args":{ - 'np': np, - 'nowrite': nowrite, - 'restart': restart, - }}) - - comm=[os.path.join(self.buildDir,"idefix")] - if inputFile: - comm.append("-i") - comm.append(inputFile) - if self.mpi: - if self.dec: - np=1 - for n in range(len(self.dec)): - np=np*int(self.dec[n]) - - comm.insert(0,"mpirun") - comm.insert(1,"-np") - comm.insert(2,str(np)) - if self.dec: - comm.append("-dec") - for n in range(len(self.dec)): - comm.append(str(self.dec[n])) - - if nowrite: - comm.append("-nowrite") - - if self.Werror: - comm.append("-Werror") - - if restart>=0: - comm.append("-restart") - comm.append(str(restart)) - - print("***************************************************") - print(f"cd {os.getcwd()}") - print(' '.join(comm)) - print("***************************************************") - - try: - self.addLog({"command": comm}) - if not self.fake: - make=subprocess.run(comm, cwd=self.problemDir) - make.check_returncode() - except subprocess.CalledProcessError as e: - print(bcolors.FAIL+"***************************************************") - print("Execution failed") - print("***************************************************"+bcolors.ENDC) - raise e - - self._readLog() - - def _readLog(self): - if self.fake: - return - - if not os.path.exists('./idefix.0.log'): - # When no idefix file is produced, we leave - return - - with open('./idefix.0.log','r') as file: - log = file.read() - - if "SINGLE PRECISION" in log: - self.single = True - else: - self.single = False - - if "Kokkos CUDA target ENABLED" in log: - self.cuda = True - else: - self.cuda = False - - if "Kokkos HIP target ENABLED" in log: - self.hip = True - else: - self.hip = False - - - self.reconstruction = 2 - if "3rd order (LimO3)" in log: - self.reconstruction = 3 - - if "4th order (PPM)" in log: - self.reconstruction = 4 - - self.mpi=False - if "MPI ENABLED" in log: - self.mpi=True - - - # Get input file from log - line = re.search('(?<=Input Parameters using input file )(.*)', log) - self.inifile=line.group(0)[:-1] - - # Get performances from log - line = re.search('Main: Perfs are (.*) cell', log) - self.perf=float(line.group(1)) - - def checkOnly(self, filename, tolerance=0): - # log - self.addLog({"call": "checkOnly", "args":{ - 'filename': filename, - 'tolerance': tolerance, - }}) - - # Assumes the code has been run manually using some configuration, so we simply - # do the test suite witout configure/compile/run - self._readLog() - self._showConfig() - if self.cuda or self.hip: - print(bcolors.WARNING+"***********************************************") - print("WARNING: Idefix guarantees floating point arithmetic accuracy") - print("ONLY when fmad instruction are explicitely disabled at compilation.") - print("Otheriwse, this test will likely fail.") - print("***********************************************"+bcolors.ENDC) - self.standardTest() - self.nonRegressionTest(filename, tolerance) - - def standardTest(self): - # log and in fake mode do not execute. - self.addLog({"call": "standardTest", "args":{}}) - if self.fake: - return - - if os.path.exists(os.path.join(self.problemDir, 'python', 'testidefix.py')): - oldPwd = os.getcwd() - os.chdir(os.path.join(self.problemDir, "python")) - comm = [sys.executable, "testidefix.py"] - if self.noplot: - comm.append("-noplot") - - print(bcolors.OKCYAN+"Running standard test...") - try: - make=subprocess.run(comm) - make.check_returncode() - except subprocess.CalledProcessError as e: - print(bcolors.FAIL+"***************************************************") - print("Standard test execution failed") - print("***************************************************"+bcolors.ENDC) - raise e - print(bcolors.OKCYAN+"Standard test succeeded"+bcolors.ENDC) - os.chdir(oldPwd) - else: - print(bcolors.WARNING+"No standard testidefix.py for this test"+bcolors.ENDC) - sys.stdout.flush() - - def nonRegressionTest(self, filename,tolerance=0): - # log and in fake mode do not execute. - self.addLog({"call": "nonRegressionTest", "args":{ - "filename": filename, - "tolerance": tolerance - }}) - if self.fake: - return - - fileref=os.path.join(self.referenceDirectory, self.testDir, self._getReferenceFilename()) - if not(os.path.exists(fileref)): - raise Exception("Reference file "+fileref+ " doesn't exist") - - filetest=filename - if not(os.path.exists(filetest)): - raise Exception("Test file "+filetest+ " doesn't exist") - - Vref=readDump(fileref) - Vtest=readDump(filetest) - error=self._computeError(Vref,Vtest) - if error > tolerance: - print(bcolors.FAIL+"Non-Regression test failed!") - self._showConfig() - print(bcolors.ENDC) - if self.ploterr: - self._plotDiff(Vref,Vtest) - assert error <= tolerance, bcolors.FAIL+"Error (%e) above tolerance (%e)"%(error,tolerance)+bcolors.ENDC - print(bcolors.OKGREEN+"Non-regression test succeeded with error=%e"%error+bcolors.ENDC) - sys.stdout.flush() - - def compareDump(self, file1, file2,tolerance=0): - self.addLog({"call": "compareDump", "args":{ - "file1": file1, - "file2": file2, - "tolerance": tolerance, - }}) - if self.fake: - return - - Vref=readDump(file1) - Vtest=readDump(file2) - error=self._computeError(Vref,Vtest) - if error > tolerance: - print(bcolors.FAIL+"Files are different !") - print(bcolors.ENDC) - - self._plotDiff(Vref,Vtest) - assert error <= tolerance, bcolors.FAIL+"Error (%e) above tolerance (%e)"%(error,tolerance)+bcolors.ENDC - print(bcolors.OKGREEN+"Files are identical up to error=%e"%error+bcolors.ENDC) - sys.stdout.flush() - - - def makeReference(self,filename): - # log and in fake mode do not execute. - self.addLog({"call": "compareDump", "args":{ - "filename": filename, - }}) - if self.fake: - return - - self._readLog() - targetDir = os.path.join(self.referenceDirectory,self.testDir) - if not os.path.exists(targetDir): - print("Creating reference directory") - os.makedirs(targetDir, exist_ok=True) - fileout = os.path.join(targetDir, self._getReferenceFilename()) - if(os.path.exists(fileout)): - ans=input(bcolors.WARNING+"This will overwrite already existing reference file:\n"+fileout+"\nDo you confirm? (type yes to continue): "+bcolors.ENDC) - if(ans != "yes"): - print(bcolors.WARNING+"Reference creation aborpted"+bcolors.ENDC) - return - - shutil.copy(filename,fileout) - print(bcolors.OKGREEN+"Reference file "+fileout+" created"+bcolors.ENDC) - sys.stdout.flush() - - def _showConfig(self): - print("**************************************************************") - if self.cuda: - print("Nvidia Cuda enabled.") - if self.hip: - print("AMD HIP enabled.") - print("CMake Opts: " +" ".join(self.cmake)) - print("Definitions file:"+self.definitions) - print("Input File: "+self.inifile) - if(self.single): - print("Precision: Single") - else: - print("Precision: Double") - if(self.reconstruction==2): - print("Reconstruction: PLM") - elif(self.reconstruction==3): - print("Reconstruction: LimO3") - elif(self.reconstruction==4): - print("Reconstruction: PPM") - if(self.vectPot): - print("Vector Potential: ON") - else: - print("Vector Potential: OFF") - if self.mpi: - print("MPI: ON") - else: - print("MPI: OFF") - - print("**************************************************************") - - def _getReferenceFilename(self): - strReconstruction="plm" - if self.reconstruction == 3: - strReconstruction = "limo3" - if self.reconstruction == 4: - strReconstruction= "ppm" - - strPrecision="double" - if self.single: - strPrecision="single" - - fileref='dump.ref.'+strPrecision+"."+strReconstruction+"."+self.inifile - if self.vectPot: - fileref=fileref+".vectPot" - - fileref=fileref+'.dmp' - return(fileref) - - def _computeError(self,Vref,Vtest): - ntested=0 - error=0 - for fld in Vtest.data.keys(): - if(Vtest.data[fld].ndim==3): - if fld in Vref.data.keys(): - #print("error in "+fld+" = "+str(np.sqrt(np.mean((Vref.data[fld]-Vtest.data[fld])**2)))) - error = error+np.sqrt(np.mean((Vref.data[fld]-Vtest.data[fld])**2)) - ntested=ntested+1 - - if ntested==0: - raise Exception(bcolors.FAIL+"There is no common field between the reference and current file"+bcolors.ENDC) - - error=error/ntested - return(error) - - def _plotDiff(self,Vref,Vtest): - - for fld in Vtest.data.keys(): - if(Vtest.data[fld].ndim==3): - if fld in Vref.data.keys(): - plt.figure() - plt.title(fld) - x1=Vref.x1 - if Vref.data[fld].shape[0] == Vref.x1.size+1: - x1=np.zeros(Vref.data[fld].shape[0]) - x1[:-1]=Vref.x1l - x1[-1]=Vref.x1r[-1] - x2=Vref.x2 - if Vref.data[fld].shape[1] == Vref.x2.size+1: - x2=np.zeros(Vref.data[fld].shape[1]) - x2[:-1]=Vref.x2l - x2[-1]=Vref.x2r[-1] - x3=Vref.x3 - if Vref.data[fld].shape[2] == Vref.x3.size+1: - x3=np.zeros(Vref.data[fld].shape[2]) - x3[:-1]=Vref.x3l - x3[-1]=Vref.x3r[-1] - if Vref.data[fld].shape[1]>1: - plt.pcolor(x1, x2, Vref.data[fld][:,:,0].T-Vtest.data[fld][:,:,0].T,cmap='seismic') - plt.xlabel("x1") - plt.ylabel("x2") - plt.colorbar() - else: - plt.plot(x1, Vref.data[fld][:,0,0]-Vtest.data[fld][:,0,0]) - plt.xlabel("x1") - plt.show() + try: + self.addLog({"command": comm}) + if not self.fake: + make = subprocess.run(comm, cwd=self.problemDir) + make.check_returncode() + except subprocess.CalledProcessError as e: + print(bcolors.FAIL + "***************************************************") + print("Execution failed") + print("***************************************************" + bcolors.ENDC) + raise e + + self._readLog() + + def _readLog(self): + if self.fake: + return + + if not os.path.exists("./idefix.0.log"): + # When no idefix file is produced, we leave + return + + with open("./idefix.0.log", "r") as file: + log = file.read() + + if "SINGLE PRECISION" in log: + self.single = True + else: + self.single = False + + if "Kokkos CUDA target ENABLED" in log: + self.cuda = True + else: + self.cuda = False + + if "Kokkos HIP target ENABLED" in log: + self.hip = True + else: + self.hip = False + + self.reconstruction = 2 + if "3rd order (LimO3)" in log: + self.reconstruction = 3 + + if "4th order (PPM)" in log: + self.reconstruction = 4 + + self.mpi = False + if "MPI ENABLED" in log: + self.mpi = True + + # Get input file from log + line = re.search("(?<=Input Parameters using input file )(.*)", log) + self.inifile = line.group(0)[:-1] + + # Get performances from log + line = re.search("Main: Perfs are (.*) cell", log) + self.perf = float(line.group(1)) + + def checkOnly(self, filename, tolerance=0): + # log + self.addLog( + { + "call": "checkOnly", + "args": { + "filename": filename, + "tolerance": tolerance, + }, + } + ) + + # Assumes the code has been run manually using some configuration, so we simply + # do the test suite witout configure/compile/run + self._readLog() + self._showConfig() + if self.cuda or self.hip: + print(bcolors.WARNING + "***********************************************") + print("WARNING: Idefix guarantees floating point arithmetic accuracy") + print("ONLY when fmad instruction are explicitely disabled at compilation.") + print("Otheriwse, this test will likely fail.") + print("***********************************************" + bcolors.ENDC) + self.standardTest() + self.nonRegressionTest(filename, tolerance) + + def standardTest(self): + # log and in fake mode do not execute. + self.addLog({"call": "standardTest", "args": {}}) + if self.fake: + return + + if os.path.exists(os.path.join(self.problemDir, "python", "testidefix.py")): + oldPwd = os.getcwd() + os.chdir(os.path.join(self.problemDir, "python")) + comm = [sys.executable, "testidefix.py"] + if self.noplot: + comm.append("-noplot") + + print(bcolors.OKCYAN + "Running standard test...") + try: + make = subprocess.run(comm) + make.check_returncode() + except subprocess.CalledProcessError as e: + print( + bcolors.FAIL + "***************************************************" + ) + print("Standard test execution failed") + print( + "***************************************************" + bcolors.ENDC + ) + raise e + print(bcolors.OKCYAN + "Standard test succeeded" + bcolors.ENDC) + os.chdir(oldPwd) + else: + print( + bcolors.WARNING + + "No standard testidefix.py for this test" + + bcolors.ENDC + ) + sys.stdout.flush() + + def nonRegressionTest(self, filename, tolerance=0): + # log and in fake mode do not execute. + self.addLog( + { + "call": "nonRegressionTest", + "args": {"filename": filename, "tolerance": tolerance}, + } + ) + if self.fake: + return + + fileref = os.path.join( + self.referenceDirectory, self.testDir, self._getReferenceFilename() + ) + if not (os.path.exists(fileref)): + raise Exception("Reference file " + fileref + " doesn't exist") + + filetest = filename + if not (os.path.exists(filetest)): + raise Exception("Test file " + filetest + " doesn't exist") + + Vref = readDump(fileref) + Vtest = readDump(filetest) + error = self._computeError(Vref, Vtest) + if error > tolerance: + print(bcolors.FAIL + "Non-Regression test failed!") + self._showConfig() + print(bcolors.ENDC) + if self.ploterr: + self._plotDiff(Vref, Vtest) + assert error <= tolerance, ( + bcolors.FAIL + + "Error (%e) above tolerance (%e)" % (error, tolerance) + + bcolors.ENDC + ) + print( + bcolors.OKGREEN + + "Non-regression test succeeded with error=%e" % error + + bcolors.ENDC + ) + sys.stdout.flush() + + def compareDump(self, file1, file2, tolerance=0): + self.addLog( + { + "call": "compareDump", + "args": { + "file1": file1, + "file2": file2, + "tolerance": tolerance, + }, + } + ) + if self.fake: + return + + Vref = readDump(file1) + Vtest = readDump(file2) + error = self._computeError(Vref, Vtest) + if error > tolerance: + print(bcolors.FAIL + "Files are different !") + print(bcolors.ENDC) + + self._plotDiff(Vref, Vtest) + assert error <= tolerance, ( + bcolors.FAIL + + "Error (%e) above tolerance (%e)" % (error, tolerance) + + bcolors.ENDC + ) + print( + bcolors.OKGREEN + + "Files are identical up to error=%e" % error + + bcolors.ENDC + ) + sys.stdout.flush() + + def makeReference(self, filename): + # log and in fake mode do not execute. + self.addLog( + { + "call": "compareDump", + "args": {"filename": filename}, + } + ) + if self.fake: + return + + self._readLog() + targetDir = os.path.join(self.referenceDirectory, self.testDir) + if not os.path.exists(targetDir): + print("Creating reference directory") + os.makedirs(targetDir, exist_ok=True) + fileout = os.path.join(targetDir, self._getReferenceFilename()) + if os.path.exists(fileout): + ans = input( + bcolors.WARNING + + "This will overwrite already existing reference file:\n" + + fileout + + "\nDo you confirm? (type yes to continue): " + + bcolors.ENDC + ) + if ans != "yes": + print(bcolors.WARNING + "Reference creation aborpted" + bcolors.ENDC) + return + + shutil.copy(filename, fileout) + print(bcolors.OKGREEN + "Reference file " + fileout + " created" + bcolors.ENDC) + sys.stdout.flush() + + def _showConfig(self): + print("**************************************************************") + if self.cuda: + print("Nvidia Cuda enabled.") + if self.hip: + print("AMD HIP enabled.") + print("CMake Opts: " + " ".join(self.cmake)) + print("Definitions file:" + self.definitions) + print("Input File: " + self.inifile) + if self.single: + print("Precision: Single") + else: + print("Precision: Double") + if self.reconstruction == 2: + print("Reconstruction: PLM") + elif self.reconstruction == 3: + print("Reconstruction: LimO3") + elif self.reconstruction == 4: + print("Reconstruction: PPM") + if self.vectPot: + print("Vector Potential: ON") + else: + print("Vector Potential: OFF") + if self.mpi: + print("MPI: ON") + else: + print("MPI: OFF") + + print("**************************************************************") + + def _getReferenceFilename(self): + strReconstruction = "plm" + if self.reconstruction == 3: + strReconstruction = "limo3" + if self.reconstruction == 4: + strReconstruction = "ppm" + + strPrecision = "double" + if self.single: + strPrecision = "single" + + fileref = ( + "dump.ref." + strPrecision + "." + strReconstruction + "." + self.inifile + ) + if self.vectPot: + fileref = fileref + ".vectPot" + + fileref = fileref + ".dmp" + return fileref + + def _computeError(self, Vref, Vtest): + ntested = 0 + error = 0 + for fld in Vtest.data.keys(): + if Vtest.data[fld].ndim == 3: + if fld in Vref.data.keys(): + # print("error in "+fld+" = "+str(np.sqrt(np.mean((Vref.data[fld]-Vtest.data[fld])**2)))) + error = error + np.sqrt( + np.mean((Vref.data[fld] - Vtest.data[fld]) ** 2) + ) + ntested = ntested + 1 + + if ntested == 0: + raise Exception( + bcolors.FAIL + + "There is no common field between the reference and current file" + + bcolors.ENDC + ) + + error = error / ntested + return error + + def _plotDiff(self, Vref, Vtest): + + for fld in Vtest.data.keys(): + if Vtest.data[fld].ndim == 3: + if fld in Vref.data.keys(): + plt.figure() + plt.title(fld) + x1 = Vref.x1 + if Vref.data[fld].shape[0] == Vref.x1.size + 1: + x1 = np.zeros(Vref.data[fld].shape[0]) + x1[:-1] = Vref.x1l + x1[-1] = Vref.x1r[-1] + x2 = Vref.x2 + if Vref.data[fld].shape[1] == Vref.x2.size + 1: + x2 = np.zeros(Vref.data[fld].shape[1]) + x2[:-1] = Vref.x2l + x2[-1] = Vref.x2r[-1] + x3 = Vref.x3 + if Vref.data[fld].shape[2] == Vref.x3.size + 1: + x3 = np.zeros(Vref.data[fld].shape[2]) + x3[:-1] = Vref.x3l + x3[-1] = Vref.x3r[-1] + if Vref.data[fld].shape[1] > 1: + plt.pcolor( + x1, + x2, + Vref.data[fld][:, :, 0].T - Vtest.data[fld][:, :, 0].T, + cmap="seismic", + ) + plt.xlabel("x1") + plt.ylabel("x2") + plt.colorbar() + else: + plt.plot(x1, Vref.data[fld][:, 0, 0] - Vtest.data[fld][:, 0, 0]) + plt.xlabel("x1") + plt.show() diff --git a/pytools/idfx_test_gen.py b/pytools/idfx_test_gen.py index ada8b962a..eaee82917 100644 --- a/pytools/idfx_test_gen.py +++ b/pytools/idfx_test_gen.py @@ -9,256 +9,271 @@ import pytest -DO_NOT_LOOP_ON = ['restart_no_overwrite', "dec", "multirun", "check_file_produced"] +DO_NOT_LOOP_ON = ["restart_no_overwrite", "dec", "multirun", "check_file_produced"] + class IdefixDirTestGenerator: - ''' - Class used to generate the various configuration to run by parsing the - files `testme.py` found in the hierarchy of the /test directory of Idefix. - ''' - - def __init__(self, currentTestFile: str, name: str = ""): - ''' - Constructor or the class. - - Args: - currentTestFile (str): - Path the the current python file. Normally you - simply pass __file__ to this parameter. - name (str): - Define a name for the test, can be empty. - ''' - - self.currentTestFile = currentTestFile - self.currentTestName = name - - # generate the list of configs to run - def genTestConfigs(self, names:str, params, whenClauses = None, defaultConfig: dict | None = None) -> list: - ''' - Generate the the list of configurations as pytest parameters. - It will unpack the configuration set by looping on all combinations defined - by the given sets. - - Args: - names (str): - Comma separated list of variables do consider to build the - name of the file. - params (dict|list): - A configuration set as a dictionnary or a list of - configuration set. - whenCaluses (dict|list): - Provide a set of clauses to apply after unpacking - the configuration so we can patch some values depending on some others. - defaultConfig (dict): - The default configuration on top of which to apply the variants. - - Returns: - A list of pytest.param() ready to be fiven to parametrized pytest functions. - ''' - if defaultConfig is None: - defaultConfig = {} - if whenClauses is None: - whenClauses = {} - # get name ordering list - nameList = names.split(',') - if '' in nameList: - nameList.remove('') - - # gen list of complete configs - all_configs = [] - if isinstance(params, dict): - all_configs += self._genOneConfigSeries(names, params, defaultConfig=defaultConfig) - elif isinstance(params, list): - for p in params: - all_configs += self._genOneConfigSeries(names, p, defaultConfig=defaultConfig) - else: - raise Exception("Should never be called !") - - # convert as parametrize with nice name - result = [] - for config in all_configs: - # append the file - config['testfile'] = self.currentTestFile - config['testname'] = self.currentTestName - # gen name - nameParts = [self.currentTestName] - for name in nameList: - if isinstance(config[name], bool): - if config[name]: - nameParts.append(name) - elif isinstance(config[name], str): - nameParts.append(str(config[name])) + """ + Class used to generate the various configuration to run by parsing the + files `testme.py` found in the hierarchy of the /test directory of Idefix. + """ + + def __init__(self, currentTestFile: str, name: str = ""): + """ + Constructor or the class. + + Args: + currentTestFile (str): + Path the the current python file. Normally you + simply pass __file__ to this parameter. + name (str): + Define a name for the test, can be empty. + """ + + self.currentTestFile = currentTestFile + self.currentTestName = name + + # generate the list of configs to run + def genTestConfigs( + self, names: str, params, whenClauses=None, defaultConfig: dict | None = None + ) -> list: + """ + Generate the the list of configurations as pytest parameters. + It will unpack the configuration set by looping on all combinations defined + by the given sets. + + Args: + names (str): + Comma separated list of variables do consider to build the + name of the file. + params (dict|list): + A configuration set as a dictionnary or a list of + configuration set. + whenCaluses (dict|list): + Provide a set of clauses to apply after unpacking + the configuration so we can patch some values depending on some others. + defaultConfig (dict): + The default configuration on top of which to apply the variants. + + Returns: + A list of pytest.param() ready to be fiven to parametrized pytest functions. + """ + if defaultConfig is None: + defaultConfig = {} + if whenClauses is None: + whenClauses = {} + # get name ordering list + nameList = names.split(",") + if "" in nameList: + nameList.remove("") + + # gen list of complete configs + all_configs = [] + if isinstance(params, dict): + all_configs += self._genOneConfigSeries( + names, params, defaultConfig=defaultConfig + ) + elif isinstance(params, list): + for p in params: + all_configs += self._genOneConfigSeries( + names, p, defaultConfig=defaultConfig + ) + else: + raise Exception("Should never be called !") + + # convert as parametrize with nice name + result = [] + for config in all_configs: + # append the file + config["testfile"] = self.currentTestFile + config["testname"] = self.currentTestName + # gen name + nameParts = [self.currentTestName] + for name in nameList: + if isinstance(config[name], bool): + if config[name]: + nameParts.append(name) + elif isinstance(config[name], str): + nameParts.append(str(config[name])) + else: + nameParts.append(f"{name}-{config[name]}") + confName = "-".join(nameParts) + + # apply when clause + config = self._applyWhen(config, whenClauses) + + result.append(pytest.param(config, id=confName)) + + # ok + return result + + def extractNamingParameters(self, params) -> list: + """ + Loop on the parameters and check automatically what are the list of variable parameters. + + Args: + params (list|dict): + The list of configuration sets to scan or a single set. + + Returns: + The list of names of the variable parameters. + """ + + # if not a list make a list + if not isinstance(params, list): + params = [params] + + # see params + seen = {} + variables = [] + + # loop + for param_set in params: + for key, value in param_set.items(): + if key in variables: + pass + elif key in DO_NOT_LOOP_ON: + pass + elif isinstance(value, list): + variables.append(key) + elif key in seen and seen[key] != value: + variables.append(key) + elif key not in seen: + seen[key] = value + + # by default sort by alphabetic order about var names + # TODO make something better by assigning a priority to vars + variables.sort() + + # ok + return ",".join(variables) + + def _genNextLevelCombinations( + self, input: list, paramName: str, paramValues: list + ) -> list: + """ + Take an input case list and unpack the given parameter to build the new combinations. + + Args: + input (list): + The incoming list of combinations already unpacked before this call. + paramName (str): + Name of the parameter to unpack. + paramValues (list): + The list of values to unpack and to build combinations for. + + Returns: + The updated list of run sets. + """ + result = [] + for entry in input: + for value in paramValues: + v = copy.deepcopy(entry) + v[paramName] = value + result.append(v) + return result + + def _genOneConfigSeries( + self, names: str, config: dict, defaultConfig: dict | None = None + ) -> list: + """ + Generate the the list of configurations as pytest parameters. + It will unpack the configuration set by looping on all combinations defined + by the given sets. + + Args: + names (str): + Comma separated list of variables do consider to build the + name of the file. + config (dict): + A configuration set as a dictionnary. + defaultConfig (dict): + The default configuration to overload with the variant part. + + Returns: + A list of pytest.param() ready to be fiven to parametrized pytest functions. + """ + if defaultConfig is None: + defaultConfig = {} + # get name ordering list + nameList = names.split(",") + + # if there is ini in the list we put it at the end + loopOrder = nameList.copy() + if "ini" in loopOrder: + loopOrder.remove("ini") + loopOrder.append("ini") + if "" in loopOrder: + loopOrder.remove("") + + # init core with everything not a list + core = copy.deepcopy(defaultConfig) + for key, value in config.items(): + if isinstance(value, list) and key not in DO_NOT_LOOP_ON: + assert key in nameList, ( + f"All variable parameteres should be ordered in the names list, '{key}' is not." + ) + else: + core[key] = copy.deepcopy(value) + + # at start we have only default core + result = [core] + + # loop + for key in loopOrder: + value = config[key] + assert isinstance(value, list), ( + f"This parameter is marked as a list but is not a list : {key}={value} !" + ) + result = self._genNextLevelCombinations(result, key, value) + + # ok + return result + + def _matchWhenClause(self, config: dict, when_clause: dict) -> bool: + """ + Check the matching of a given when clause on the given configuration. + + Args: + config (dict): The configuration. + when_clause (dict): The when clause to check. + + Returns: + True if the clause, match, False otherwise. + """ + for key, value in when_clause.items(): + if config[key] != value: + return False + return True + + def _applyWhen(self, config: dict, when: dict) -> dict: + """ + Check if the when clause applies and apply if if any. + + Args: + config (dict): The configuration. + when_clause (dict): The when clause to check and apply. + + Returns: + The fixed config. + """ + # nothing to do + if when == {}: + return config + + # clone + result = copy.deepcopy(config) + + # loop on when + if isinstance(when, list): + for clause in when: + if self._matchWhenClause(config, clause["conditions"]): + result.update(clause["apply"]) + elif isinstance(when, dict): + if self._matchWhenClause(config, when["conditions"]): + result.update(when["apply"]) else: - nameParts.append(f"{name}-{config[name]}") - confName = "-".join(nameParts) - - # apply when clause - config = self._applyWhen(config, whenClauses) - - result.append(pytest.param(config, id=confName)) - - # ok - return result - - def extractNamingParameters(self, params) -> list: - ''' - Loop on the parameters and check automatically what are the list of variable parameters. - - Args: - params (list|dict): - The list of configuration sets to scan or a single set. - - Returns: - The list of names of the variable parameters. - ''' - - # if not a list make a list - if not isinstance(params, list): - params = [params] - - # see params - seen = {} - variables = [] - - # loop - for param_set in params: - for key, value in param_set.items(): - if key in variables: - pass - elif key in DO_NOT_LOOP_ON: - pass - elif isinstance(value, list): - variables.append(key) - elif key in seen and seen[key] != value: - variables.append(key) - elif key not in seen: - seen[key] = value - - # by default sort by alphabetic order about var names - # TODO make something better by assigning a priority to vars - variables.sort() - - # ok - return ','.join(variables) - - def _genNextLevelCombinations(self, input: list, paramName: str, paramValues: list) -> list: - ''' - Take an input case list and unpack the given parameter to build the new combinations. - - Args: - input (list): - The incoming list of combinations already unpacked before this call. - paramName (str): - Name of the parameter to unpack. - paramValues (list): - The list of values to unpack and to build combinations for. - - Returns: - The updated list of run sets. - ''' - result = [] - for entry in input: - for value in paramValues: - v = copy.deepcopy(entry) - v[paramName] = value - result.append(v) - return result - - def _genOneConfigSeries(self, names: str, config: dict, defaultConfig: dict | None = None) -> list: - ''' - Generate the the list of configurations as pytest parameters. - It will unpack the configuration set by looping on all combinations defined - by the given sets. - - Args: - names (str): - Comma separated list of variables do consider to build the - name of the file. - config (dict): - A configuration set as a dictionnary. - defaultConfig (dict): - The default configuration to overload with the variant part. - - Returns: - A list of pytest.param() ready to be fiven to parametrized pytest functions. - ''' - if defaultConfig is None: - defaultConfig = {} - # get name ordering list - nameList = names.split(',') - - # if there is ini in the list we put it at the end - loopOrder = nameList.copy() - if 'ini' in loopOrder: - loopOrder.remove('ini') - loopOrder.append('ini') - if '' in loopOrder: - loopOrder.remove('') - - # init core with everything not a list - core = copy.deepcopy(defaultConfig) - for key, value in config.items(): - if isinstance(value, list) and key not in DO_NOT_LOOP_ON: - assert key in nameList, f"All variable parameteres should be ordered in the names list, '{key}' is not." - else: - core[key] = copy.deepcopy(value) - - # at start we have only default core - result = [core] - - # loop - for key in loopOrder: - value = config[key] - assert isinstance(value, list), f"This parameter is marked as a list but is not a list : {key}={value} !" - result = self._genNextLevelCombinations(result, key, value) - - # ok - return result - - def _matchWhenClause(self, config: dict, when_clause: dict) -> bool: - ''' - Check the matching of a given when clause on the given configuration. - - Args: - config (dict): The configuration. - when_clause (dict): The when clause to check. - - Returns: - True if the clause, match, False otherwise. - ''' - for key, value in when_clause.items(): - if config[key] != value: - return False - return True - - def _applyWhen(self, config: dict, when: dict) -> dict: - ''' - Check if the when clause applies and apply if if any. - - Args: - config (dict): The configuration. - when_clause (dict): The when clause to check and apply. - - Returns: - The fixed config. - ''' - # nothing to do - if when == {}: - return config - - # clone - result = copy.deepcopy(config) - - # loop on when - if isinstance(when, list): - for clause in when: - if self._matchWhenClause(config, clause['conditions']): - result.update(clause['apply']) - elif isinstance(when, dict): - if self._matchWhenClause(config, when['conditions']): - result.update(when['apply']) - else: - raise Exception(f"Invalid type for 'when' : {when}") - - # ok - return result + raise Exception(f"Invalid type for 'when' : {when}") + + # ok + return result diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index b96ce8408..250716125 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -21,10 +21,10 @@ @contextmanager def moveInDir(path): - ''' + """ Change current working dir for the given directoy for what is inside the with statement. - ''' + """ oldpwd = os.getcwd() os.chdir(path) try: @@ -32,236 +32,353 @@ def moveInDir(path): finally: os.chdir(oldpwd) + class IdexPytestRunner: - ''' - Implement the Idefix pytest runner to scan and run all the tests described by the files - testme.json into the /test directory of Idefix sources. - ''' - - def __init__(self, parentScriptFile: str): - self.currentTestFile="" - self.currentTestRunner: tst.idfxTest=None - self.parentScritFile=parentScriptFile - self.filterSubdir = os.environ.get("IDEFIX_TEST_FILTER_SUBDIR", "./test/") - - def _validateNaming(self, namings: str, autoExtracted: str, file: str): - names = namings.split(',') - for n in autoExtracted.split(','): - if not n in names: - raise Exception(f"Naming parameter list not match the auto-detectection, some are missinge. You gave : '{names}', detected '{autoExtracted}' into {file}") - - def _makeVariableArgAsList(self, namings: str, variants) -> list: - # make as a list - if isinstance(variants, list) == False: - variants = [variants] - - # split namings - namings = namings.split(",") - - # loop on each - for variant in variants: - for name in namings: - if name in variant and isinstance(variant[name], list) == False: - variant[name] = [variant[name]] - - def genTests(self) -> list: - sourceDir = os.path.dirname(self.parentScritFile) - - # loop over all tests - result = [] - with moveInDir(sourceDir): - # if missing / - if self.filterSubdir != "" and self.filterSubdir[-1] != "/": - self.filterSubdir += "/" - - # walk in test dir to find the tests & sort by name - testfiles = glob.glob(self.filterSubdir + "**/testme.json", recursive=True) - testfiles.sort() - - # loop over each - for testfile in testfiles: - try: - # calc some paths - testfileRelPath = os.path.relpath(testfile, os.path.join(sourceDir, 'test')) - testfilePath = os.path.abspath(os.path.join('test',testfileRelPath)) - testfileDir = os.path.dirname(testfileRelPath) - - # load json & build the inner test combinations - with open(testfilePath, 'r') as fp: - # load - test = json.load(fp) - idefixTestGenerator=IdefixDirTestGenerator(testfilePath, testfileDir) - - # extract default config & when & variants - defaultConfig = test.get('default', {}) - whenClauses = test.get('when', {}) - variants = test.get('variants', {}) - - if 'namings' in test: - namings = test['namings'] - autoExtracted = idefixTestGenerator.extractNamingParameters(variants) - self._validateNaming(namings, autoExtracted, testfilePath) - else: - namings = idefixTestGenerator.extractNamingParameters(variants) - - # required to simplify the algos later, if var is listed as variable, we need to loop over it. - self._makeVariableArgAsList(namings, variants) - - # gen - result += idefixTestGenerator.genTestConfigs(namings, variants, whenClauses=whenClauses, defaultConfig=defaultConfig) - except Exception as e: - raise Exception(f"Fail to generate tests from {testfileRelPath}") from e - - # ok - return result - - def run(self, config: dict) -> None: - # clone before modify to not modity for caller - config = copy.deepcopy(config) - - # print config - print("***************************************************") - print(json.dumps(config, indent='\t')) - print("***************************************************") - - # extract some infos for local usage - testfile = config["testfile"] - dumpname = config['dumpname'] - testname = config["testname"] - tolerance = config.get("tolerance", 0) - definitionFile = config.get("definitionFile", "") - standardTest = config.get("standardTest", True) - nonRegressionTest = config.get("nonRegressionTest", True) - nonRegressionTestIni = config.get("nonRegressionTestIni", None) - check_file_produced = config.get("check_file_produced", []) - problemDir = os.path.dirname(testfile) - - # cleanup some keyword not handled at the - # level of idx_test so we don't perturbate it - del config['dumpname'] - if 'definitionFile' in config: - del config['definitionFile'] - if 'tolerance' in config: - del config['tolerance'] - if 'standardTest' in config: - del config['standardTest'] - if 'nonRegressionTest' in config: - del config['nonRegressionTest'] - if 'nonRegressionTestIni' in config: - del config['nonRegressionTestIni'] - - # if switch from test, rebuild the runner (a runner make for one dir) - if self.currentTestFile != testfile: - self.currentTestRunner = tst.idfxTest(testfile, name=testname) - self.currentTestFile = testfile - - # run - with moveInDir(problemDir): - self._runNonRegression(dumpname, config['ini'], config, tolerance=tolerance, definitionFile=definitionFile, standardTest=standardTest, nonReg=nonRegressionTest, nonRegIni=nonRegressionTestIni) - - # check produced - for file in check_file_produced: - if not os.path.exists(file) and not self.currentTestRunner.fake: - raise Exception(f"Don't find expected file to be produced by the run : {file} !") - - def _runNonRegression(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): - if 'multirun' in config_override: - self._runNonRegMultirun(dumpname, ini, config_override, tolerance=tolerance, nonReg=nonReg, nonRegIni=nonRegIni, standardTest=standardTest, configure_and_compile=configure_and_compile, definitionFile=definitionFile, first_run_ini=first_run_ini, first_run_dumpname=first_run_dumpname) - else: - # single basic run - self._runNonRegSingleRun(dumpname, ini, config_override, tolerance=tolerance, nonReg=nonReg, standardTest=standardTest, configure_and_compile=configure_and_compile, definitionFile=definitionFile, first_run_ini=first_run_ini, first_run_dumpname=first_run_dumpname) - - def _runNonRegMultirun(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): - # check - assert 'multirun' in config_override - - # loop over runs - for run in config_override['multirun']: - # copy config - run_config = copy.deepcopy(config_override) - - # patch a bit - del run_config['multirun'] - run_config.update(run) - nonReg=run_config.get('nonRegressionTest', nonReg) - dumpname=run_config.get('dumpname', dumpname) - if 'nonRegressionTest' in run_config: - del run_config['nonRegressionTest'] - standardTest=run_config.get('standardTest', standardTest) - if 'standardTest' in run_config: - del run_config['standardTest'] - - # make single run - self._runNonRegSingleRun(dumpname, run_config['ini'], run_config, definitionFile=definitionFile, tolerance=tolerance, nonReg=nonReg, nonRegIni=nonRegIni, standardTest=standardTest) - - def _runNonRegSingleRun(self, dumpname, ini, config_override, tolerance=0, definitionFile="", nonReg=True, nonRegIni=None, standardTest=True, first_run_ini=None,first_run_dumpname=None,configure_and_compile=True): - # build the runner - idefixTest = self.currentTestRunner - - # handle special override which should not go into - # idefixTest because it is not supported by the idfx_test layer. - config_override = copy.deepcopy(config_override) - nonRegIni = config_override.get("nonRegressionTestIni", nonRegIni) - if 'nonRegressionTestIni' in config_override: - del config_override['nonRegressionTestIni'] - - # apply config - idefixTest.applyConfig(config_override) - - # recompile if needed - if configure_and_compile: - idefixTest.configure(override=config_override, definitionFile=definitionFile) - idefixTest.compile() - - if first_run_ini: - idefixTest.run(inputFile=first_run_ini) - if nonReg: - idefixTest.nonRegressionTest(filename=first_run_dumpname, tolerance=tolerance) - - # Test the restart option - file_mtime={} - if not idefixTest.fake: - for file in idefixTest.restart_no_overwrite: - file_mtime[file] = os.path.getmtime(file) - - # restart - if idefixTest.restart: - restart = 1 - else: - restart = -1 - - # run - idefixTest.run(inputFile=ini, restart=restart) - - # regen ref if needed - if idefixTest.init: - idefixTest.makeReference(filename=dumpname) - - # check outputs - if standardTest: - idefixTest.standardTest() - if nonReg: - if nonRegIni: - idefixTest.inifile = nonRegIni - idefixTest.nonRegressionTest(filename=dumpname, tolerance=tolerance) - - # check that we didn't overrite the file during the restart - if not idefixTest.fake: - for file in idefixTest.restart_no_overwrite: - assert file_mtime[file] == os.path.getmtime(file), f"Dump file {file} was overwritten on restart" - - def main(self, all: bool = False): - if all: - sys.argv.append("-all") - idefixTest = tst.idfxTest(self.parentScritFile, name="main") - os.environ["IDEFIX_TEST_FILTER_SUBDIR"] = idefixTest.filterSubdir - - if idefixTest.all: - pytest.main(['-v', '--no-header', '--junit-xml=idefix-tests.junit.xml', '--tb=short'] + idefixTest.remainingArgs + [self.parentScritFile]) - else: - raise NotImplementedError("Not yet supported !") - #elif self.check: - # idefixTest.checkOnly(filename=dumpname, tolerance=tolerance) - #else: - # for ini in ini_list: - # self.runNonRegression(dumpname, ini, {}, tolerance=tolerance) + """ + Implement the Idefix pytest runner to scan and run all the tests described by the files + testme.json into the /test directory of Idefix sources. + """ + + def __init__(self, parentScriptFile: str): + self.currentTestFile = "" + self.currentTestRunner: tst.idfxTest = None + self.parentScritFile = parentScriptFile + self.filterSubdir = os.environ.get("IDEFIX_TEST_FILTER_SUBDIR", "./test/") + + def _validateNaming(self, namings: str, autoExtracted: str, file: str): + names = namings.split(",") + for n in autoExtracted.split(","): + if not n in names: + raise Exception( + f"Naming parameter list not match the auto-detectection, some are missinge. You gave : '{names}', detected '{autoExtracted}' into {file}" + ) + + def _makeVariableArgAsList(self, namings: str, variants) -> list: + # make as a list + if isinstance(variants, list) == False: + variants = [variants] + + # split namings + namings = namings.split(",") + + # loop on each + for variant in variants: + for name in namings: + if name in variant and isinstance(variant[name], list) == False: + variant[name] = [variant[name]] + + def genTests(self) -> list: + sourceDir = os.path.dirname(self.parentScritFile) + + # loop over all tests + result = [] + with moveInDir(sourceDir): + # if missing / + if self.filterSubdir != "" and self.filterSubdir[-1] != "/": + self.filterSubdir += "/" + + # walk in test dir to find the tests & sort by name + testfiles = glob.glob(self.filterSubdir + "**/testme.json", recursive=True) + testfiles.sort() + + # loop over each + for testfile in testfiles: + try: + # calc some paths + testfileRelPath = os.path.relpath( + testfile, os.path.join(sourceDir, "test") + ) + testfilePath = os.path.abspath( + os.path.join("test", testfileRelPath) + ) + testfileDir = os.path.dirname(testfileRelPath) + + # load json & build the inner test combinations + with open(testfilePath, "r") as fp: + # load + test = json.load(fp) + idefixTestGenerator = IdefixDirTestGenerator( + testfilePath, testfileDir + ) + + # extract default config & when & variants + defaultConfig = test.get("default", {}) + whenClauses = test.get("when", {}) + variants = test.get("variants", {}) + + if "namings" in test: + namings = test["namings"] + autoExtracted = idefixTestGenerator.extractNamingParameters( + variants + ) + self._validateNaming(namings, autoExtracted, testfilePath) + else: + namings = idefixTestGenerator.extractNamingParameters( + variants + ) + + # required to simplify the algos later, if var is listed as variable, we need to loop over it. + self._makeVariableArgAsList(namings, variants) + + # gen + result += idefixTestGenerator.genTestConfigs( + namings, + variants, + whenClauses=whenClauses, + defaultConfig=defaultConfig, + ) + except Exception as e: + raise Exception( + f"Fail to generate tests from {testfileRelPath}" + ) from e + + # ok + return result + + def run(self, config: dict) -> None: + # clone before modify to not modity for caller + config = copy.deepcopy(config) + + # print config + print("***************************************************") + print(json.dumps(config, indent="\t")) + print("***************************************************") + + # extract some infos for local usage + testfile = config["testfile"] + dumpname = config["dumpname"] + testname = config["testname"] + tolerance = config.get("tolerance", 0) + definitionFile = config.get("definitionFile", "") + standardTest = config.get("standardTest", True) + nonRegressionTest = config.get("nonRegressionTest", True) + nonRegressionTestIni = config.get("nonRegressionTestIni", None) + check_file_produced = config.get("check_file_produced", []) + problemDir = os.path.dirname(testfile) + + # cleanup some keyword not handled at the + # level of idx_test so we don't perturbate it + del config["dumpname"] + if "definitionFile" in config: + del config["definitionFile"] + if "tolerance" in config: + del config["tolerance"] + if "standardTest" in config: + del config["standardTest"] + if "nonRegressionTest" in config: + del config["nonRegressionTest"] + if "nonRegressionTestIni" in config: + del config["nonRegressionTestIni"] + + # if switch from test, rebuild the runner (a runner make for one dir) + if self.currentTestFile != testfile: + self.currentTestRunner = tst.idfxTest(testfile, name=testname) + self.currentTestFile = testfile + + # run + with moveInDir(problemDir): + self._runNonRegression( + dumpname, + config["ini"], + config, + tolerance=tolerance, + definitionFile=definitionFile, + standardTest=standardTest, + nonReg=nonRegressionTest, + nonRegIni=nonRegressionTestIni, + ) + + # check produced + for file in check_file_produced: + if not os.path.exists(file) and not self.currentTestRunner.fake: + raise Exception( + f"Don't find expected file to be produced by the run : {file} !" + ) + + def _runNonRegression( + self, + dumpname, + ini, + config_override, + tolerance=0, + definitionFile="", + nonReg=True, + nonRegIni=None, + standardTest=True, + first_run_ini=None, + first_run_dumpname=None, + configure_and_compile=True, + ): + if "multirun" in config_override: + self._runNonRegMultirun( + dumpname, + ini, + config_override, + tolerance=tolerance, + nonReg=nonReg, + nonRegIni=nonRegIni, + standardTest=standardTest, + configure_and_compile=configure_and_compile, + definitionFile=definitionFile, + first_run_ini=first_run_ini, + first_run_dumpname=first_run_dumpname, + ) + else: + # single basic run + self._runNonRegSingleRun( + dumpname, + ini, + config_override, + tolerance=tolerance, + nonReg=nonReg, + standardTest=standardTest, + configure_and_compile=configure_and_compile, + definitionFile=definitionFile, + first_run_ini=first_run_ini, + first_run_dumpname=first_run_dumpname, + ) + + def _runNonRegMultirun( + self, + dumpname, + ini, + config_override, + tolerance=0, + definitionFile="", + nonReg=True, + nonRegIni=None, + standardTest=True, + first_run_ini=None, + first_run_dumpname=None, + configure_and_compile=True, + ): + # check + assert "multirun" in config_override + + # loop over runs + for run in config_override["multirun"]: + # copy config + run_config = copy.deepcopy(config_override) + + # patch a bit + del run_config["multirun"] + run_config.update(run) + nonReg = run_config.get("nonRegressionTest", nonReg) + dumpname = run_config.get("dumpname", dumpname) + if "nonRegressionTest" in run_config: + del run_config["nonRegressionTest"] + standardTest = run_config.get("standardTest", standardTest) + if "standardTest" in run_config: + del run_config["standardTest"] + + # make single run + self._runNonRegSingleRun( + dumpname, + run_config["ini"], + run_config, + definitionFile=definitionFile, + tolerance=tolerance, + nonReg=nonReg, + nonRegIni=nonRegIni, + standardTest=standardTest, + ) + + def _runNonRegSingleRun( + self, + dumpname, + ini, + config_override, + tolerance=0, + definitionFile="", + nonReg=True, + nonRegIni=None, + standardTest=True, + first_run_ini=None, + first_run_dumpname=None, + configure_and_compile=True, + ): + # build the runner + idefixTest = self.currentTestRunner + + # handle special override which should not go into + # idefixTest because it is not supported by the idfx_test layer. + config_override = copy.deepcopy(config_override) + nonRegIni = config_override.get("nonRegressionTestIni", nonRegIni) + if "nonRegressionTestIni" in config_override: + del config_override["nonRegressionTestIni"] + + # apply config + idefixTest.applyConfig(config_override) + + # recompile if needed + if configure_and_compile: + idefixTest.configure( + override=config_override, definitionFile=definitionFile + ) + idefixTest.compile() + + if first_run_ini: + idefixTest.run(inputFile=first_run_ini) + if nonReg: + idefixTest.nonRegressionTest( + filename=first_run_dumpname, tolerance=tolerance + ) + + # Test the restart option + file_mtime = {} + if not idefixTest.fake: + for file in idefixTest.restart_no_overwrite: + file_mtime[file] = os.path.getmtime(file) + + # restart + if idefixTest.restart: + restart = 1 + else: + restart = -1 + + # run + idefixTest.run(inputFile=ini, restart=restart) + + # regen ref if needed + if idefixTest.init: + idefixTest.makeReference(filename=dumpname) + + # check outputs + if standardTest: + idefixTest.standardTest() + if nonReg: + if nonRegIni: + idefixTest.inifile = nonRegIni + idefixTest.nonRegressionTest(filename=dumpname, tolerance=tolerance) + + # check that we didn't overrite the file during the restart + if not idefixTest.fake: + for file in idefixTest.restart_no_overwrite: + assert file_mtime[file] == os.path.getmtime(file), ( + f"Dump file {file} was overwritten on restart" + ) + + def main(self, all: bool = False): + if all: + sys.argv.append("-all") + idefixTest = tst.idfxTest(self.parentScritFile, name="main") + os.environ["IDEFIX_TEST_FILTER_SUBDIR"] = idefixTest.filterSubdir + + if idefixTest.all: + pytest.main( + [ + "-v", + "--no-header", + "--junit-xml=idefix-tests.junit.xml", + "--tb=short", + ] + + idefixTest.remainingArgs + + [self.parentScritFile] + ) + else: + raise NotImplementedError("Not yet supported !") + # elif self.check: + # idefixTest.checkOnly(filename=dumpname, tolerance=tolerance) + # else: + # for ini in ini_list: + # self.runNonRegression(dumpname, ini, {}, tolerance=tolerance) diff --git a/pytools/sod.py b/pytools/sod.py index ba0e16314..3639825f9 100644 --- a/pytools/sod.py +++ b/pytools/sod.py @@ -11,7 +11,7 @@ import scipy.optimize -def sound_speed(gamma, pressure, density, dustFrac=0.): +def sound_speed(gamma, pressure, density, dustFrac=0.0): """ Calculate sound speed, scaled by the dust fraction according to: @@ -21,27 +21,28 @@ def sound_speed(gamma, pressure, density, dustFrac=0.): Where :math:`\epsilon` is the dustFrac """ scale = np.sqrt(1 - dustFrac) - return np.sqrt(gamma * pressure/ density) * scale + return np.sqrt(gamma * pressure / density) * scale -def shock_tube_function(p4, p1, p5, rho1, rho5, gamma, dustFrac=0.): + +def shock_tube_function(p4, p1, p5, rho1, rho5, gamma, dustFrac=0.0): """ Shock tube equation """ - z = (p4 / p5 - 1.) + z = p4 / p5 - 1.0 c1 = sound_speed(gamma, p1, rho1, dustFrac) c5 = sound_speed(gamma, p5, rho5, dustFrac) - gm1 = gamma - 1. - gp1 = gamma + 1. - g2 = 2. * gamma + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 + g2 = 2.0 * gamma - fact = gm1 / g2 * (c5 / c1) * z / np.sqrt(1. + gp1 / g2 * z) - fact = (1. - fact) ** (g2 / gm1) + fact = gm1 / g2 * (c5 / c1) * z / np.sqrt(1.0 + gp1 / g2 * z) + fact = (1.0 - fact) ** (g2 / gm1) return p1 * fact - p4 -def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): +def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.0): """ Compute regions :rtype : tuple @@ -68,18 +69,18 @@ def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): p4 = scipy.optimize.fsolve(shock_tube_function, p1, (p1, p5, rho1, rho5, gamma))[0] # compute post-shock density and velocity - z = (p4 / p5 - 1.) + z = p4 / p5 - 1.0 c5 = sound_speed(gamma, p5, rho5, dustFrac) - gm1 = gamma - 1. - gp1 = gamma + 1. + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 gmfac1 = 0.5 * gm1 / gamma gmfac2 = 0.5 * gp1 / gamma - fact = np.sqrt(1. + gmfac2 * z) + fact = np.sqrt(1.0 + gmfac2 * z) u4 = c5 * z / (gamma * fact) - rho4 = rho5 * (1. + gmfac2 * z) / (1. + gmfac1 * z) + rho4 = rho5 * (1.0 + gmfac2 * z) / (1.0 + gmfac1 * z) # shock speed w = c5 * fact @@ -87,11 +88,11 @@ def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): # compute values at foot of rarefaction p3 = p4 u3 = u4 - rho3 = rho1 * (p3 / p1)**(1. / gamma) + rho3 = rho1 * (p3 / p1) ** (1.0 / gamma) return (p1, rho1, u1), (p3, rho3, u3), (p4, rho4, u4), (p5, rho5, u5), w -def calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac=0.): +def calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac=0.0): """ :return: tuple of positions in the following order -> Head of Rarefaction: xhd, Foot of Rarefaction: xft, @@ -123,21 +124,39 @@ def region_states(pl, pr, region1, region3, region4, region5): where the value is a string, obviously """ if pl > pr: - return {'Region 1': region1, - 'Region 2': 'RAREFACTION', - 'Region 3': region3, - 'Region 4': region4, - 'Region 5': region5} + return { + "Region 1": region1, + "Region 2": "RAREFACTION", + "Region 3": region3, + "Region 4": region4, + "Region 5": region5, + } else: - return {'Region 1': region5, - 'Region 2': region4, - 'Region 3': region3, - 'Region 4': 'RAREFACTION', - 'Region 5': region1} - - -def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, - npts, gamma, t, xi, dustFrac=0.): + return { + "Region 1": region5, + "Region 2": region4, + "Region 3": region3, + "Region 4": "RAREFACTION", + "Region 5": region1, + } + + +def create_arrays( + pl, + pr, + xl, + xr, + positions, + state1, + state3, + state4, + state5, + npts, + gamma, + t, + xi, + dustFrac=0.0, +): """ :return: tuple of x, p, rho and u values across the domain of interest """ @@ -146,8 +165,8 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p3, rho3, u3 = state3 p4, rho4, u4 = state4 p5, rho5, u5 = state5 - gm1 = gamma - 1. - gp1 = gamma + 1. + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 x_arr = np.linspace(xl, xr, npts) rho = np.zeros(npts, dtype=float) @@ -161,10 +180,10 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p[i] = p1 u[i] = u1 elif x < xft: - u[i] = 2. / gp1 * (c1 + (x - xi) / t) - fact = 1. - 0.5 * gm1 * u[i] / c1 - rho[i] = rho1 * fact ** (2. / gm1) - p[i] = p1 * fact ** (2. * gamma / gm1) + u[i] = 2.0 / gp1 * (c1 + (x - xi) / t) + fact = 1.0 - 0.5 * gm1 * u[i] / c1 + rho[i] = rho1 * fact ** (2.0 / gm1) + p[i] = p1 * fact ** (2.0 * gamma / gm1) elif x < xcd: rho[i] = rho3 p[i] = p3 @@ -192,10 +211,10 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p[i] = p3 u[i] = -u3 elif x < xhd: - u[i] = -2. / gp1 * (c1 + (xi - x) / t) - fact = 1. + 0.5 * gm1 * u[i] / c1 - rho[i] = rho1 * fact ** (2. / gm1) - p[i] = p1 * fact ** (2. * gamma / gm1) + u[i] = -2.0 / gp1 * (c1 + (xi - x) / t) + fact = 1.0 + 0.5 * gm1 * u[i] / c1 + rho[i] = rho1 * fact ** (2.0 / gm1) + p[i] = p1 * fact ** (2.0 * gamma / gm1) else: rho[i] = rho1 p[i] = p1 @@ -204,8 +223,7 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, return x_arr, p, rho, u -def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, - dustFrac=0.): +def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, dustFrac=0.0): """ Solves the Sod shock tube problem (i.e. riemann problem) of discontinuity across an interface. @@ -246,34 +264,57 @@ def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, # basic checking if xl >= xr: - print('xl has to be less than xr!') + print("xl has to be less than xr!") exit() if xi >= xr or xi <= xl: - print('xi has in between xl and xr!') + print("xi has in between xl and xr!") exit() # calculate regions - region1, region3, region4, region5, w = \ - calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma, dustFrac) + region1, region3, region4, region5, w = calculate_regions( + pl, ul, rhol, pr, ur, rhor, gamma, dustFrac + ) regions = region_states(pl, pr, region1, region3, region4, region5) # calculate positions - x_positions = calc_positions(pl, pr, region1, region3, w, xi, t, gamma, - dustFrac) - - pos_description = ('Head of Rarefaction', 'Foot of Rarefaction', - 'Contact Discontinuity', 'Shock') + x_positions = calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac) + + pos_description = ( + "Head of Rarefaction", + "Foot of Rarefaction", + "Contact Discontinuity", + "Shock", + ) positions = dict(zip(pos_description, x_positions, strict=True)) # create arrays - x, p, rho, u = create_arrays(pl, pr, xl, xr, x_positions, - region1, region3, region4, region5, - npts, gamma, t, xi, dustFrac) - - energy = p/(rho * (gamma - 1.0)) - rho_total = rho/(1.0 - dustFrac) - val_dict = {'x':x, 'p':p, 'rho':rho, 'u':u, 'energy':energy, - 'rho_total':rho_total} + x, p, rho, u = create_arrays( + pl, + pr, + xl, + xr, + x_positions, + region1, + region3, + region4, + region5, + npts, + gamma, + t, + xi, + dustFrac, + ) + + energy = p / (rho * (gamma - 1.0)) + rho_total = rho / (1.0 - dustFrac) + val_dict = { + "x": x, + "p": p, + "rho": rho, + "u": u, + "energy": energy, + "rho_total": rho_total, + } return positions, regions, val_dict diff --git a/pytools/tests/test_idfx_test_gen.py b/pytools/tests/test_idfx_test_gen.py index d92a7d486..11a9603a1 100644 --- a/pytools/tests/test_idfx_test_gen.py +++ b/pytools/tests/test_idfx_test_gen.py @@ -11,200 +11,200 @@ def test_extractNamingParameters(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - lst = gen.extractNamingParameters([ - { - "dec": [1,2,3], - "a": 10, - "b": 11, - "c": [True, False] - }, - { - "dec": [1,2,4], - "a": 10, - "b": 12, - "d": [True, False] - }, - ]) - - # valid - assert lst == 'b,c,d' + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + lst = gen.extractNamingParameters( + [ + { + "dec": [1, 2, 3], + "a": 10, + "b": 11, + "c": [True, False], + }, + { + "dec": [1, 2, 4], + "a": 10, + "b": 12, + "d": [True, False], + }, + ] + ) + + # valid + assert lst == "b,c,d" + def test_genNextLevelCombinations(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # init with single element - core = {} - init = [core] - - # gen first set of combinations - lst1 = gen._genNextLevelCombinations(init, "mpi", [True, False]) - assert lst1 == [ - {"mpi": True}, - {"mpi": False}, - ] - - # gen first second set of combinations - lst3 = gen._genNextLevelCombinations(lst1, "name", ["a", "b"]) - assert lst3 == [ - {"mpi": True, "name": "a"}, - {"mpi": True, "name": "b"}, - {"mpi": False, "name": "a"}, - {"mpi": False, "name": "b"}, - ] + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # init with single element + core = {} + init = [core] + + # gen first set of combinations + lst1 = gen._genNextLevelCombinations(init, "mpi", [True, False]) + assert lst1 == [{"mpi": True}, {"mpi": False}] + + # gen first second set of combinations + lst3 = gen._genNextLevelCombinations(lst1, "name", ["a", "b"]) + assert lst3 == [ + {"mpi": True, "name": "a"}, + {"mpi": True, "name": "b"}, + {"mpi": False, "name": "a"}, + {"mpi": False, "name": "b"}, + ] + def test_genOneConfigSeries(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # gen - result = gen._genOneConfigSeries("mpi,name", { - "mpi": [True, False], - "name": ["a", "b"] - }) - - # check - assert result == [ - { - 'mpi': True, - 'name': 'a', - },{ - 'mpi': True, - 'name': 'b', - },{ - 'mpi': False, - 'name': 'a', - },{ - 'mpi': False, - 'name': 'b', - }, - ] + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # gen + result = gen._genOneConfigSeries( + "mpi,name", {"mpi": [True, False], "name": ["a", "b"]} + ) + + # check + assert result == [ + {"mpi": True, "name": "a"}, + {"mpi": True, "name": "b"}, + {"mpi": False, "name": "a"}, + {"mpi": False, "name": "b"}, + ] + def test_matchWhenClause_single(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # calls + assert gen._matchWhenClause({"a": 10, "b": 11}, {"a": 10}) == True + assert gen._matchWhenClause({"a": 10, "b": 11}, {"a": 11}) == False + assert gen._matchWhenClause({"a": 10, "b": 11}, {"b": 11}) == True + assert gen._matchWhenClause({"a": 10, "b": 11}, {"b": 10}) == False - # calls - assert gen._matchWhenClause({"a":10, "b": 11}, {"a":10}) == True - assert gen._matchWhenClause({"a":10, "b": 11}, {"a":11}) == False - assert gen._matchWhenClause({"a":10, "b": 11}, {"b":11}) == True - assert gen._matchWhenClause({"a":10, "b": 11}, {"b":10}) == False def test_matchWhenClause_and(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # calls + assert gen._matchWhenClause({"a": 10, "b": 11}, {"a": 10, "b": 11}) == True + assert gen._matchWhenClause({"a": 10, "b": 11}, {"a": 11, "b": 11}) == False - # calls - assert gen._matchWhenClause({"a":10, "b": 11}, {"a":10, "b":11}) == True - assert gen._matchWhenClause({"a":10, "b": 11}, {"a":11, "b":11}) == False def test_applyWhen_none(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen({"a": 10, "b": 11}, when={}) - # call when clause - res = gen._applyWhen({ - "a": 10, - "b": 11 - }, when={}) + # check result + assert res == {"a": 10, "b": 11} - # check result - assert res == {"a": 10, "b": 11} def test_applyWhen_single_apply_yes(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # call when clause - res = gen._applyWhen({ - "a": 10, - "b": 11 - }, when={ - "conditions": { - "a": 10, - }, - "apply": { - "b": 12 - } - }) - - # check result - assert res == {"a": 10, "b": 12} + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen( + {"a": 10, "b": 11}, + when={ + "conditions": {"a": 10}, + "apply": {"b": 12}, + }, + ) + + # check result + assert res == {"a": 10, "b": 12} + def test_applyWhen_single_apply_no(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # call when clause - res = gen._applyWhen({ - "a": 10, - "b": 11 - }, when={ - "conditions": { - "a": 9, - }, - "apply": { - "b": 12 - } - }) - - # check result - assert res == {"a": 10, "b": 11} + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen( + {"a": 10, "b": 11}, + when={ + "conditions": {"a": 9}, + "apply": {"b": 12}, + }, + ) + + # check result + assert res == {"a": 10, "b": 11} + def test_applyWhen_list_apply_yes(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # call when clause - res = gen._applyWhen({ - "a": 10, - "b": 11 - }, when=[ - { - "conditions": { - "a": 10, - }, - "apply": { - "b": 12 - } - }, - { - "conditions": { - "a": 13, - }, - "apply": { - "b": 13 - } - } - ]) - - # check result - assert res == {"a": 10, "b": 12} + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # call when clause + res = gen._applyWhen( + {"a": 10, "b": 11}, + when=[ + { + "conditions": {"a": 10}, + "apply": {"b": 12}, + }, + { + "conditions": {"a": 13}, + "apply": {"b": 13}, + }, + ], + ) + + # check result + assert res == {"a": 10, "b": 12} + def test_gen_full(): - # build generator - gen = IdefixDirTestGenerator(__file__, "unit-test") - - # gen - result = gen.genTestConfigs("mpi,name", { - "mpi": [True, False], - "name": ["a", "b"] - }, { - "conditions": { - "mpi": True - }, - "apply": { - "extra": 10, - } - }) - - # check - assert result == [ - pytest.param({'mpi': True, 'name': 'a', 'testfile': __file__, 'testname': 'unit-test', 'extra': 10}, id='unit-test-mpi-a'), - pytest.param({'mpi': True, 'name': 'b', 'testfile': __file__, 'testname': 'unit-test', 'extra': 10}, id='unit-test-mpi-b'), - pytest.param({'mpi': False, 'name': 'a', 'testfile': __file__, 'testname': 'unit-test'}, id='unit-test-a'), - pytest.param({'mpi': False, 'name': 'b', 'testfile': __file__, 'testname': 'unit-test'}, id='unit-test-b'), - ] + # build generator + gen = IdefixDirTestGenerator(__file__, "unit-test") + + # gen + result = gen.genTestConfigs( + "mpi,name", + {"mpi": [True, False], "name": ["a", "b"]}, + { + "conditions": {"mpi": True}, + "apply": {"extra": 10}, + }, + ) + + # check + assert result == [ + pytest.param( + { + "mpi": True, + "name": "a", + "testfile": __file__, + "testname": "unit-test", + "extra": 10, + }, + id="unit-test-mpi-a", + ), + pytest.param( + { + "mpi": True, + "name": "b", + "testfile": __file__, + "testname": "unit-test", + "extra": 10, + }, + id="unit-test-mpi-b", + ), + pytest.param( + {"mpi": False, "name": "a", "testfile": __file__, "testname": "unit-test"}, + id="unit-test-a", + ), + pytest.param( + {"mpi": False, "name": "b", "testfile": __file__, "testname": "unit-test"}, + id="unit-test-b", + ), + ] diff --git a/pytools/tests/test_idfx_test_run.py b/pytools/tests/test_idfx_test_run.py index 58dc31ebe..dfe32ac56 100644 --- a/pytools/tests/test_idfx_test_run.py +++ b/pytools/tests/test_idfx_test_run.py @@ -13,79 +13,91 @@ def test_genTests(): - # build runner - runner = IdexPytestRunner(__file__) + # build runner + runner = IdexPytestRunner(__file__) - # dir - dir = os.path.dirname(__file__) + # dir + dir = os.path.dirname(__file__) - # generate - result = runner.genTests() - assert result == [ - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': True, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix.ini', - 'testfile': dir + '/test/pb1/testme.json', - 'testname': 'pb1' - }, marks=(), id='pb1-idefix.ini' - ), - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': True, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix-implicit.ini', - 'testfile': dir + '/test/pb1/testme.json', - 'testname': 'pb1' - }, marks=(), id='pb1-idefix-implicit.ini' - ), - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': True, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix.ini', - 'testfile': dir + '/test/pb2/testme.json', - 'testname': 'pb2' - }, marks=(), id='pb2-idefix.ini-noplot' - ), - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': True, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix-implicit.ini', - 'testfile': dir + '/test/pb2/testme.json', - 'testname': 'pb2' - }, marks=(), id='pb2-idefix-implicit.ini-noplot' - ), - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': False, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix.ini', - 'testfile': dir + '/test/pb2/testme.json', - 'testname': 'pb2' - }, marks=(), id='pb2-idefix.ini' - ), - pytest.param( - { - 'dumpname': 'dump.0001.dmp', - 'noplot': False, - 'reconstruction': 2, - 'tolerance': 1e-14, - 'ini': 'idefix-implicit.ini', - 'testfile': dir + '/test/pb2/testme.json', - 'testname': 'pb2' - }, marks=(), id='pb2-idefix-implicit.ini' - ), - ] + # generate + result = runner.genTests() + assert result == [ + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": True, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix.ini", + "testfile": dir + "/test/pb1/testme.json", + "testname": "pb1", + }, + marks=(), + id="pb1-idefix.ini", + ), + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": True, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix-implicit.ini", + "testfile": dir + "/test/pb1/testme.json", + "testname": "pb1", + }, + marks=(), + id="pb1-idefix-implicit.ini", + ), + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": True, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix.ini", + "testfile": dir + "/test/pb2/testme.json", + "testname": "pb2", + }, + marks=(), + id="pb2-idefix.ini-noplot", + ), + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": True, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix-implicit.ini", + "testfile": dir + "/test/pb2/testme.json", + "testname": "pb2", + }, + marks=(), + id="pb2-idefix-implicit.ini-noplot", + ), + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": False, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix.ini", + "testfile": dir + "/test/pb2/testme.json", + "testname": "pb2", + }, + marks=(), + id="pb2-idefix.ini", + ), + pytest.param( + { + "dumpname": "dump.0001.dmp", + "noplot": False, + "reconstruction": 2, + "tolerance": 1e-14, + "ini": "idefix-implicit.ini", + "testfile": dir + "/test/pb2/testme.json", + "testname": "pb2", + }, + marks=(), + id="pb2-idefix-implicit.ini", + ), + ] diff --git a/pytools/vtk_io.py b/pytools/vtk_io.py index ac4551b2f..6d8041091 100644 --- a/pytools/vtk_io.py +++ b/pytools/vtk_io.py @@ -97,7 +97,9 @@ def _load_header(self, fh, geometry=None): self.periodicity = np.fromfile(fh, dtype=dint, count=3).astype(bool) elif NATIVE_COORDINATE_REGEXP.match(d): native_name, _ncomp, native_dim, _dtype = d.split() - self.native_coordinates[native_name] = np.fromfile(fh, dtype=dt, count=int(native_dim)) + self.native_coordinates[native_name] = np.fromfile( + fh, dtype=dt, count=int(native_dim) + ) else: warnings.warn("Found unknown field %s" % d, stacklevel=3) fh.readline() # skip extra linefeed (empty line) @@ -211,7 +213,6 @@ def _load_hydro(self, fh): # Reconstruct the polar coordinate system if self.geometry == "polar": - r = np.sqrt(xcart[:, 0, 0] ** 2 + ycart[:, 0, 0] ** 2) theta = np.unwrap(np.arctan2(ycart[0, :, 0], xcart[0, :, 0])) z = zcart[0, 0, :] @@ -377,6 +378,7 @@ def _setup_coordinates_from_native(self): def __repr__(self): return "VTKDataset('%s')" % self.filename + # ////// public API ////// def readVTK(filename, geometry=None): r"""Read a VTK file for any geometry. diff --git a/test.py b/test.py index 081d31664..1bb6768fe 100755 --- a/test.py +++ b/test.py @@ -17,11 +17,13 @@ # to build for each run if we just changed the ini file and run options. gblIdefixPytestRunner = IdexPytestRunner(__file__) + # define the pytest test @pytest.mark.parametrize("config", gblIdefixPytestRunner.genTests()) def test_idefix_build_run_check(config): - gblIdefixPytestRunner.run(config) + gblIdefixPytestRunner.run(config) + # if called directly as a script if __name__ == "__main__": - gblIdefixPytestRunner.main(all=True) + gblIdefixPytestRunner.main(all=True) diff --git a/test/Dust/DustEnergy/python/testidefix.py b/test/Dust/DustEnergy/python/testidefix.py index 14b64e002..241121233 100755 --- a/test/Dust/DustEnergy/python/testidefix.py +++ b/test/Dust/DustEnergy/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + import argparse import sys @@ -12,47 +13,43 @@ import numpy as np parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # solve eq. A6 in Riols & Lesur (2018) - - - # load the dat file produced by the setup -raw=np.loadtxt('../timevol.dat',skiprows=1) -t=raw[:,0] -Ekg=raw[:,1] -Ekd=raw[:,2] -Eth=raw[:,3] - -etot=Ekg+Ekd+Eth - -if not(args.noplot): - plt.figure() - plt.plot(t,Ekg,label="Ek_g") - plt.plot(t,Ekd,label="Ek_d") - plt.plot(t,Eth,label="Eth") - plt.plot(t,etot,'--',label="Etot") - plt.legend() - plt.xlabel("t") - plt.ylabel("Flow energy") - plt.show() +raw = np.loadtxt("../timevol.dat", skiprows=1) +t = raw[:, 0] +Ekg = raw[:, 1] +Ekd = raw[:, 2] +Eth = raw[:, 3] + +etot = Ekg + Ekd + Eth + +if not (args.noplot): + plt.figure() + plt.plot(t, Ekg, label="Ek_g") + plt.plot(t, Ekd, label="Ek_d") + plt.plot(t, Eth, label="Eth") + plt.plot(t, etot, "--", label="Etot") + plt.legend() + plt.xlabel("t") + plt.ylabel("Flow energy") + plt.show() # Compute relative evolution of total energy -error=abs((etot[-1]-etot[0])/etot[0]) +error = abs((etot[-1] - etot[0]) / etot[0]) -print("error=%f"%error) -if(error<1e-4): - print("Success!") +print("error=%f" % error) +if error < 1e-4: + print("Success!") else: - print("Failure!") - sys.exit(1) + print("Failure!") + sys.exit(1) diff --git a/test/Dust/DustEnergy/testme.py b/test/Dust/DustEnergy/testme.py index 1d997a4ba..473f39db0 100755 --- a/test/Dust/DustEnergy/testme.py +++ b/test/Dust/DustEnergy/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,30 +12,31 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-implicit.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-implicit.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - test.reconstruction=2 - testMe(test) + test.noplot = True + test.reconstruction = 2 + testMe(test) diff --git a/test/Dust/DustyShock/python/testidefix.py b/test/Dust/DustyShock/python/testidefix.py index df575bfe2..b87708be1 100755 --- a/test/Dust/DustyShock/python/testidefix.py +++ b/test/Dust/DustyShock/python/testidefix.py @@ -19,80 +19,95 @@ from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() -V=readVTK('../data.0001.vtk', geometry='cartesian') +V = readVTK("../data.0001.vtk", geometry="cartesian") # Find where the shock starts -istart = np.argwhere(V.data['RHO'][:,0,0]>2.0)[0][0]-1 +istart = np.argwhere(V.data["RHO"][:, 0, 0] > 2.0)[0][0] - 1 # Compute analytical solution -M=2 # Mach number -K=np.asarray([1,3,5])/M # Drag coefficients +M = 2 # Mach number +K = np.asarray([1, 3, 5]) / M # Drag coefficients + # (56) from Benitez-Llambay 2018 def get_wg(Mach, wi): - coeff=[1,np.sum(wi-1)-1/Mach**2-1,1/Mach**2] - solution=np.roots(coeff) - return(np.min(solution)) + coeff = [1, np.sum(wi - 1) - 1 / Mach**2 - 1, 1 / Mach**2] + solution = np.roots(coeff) + return np.min(solution) + # (55) from Benitez-Llambay 2018 -def rhs(t,wi,Mach,K): - wg = get_wg(Mach,wi) - return K*(wg-wi) +def rhs(t, wi, Mach, K): + wg = get_wg(Mach, wi) + return K * (wg - wi) + -wi0=np.asarray([1.0,1.0,1.0]) -x=V.x[istart:] -arguments=M,K +wi0 = np.asarray([1.0, 1.0, 1.0]) +x = V.x[istart:] +arguments = M, K -sol = solve_ivp(rhs, t_span=[x[0],x[-1]], y0=wi0, t_eval=x,args=arguments) +sol = solve_ivp(rhs, t_span=[x[0], x[-1]], y0=wi0, t_eval=x, args=arguments) # compute gas velocity -wg=np.zeros(len(x)) -for i in range(0,len(wg)): - wg[i]=get_wg(M,sol.y[:,i]) +wg = np.zeros(len(x)) +for i in range(0, len(wg)): + wg[i] = get_wg(M, sol.y[:, i]) -if(not args.noplot): +if not args.noplot: plt.figure(1) - plt.plot(V.x,V.data['RHO'][:,0,0],'o',markersize=4,color='tab:purple') - plt.plot(x,1/wg,color='tab:purple') - plt.plot(V.x,V.data['Dust0_RHO'][:,0,0],'o',markersize=4,color='tab:orange') - plt.plot(x,1/sol.y[0,:],color='tab:orange') - plt.plot(V.x,V.data['Dust1_RHO'][:,0,0],'o',markersize=4,color='tab:blue') - plt.plot(x,1/sol.y[1,:],color='tab:blue') - plt.plot(V.x,V.data['Dust2_RHO'][:,0,0],'o',markersize=4,color='tab:green') - plt.plot(x,1/sol.y[2,:],color='tab:green') - plt.xlim([0,10]) - plt.title('Density') + plt.plot(V.x, V.data["RHO"][:, 0, 0], "o", markersize=4, color="tab:purple") + plt.plot(x, 1 / wg, color="tab:purple") + plt.plot(V.x, V.data["Dust0_RHO"][:, 0, 0], "o", markersize=4, color="tab:orange") + plt.plot(x, 1 / sol.y[0, :], color="tab:orange") + plt.plot(V.x, V.data["Dust1_RHO"][:, 0, 0], "o", markersize=4, color="tab:blue") + plt.plot(x, 1 / sol.y[1, :], color="tab:blue") + plt.plot(V.x, V.data["Dust2_RHO"][:, 0, 0], "o", markersize=4, color="tab:green") + plt.plot(x, 1 / sol.y[2, :], color="tab:green") + plt.xlim([0, 10]) + plt.title("Density") plt.figure(2) - plt.plot(V.x,V.data['VX1'][:,0,0],'o',markersize=4,color='tab:purple') - plt.plot(x,M*wg,color='tab:purple') - plt.plot(V.x[::4],V.data['Dust0_VX1'][::4,0,0],'o',markersize=4,color='tab:orange') - plt.plot(x,M*sol.y[0,:],color='tab:orange') - plt.plot(V.x[::4],V.data['Dust1_VX1'][::4,0,0],'o',markersize=4,color='tab:blue') - plt.plot(x,M*sol.y[1,:],color='tab:blue') - plt.plot(V.x[::4],V.data['Dust2_VX1'][::4,0,0],'o',markersize=4,color='tab:green') - plt.plot(x,M*sol.y[2,:],color='tab:green') - - plt.xlim([0,10]) - plt.title('Velocity') + plt.plot(V.x, V.data["VX1"][:, 0, 0], "o", markersize=4, color="tab:purple") + plt.plot(x, M * wg, color="tab:purple") + plt.plot( + V.x[::4], V.data["Dust0_VX1"][::4, 0, 0], "o", markersize=4, color="tab:orange" + ) + plt.plot(x, M * sol.y[0, :], color="tab:orange") + plt.plot( + V.x[::4], V.data["Dust1_VX1"][::4, 0, 0], "o", markersize=4, color="tab:blue" + ) + plt.plot(x, M * sol.y[1, :], color="tab:blue") + plt.plot( + V.x[::4], V.data["Dust2_VX1"][::4, 0, 0], "o", markersize=4, color="tab:green" + ) + plt.plot(x, M * sol.y[2, :], color="tab:green") + + plt.xlim([0, 10]) + plt.title("Velocity") plt.ioff() plt.show() # Compute the error on the dust densities -error=np.mean(np.fabs(V.data['Dust0_RHO'][istart:,0,0]-1/sol.y[0,:]) + np.fabs(V.data['Dust1_RHO'][istart:,0,0]-1/sol.y[1,:]) + np.fabs(V.data['Dust2_RHO'][istart:,0,0]-1/sol.y[2,:])) / 3 -print("Error=%e"%error) -if error<3.6e-2: +error = ( + np.mean( + np.fabs(V.data["Dust0_RHO"][istart:, 0, 0] - 1 / sol.y[0, :]) + + np.fabs(V.data["Dust1_RHO"][istart:, 0, 0] - 1 / sol.y[1, :]) + + np.fabs(V.data["Dust2_RHO"][istart:, 0, 0] - 1 / sol.y[2, :]) + ) + / 3 +) +print("Error=%e" % error) +if error < 3.6e-2: print("SUCCESS!") sys.exit(0) else: diff --git a/test/Dust/DustyShock/testme.py b/test/Dust/DustyShock/testme.py index b3cfab716..2aecf0253 100755 --- a/test/Dust/DustyShock/testme.py +++ b/test/Dust/DustyShock/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,30 +12,31 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-implicit.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-implicit.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=1e-14) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=1e-14) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - test.reconstruction=2 - testMe(test) + test.noplot = True + test.reconstruction = 2 + testMe(test) diff --git a/test/Dust/DustyWave/python/testidefix.py b/test/Dust/DustyWave/python/testidefix.py index 1c386e6bf..9e05128b9 100755 --- a/test/Dust/DustyWave/python/testidefix.py +++ b/test/Dust/DustyWave/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + import argparse import sys @@ -12,55 +13,56 @@ import numpy as np parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # solve eq. A6 in Riols & Lesur (2018) -cs=1.0 -chi=1.0 -kx=2.0*np.pi -taus=1.0 -poly=np.zeros(4,dtype=complex) -poly[0]=1 -poly[1]=1j/taus*(1+chi) -poly[2]=-kx**2*cs**2 -poly[3]=-1j*kx**2*cs**2/taus -sol=np.roots(poly) +cs = 1.0 +chi = 1.0 +kx = 2.0 * np.pi +taus = 1.0 +poly = np.zeros(4, dtype=complex) +poly[0] = 1 +poly[1] = 1j / taus * (1 + chi) +poly[2] = -(kx**2) * cs**2 +poly[3] = -1j * kx**2 * cs**2 / taus +sol = np.roots(poly) # Get the minimal decay rate (this should be the one that pops up) -tau=np.amax(np.imag(sol)) +tau = np.amax(np.imag(sol)) # load the dat file produced by the setup -raw=np.loadtxt('../timevol.dat',skiprows=1) -t=raw[:,0] -vx2=raw[:,1] -rho2=raw[:,2] +raw = np.loadtxt("../timevol.dat", skiprows=1) +t = raw[:, 0] +vx2 = raw[:, 1] +rho2 = raw[:, 2] -etot=vx2+rho2 +etot = vx2 + rho2 -if not(args.noplot): - plt.figure() - plt.semilogy(t,etot,label="idefix") - plt.semilogy(t,np.exp(2*tau*t)*etot[10],'--',label="theoretical decay rate") - plt.legend() - plt.xlabel("t") - plt.ylabel("Wave energy") - plt.show() +if not (args.noplot): + plt.figure() + plt.semilogy(t, etot, label="idefix") + plt.semilogy( + t, np.exp(2 * tau * t) * etot[10], "--", label="theoretical decay rate" + ) + plt.legend() + plt.xlabel("t") + plt.ylabel("Wave energy") + plt.show() # Compute decay rate: -tau_measured=t[-1]/(2*np.log(etot[-1]/etot[0])) +tau_measured = t[-1] / (2 * np.log(etot[-1] / etot[0])) # error on the decay rate: -error=np.abs((tau_measured-tau)/tau) +error = np.abs((tau_measured - tau) / tau) -print("error=%f"%error) -if(error<0.07): - print("Success!") +print("error=%f" % error) +if error < 0.07: + print("Success!") else: - print("Failure!") - sys.exit(1) + print("Failure!") + sys.exit(1) diff --git a/test/Dust/DustyWave/testme.py b/test/Dust/DustyWave/testme.py index b3cfab716..2aecf0253 100755 --- a/test/Dust/DustyWave/testme.py +++ b/test/Dust/DustyWave/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,30 +12,31 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-implicit.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-implicit.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=1e-14) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=1e-14) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - test.reconstruction=2 - testMe(test) + test.noplot = True + test.reconstruction = 2 + testMe(test) diff --git a/test/HD/FargoPlanet/testme.py b/test/HD/FargoPlanet/testme.py index 5a0364443..7be82a4ba 100755 --- a/test/HD/FargoPlanet/testme.py +++ b/test/HD/FargoPlanet/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,39 +12,41 @@ import pytools.idfx_test as tst -tolerance=1e-13 -def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini"] - mytol=tolerance - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - if ini == "idefix-rkl.ini": - mytol = 1e-12 - else: - mytol = tolerance - test.standardTest() - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) +tolerance = 1e-13 -test=tst.idfxTest(__file__) +def testMe(test): + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini"] + mytol = tolerance + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + if ini == "idefix-rkl.ini": + mytol = 1e-12 + else: + mytol = tolerance + test.standardTest() + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) + + +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/HD/MachReflection/testme.py b/test/HD/MachReflection/testme.py index cc8cf72e6..7007c6e39 100755 --- a/test/HD/MachReflection/testme.py +++ b/test/HD/MachReflection/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -13,33 +14,33 @@ def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-hll.ini","idefix-hllc.ini","idefix-tvdlf.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-hll.ini", "idefix-hllc.ini", "idefix-tvdlf.ini"] - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - test.nonRegressionTest(filename="dump.0001.dmp") + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + test.nonRegressionTest(filename="dump.0001.dmp") -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp") - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/HD/SedovBlastWave/python/testidefix.py b/test/HD/SedovBlastWave/python/testidefix.py index 40d39a79a..e926a19dd 100755 --- a/test/HD/SedovBlastWave/python/testidefix.py +++ b/test/HD/SedovBlastWave/python/testidefix.py @@ -19,63 +19,61 @@ from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() - -V=readVTK('../data.0001.vtk') -R=readVTK('1Dsolution/1Dsolution.vtk') +args, unknown = parser.parse_known_args() +V = readVTK("../data.0001.vtk") +R = readVTK("1Dsolution/1Dsolution.vtk") # Finally, let's plot solutions -p = R.data['PRS'][:,0,0] -x= R.r +p = R.data["PRS"][:, 0, 0] +x = R.r -if V.geometry=="cartesian": - [x3D, y3D, z3D]= np.meshgrid(V.x,V.y,V.z,indexing='ij') +if V.geometry == "cartesian": + [x3D, y3D, z3D] = np.meshgrid(V.x, V.y, V.z, indexing="ij") -elif V.geometry=="spherical": - [r, theta, phi] = np.meshgrid(V.r,V.theta,V.phi,indexing='ij') - x0=0.1 - y0=0 - z0=1.0 +elif V.geometry == "spherical": + [r, theta, phi] = np.meshgrid(V.r, V.theta, V.phi, indexing="ij") + x0 = 0.1 + y0 = 0 + z0 = 1.0 - x3D=r*np.sin(theta)*np.cos(phi)-x0 - y3D=r*np.sin(theta)*np.sin(phi)-y0 - z3D=r*np.cos(theta)-z0 + x3D = r * np.sin(theta) * np.cos(phi) - x0 + y3D = r * np.sin(theta) * np.sin(phi) - y0 + z3D = r * np.cos(theta) - z0 else: - print("Unknown geometry "+V.geometry) - sys.exit(1) + print("Unknown geometry " + V.geometry) + sys.exit(1) -r3D=np.sqrt(x3D**2+y3D**2+z3D**2).flatten() -p3D=V.data['PRS'].flatten() +r3D = np.sqrt(x3D**2 + y3D**2 + z3D**2).flatten() +p3D = V.data["PRS"].flatten() -index=np.argwhere((r3D>0.4) & (r3D<0.458)) +index = np.argwhere((r3D > 0.4) & (r3D < 0.458)) -solinterp=interp1d(x,p) +solinterp = interp1d(x, p) -if(not args.noplot): +if not args.noplot: plt.figure(1) - plt.plot(r3D.flatten(),p3D.flatten(),'+',markersize=2) - plt.plot(x,p) - plt.title('Pressure') + plt.plot(r3D.flatten(), p3D.flatten(), "+", markersize=2) + plt.plot(x, p) + plt.title("Pressure") plt.ioff() plt.show() -error=np.mean(np.fabs(p3D[index]-solinterp(r3D[index]))) -print("Error=%e"%error) +error = np.mean(np.fabs(p3D[index] - solinterp(r3D[index]))) +print("Error=%e" % error) erroref = 7.7e-2 if V.geometry == "spherical": erroref = 1.9e-1 -if errorV.x.size): - x=V.y - bxSim=V.data['BX2'].flatten() - bySim=V.data['BX3'].flatten() -elif(V.z.size>V.x.size): - x=V.z - bxSim=V.data['BX3'].flatten() - bySim=V.data['BX1'].flatten() +V = readVTK("../data.0001.vtk", geometry="cartesian") + +DSim = V.data["RHO"].flatten() +if V.y.size > V.x.size: + x = V.y + bxSim = V.data["BX2"].flatten() + bySim = V.data["BX3"].flatten() +elif V.z.size > V.x.size: + x = V.z + bxSim = V.data["BX3"].flatten() + bySim = V.data["BX1"].flatten() else: - x=V.x - bxSim=V.data['BX1'].flatten() - bySim=V.data['BX2'].flatten() + x = V.x + bxSim = V.data["BX1"].flatten() + bySim = V.data["BX2"].flatten() -bSim=bySim/np.sqrt(bySim[0]**2+bxSim[0]**2) +bSim = bySim / np.sqrt(bySim[0] ** 2 + bxSim[0] ** 2) # Index where the two solutions are assumed to match -iref=np.argwhere(DSim>5.0)[0][0] +iref = np.argwhere(DSim > 5.0)[0][0] -#spatial index where we cut the solution -iend=np.argwhere(x>xcut)[0][0] +# spatial index where we cut the solution +iend = np.argwhere(x > xcut)[0][0] # compute analytical solution -r=ode(f).set_integrator('vode',rtol=1e-6) -r.set_initial_value(DSim[iref],x[iref]) +r = ode(f).set_integrator("vode", rtol=1e-6) +r.set_initial_value(DSim[iref], x[iref]) -Dth=np.zeros(x.shape) +Dth = np.zeros(x.shape) for i in range(x.size): - r.set_initial_value(DSim[iref],x[iref]) - Dth[i]=r.integrate(x[i]).item() - #print("Dth[%d]=%g"%(i,Dth[i])) + r.set_initial_value(DSim[iref], x[iref]) + Dth[i] = r.integrate(x[i]).item() + # print("Dth[%d]=%g"%(i,Dth[i])) -bTh=np.sqrt(b0**2+2*A**2*(Dth-1)*(1/Dth-1/M**2)) +bTh = np.sqrt(b0**2 + 2 * A**2 * (Dth - 1) * (1 / Dth - 1 / M**2)) -errb=(bSim[:iend]-bTh[:iend])/np.amax(bTh[:iend]) -errD=(DSim[:iend]-Dth[:iend])/np.amax(Dth[:iend]) +errb = (bSim[:iend] - bTh[:iend]) / np.amax(bTh[:iend]) +errD = (DSim[:iend] - Dth[:iend]) / np.amax(Dth[:iend]) -if(not args.noplot): - plt.close('all') +if not args.noplot: + plt.close("all") plt.figure() plt.subplot(211) - plt.plot(x[:iend]/L,bSim[:iend],'--',label='Sim') - plt.plot(x[:iend]/L,bTh[:iend],label='Theoretical') - plt.xlabel('x/L') - plt.ylabel('b') + plt.plot(x[:iend] / L, bSim[:iend], "--", label="Sim") + plt.plot(x[:iend] / L, bTh[:iend], label="Theoretical") + plt.xlabel("x/L") + plt.ylabel("b") plt.subplot(212) - plt.plot(x[:iend]/L,errb,'--',label='Error') - plt.xlabel('x/L') - plt.ylabel('b') + plt.plot(x[:iend] / L, errb, "--", label="Error") + plt.xlabel("x/L") + plt.ylabel("b") plt.legend() plt.figure() plt.subplot(211) - plt.plot(x[:iend]/L,DSim[:iend],label='Sim') - plt.plot(x[:iend]/L,Dth[:iend],'--',label='Theoretical') - plt.xlabel('x/L') - plt.ylabel('D') + plt.plot(x[:iend] / L, DSim[:iend], label="Sim") + plt.plot(x[:iend] / L, Dth[:iend], "--", label="Theoretical") + plt.xlabel("x/L") + plt.ylabel("D") plt.subplot(212) - plt.plot(x[:iend]/L,errD,'--',label='Error') - plt.xlabel('x/L') - plt.ylabel('D') + plt.plot(x[:iend] / L, errD, "--", label="Error") + plt.xlabel("x/L") + plt.ylabel("D") plt.legend() plt.ioff() plt.show() -err=np.mean(0.5*np.sqrt(errb**2+errD**2)) -print("Error total=%e"%err) -if(err<5e-3): +err = np.mean(0.5 * np.sqrt(errb**2 + errD**2)) +print("Error total=%e" % err) +if err < 5e-3: print("Success!") sys.exit(0) else: diff --git a/test/MHD/AmbipolarCshock/testme.py b/test/MHD/AmbipolarCshock/testme.py index b8bd69459..1b3f843f7 100755 --- a/test/MHD/AmbipolarCshock/testme.py +++ b/test/MHD/AmbipolarCshock/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,30 +12,31 @@ import pytools.idfx_test as tst -tolerance=0 +tolerance = 0 + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini"] - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tolerance) + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini"] + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/MHD/AmbipolarCshock3D/python/testidefix.py b/test/MHD/AmbipolarCshock3D/python/testidefix.py index c151dd789..2e62c09d6 100755 --- a/test/MHD/AmbipolarCshock3D/python/testidefix.py +++ b/test/MHD/AmbipolarCshock3D/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + import os import sys @@ -18,106 +19,107 @@ from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # Parameters from Maclow+ 1995 -theta=np.pi/4 -M=50 -b0=np.sin(theta) -A=10 -L=1 +theta = np.pi / 4 +M = 50 +b0 = np.sin(theta) +A = 10 +L = 1 + +xcut = 40.0 + -xcut=40.0 +def f(x, D): + b = np.sqrt(b0**2 + 2 * A**2 * (D - 1) * (1 / D - 1 / M**2)) + diff = (b - b0) / A**2 * np.cos(theta) ** 2 + np.sin(theta) + diff = (b - D * diff) / (b**2 + np.cos(theta) ** 2) + diff = (b / A) * diff / (L * (1 / D**2 - 1 / M**2)) -def f(x,D): - b=np.sqrt(b0**2+2*A**2*(D-1)*(1/D-1/M**2)) - diff=(b-b0)/A**2*np.cos(theta)**2+np.sin(theta) - diff=(b-D*diff)/(b**2+np.cos(theta)**2) - diff=(b/A)*diff/(L*(1/D**2-1/M**2)) + return diff - return(diff) # load solution -V=readVTK('../data.0001.vtk', geometry='cartesian') - - -if(V.y.size>V.x.size): - x=V.y - DSim=V.data['RHO'][0,:,0] - bxSim=V.data['BX2'][0,:,0] - bySim=V.data['BX3'][0,:,0] -elif(V.z.size>V.x.size): - x=V.z - DSim=V.data['RHO'][0,0,:] - bxSim=V.data['BX3'][0,0,:] - bySim=V.data['BX1'][0,0,:] +V = readVTK("../data.0001.vtk", geometry="cartesian") + + +if V.y.size > V.x.size: + x = V.y + DSim = V.data["RHO"][0, :, 0] + bxSim = V.data["BX2"][0, :, 0] + bySim = V.data["BX3"][0, :, 0] +elif V.z.size > V.x.size: + x = V.z + DSim = V.data["RHO"][0, 0, :] + bxSim = V.data["BX3"][0, 0, :] + bySim = V.data["BX1"][0, 0, :] else: - x=V.x - DSim=V.data['RHO'][:,0,0] - bxSim=V.data['BX1'][:,0,0] - bySim=V.data['BX2'][:,0,0] + x = V.x + DSim = V.data["RHO"][:, 0, 0] + bxSim = V.data["BX1"][:, 0, 0] + bySim = V.data["BX2"][:, 0, 0] -bSim=bySim/np.sqrt(bySim[0]**2+bxSim[0]**2) +bSim = bySim / np.sqrt(bySim[0] ** 2 + bxSim[0] ** 2) # Index where the two solutions are assumed to match -iref=np.argwhere(DSim>5.0)[0][0] +iref = np.argwhere(DSim > 5.0)[0][0] -#spatial index where we cut the solution -iend=np.argwhere(x>xcut)[0][0] +# spatial index where we cut the solution +iend = np.argwhere(x > xcut)[0][0] # compute analytical solution -r=ode(f).set_integrator('vode',rtol=1e-6) -r.set_initial_value(DSim[iref],x[iref]) +r = ode(f).set_integrator("vode", rtol=1e-6) +r.set_initial_value(DSim[iref], x[iref]) -Dth=np.zeros(x.shape) +Dth = np.zeros(x.shape) for i in range(x.size): - r.set_initial_value(DSim[iref],x[iref]) - Dth[i]=r.integrate(x[i]).item() - #print("Dth[%d]=%g"%(i,Dth[i])) + r.set_initial_value(DSim[iref], x[iref]) + Dth[i] = r.integrate(x[i]).item() + # print("Dth[%d]=%g"%(i,Dth[i])) -bTh=np.sqrt(b0**2+2*A**2*(Dth-1)*(1/Dth-1/M**2)) +bTh = np.sqrt(b0**2 + 2 * A**2 * (Dth - 1) * (1 / Dth - 1 / M**2)) -errb=(bSim[:iend]-bTh[:iend])/np.amax(bTh[:iend]) -errD=(DSim[:iend]-Dth[:iend])/np.amax(Dth[:iend]) +errb = (bSim[:iend] - bTh[:iend]) / np.amax(bTh[:iend]) +errD = (DSim[:iend] - Dth[:iend]) / np.amax(Dth[:iend]) -if(not args.noplot): - plt.close('all') +if not args.noplot: + plt.close("all") plt.figure() plt.subplot(211) - plt.plot(x[:iend]/L,bSim[:iend],'--',label='Sim') - plt.plot(x[:iend]/L,bTh[:iend],label='Theoretical') - plt.xlabel('x/L') - plt.ylabel('b') + plt.plot(x[:iend] / L, bSim[:iend], "--", label="Sim") + plt.plot(x[:iend] / L, bTh[:iend], label="Theoretical") + plt.xlabel("x/L") + plt.ylabel("b") plt.subplot(212) - plt.plot(x[:iend]/L,errb,'--',label='Error') - plt.xlabel('x/L') - plt.ylabel('b') + plt.plot(x[:iend] / L, errb, "--", label="Error") + plt.xlabel("x/L") + plt.ylabel("b") plt.legend() plt.figure() plt.subplot(211) - plt.plot(x[:iend]/L,DSim[:iend],label='Sim') - plt.plot(x[:iend]/L,Dth[:iend],'--',label='Theoretical') - plt.xlabel('x/L') - plt.ylabel('D') + plt.plot(x[:iend] / L, DSim[:iend], label="Sim") + plt.plot(x[:iend] / L, Dth[:iend], "--", label="Theoretical") + plt.xlabel("x/L") + plt.ylabel("D") plt.subplot(212) - plt.plot(x[:iend]/L,errD,'--',label='Error') - plt.xlabel('x/L') - plt.ylabel('D') + plt.plot(x[:iend] / L, errD, "--", label="Error") + plt.xlabel("x/L") + plt.ylabel("D") plt.legend() plt.ioff() plt.show() -err=np.mean(0.5*np.sqrt(errb**2+errD**2)) -print("Error total=%e"%err) -if(err<5.9e-3): +err = np.mean(0.5 * np.sqrt(errb**2 + errD**2)) +print("Error total=%e" % err) +if err < 5.9e-3: print("Success!") sys.exit(0) else: diff --git a/test/MHD/AmbipolarCshock3D/testme.py b/test/MHD/AmbipolarCshock3D/testme.py index 981fbff38..37363d5bc 100755 --- a/test/MHD/AmbipolarCshock3D/testme.py +++ b/test/MHD/AmbipolarCshock3D/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,43 +12,45 @@ import pytools.idfx_test as tst -tolerance=3e-14 +tolerance = 3e-14 + + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini"] - for ini in inifiles: - mytol=tolerance - - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - # When using RKL, except larger error due to B reconstruction and RKL # of substeps - if test.mpi and ini=="idefix-rkl.ini": - mytol=2e-10 - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) - - -test=tst.idfxTest(__file__) + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini"] + for ini in inifiles: + mytol = tolerance + + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + # When using RKL, except larger error due to B reconstruction and RKL # of substeps + if test.mpi and ini == "idefix-rkl.ini": + mytol = 2e-10 + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) + + +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','1','1'] + test.dec = ["2", "1", "1"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.vectPot=True - testMe(test) - - test.vectPot=False - test.mpi=True - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.vectPot = True + testMe(test) + + test.vectPot = False + test.mpi = True + testMe(test) diff --git a/test/MHD/AmbipolarShearingBox/python/testidefix.py b/test/MHD/AmbipolarShearingBox/python/testidefix.py index 6aec86a64..779ecfae2 100755 --- a/test/MHD/AmbipolarShearingBox/python/testidefix.py +++ b/test/MHD/AmbipolarShearingBox/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + import os import sys @@ -14,27 +15,27 @@ sys.path.append(os.getenv("IDEFIX_DIR")) from pytools.vtk_io import readVTK -rep='../' -nend=1000 +rep = "../" +nend = 1000 -n=0 -dt=0.1 +n = 0 +dt = 0.1 -Bx=np.zeros(nend) +Bx = np.zeros(nend) -t=dt*np.arange(0,nend) +t = dt * np.arange(0, nend) for n in range(nend): - V=readVTK(rep+'/data.'+'%0*d'%(4,n)+'.vtk', geometry='cartesian') - Bx[n]=np.sqrt(np.mean(np.mean(V.data['BX1']**2,axis=2),axis=0)) + V = readVTK(rep + "/data." + "%0*d" % (4, n) + ".vtk", geometry="cartesian") + Bx[n] = np.sqrt(np.mean(np.mean(V.data["BX1"] ** 2, axis=2), axis=0)) plt.figure() -plt.semilogy(t,Bx) -plt.semilogy(t,Bx[-1]*np.exp(0.171*(t-t[-1]))) +plt.semilogy(t, Bx) +plt.semilogy(t, Bx[-1] * np.exp(0.171 * (t - t[-1]))) -gr=np.log(Bx[-1]/Bx[-700])/(t[-1]-t[-700]) -print('growth rate=%g'%gr) -if np.abs(gr-0.171)/0.171<0.05: +gr = np.log(Bx[-1] / Bx[-700]) / (t[-1] - t[-700]) +print("growth rate=%g" % gr) +if np.abs(gr - 0.171) / 0.171 < 0.05: print("SUCCESS!") else: print("FAILED!") diff --git a/test/MHD/AxisFluxTube/python/checkAxisBounds.py b/test/MHD/AxisFluxTube/python/checkAxisBounds.py index 774069886..cb313a44e 100755 --- a/test/MHD/AxisFluxTube/python/checkAxisBounds.py +++ b/test/MHD/AxisFluxTube/python/checkAxisBounds.py @@ -5,6 +5,7 @@ @author: lesurg """ + import os import sys @@ -13,59 +14,59 @@ from pytools.idfx_io import readIdfxFile -rep="../" +rep = "../" -idfx=readIdfxFile(rep+"analysis.99.0.idfx") -d=idfx.data -Bx1s=d['Vs'][0,:-1,:-1,:] -Bx2s=d['Vs'][1,:-1,:,:-1] -Bx3s=d['Vs'][2,:,:-1,:-1] +idfx = readIdfxFile(rep + "analysis.99.0.idfx") +d = idfx.data +Bx1s = d["Vs"][0, :-1, :-1, :] +Bx2s = d["Vs"][1, :-1, :, :-1] +Bx3s = d["Vs"][2, :, :-1, :-1] -nxhalf=10 -Bx1slice=Bx1s[:,:,nxhalf] -Bx2slice=Bx2s[:,:,nxhalf] -Bx3slice=Bx3s[:,:,nxhalf] +nxhalf = 10 +Bx1slice = Bx1s[:, :, nxhalf] +Bx2slice = Bx2s[:, :, nxhalf] +Bx3slice = Bx3s[:, :, nxhalf] -plt.matshow(Bx1slice,cmap='RdBu_r') +plt.matshow(Bx1slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx1") -plt.matshow(Bx2slice,cmap='RdBu_r') +plt.matshow(Bx2slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx2") -plt.matshow(Bx3slice,cmap='RdBu_r') +plt.matshow(Bx3slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx3") # inner boundary -Bx1slice=Bx1s[:,:5,nxhalf] -Bx2slice=Bx2s[:,:5,nxhalf] -Bx3slice=Bx3s[:,:5,nxhalf] +Bx1slice = Bx1s[:, :5, nxhalf] +Bx2slice = Bx2s[:, :5, nxhalf] +Bx3slice = Bx3s[:, :5, nxhalf] -Vx1slice=d['Vc'][1,:,:5,nxhalf] -Vx2slice=d['Vc'][2,:,:5,nxhalf] -Vx3slice=d['Vc'][3,:,:5,nxhalf] +Vx1slice = d["Vc"][1, :, :5, nxhalf] +Vx2slice = d["Vc"][2, :, :5, nxhalf] +Vx3slice = d["Vc"][3, :, :5, nxhalf] -plt.matshow(Bx1slice,cmap='RdBu_r') +plt.matshow(Bx1slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx1") -plt.matshow(Bx2slice,cmap='RdBu_r') +plt.matshow(Bx2slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx2") -plt.matshow(Bx3slice,cmap='RdBu_r') +plt.matshow(Bx3slice, cmap="RdBu_r") plt.colorbar() plt.title("Bx3") -plt.matshow(Vx1slice,cmap='RdBu_r') +plt.matshow(Vx1slice, cmap="RdBu_r") plt.colorbar() plt.title("Vx1") -plt.matshow(Vx2slice,cmap='RdBu_r') +plt.matshow(Vx2slice, cmap="RdBu_r") plt.colorbar() plt.title("Vx2") -plt.matshow(Vx3slice,cmap='RdBu_r') +plt.matshow(Vx3slice, cmap="RdBu_r") plt.colorbar() plt.title("Vx3") diff --git a/test/MHD/AxisFluxTube/testme.py b/test/MHD/AxisFluxTube/testme.py index c5db6cfac..f027b24b4 100755 --- a/test/MHD/AxisFluxTube/testme.py +++ b/test/MHD/AxisFluxTube/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,39 +12,40 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-14 -tolerance=1e-14 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-coarsening.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-coarsening.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True + test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) - # test with MPI - test.mpi=True - testMe(test) + # test with MPI + test.mpi = True + testMe(test) diff --git a/test/MHD/Coarsening/python/testidefix.py b/test/MHD/Coarsening/python/testidefix.py index 206c01600..d901d805a 100755 --- a/test/MHD/Coarsening/python/testidefix.py +++ b/test/MHD/Coarsening/python/testidefix.py @@ -19,31 +19,30 @@ from pytools.vtk_io import readVTK parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # find which ini file was used -with open('../idefix.0.log','r') as fp: - lines = fp.readlines() - for line in lines: - if line.find(".ini") != -1: - s=line.split() - inputFile=s[5][:-1] - -input = inifix.load('../'+inputFile) +with open("../idefix.0.log", "r") as fp: + lines = fp.readlines() + for line in lines: + if line.find(".ini") != -1: + s = line.split() + inputFile = s[5][:-1] + +input = inifix.load("../" + inputFile) componentDir = input["Setup"]["direction"][0] spatialDir = input["Setup"]["direction"][1] # Convert componentDir -componentName=["BX1","BX2","BX3"] +componentName = ["BX1", "BX2", "BX3"] -V=readVTK('../data.0001.vtk', geometry='cartesian') +V = readVTK("../data.0001.vtk", geometry="cartesian") # left_state and right_state set p, rho and u # geometry sets left boundary on 0., right boundary on 1 and initial @@ -52,48 +51,46 @@ # gamma denotes specific heat # note that gamma and npts are default parameters (1.4 and 500) in solve function -x=V.x -if spatialDir==0: - qside=V.data[componentName[componentDir]][:,4,0] - qcenter=V.data[componentName[componentDir]][:,32,0] - x=V.x -if spatialDir==1: - qside=V.data[componentName[componentDir]][4,:,0] - qcenter=V.data[componentName[componentDir]][32,:,0] - x=V.y -if spatialDir==2: - qside=V.data[componentName[componentDir]][4,0,:] - qcenter=V.data[componentName[componentDir]][32,0,:] - x=V.z - -#initial condition in the code -q0=0.*x+0.1*(np.abs(x)<0.1) +x = V.x +if spatialDir == 0: + qside = V.data[componentName[componentDir]][:, 4, 0] + qcenter = V.data[componentName[componentDir]][:, 32, 0] + x = V.x +if spatialDir == 1: + qside = V.data[componentName[componentDir]][4, :, 0] + qcenter = V.data[componentName[componentDir]][32, :, 0] + x = V.y +if spatialDir == 2: + qside = V.data[componentName[componentDir]][4, 0, :] + qcenter = V.data[componentName[componentDir]][32, 0, :] + x = V.z + +# initial condition in the code +q0 = 0.0 * x + 0.1 * (np.abs(x) < 0.1) # compute solution to diffusion equation using Fourier transforms -qf0=np.fft.fft(q0) -k2=(2.0*np.pi*q0.size*np.fft.fftfreq(q0.size))**2 -qf=qf0*np.exp(-k2*V.t*0.05) -qtheory=np.real(np.fft.ifft(qf)) +qf0 = np.fft.fft(q0) +k2 = (2.0 * np.pi * q0.size * np.fft.fftfreq(q0.size)) ** 2 +qf = qf0 * np.exp(-k2 * V.t * 0.05) +qtheory = np.real(np.fft.ifft(qf)) -if(not args.noplot): +if not args.noplot: plt.figure(1) - plt.plot(x,qside,'+',markersize=6,label='side') - plt.plot(x,qcenter,'+',markersize=6,label='center') + plt.plot(x, qside, "+", markersize=6, label="side") + plt.plot(x, qcenter, "+", markersize=6, label="center") - #plt.plot(x,q0) - plt.plot(x,qtheory,label='theory') + # plt.plot(x,q0) + plt.plot(x, qtheory, label="theory") plt.legend() plt.title(componentName[componentDir]) - - plt.ioff() plt.show() -errorCenter=np.mean((qcenter-qtheory)**2) -errorSide=np.mean((qside-qtheory)**2) -print("Error Side=%e, Error Center=%e"%(errorSide,errorCenter)) -assert(errorCenter<2e-5) -assert(errorSide<2e-8) +errorCenter = np.mean((qcenter - qtheory) ** 2) +errorSide = np.mean((qside - qtheory) ** 2) +print("Error Side=%e, Error Center=%e" % (errorSide, errorCenter)) +assert errorCenter < 2e-5 +assert errorSide < 2e-8 print("SUCCESS!") diff --git a/test/MHD/Coarsening/testme.py b/test/MHD/Coarsening/testme.py index e82277ee6..c1e63ac80 100755 --- a/test/MHD/Coarsening/testme.py +++ b/test/MHD/Coarsening/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,33 +12,34 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini","idefix-x2.ini","idefix-x3.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini", "idefix-x2.ini", "idefix-x3.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - test.mpi=False - testMe(test) + test.noplot = True + test.mpi = False + testMe(test) - test.mpi=True - testMe(test) + test.mpi = True + testMe(test) diff --git a/test/MHD/FargoMHDSpherical/testme.py b/test/MHD/FargoMHDSpherical/testme.py index ee74c24db..5f003ed52 100755 --- a/test/MHD/FargoMHDSpherical/testme.py +++ b/test/MHD/FargoMHDSpherical/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,50 +12,51 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-14 -tolerance=1e-14 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2','2'] + test.dec = ["2", "2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - #test vector potential formulation - test.vectPot=True - testMe(test) - - # test with MPI - test.vectPot=False - test.mpi=True - testMe(test) - - test.vectPot=True - test.mpi=True - testMe(test) + test.noplot = True + + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + # test vector potential formulation + test.vectPot = True + testMe(test) + + # test with MPI + test.vectPot = False + test.mpi = True + testMe(test) + + test.vectPot = True + test.mpi = True + testMe(test) diff --git a/test/MHD/HallWhistler/python/testidefix.py b/test/MHD/HallWhistler/python/testidefix.py index 2ca5d6bf8..2e08f387c 100755 --- a/test/MHD/HallWhistler/python/testidefix.py +++ b/test/MHD/HallWhistler/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + #!/usr/bin/env python3 # -*- coding: utf-8 -*- """ @@ -20,69 +21,67 @@ from scipy.signal import argrelextrema parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # values for the field strength to compute theoretical eigenfrequency values -lH=1.0 -B=1.0 -Va=1.0 -k=2.0*np.pi +lH = 1.0 +B = 1.0 +Va = 1.0 +k = 2.0 * np.pi # load the dat file produced by the setup -raw=np.loadtxt('../timevol.dat',skiprows=1) -t=raw[:,0] -by=raw[:,1] +raw = np.loadtxt("../timevol.dat", skiprows=1) +t = raw[:, 0] +by = raw[:, 1] # Theoretical speedes -f_w=Va/(2*np.pi)*k*(np.sqrt(1+(k*lH/2)**2)+k*lH/2) -f_i=Va/(2*np.pi)*k*(np.sqrt(1+(k*lH/2)**2)-k*lH/2) -f_A=k*Va/(2*np.pi) - +f_w = Va / (2 * np.pi) * k * (np.sqrt(1 + (k * lH / 2) ** 2) + k * lH / 2) +f_i = Va / (2 * np.pi) * k * (np.sqrt(1 + (k * lH / 2) ** 2) - k * lH / 2) +f_A = k * Va / (2 * np.pi) # Compute temporal spectrum and get frequency -#by=By[:,0] -sp=np.abs(np.fft.rfft(by)) -f=np.arange(sp.size)/(t[-1]-t[0]) - -r=10**np.arange(np.floor(np.log10(np.amin(sp))),np.ceil(np.log10(np.amax(sp))),0.1) - - - +# by=By[:,0] +sp = np.abs(np.fft.rfft(by)) +f = np.arange(sp.size) / (t[-1] - t[0]) -if(not args.noplot): +r = 10 ** np.arange( + np.floor(np.log10(np.amin(sp))), np.ceil(np.log10(np.amax(sp))), 0.1 +) - plt.close('all') +if not args.noplot: + plt.close("all") plt.figure() - plt.loglog(f,sp,label='signal') - plt.loglog(f_w+0*r,r,'--',label='whistler') - plt.loglog(f_i+0*r,r,'-.',label='ion cyclotron') - plt.loglog(f_A+0*r,r,':',label='Alfven') - plt.xlabel('frequency') - plt.ylabel('By amplitude') + plt.loglog(f, sp, label="signal") + plt.loglog(f_w + 0 * r, r, "--", label="whistler") + plt.loglog(f_i + 0 * r, r, "-.", label="ion cyclotron") + plt.loglog(f_A + 0 * r, r, ":", label="Alfven") + plt.xlabel("frequency") + plt.ylabel("By amplitude") plt.legend() plt.ioff() plt.show() -imax=argrelextrema(sp,np.greater,order=2)[0][0] -f_wnum=f[imax] -error=np.fabs(f_w-f_wnum)/f_w -print("Theoretical whistler frequency=%g, numerical=%g, error=%g"%(f_w,f_wnum,error)) +imax = argrelextrema(sp, np.greater, order=2)[0][0] +f_wnum = f[imax] +error = np.fabs(f_w - f_wnum) / f_w +print( + "Theoretical whistler frequency=%g, numerical=%g, error=%g" % (f_w, f_wnum, error) +) -if(error<0.06): +if error < 0.06: print("SUCCESS") sys.exit(0) else: diff --git a/test/MHD/HallWhistler/testme.py b/test/MHD/HallWhistler/testme.py index ce50a7ae6..2e0b0abc0 100755 --- a/test/MHD/HallWhistler/testme.py +++ b/test/MHD/HallWhistler/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,34 +12,36 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" -tolerance=1e-15 +name = "dump.0001.dmp" +tolerance = 1e-15 + + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest(); - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True + test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/MHD/LinearWaveTest/python/testidefix.py b/test/MHD/LinearWaveTest/python/testidefix.py index 8603ee8ed..f15559915 100755 --- a/test/MHD/LinearWaveTest/python/testidefix.py +++ b/test/MHD/LinearWaveTest/python/testidefix.py @@ -15,54 +15,62 @@ from pytools.dump_io import readDump parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() def getError(rep): try: - V=readDump(rep+'/dump.0000.dmp') - U=readDump(rep+'/dump.0001.dmp') + V = readDump(rep + "/dump.0000.dmp") + U = readDump(rep + "/dump.0001.dmp") except: return math.nan - keylist=[] - keylist=['Vc-RHO','Vc-VX1','Vc-VX2','Vc-VX3','Vs-BX1s','Vs-BX2s','Vs-BX3s','Vc-PRS'] + keylist = [] + keylist = [ + "Vc-RHO", + "Vc-VX1", + "Vc-VX2", + "Vc-VX3", + "Vs-BX1s", + "Vs-BX2s", + "Vs-BX3s", + "Vc-PRS", + ] err = 0.0 for key in keylist: - Q1=V.data[key] - Q2=U.data[key] - - Q1=Q1-np.mean(Q1) - Q2=Q2-np.mean(Q2) - print(key+" error=%e"%((np.mean(np.abs(Q1-Q2)))*1e6)) - err=err + (np.mean(np.abs(Q1-Q2)))**2 - if(not args.noplot): - plt.figure() - plt.contourf(V.data[key][:,:,16]-U.data[key][:,:,16]) - plt.title(key) - - - err = err/len(keylist) + Q1 = V.data[key] + Q2 = U.data[key] + + Q1 = Q1 - np.mean(Q1) + Q2 = Q2 - np.mean(Q2) + print(key + " error=%e" % ((np.mean(np.abs(Q1 - Q2))) * 1e6)) + err = err + (np.mean(np.abs(Q1 - Q2))) ** 2 + if not args.noplot: + plt.figure() + plt.contourf(V.data[key][:, :, 16] - U.data[key][:, :, 16]) + plt.title(key) + + err = err / len(keylist) err = np.sqrt(err) return err + error = getError("..") -print("Error=%e"%(error*1e6)) +print("Error=%e" % (error * 1e6)) -if(not args.noplot): - plt.show() +if not args.noplot: + plt.show() -if error*1e6<3e-2: - print("SUCCESS") - sys.exit(0) +if error * 1e6 < 3e-2: + print("SUCCESS") + sys.exit(0) else: - print("Failed") - sys.exit(1) + print("Failed") + sys.exit(1) diff --git a/test/MHD/LinearWaveTest/testme.py b/test/MHD/LinearWaveTest/testme.py index 5b4aed87f..4e6ae7498 100755 --- a/test/MHD/LinearWaveTest/testme.py +++ b/test/MHD/LinearWaveTest/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,43 +12,50 @@ import pytools.idfx_test as tst -tolerance=2e-13 -def testMe(test): - test.configure() - test.compile() - inifiles=["idefix-fast.ini","idefix-slow.ini","idefix-alfven.ini","idefix-entropy.ini"] - for ini in inifiles: - mytol=tolerance - - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) +tolerance = 2e-13 -test=tst.idfxTest(__file__) +def testMe(test): + test.configure() + test.compile() + inifiles = [ + "idefix-fast.ini", + "idefix-slow.ini", + "idefix-alfven.ini", + "idefix-entropy.ini", + ] + for ini in inifiles: + mytol = tolerance + + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) + + +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2','2'] + test.dec = ["2", "2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) - test.mpi=True - testMe(test) + test.mpi = True + testMe(test) - test.mpi=False - test.reconstruction=3 - testMe(test) + test.mpi = False + test.reconstruction = 3 + testMe(test) - test.reconstruction=4 - testMe(test) + test.reconstruction = 4 + testMe(test) diff --git a/test/MHD/MTI/python/testidefix.py b/test/MHD/MTI/python/testidefix.py index 18481692d..28c721619 100644 --- a/test/MHD/MTI/python/testidefix.py +++ b/test/MHD/MTI/python/testidefix.py @@ -14,60 +14,71 @@ import inifix import numpy as np -n = 1 # fondamental mode +n = 1 # fondamental mode conf = inifix.load("../idefix.ini") -Pr=conf["Setup"]["pr"] -ksi=conf["Setup"]["ksi"] +Pr = conf["Setup"]["pr"] +ksi = conf["Setup"]["ksi"] L = 0.1 -H = 3. -wbuoy = 1/np.sqrt(3) -gamma = 5/3 +H = 3.0 +wbuoy = 1 / np.sqrt(3) +gamma = 5 / 3 -kn = 2*np.pi*n*np.sqrt(2)/L +kn = 2 * np.pi * n * np.sqrt(2) / L -fid=open('../average.dat',"r") +fid = open("../average.dat", "r") # read the first line to get data names -varnames=fid.readline().split() +varnames = fid.readline().split() fid.close() # load the bulk of the file -data=np.loadtxt('../average.dat',skiprows=1) +data = np.loadtxt("../average.dat", skiprows=1) # store this in our data structure -V={} -i=0 +V = {} +i = 0 for name in varnames: - V[name]=data[:,i] - i=i+1 + V[name] = data[:, i] + i = i + 1 + +sigma_vx = ( + 0.5 * (np.log(V["kinx"][20]) - np.log(V["kinx"][15])) / (V["t"][20] - V["t"][15]) +) +sigma_vy = ( + 0.5 * (np.log(V["kiny"][20]) - np.log(V["kiny"][15])) / (V["t"][20] - V["t"][15]) +) +sigma_by = ( + 0.5 * (np.log(V["by_2"][20]) - np.log(V["by_2"][15])) / (V["t"][20] - V["t"][15]) +) +sigma_num = (sigma_vx + sigma_vy + sigma_by) / 3.0 -sigma_vx = 0.5*(np.log(V['kinx'][20]) - np.log(V['kinx'][15]))/(V['t'][20] - V['t'][15]) -sigma_vy = 0.5*(np.log(V['kiny'][20]) - np.log(V['kiny'][15]))/(V['t'][20] - V['t'][15]) -sigma_by = 0.5*(np.log(V['by_2'][20]) - np.log(V['by_2'][15]))/(V['t'][20] - V['t'][15]) -sigma_num = (sigma_vx + sigma_vy + sigma_by)/3. def dispMTI(wcond, k, Pr): - cosk_2 = 0.5 # here cosk_2 = sqrt(bhat) dot khat i.e. xhat dot khat + cosk_2 = 0.5 # here cosk_2 = sqrt(bhat) dot khat i.e. xhat dot khat k_2 = k**2 - ksi = 2.5/k_2/cosk_2*wcond - kx_2 = k_2*cosk_2 - K = kx_2/k_2 + ksi = 2.5 / k_2 / cosk_2 * wcond + kx_2 = k_2 * cosk_2 + K = kx_2 / k_2 - bk_2 = k_2*cosk_2 + bk_2 = k_2 * cosk_2 bkhat_2 = cosk_2 - nu = Pr*ksi - wvisc = 3*nu*bk_2 - v = wvisc*(1 - bkhat_2) - N_2 = wbuoy**2/gamma*((H-1)*gamma-H) - return np.array([1, wcond+v, wcond*v+N_2*kx_2/k_2, K*wcond*-wbuoy**2]) + nu = Pr * ksi + wvisc = 3 * nu * bk_2 + v = wvisc * (1 - bkhat_2) + N_2 = wbuoy**2 / gamma * ((H - 1) * gamma - H) + return np.array( + [1, wcond + v, wcond * v + N_2 * kx_2 / k_2, K * wcond * -(wbuoy**2)] + ) + def sigmaMTI(wcond, k, Pr): - roots = np.roots(dispMTI(wcond,k,Pr)) + roots = np.roots(dispMTI(wcond, k, Pr)) return np.real(roots[np.real(roots) > 0])[0] -wcd = 0.4*ksi*kn**2/2 + +wcd = 0.4 * ksi * kn**2 / 2 sigma_analytic = sigmaMTI(wcd, kn, Pr) -if np.abs(np.log(sigma_analytic/sigma_num)/np.log(sigma_num)) >= 0.1: +if np.abs(np.log(sigma_analytic / sigma_num) / np.log(sigma_num)) >= 0.1: print("Failed") sys.exit(1) else: diff --git a/test/MHD/MTI/testme.py b/test/MHD/MTI/testme.py index baaed6302..cb145f3a6 100755 --- a/test/MHD/MTI/testme.py +++ b/test/MHD/MTI/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -13,32 +14,32 @@ def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini","idefix-sl.ini"] -# inifiles=["idefix-rkl.ini","idefix-sl.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini", "idefix-sl.ini"] + # inifiles=["idefix-rkl.ini","idefix-sl.ini"] - # loop on all the ini files for this test - name="dump.0001.dmp" - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest() - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name) + # loop on all the ini files for this test + name = "dump.0001.dmp" + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp") - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/MHD/OrszagTang/testme.py b/test/MHD/OrszagTang/testme.py index 7f9688eb0..3c0e56bc2 100755 --- a/test/MHD/OrszagTang/testme.py +++ b/test/MHD/OrszagTang/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,58 +12,64 @@ import pytools.idfx_test as tst -tolerance=1e-12 +tolerance = 1e-12 + + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini", - "idefix-hll.ini","idefix-hlld-arithmetic.ini", - "idefix-hlld-hll.ini", - "idefix-hlld-hlld.ini", - "idefix-hlld-uct0.ini", - "idefix-hlld.ini","idefix-tvdlf.ini"] + test.configure() + test.compile() + inifiles = [ + "idefix.ini", + "idefix-hll.ini", + "idefix-hlld-arithmetic.ini", + "idefix-hlld-hll.ini", + "idefix-hlld-hlld.ini", + "idefix-hlld-uct0.ini", + "idefix-hlld.ini", + "idefix-tvdlf.ini", + ] - for ini in inifiles: - mytol=tolerance + for ini in inifiles: + mytol = tolerance - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") - if(test.single): - mytol=1e-5 + if test.single: + mytol = 1e-5 - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - for rec in [2,3,4]: - test.noplot = True - test.vectPot = False - test.single=False - test.reconstruction=rec - test.mpi=False - testMe(test) - test.mpi=True + for rec in [2, 3, 4]: + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = rec + test.mpi = False + testMe(test) + test.mpi = True + testMe(test) + + # single precision validation + test.reconstruction = 2 + test.mpi = False + test.single = True testMe(test) - # single precision validation - test.reconstruction=2 - test.mpi=False - test.single=True - testMe(test) - - # Vector potential validation - test.single=False - test.mpi=False - test.vectPot=True - testMe(test) + # Vector potential validation + test.single = False + test.mpi = False + test.vectPot = True + testMe(test) diff --git a/test/MHD/OrszagTang3D/testme.py b/test/MHD/OrszagTang3D/testme.py index 662ba4066..885da1dea 100755 --- a/test/MHD/OrszagTang3D/testme.py +++ b/test/MHD/OrszagTang3D/testme.py @@ -3,6 +3,7 @@ @author: glesur """ + import os import sys @@ -12,59 +13,59 @@ # Whether we should reset our reference run (only do that on purpose!) -tolerance=1e-13 +tolerance = 1e-13 + def testMe(test): - test.configure() - test.compile() - tol=tolerance - if test.single: - tol=1e-6 + test.configure() + test.compile() + tol = tolerance + if test.single: + tol = 1e-6 - # default with idefix.ini - test.run() - if test.init: - if not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=tol) + # default with idefix.ini + test.run() + if test.init: + if not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=tol) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) # if no decomposition is specified, use that one if not test.dec: - test.dec=["2","2","2"] + test.dec = ["2", "2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.vectPot=False - test.reconstruction=2 - test.mpi=False - testMe(test) - # test in MPI mode - test.mpi=True - testMe(test) - - - # test with vector potential - test.mpi=False - test.vectPot=True - test.reconstruction=2 - testMe(test) - - test.mpi=True - testMe(test) - - # test with other precision - test.single=True - test.vectPot=False - test.reconstruction=2 - test.mpi=False - testMe(test) - # test in MPI mode - test.mpi=True - testMe(test) + test.vectPot = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + # test in MPI mode + test.mpi = True + testMe(test) + + # test with vector potential + test.mpi = False + test.vectPot = True + test.reconstruction = 2 + testMe(test) + + test.mpi = True + testMe(test) + + # test with other precision + test.single = True + test.vectPot = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + # test in MPI mode + test.mpi = True + testMe(test) diff --git a/test/MHD/ResistiveAlfvenWave/python/testidefix.py b/test/MHD/ResistiveAlfvenWave/python/testidefix.py index 52b11c8c8..c221544dc 100644 --- a/test/MHD/ResistiveAlfvenWave/python/testidefix.py +++ b/test/MHD/ResistiveAlfvenWave/python/testidefix.py @@ -5,41 +5,39 @@ import numpy as np parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() # values for the field strength to compute theoretical decay rate -eta=0.05 -k=2.0*np.pi -B0=1.0 +eta = 0.05 +k = 2.0 * np.pi +B0 = 1.0 # decay rate of the energy, assuming k^2eta^2 < 2B0^2 -gamma=-k**2*eta/2 +gamma = -(k**2) * eta / 2 -raw=np.loadtxt('../timevol.dat',skiprows=1) -t=raw[:,0] -e=raw[:,1] +raw = np.loadtxt("../timevol.dat", skiprows=1) +t = raw[:, 0] +e = raw[:, 1] -eth=e[0]*np.exp(2*gamma*t) -error=np.mean(e/eth-1.0) +eth = e[0] * np.exp(2 * gamma * t) +error = np.mean(e / eth - 1.0) -if(not args.noplot): - - plt.close('all') +if not args.noplot: + plt.close("all") plt.figure() - plt.semilogy(t,e) - plt.semilogy(t,eth) + plt.semilogy(t, e) + plt.semilogy(t, eth) plt.ioff() plt.show() -if(error<0.03): +if error < 0.03: print("SUCCESS") sys.exit(0) else: diff --git a/test/MHD/ResistiveAlfvenWave/testme.py b/test/MHD/ResistiveAlfvenWave/testme.py index 72014c7cc..b7ce4a73c 100755 --- a/test/MHD/ResistiveAlfvenWave/testme.py +++ b/test/MHD/ResistiveAlfvenWave/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,35 +12,36 @@ import pytools.idfx_test as tst -tolerance=1e-14 +tolerance = 1e-14 + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-rkl.ini"] - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - mytol=tolerance - if ini=="idefix-rkl.ini": - mytol=1e-10 - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) - - -test=tst.idfxTest(__file__) + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-rkl.ini"] + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + mytol = tolerance + if ini == "idefix-rkl.ini": + mytol = 1e-10 + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) + + +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - test.mpi=True - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + test.mpi = True + testMe(test) diff --git a/test/MHD/ShearingBox/python/testidefix.py b/test/MHD/ShearingBox/python/testidefix.py index 1ab5b2935..6f75c6af7 100755 --- a/test/MHD/ShearingBox/python/testidefix.py +++ b/test/MHD/ShearingBox/python/testidefix.py @@ -5,6 +5,7 @@ @author: lesurg """ + import argparse import sys @@ -13,13 +14,13 @@ from scipy.integrate import solve_ivp -#compute theoretical solution (from Balbus & Hawley 2006, using notations from Lesur 2021) +# compute theoretical solution (from Balbus & Hawley 2006, using notations from Lesur 2021) def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): - kx = k0x + q*Omega * t * k0y + kx = k0x + q * Omega * t * k0y ky = k0y kz = k0z - k2 = kx*kx+ky*ky+kz*kz + k2 = kx * kx + ky * ky + kz * kz vx = y[0] vy = y[1] vz = y[2] @@ -27,100 +28,114 @@ def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): by = y[4] bz = y[5] - gxx = kx*kx/k2 - gxy = kx*ky/k2 - gyy = ky*ky/k2 - gyz = ky*kz/k2 - gxz = kx*kz/k2 - #gzz = kz*kz/k2 + gxx = kx * kx / k2 + gxy = kx * ky / k2 + gyy = ky * ky / k2 + gyz = ky * kz / k2 + gxz = kx * kz / k2 + # gzz = kz*kz/k2 + + kdotB = ky * B0y + kz * B0z - kdotB = ky*B0y+kz*B0z + # we assume b=1j*db hence db=-1j*b - #we assume b=1j*db hence db=-1j*b + dvx = kdotB * bx + 2 * Omega * vy * (1 - gxx) + 2 * (1 - q) * Omega * gxy * vx + dvy = ( + kdotB * by + - q * Omega * vx * gyy + - (2 - q) * Omega * (1 - gyy) * vx + - 2 * Omega * vy * gxy + ) + dvz = kdotB * bz + 2 * (1 - q) * Omega * vx * gyz - 2 * Omega * vy * gxz - dvx = kdotB*bx + 2*Omega*vy*(1-gxx) + 2*(1-q)*Omega*gxy*vx - dvy = kdotB*by - q*Omega*vx*gyy - (2-q)*Omega*(1-gyy)*vx - 2*Omega*vy*gxy - dvz= kdotB*bz +2*(1-q)*Omega*vx*gyz-2*Omega*vy*gxz + dbx = -kdotB * vx + dby = -kdotB * vy - q * Omega * bx + dbz = -kdotB * vz - dbx = - kdotB*vx - dby = - kdotB*vy - q*Omega*bx - dbz = - kdotB*vz + return np.asarray([dvx, dvy, dvz, dbx, dby, dbz]) - return np.asarray([dvx,dvy,dvz,dbx,dby,dbz]) parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() -#initial condition: vr=1, rest is 0, mode initial is nx=0, ny=1, nz=5) -y=solve_ivp(rhs, [0,30], [1, 0, 0, 0, 0, 0], args=(1, 1.5, 0.02, 0.05, 0, 2.0*np.pi, 4*np.pi), dense_output=True) +# initial condition: vr=1, rest is 0, mode initial is nx=0, ny=1, nz=5) +y = solve_ivp( + rhs, + [0, 30], + [1, 0, 0, 0, 0, 0], + args=(1, 1.5, 0.02, 0.05, 0, 2.0 * np.pi, 4 * np.pi), + dense_output=True, +) # read timevol file rep = "../" filename = "timevol.dat" -fid=open(rep+filename,"r") +fid = open(rep + filename, "r") -gamma=5/3 +gamma = 5 / 3 # read the first line to get data names -varnames=fid.readline().split() +varnames = fid.readline().split() fid.close() # load the bulk of the file -data=np.loadtxt(rep+filename,skiprows=1) +data = np.loadtxt(rep + filename, skiprows=1) # store this in our data structure -V={} +V = {} -i=0 +i = 0 for name in varnames: - V[name]=data[:,i] - i=i+1 + V[name] = data[:, i] + i = i + 1 # velocity normalisation -v0=V['vx'][0] +v0 = V["vx"][0] # compute L2 error norm -error=np.sqrt((V['vx']/v0-y.sol(V["t"])[0,:])**2 + (V['vy']/v0-y.sol(V["t"])[1,:])**2+ + (V['vz']/v0-y.sol(V["t"])[2,:])**2) - - - -if(not args.noplot): - # Comparison with exact solution - plt.rc('text', usetex=True) - plt.rc('font', family='serif') - plt.rc('font', size=16) - plt.close('all') - plt.figure(1) - plt.plot(V["t"],V['vx']/v0,'r-',label=r'$u_{R}$') - plt.plot(V["t"],y.sol(V["t"])[0,:],'r--') - plt.plot(V["t"],V['vy']/v0,'b-',label=r'$u_{\varphi}$') - plt.plot(V["t"],y.sol(V["t"])[1,:],'b--') - plt.plot(V["t"],V['vz']/v0,'g-',label=r'$u_{z}$') - plt.plot(V["t"],y.sol(V["t"])[2,:],'g--') - plt.legend() - plt.xlabel('t') - - # plot error - plt.figure() - plt.semilogy(V["t"],error) - plt.xlim([0,10]) - plt.ylim([1e-3,1]) - - plt.ioff() - plt.show() - -err=np.mean(error) -print("Error=",err) - -if(err<0.03): - print("SUCCESS") - sys.exit(0) +error = np.sqrt( + (V["vx"] / v0 - y.sol(V["t"])[0, :]) ** 2 + + (V["vy"] / v0 - y.sol(V["t"])[1, :]) ** 2 + + (V["vz"] / v0 - y.sol(V["t"])[2, :]) ** 2 +) + + +if not args.noplot: + # Comparison with exact solution + plt.rc("text", usetex=True) + plt.rc("font", family="serif") + plt.rc("font", size=16) + plt.close("all") + plt.figure(1) + plt.plot(V["t"], V["vx"] / v0, "r-", label=r"$u_{R}$") + plt.plot(V["t"], y.sol(V["t"])[0, :], "r--") + plt.plot(V["t"], V["vy"] / v0, "b-", label=r"$u_{\varphi}$") + plt.plot(V["t"], y.sol(V["t"])[1, :], "b--") + plt.plot(V["t"], V["vz"] / v0, "g-", label=r"$u_{z}$") + plt.plot(V["t"], y.sol(V["t"])[2, :], "g--") + plt.legend() + plt.xlabel("t") + + # plot error + plt.figure() + plt.semilogy(V["t"], error) + plt.xlim([0, 10]) + plt.ylim([1e-3, 1]) + + plt.ioff() + plt.show() + +err = np.mean(error) +print("Error=", err) + +if err < 0.03: + print("SUCCESS") + sys.exit(0) else: - print("FAILED") + print("FAILED") diff --git a/test/MHD/ShearingBox/testme.py b/test/MHD/ShearingBox/testme.py index 1e30e1745..0d782c1c5 100755 --- a/test/MHD/ShearingBox/testme.py +++ b/test/MHD/ShearingBox/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,38 +12,39 @@ import pytools.idfx_test as tst -tolerance=1e-14 +tolerance = 1e-14 + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-fargo.ini"] - for ini in inifiles: - mytol=tolerance + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-fargo.ini"] + for ini in inifiles: + mytol = tolerance - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename="dump.0001.dmp") - test.standardTest() - # When using RKL, except larger error due to B reconstruction and RKL # of substeps - test.nonRegressionTest(filename="dump.0001.dmp",tolerance=mytol) + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename="dump.0001.dmp") + test.standardTest() + # When using RKL, except larger error due to B reconstruction and RKL # of substeps + test.nonRegressionTest(filename="dump.0001.dmp", tolerance=mytol) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','1','2'] + test.dec = ["2", "1", "2"] if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp",tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp", tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py index f37cf5032..b68a52bad 100644 --- a/test/MHD/clessTDiffusion/python/testidefix.py +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -11,26 +11,28 @@ gamma = conf["Hydro"]["gamma"] kappa = conf["Hydro"]["bragTDiffusion"][-1] -current_VTK = readVTK('../data.0003.vtk', geometry='spherical') +current_VTK = readVTK("../data.0003.vtk", geometry="spherical") -rho = current_VTK.data['RHO'].squeeze() -prs = current_VTK.data['PRS'].squeeze() -r = current_VTK.r +rho = current_VTK.data["RHO"].squeeze() +prs = current_VTK.data["PRS"].squeeze() +r = current_VTK.r + +idx1 = np.where(r > 20)[0][0] +idx2 = np.where(r > 30)[0][0] -idx1=np.where(r > 20)[0][0] -idx2=np.where(r > 30)[0][0] def gamma_prime(gamma, beta): - return (gamma+beta*(gamma-1))/(1+beta*(gamma-1)) + return (gamma + beta * (gamma - 1)) / (1 + beta * (gamma - 1)) + success = True eps = 3e-4 -gamma_eff = np.gradient(prs, r)/np.gradient(rho, r)*rho/prs +gamma_eff = np.gradient(prs, r) / np.gradient(rho, r) * rho / prs -Error=np.abs(gamma_eff[idx1:idx2]-gamma_prime(gamma, 1.5)).mean() +Error = np.abs(gamma_eff[idx1:idx2] - gamma_prime(gamma, 1.5)).mean() if Error > eps: - success=False + success = False if success: print("SUCCESS") diff --git a/test/MHD/clessTDiffusion/testme.py b/test/MHD/clessTDiffusion/testme.py index 98e3def92..0d1ca73c9 100755 --- a/test/MHD/clessTDiffusion/testme.py +++ b/test/MHD/clessTDiffusion/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -13,31 +14,31 @@ def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - name = "dump.0001.dmp" - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest() - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name, tolerance=2e-15) + # loop on all the ini files for this test + name = "dump.0001.dmp" + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=2e-15) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp") - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/MHD/sod-iso/testme.py b/test/MHD/sod-iso/testme.py index 70c7daaad..f559eeb17 100755 --- a/test/MHD/sod-iso/testme.py +++ b/test/MHD/sod-iso/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,40 +12,41 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"] - if test.reconstruction==4: - inifiles=["idefix-rk3.ini","idefix-hlld-rk3.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-hll.ini", "idefix-hlld.ini", "idefix-tvdlf.ini"] + if test.reconstruction == 4: + inifiles = ["idefix-rk3.ini", "idefix-hlld-rk3.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - for rec in range(2,5): - test.vectPot=False - test.single=False - test.reconstruction=rec - test.mpi=False + test.noplot = True + for rec in range(2, 5): + test.vectPot = False + test.single = False + test.reconstruction = rec + test.mpi = False + testMe(test) + + # test in single precision + test.reconstruction = 2 + test.single = True testMe(test) - - # test in single precision - test.reconstruction=2 - test.single=True - testMe(test) diff --git a/test/MHD/sod/testme.py b/test/MHD/sod/testme.py index 70c7daaad..f559eeb17 100755 --- a/test/MHD/sod/testme.py +++ b/test/MHD/sod/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,40 +12,41 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini","idefix-hll.ini","idefix-hlld.ini","idefix-tvdlf.ini"] - if test.reconstruction==4: - inifiles=["idefix-rk3.ini","idefix-hlld-rk3.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini", "idefix-hll.ini", "idefix-hlld.ini", "idefix-tvdlf.ini"] + if test.reconstruction == 4: + inifiles = ["idefix-rk3.ini", "idefix-hlld-rk3.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name) + else: + testMe(test) else: - test.noplot = True - for rec in range(2,5): - test.vectPot=False - test.single=False - test.reconstruction=rec - test.mpi=False + test.noplot = True + for rec in range(2, 5): + test.vectPot = False + test.single = False + test.reconstruction = rec + test.mpi = False + testMe(test) + + # test in single precision + test.reconstruction = 2 + test.single = True testMe(test) - - # test in single precision - test.reconstruction=2 - test.single=True - testMe(test) diff --git a/test/MHD/sphBragTDiffusion/python/testidefix.py b/test/MHD/sphBragTDiffusion/python/testidefix.py index d42c8bc92..f96cbe6af 100644 --- a/test/MHD/sphBragTDiffusion/python/testidefix.py +++ b/test/MHD/sphBragTDiffusion/python/testidefix.py @@ -14,14 +14,14 @@ time_step = conf["Output"]["vtk"] nfile = 6 -list_time = [round(i*time_step, 3) for i in range(nfile)] +list_time = [round(i * time_step, 3) for i in range(nfile)] list_VTK = list() for k in range(nfile): if k >= 10: current_number = str(k) else: - current_number = '0' + str(k) - current_VTK = readVTK('../data.00' + current_number + '.vtk', geometry='spherical') + current_number = "0" + str(k) + current_VTK = readVTK("../data.00" + current_number + ".vtk", geometry="spherical") list_VTK.append(current_VTK) list_VX = list() @@ -30,55 +30,65 @@ list_K = list() list_T = list() for VTK in list_VTK: - list_VX.append(VTK.data['VX1']) - list_RHO.append(VTK.data['RHO']) - list_PRS.append(VTK.data['PRS']) - list_K.append(VTK.data['PRS']/(VTK.data['RHO']**gamma)) - list_T.append(VTK.data['PRS']/VTK.data['RHO']) + list_VX.append(VTK.data["VX1"]) + list_RHO.append(VTK.data["RHO"]) + list_PRS.append(VTK.data["PRS"]) + list_K.append(VTK.data["PRS"] / (VTK.data["RHO"] ** gamma)) + list_T.append(VTK.data["PRS"] / VTK.data["RHO"]) VTK = list_VTK[-1] R = VTK.r TH = VTK.theta PHI = VTK.phi -ir = len(R)//5 -ith = len(TH)//14 -iphi = len(PHI)*5//7 +ir = len(R) // 5 +ith = len(TH) // 14 +iphi = len(PHI) * 5 // 7 + +rho0 = 1.0 +c = 1.0 / (gamma - 1.0) +D = kappa / (rho0 * c) -rho0 = 1. -c = 1./(gamma - 1.) -D = kappa/(rho0*c) def analytic_sol(r, th, phi, t): - lambd2 = 1./r**2/np.sin(th)**2 - return amplitude*((3/r**2 - 1)*np.sin(r)/r - 3*np.cos(r)/r**2)*(-3*np.cos(th)*np.sin(th))*(np.sin(phi))*np.exp(-t*D*lambd2) + 1 + lambd2 = 1.0 / r**2 / np.sin(th) ** 2 + return ( + amplitude + * ((3 / r**2 - 1) * np.sin(r) / r - 3 * np.cos(r) / r**2) + * (-3 * np.cos(th) * np.sin(th)) + * (np.sin(phi)) + * np.exp(-t * D * lambd2) + + 1 + ) + def analytic_rad_sol(r, t): th = TH[ith] phi = PHI[iphi] - return analytic_sol(r,th,phi,t) + return analytic_sol(r, th, phi, t) + def analytic_th_sol(th, t): r = R[ir] phi = PHI[iphi] - return analytic_sol(r,th,phi,t) + return analytic_sol(r, th, phi, t) def analytic_phi_sol(phi, t): r = R[ir] th = TH[ith] - return analytic_sol(r,th,phi,t) + return analytic_sol(r, th, phi, t) success = True eps = 6.4e-8 -for it,t in enumerate(list_time): +for it, t in enumerate(list_time): analytic_T = np.zeros((R.shape[0], TH.shape[0], PHI.shape[0])) - for ir,r in enumerate(R): - for ith,th in enumerate(TH): - for iphi,phi in enumerate(PHI): - analytic_T[ir,ith,iphi] = analytic_sol(r,th,phi,t) + for ir, r in enumerate(R): + for ith, th in enumerate(TH): + for iphi, phi in enumerate(PHI): + analytic_T[ir, ith, iphi] = analytic_sol(r, th, phi, t) TEMP = list_T[it] if np.mean(np.fabs(TEMP - analytic_T)) > eps: - success = False + success = False if success: print("SUCCESS") diff --git a/test/MHD/sphBragTDiffusion/testme.py b/test/MHD/sphBragTDiffusion/testme.py index 98e3def92..0d1ca73c9 100755 --- a/test/MHD/sphBragTDiffusion/testme.py +++ b/test/MHD/sphBragTDiffusion/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -13,31 +14,31 @@ def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - name = "dump.0001.dmp" - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest() - if test.init: - test.makeReference(filename=name) - test.nonRegressionTest(filename=name, tolerance=2e-15) + # loop on all the ini files for this test + name = "dump.0001.dmp" + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + if test.init: + test.makeReference(filename=name) + test.nonRegressionTest(filename=name, tolerance=2e-15) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp") - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/MHD/sphBragViscosity/python/testidefix.py b/test/MHD/sphBragViscosity/python/testidefix.py index 7369f636e..84c60dfc6 100644 --- a/test/MHD/sphBragViscosity/python/testidefix.py +++ b/test/MHD/sphBragViscosity/python/testidefix.py @@ -13,10 +13,10 @@ time_step = conf["Output"]["vtk"] nfile = 10 -list_time = [round(i*time_step, 7) for i in range(nfile)] +list_time = [round(i * time_step, 7) for i in range(nfile)] list_VTK = list() for k in range(nfile): - current_VTK = readVTK('../data.00{0:02d}.vtk'.format(k), 'spherical') + current_VTK = readVTK("../data.00{0:02d}.vtk".format(k), "spherical") list_VTK.append(current_VTK) list_VX = list() @@ -27,32 +27,33 @@ list_BY = list() list_BZ = list() for VTK in list_VTK: - list_VX.append(VTK.data['VX1']) - list_VY.append(VTK.data['VX2']) - list_VZ.append(VTK.data['VX3']) - list_BX.append(VTK.data['BX1']) - list_BY.append(VTK.data['BX2']) - list_BZ.append(VTK.data['BX3']) - list_RHO.append(VTK.data['RHO']) + list_VX.append(VTK.data["VX1"]) + list_VY.append(VTK.data["VX2"]) + list_VZ.append(VTK.data["VX3"]) + list_BX.append(VTK.data["BX1"]) + list_BY.append(VTK.data["BX2"]) + list_BZ.append(VTK.data["BX3"]) + list_RHO.append(VTK.data["RHO"]) X = VTK.r Y = VTK.theta Z = VTK.phi mu = conf["Hydro"]["bragViscosity"][-1] + def analytic_sol(r, th, phi, t): - lambd2 = 2. - return amplitude*jn(1,r)/r*np.exp(-t*lambd2*mu) + lambd2 = 2.0 + return amplitude * jn(1, r) / r * np.exp(-t * lambd2 * mu) eps = 7e-7 for k, Vx in enumerate(list_VX): t = list_time[k] - current_sol = np.zeros((len(X),len(Y),len(Z))) - for ix,x in enumerate(X): - for iy,y in enumerate(Y): - for iz,z in enumerate(Z): - current_sol[ix,iy,iz] = analytic_sol(x,y,z,t) + current_sol = np.zeros((len(X), len(Y), len(Z))) + for ix, x in enumerate(X): + for iy, y in enumerate(Y): + for iz, z in enumerate(Z): + current_sol[ix, iy, iz] = analytic_sol(x, y, z, t) if np.mean(abs(current_sol - Vx)) > eps: print("Failed") sys.exit(1) diff --git a/test/MHD/sphBragViscosity/testme.py b/test/MHD/sphBragViscosity/testme.py index 0ad8ef254..47c90c0ef 100755 --- a/test/MHD/sphBragViscosity/testme.py +++ b/test/MHD/sphBragViscosity/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -13,34 +14,34 @@ def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - name = "dump.0001.dmp" - for ini in inifiles: - test.run(inputFile=ini) -## The current test is not physics, but merely a non-regression check -## The physical test needs to have the divergence of the velocity field artifiacially set to zero -# test.standardTest() - if test.init: - test.makeReference(filename=name) + # loop on all the ini files for this test + name = "dump.0001.dmp" + for ini in inifiles: + test.run(inputFile=ini) + ## The current test is not physics, but merely a non-regression check + ## The physical test needs to have the divergence of the velocity field artifiacially set to zero + # test.standardTest() + if test.init: + test.makeReference(filename=name) - test.nonRegressionTest(filename=name, tolerance=1e-15) + test.nonRegressionTest(filename=name, tolerance=1e-15) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename="dump.0001.dmp") - else: - testMe(test) + if test.check: + test.checkOnly(filename="dump.0001.dmp") + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/Planet/Planet3Body/python/testidefix.py b/test/Planet/Planet3Body/python/testidefix.py index 91a680d63..c66176f48 100755 --- a/test/Planet/Planet3Body/python/testidefix.py +++ b/test/Planet/Planet3Body/python/testidefix.py @@ -16,69 +16,91 @@ def separation(resonance): a = int(resonance[-1]) b = int(resonance[0]) - return pow(a/b,2/3) + return pow(a / b, 2 / 3) + def datafile(filename): return np.loadtxt(filename, dtype="float64").T + planet0 = datafile("../planet0.dat") planet1 = datafile("../planet1.dat") resonance = "3:2" plot_orbit = False -theta1 = np.arctan2(planet1[2],planet1[1]) +theta1 = np.arctan2(planet1[2], planet1[1]) apl1 = 1.0 ecc1 = 0.0 -rpl1 = (apl1*(1-ecc1**2)/(1-ecc1*np.cos(theta1))) -xpl1 = rpl1*np.cos(theta1) -ypl1 = rpl1*np.sin(theta1) +rpl1 = apl1 * (1 - ecc1**2) / (1 - ecc1 * np.cos(theta1)) +xpl1 = rpl1 * np.cos(theta1) +ypl1 = rpl1 * np.sin(theta1) -theta0 = np.arctan2(planet0[2],planet0[1]) +theta0 = np.arctan2(planet0[2], planet0[1]) apl0 = separation(resonance) ecc0 = 0.2 -rpl0 = (apl0*(1-ecc0**2)/(1+ecc0*np.cos(theta0))) -xpl0 = rpl0*np.cos(theta0) -ypl0 = rpl0*np.sin(theta0) +rpl0 = apl0 * (1 - ecc0**2) / (1 + ecc0 * np.cos(theta0)) +xpl0 = rpl0 * np.cos(theta0) +ypl0 = rpl0 * np.sin(theta0) if plot_orbit: import matplotlib.pyplot as plt + plt.close("all") - fig, ax = plt.subplots(figsize=(6,6)) + fig, ax = plt.subplots(figsize=(6, 6)) ax.scatter(planet0[1], planet0[2], ls="-", c="k") ax.scatter(planet1[1], planet1[2], ls="--", c="r") - ax.scatter(0,0,marker="+") + ax.scatter(0, 0, marker="+") ax.plot(xpl0, ypl0, c="b") ax.plot(xpl1, ypl1, c="g") - ax.set(xlabel="x", ylabel="y", aspect="equal", xlim=(-1.2,1.2), ylim=(-1.2,1.2)) + ax.set(xlabel="x", ylabel="y", aspect="equal", xlim=(-1.2, 1.2), ylim=(-1.2, 1.2)) # ax.set(xlabel="x", ylabel="y", aspect="equal", xlim=(-2.5,2.5), ylim=(-2.5,2.5)) - ax.set_title(r"m$_{\rm sat}=0$, e=%.1f, n/n$_s$=%s (a0=%.3f)"%(ecc0,resonance,separation(resonance=resonance)), pad=20) + ax.set_title( + r"m$_{\rm sat}=0$, e=%.1f, n/n$_s$=%s (a0=%.3f)" + % (ecc0, resonance, separation(resonance=resonance)), + pad=20, + ) # plt.savefig(f"resonance{resonance}_e{ecc}.png", dpi=200) fig.tight_layout() - fig2, ax2 = plt.subplots(figsize=(6,6)) - ax2.scatter(theta0, (rpl0-np.sqrt(planet0[1]**2 + planet0[2]**2))/(rpl0), c="b", s=200) - ax2.scatter(theta1, (rpl1-np.sqrt(planet1[1]**2 + planet1[2]**2))/(rpl1), c="g", s=200) + fig2, ax2 = plt.subplots(figsize=(6, 6)) + ax2.scatter( + theta0, + (rpl0 - np.sqrt(planet0[1] ** 2 + planet0[2] ** 2)) / (rpl0), + c="b", + s=200, + ) + ax2.scatter( + theta1, + (rpl1 - np.sqrt(planet1[1] ** 2 + planet1[2] ** 2)) / (rpl1), + c="g", + s=200, + ) plt.show() -rpl0_sim = np.sqrt(planet0[1]**2 + planet0[2]**2) -rpl1_sim = np.sqrt(planet1[1]**2 + planet1[2]**2) +rpl0_sim = np.sqrt(planet0[1] ** 2 + planet0[2] ** 2) +rpl1_sim = np.sqrt(planet1[1] ** 2 + planet1[2] ** 2) -mean0 = np.mean(100*(rpl0-rpl0_sim)/rpl0) -mean1 = np.mean(100*(rpl1-rpl1_sim)/rpl1) -std0 = np.std(100*(rpl0-rpl0_sim)/rpl0) -std1 = np.std(100*(rpl1-rpl1_sim)/rpl1) +mean0 = np.mean(100 * (rpl0 - rpl0_sim) / rpl0) +mean1 = np.mean(100 * (rpl1 - rpl1_sim) / rpl1) +std0 = np.std(100 * (rpl0 - rpl0_sim) / rpl0) +std1 = np.std(100 * (rpl1 - rpl1_sim) / rpl1) error_mean0 = mean0 error_mean1 = mean1 -error_dispersion0 = np.max([abs(mean0+std0),abs(mean0-std0)]) -error_dispersion1 = np.max([abs(mean1+std1),abs(mean1-std1)]) - -print("Mean Error (planet0)=%s"%error_mean0) -print("Mean Error (planet1)=%s"%error_mean1) -print("max(mean +/- std) (planet0)=%s"%error_dispersion0) -print("max(mean +/- std) (planet1)=%s"%error_dispersion1) -if error_mean0<1.0e-10 and error_dispersion0<1.0e-9 and error_mean1<1.0e-10 and error_dispersion1<1.0e-9: +error_dispersion0 = np.max([abs(mean0 + std0), abs(mean0 - std0)]) +error_dispersion1 = np.max([abs(mean1 + std1), abs(mean1 - std1)]) + +print("Mean Error (planet0)=%s" % error_mean0) +print("Mean Error (planet1)=%s" % error_mean1) +print("max(mean +/- std) (planet0)=%s" % error_dispersion0) +print("max(mean +/- std) (planet1)=%s" % error_dispersion1) +if ( + error_mean0 < 1.0e-10 + and error_dispersion0 < 1.0e-9 + and error_mean1 < 1.0e-10 + and error_dispersion1 < 1.0e-9 +): print("SUCCESS!") sys.exit(0) else: diff --git a/test/Planet/Planet3Body/testme.py b/test/Planet/Planet3Body/testme.py index bdb0e193b..4a54d197c 100755 --- a/test/Planet/Planet3Body/testme.py +++ b/test/Planet/Planet3Body/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,38 +12,39 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 2e-11 -tolerance=2e-11 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/Planet/PlanetMigration2D/python/testidefix.py b/test/Planet/PlanetMigration2D/python/testidefix.py index 0a47d24f7..3414df983 100755 --- a/test/Planet/PlanetMigration2D/python/testidefix.py +++ b/test/Planet/PlanetMigration2D/python/testidefix.py @@ -16,36 +16,38 @@ def datafile(filename): return np.loadtxt(filename, dtype="float64").T + plot = False planet_ref = datafile("planet0.ref.dat") planet = datafile("../planet0.dat") -migration_ref = np.sqrt(planet_ref[1]**2+planet_ref[2]**2+planet_ref[3]**2) -migration = np.sqrt(planet[1]**2+planet[2]**2+planet[3]**2) +migration_ref = np.sqrt(planet_ref[1] ** 2 + planet_ref[2] ** 2 + planet_ref[3] ** 2) +migration = np.sqrt(planet[1] ** 2 + planet[2] ** 2 + planet[3] ** 2) # Compute the error on the planet distance -error_d=np.max(np.abs((migration-migration_ref)/migration_ref)) +error_d = np.max(np.abs((migration - migration_ref) / migration_ref)) torque_ref = datafile("tqwk0.ref.dat") torque = datafile("../tqwk0.dat") -tq_tot_ref = torque_ref[1]+torque_ref[2] -tq_tot = torque[1]+torque[2] +tq_tot_ref = torque_ref[1] + torque_ref[2] +tq_tot = torque[1] + torque[2] # Compute the error on the planet torque -error_t=np.max(np.abs((tq_tot-tq_tot_ref)/tq_tot_ref)) +error_t = np.max(np.abs((tq_tot - tq_tot_ref) / tq_tot_ref)) if plot: import matplotlib.pyplot as plt + plt.close("all") - fig, ax = plt.subplots(figsize=(6,6)) + fig, ax = plt.subplots(figsize=(6, 6)) ax.plot(planet_ref[-1], migration_ref, ls="-", c="k", label="dist ref") ax.plot(planet[-1], migration, ls="--", c="r", label="dist new") ax.set(xlabel="time") fig.tight_layout() ax.legend(frameon=False) - fig2, ax2 = plt.subplots(figsize=(6,6)) + fig2, ax2 = plt.subplots(figsize=(6, 6)) ax2.plot(torque_ref[-1], tq_tot_ref, ls="-", c="k", label="torque ref") ax2.plot(torque[-1], tq_tot, ls="--", c="r", label="torque new") ax2.set(xlabel="time") @@ -53,12 +55,12 @@ def datafile(filename): ax2.legend(frameon=False) plt.show() -diff_torque = np.max(np.abs(tq_tot-tq_tot_ref)) -print("diff_torque=%e"%diff_torque) -print("Error_dist=%e"%error_d) +diff_torque = np.max(np.abs(tq_tot - tq_tot_ref)) +print("diff_torque=%e" % diff_torque) +print("Error_dist=%e" % error_d) # print("Error_torque=%e"%error_t) # if error_d<5.0e-2 and error_t<5.0e-2 and error_rho<5.0e-2: -if error_d<5.0e-2 and diff_torque<1.0e-15: +if error_d < 5.0e-2 and diff_torque < 1.0e-15: print("SUCCESS!") sys.exit(0) else: diff --git a/test/Planet/PlanetMigration2D/testme.py b/test/Planet/PlanetMigration2D/testme.py index 7aff376d0..94c277343 100755 --- a/test/Planet/PlanetMigration2D/testme.py +++ b/test/Planet/PlanetMigration2D/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,40 +12,41 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-13 -tolerance=1e-13 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/Planet/PlanetPlanetRK42D/python/testidefix.py b/test/Planet/PlanetPlanetRK42D/python/testidefix.py index 656e55c28..fdb4aa2a0 100755 --- a/test/Planet/PlanetPlanetRK42D/python/testidefix.py +++ b/test/Planet/PlanetPlanetRK42D/python/testidefix.py @@ -16,15 +16,16 @@ def filter_index(t): # get read of data previously generated (when the code was restarted) - tref=t[-1] - idx=np.array([2]) - idx[0]=t.size-1 - for i in range(t.size-2,0,-1): - if(t[i] 0: - integ = ( - np.nansum( - (data * dR)[k : kk + 1], - dtype="float64", - ) + integ = np.nansum( + (data * dR)[k : kk + 1], + dtype="float64", ) else: integ = -( @@ -97,8 +101,9 @@ def _integral( ) return integ + # Phase equation for m,n -#(phi-wavenumber,order of the spiral) +# (phi-wavenumber,order of the spiral) def phaseEquation( RR, *, @@ -108,17 +113,22 @@ def phaseEquation( Rp=Rp, info=False, ): - phieq = -np.sign(RR-Rp)*np.pi/4/m + 2*np.pi*n/m -_integral( - RR, - resonance=resonance, - m=mdom, - Rp=Rp, - h0=h0, - flaring=flaring, - info=info, - ) + phieq = ( + -np.sign(RR - Rp) * np.pi / 4 / m + + 2 * np.pi * n / m + - _integral( + RR, + resonance=resonance, + m=mdom, + Rp=Rp, + h0=h0, + flaring=flaring, + info=info, + ) + ) return phieq + plot = False RwkzMin = find_nearest(Rmed, 0.7) @@ -127,45 +137,45 @@ def phaseEquation( spiralR = [] spiralP = [] spiralP_theo = [] -for ir in range(RwkzMin, RwkzMax+1): - if (Rmed[ir] < Rmm): - rho = ds.data["RHO"][ir,:,0] +for ir in range(RwkzMin, RwkzMax + 1): + if Rmed[ir] < Rmm: + rho = ds.data["RHO"][ir, :, 0] spiralR.append(Rmed[ir]) - spiralP.append(phimed[find_nearest(rho,rho.max())]) - spiralP_theo.append(phaseEquation(Rmed[ir],resonance=-1)) - if (Rmed[ir] > Rmp): - rho = ds.data["RHO"][ir,:,0] + spiralP.append(phimed[find_nearest(rho, rho.max())]) + spiralP_theo.append(phaseEquation(Rmed[ir], resonance=-1)) + if Rmed[ir] > Rmp: + rho = ds.data["RHO"][ir, :, 0] spiralR.append(Rmed[ir]) - spiralP.append(phimed[find_nearest(rho,rho.max())]) - spiralP_theo.append(phaseEquation(Rmed[ir],resonance=+1)) + spiralP.append(phimed[find_nearest(rho, rho.max())]) + spiralP_theo.append(phaseEquation(Rmed[ir], resonance=+1)) spiralR_theo = spiralR spiralP = np.array(spiralP) -spiralP_theo = (np.array(spiralP_theo)/(np.pi))%2*np.pi-np.pi +spiralP_theo = (np.array(spiralP_theo) / (np.pi)) % 2 * np.pi - np.pi if plot: - fig, ax = plt.subplots(figsize=(5,4)) + fig, ax = plt.subplots(figsize=(5, 4)) ax.axvline(x=1.0, ls="--", c="k") - ax.scatter(spiralR_theo,spiralP_theo, c="r",marker="+", label="theoretical") - ax.scatter(spiralR,spiralP,c="k",marker="x", label=r"max $\rho$ simulation") + ax.scatter(spiralR_theo, spiralP_theo, c="r", marker="+", label="theoretical") + ax.scatter(spiralR, spiralP, c="k", marker="x", label=r"max $\rho$ simulation") fig.tight_layout() ax.legend(frameon=False) fig2, ax2 = plt.subplots() - ax2.scatter(spiralR, 100*(spiralP-spiralP_theo)/spiralP_theo) + ax2.scatter(spiralR, 100 * (spiralP - spiralP_theo) / spiralP_theo) fig2.tight_layout() plt.show() -mean = np.mean(100*(spiralP-spiralP_theo)/spiralP_theo) -std = np.std(100*(spiralP-spiralP_theo)/spiralP_theo) +mean = np.mean(100 * (spiralP - spiralP_theo) / spiralP_theo) +std = np.std(100 * (spiralP - spiralP_theo) / spiralP_theo) error_mean = mean -error_dispersion = np.max([abs(mean+std),abs(mean-std)]) +error_dispersion = np.max([abs(mean + std), abs(mean - std)]) -print("Mean Error=%.2f"%error_mean) -print("max(mean +/- std)=%.2f"%error_dispersion) -if error_mean<1.0 and error_dispersion<5.0: +print("Mean Error=%.2f" % error_mean) +print("max(mean +/- std)=%.2f" % error_dispersion) +if error_mean < 1.0 and error_dispersion < 5.0: print("SUCCESS!") sys.exit(0) else: diff --git a/test/Planet/PlanetSpiral2D/testme.py b/test/Planet/PlanetSpiral2D/testme.py index 7aff376d0..94c277343 100755 --- a/test/Planet/PlanetSpiral2D/testme.py +++ b/test/Planet/PlanetSpiral2D/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,40 +12,41 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-13 -tolerance=1e-13 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/Planet/PlanetTorque3D/python/testidefix.py b/test/Planet/PlanetTorque3D/python/testidefix.py index f51b4974b..ce8d911d5 100755 --- a/test/Planet/PlanetTorque3D/python/testidefix.py +++ b/test/Planet/PlanetTorque3D/python/testidefix.py @@ -16,6 +16,7 @@ def datafile(filename): return np.loadtxt(filename, dtype="float64").T + plot = False torque_ref = datafile("tqwk0.ref.dat") @@ -23,18 +24,19 @@ def datafile(filename): # Factor 2 here because the reference has been computed for half the disk # (hence the torque was half) -tq_tot_ref = 2*(torque_ref[1]+torque_ref[2]) -tq_tot = torque[1]+torque[2] -tqh_tot_ref = 2*(torque_ref[3]+torque_ref[4]) -tqh_tot = torque[3]+torque[4] +tq_tot_ref = 2 * (torque_ref[1] + torque_ref[2]) +tq_tot = torque[1] + torque[2] +tqh_tot_ref = 2 * (torque_ref[3] + torque_ref[4]) +tqh_tot = torque[3] + torque[4] # Compute the error on the planet torque -error_t=np.max(np.abs((tq_tot-tq_tot_ref)/tq_tot_ref)) -error_th=np.max(np.abs((tqh_tot-tqh_tot_ref)/tqh_tot_ref)) +error_t = np.max(np.abs((tq_tot - tq_tot_ref) / tq_tot_ref)) +error_th = np.max(np.abs((tqh_tot - tqh_tot_ref) / tqh_tot_ref)) if plot: import matplotlib.pyplot as plt - fig, ax = plt.subplots(figsize=(6,6)) + + fig, ax = plt.subplots(figsize=(6, 6)) ax.plot(torque_ref[-1], tq_tot_ref, ls="-", c="k", label="torque ref") ax.plot(torque[-1], tq_tot, ls="--", c="r", label="torque new") ax.plot(torque_ref[-1], tqh_tot_ref, ls="-", c="b", label="torque nohill ref") @@ -45,14 +47,14 @@ def datafile(filename): plt.show() -diff_torque = np.max(np.abs(tq_tot-tq_tot_ref)) -diff_torqueh = np.max(np.abs(tqh_tot-tqh_tot_ref)) -print("diff_torque=%e"%diff_torque) -print("diff_torque_nohill=%e"%diff_torqueh) +diff_torque = np.max(np.abs(tq_tot - tq_tot_ref)) +diff_torqueh = np.max(np.abs(tqh_tot - tqh_tot_ref)) +print("diff_torque=%e" % diff_torque) +print("diff_torque_nohill=%e" % diff_torqueh) # print("Error_torque=%e"%error_t) # print("Error_torque_nohill=%e"%error_th) # if error_t<5.0e-2 and error_th<5.0e-2 and error_rho<5.0e-2: -if diff_torque<1.0e-12 and diff_torqueh<1.0e-13: +if diff_torque < 1.0e-12 and diff_torqueh < 1.0e-13: print("SUCCESS!") sys.exit(0) else: diff --git a/test/Planet/PlanetTorque3D/testme.py b/test/Planet/PlanetTorque3D/testme.py index d68987dfa..ab5e88603 100755 --- a/test/Planet/PlanetTorque3D/testme.py +++ b/test/Planet/PlanetTorque3D/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,40 +12,41 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-13 -tolerance=1e-13 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - if test.init and not test.mpi: - test.makeReference(filename=name) - test.standardTest() - test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + if test.init and not test.mpi: + test.makeReference(filename=name) + test.standardTest() + test.nonRegressionTest(filename=name, tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2','2'] + test.dec = ["2", "2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py index c39f51784..0baa46a21 100755 --- a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py +++ b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py @@ -18,12 +18,15 @@ def find_nearest(array, value): idx = (np.abs(array - value)).argmin() return idx + def datafile(filename): return np.loadtxt(filename, dtype="float64").T + def time_dist(filename): columns = datafile(filename) - return(columns[-1], np.sqrt(columns[1]**2+columns[2]**2+columns[3]**2)) + return (columns[-1], np.sqrt(columns[1] ** 2 + columns[2] ** 2 + columns[3] ** 2)) + plot = False @@ -41,14 +44,15 @@ def time_dist(filename): time1, dist1 = time_dist("../planet1.dat") # Compute the error on the planet distance -error_d0=np.max(np.abs((dist0-dist0_rk5)/dist0_rk5)) -error_d1=np.max(np.abs((dist1-dist1_rk5)/dist1_rk5)) +error_d0 = np.max(np.abs((dist0 - dist0_rk5) / dist0_rk5)) +error_d1 = np.max(np.abs((dist1 - dist1_rk5) / dist1_rk5)) if plot: import matplotlib.pyplot as plt + plt.close("all") - fig, ax = plt.subplots(figsize=(6,6)) + fig, ax = plt.subplots(figsize=(6, 6)) ax.plot(time0_rk5, dist0_rk5, ls="-", c="k", label="dist 0 rk5") ax.plot(time0, dist0, ls="--", c="r", label="dist 0 new") ax.plot(time1_rk5, dist1_rk5, ls="-", c="b", label="dist 1 rk5") @@ -56,7 +60,7 @@ def time_dist(filename): ax.set(xlabel="time") fig.tight_layout() ax.legend(frameon=False) - fig1, ax1 = plt.subplots(figsize=(6,6)) + fig1, ax1 = plt.subplots(figsize=(6, 6)) ax1.plot(time0_active, active0, ls="-", c="k", label="isActive 0") ax1.plot(time1_active, active1, ls="--", c="r", label="isActive 1") ax1.axvline(x=time0_active[i0_active], c="k", ls=":") @@ -66,11 +70,19 @@ def time_dist(filename): ax1.legend(frameon=False) plt.show() -print("Error_dist0=%e"%error_d0) -print("Error_dist1=%e"%error_d1) -print("active0[ip0]=%e"%active0[i0_active]) -print("active1[ip1]=%e, active1[ip1-1]=%e"%(active1[i1_active],active1[i1_active-1])) -if error_d0<5.0e-10 and error_d1<5.0e-10 and active0[i0_active]==1.0 and active1[i1_active]==1.0 and active1[i1_active-1]==0.0: +print("Error_dist0=%e" % error_d0) +print("Error_dist1=%e" % error_d1) +print("active0[ip0]=%e" % active0[i0_active]) +print( + "active1[ip1]=%e, active1[ip1-1]=%e" % (active1[i1_active], active1[i1_active - 1]) +) +if ( + error_d0 < 5.0e-10 + and error_d1 < 5.0e-10 + and active0[i0_active] == 1.0 + and active1[i1_active] == 1.0 + and active1[i1_active - 1] == 0.0 +): print("SUCCESS!") sys.exit(0) else: diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.py b/test/Planet/PlanetsIsActiveRK52D/testme.py index 562334d58..769be8fbf 100755 --- a/test/Planet/PlanetsIsActiveRK52D/testme.py +++ b/test/Planet/PlanetsIsActiveRK52D/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,38 +12,39 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-13 -tolerance=1e-13 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix-rk4.ini", "idefix-rk5.ini"] + test.configure() + test.compile() + inifiles = ["idefix-rk4.ini", "idefix-rk5.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest() - # test.nonRegressionTest(filename=name,tolerance=tolerance) + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() + # test.nonRegressionTest(filename=name,tolerance=tolerance) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.dec: - test.dec=['2','2'] + test.dec = ["2", "2"] if not test.all: - if(test.check): - test.checkOnly(filename=name,tolerance=tolerance) - else: - testMe(test) + if test.check: + test.checkOnly(filename=name, tolerance=tolerance) + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) - - test.mpi=True - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) + + test.mpi = True + testMe(test) diff --git a/test/Pluto/HD/sod/python/idefixTools.py b/test/Pluto/HD/sod/python/idefixTools.py index 06e63afa8..5dd73f7bf 100644 --- a/test/Pluto/HD/sod/python/idefixTools.py +++ b/test/Pluto/HD/sod/python/idefixTools.py @@ -5,373 +5,385 @@ @author: glesur """ - import numpy as np class DataStructure: pass + # Read a vtk file def readVTKCart(filename): try: - fid=open(filename,"rb") + fid = open(filename, "rb") except: print("Can't open file") return 0 # define our datastructure - V=DataStructure() + V = DataStructure() # raw data which will be read from the file - V.data={} + V.data = {} - #print("Hello") + # print("Hello") # datatype we read - dt=np.dtype(">f") # Big endian single precision floats + dt = np.dtype(">f") # Big endian single precision floats - s=fid.readline() # VTK DataFile Version x.x - s=fid.readline() # Comments + s = fid.readline() # VTK DataFile Version x.x + s = fid.readline() # Comments - s=fid.readline() # BINARY - s=fid.readline() # DATASET RECTILINEAR_GRID - slist=s.split() - grid_type=str(slist[1],'utf-8') - if(grid_type != "RECTILINEAR_GRID"): + s = fid.readline() # BINARY + s = fid.readline() # DATASET RECTILINEAR_GRID + slist = s.split() + grid_type = str(slist[1], "utf-8") + if grid_type != "RECTILINEAR_GRID": print("ERROR: Wrong VTK file type.") print("This routine can only open Cartesian or Cylindrical VTK files.") fid.close() return 0 - s=fid.readline() # DIMENSIONS NX NY NZ - slist=s.split() - #s=fid.readline() # Extre line feed - V.nx=int(slist[1]) - V.ny=int(slist[2]) - V.nz=int(slist[3]) - - s=fid.readline() # X_COORDINATES NX float - - x=np.fromfile(fid,dt,V.nx) - s=fid.readline() # Extra line feed added by pluto + s = fid.readline() # DIMENSIONS NX NY NZ + slist = s.split() + # s=fid.readline() # Extre line feed + V.nx = int(slist[1]) + V.ny = int(slist[2]) + V.nz = int(slist[3]) + s = fid.readline() # X_COORDINATES NX float - s=fid.readline() # X_COORDINATES NX float + x = np.fromfile(fid, dt, V.nx) + s = fid.readline() # Extra line feed added by pluto - y=np.fromfile(fid,dt,V.ny) - s=fid.readline() # Extra line feed added by pluto + s = fid.readline() # X_COORDINATES NX float - s=fid.readline() # X_COORDINATES NX float + y = np.fromfile(fid, dt, V.ny) + s = fid.readline() # Extra line feed added by pluto - z=np.fromfile(fid,dt,V.nz) - s=fid.readline() # Extra line feed added by pluto + s = fid.readline() # X_COORDINATES NX float + z = np.fromfile(fid, dt, V.nz) + s = fid.readline() # Extra line feed added by pluto + s = fid.readline() # POINT_DATA NXNYNZ - s=fid.readline() # POINT_DATA NXNYNZ + slist = s.split() + point_type = str(slist[0], "utf-8") + npoints = int(slist[1]) + s = fid.readline() # EXTRA LINE FEED - slist=s.split() - point_type=str(slist[0],'utf-8') - npoints=int(slist[1]) - s=fid.readline() # EXTRA LINE FEED - - if(point_type == "CELL_DATA"): + if point_type == "CELL_DATA": # The file contains face coordinates, so we extrapolate to get the cell center coordinates. - if V.nx>1: - V.nx=V.nx-1 - V.x=0.5*(x[1:]+x[:-1]) + if V.nx > 1: + V.nx = V.nx - 1 + V.x = 0.5 * (x[1:] + x[:-1]) else: - V.x=x - if V.ny>1: - V.ny=V.ny-1 - V.y=0.5*(y[1:]+y[:-1]) + V.x = x + if V.ny > 1: + V.ny = V.ny - 1 + V.y = 0.5 * (y[1:] + y[:-1]) else: - V.y=y - if V.nz>1: - V.nz=V.nz-1 - V.z=0.5*(z[1:]+z[:-1]) + V.y = y + if V.nz > 1: + V.nz = V.nz - 1 + V.z = 0.5 * (z[1:] + z[:-1]) else: - V.z=z - elif(point_type == "POINT_DATA"): - V.x=x - V.y=y - V.z=z + V.z = z + elif point_type == "POINT_DATA": + V.x = x + V.y = y + V.z = z - if V.nx*V.ny*V.nz != npoints: + if V.nx * V.ny * V.nz != npoints: print("ERROR: Grid size incompatible with number of points in the data set") while 1: - s=fid.readline() # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) - #print repr(s) - if len(s)<2: # leave if end of file + s = ( + fid.readline() + ) # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) + # print repr(s) + if len(s) < 2: # leave if end of file break - slist=s.split() - datatype=str(slist[0],'utf-8') - varname=str(slist[1],'utf-8') + slist = s.split() + datatype = str(slist[0], "utf-8") + varname = str(slist[1], "utf-8") if datatype == "SCALARS": fid.readline() # LOOKUP TABLE - V.data[varname] = np.transpose(np.fromfile(fid,dt,V.nx*V.ny*V.nz).reshape(V.nz,V.ny,V.nx)) + V.data[varname] = np.transpose( + np.fromfile(fid, dt, V.nx * V.ny * V.nz).reshape(V.nz, V.ny, V.nx) + ) elif datatype == "VECTORS": - Q=np.fromfile(fid,dt,3*V.nx*V.ny*V.nz) + Q = np.fromfile(fid, dt, 3 * V.nx * V.ny * V.nz) - V.data[varname+'_X']=np.transpose(Q[::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Y']=np.transpose(Q[1::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Z']=np.transpose(Q[2::3].reshape(V.nz,V.ny,V.nx)) + V.data[varname + "_X"] = np.transpose(Q[::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Y"] = np.transpose(Q[1::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Z"] = np.transpose(Q[2::3].reshape(V.nz, V.ny, V.nx)) else: print("ERROR: Unknown datatype %s" % datatype) - break; + break - fid.readline() #extra line feed + fid.readline() # extra line feed fid.close() return V + # Read a vtk file def readVTKPolar(filename): try: - fid=open(filename,"rb") + fid = open(filename, "rb") except: print("Can't open file") return 0 # define our datastructure - V=DataStructure() + V = DataStructure() # raw data which will be read from the file - V.data={} + V.data = {} - #print("Hello") + # print("Hello") # datatype we read - dt=np.dtype(">f") # Big endian single precision floats + dt = np.dtype(">f") # Big endian single precision floats - s=fid.readline() # VTK DataFile Version x.x - s=fid.readline() # Comments + s = fid.readline() # VTK DataFile Version x.x + s = fid.readline() # Comments - s=fid.readline() # BINARY - s=fid.readline() # DATASET RECTILINEAR_GRID + s = fid.readline() # BINARY + s = fid.readline() # DATASET RECTILINEAR_GRID print(s) - slist=s.split() - grid_type=str(slist[1],'utf-8') - if(grid_type != "STRUCTURED_GRID"): + slist = s.split() + grid_type = str(slist[1], "utf-8") + if grid_type != "STRUCTURED_GRID": print("ERROR: Wrong VTK file type.") - print("Current type is: %s"%(grid_type)) + print("Current type is: %s" % (grid_type)) print("This routine can only open Polar VTK files.") fid.close() return 0 - s=fid.readline() # DIMENSIONS NX NY NZ - slist=s.split() - V.nx=int(slist[1]) - V.ny=int(slist[2]) - V.nz=int(slist[3]) + s = fid.readline() # DIMENSIONS NX NY NZ + slist = s.split() + V.nx = int(slist[1]) + V.ny = int(slist[2]) + V.nz = int(slist[3]) - print("nx=%d, ny=%d, nz=%d"%(V.nx,V.ny,V.nz)) + print("nx=%d, ny=%d, nz=%d" % (V.nx, V.ny, V.nz)) - s=fid.readline() # POINTS NXNYNZ float - slist=s.split() - npoints=int(slist[1]) - points=np.fromfile(fid,dt,3*npoints) - s=fid.readline() # EXTRA LINE FEED + s = fid.readline() # POINTS NXNYNZ float + slist = s.split() + npoints = int(slist[1]) + points = np.fromfile(fid, dt, 3 * npoints) + s = fid.readline() # EXTRA LINE FEED - V.points=points + V.points = points - if V.nx*V.ny*V.nz != npoints: + if V.nx * V.ny * V.nz != npoints: print("ERROR: Grid size incompatible with number of points in the data set") return 0 # Reconstruct the polar coordinate system - x1d=points[::3] - y1d=points[1::3] - z1d=points[2::3] - - xcart=np.transpose(x1d.reshape(V.nz,V.ny,V.nx)) - ycart=np.transpose(y1d.reshape(V.nz,V.ny,V.nx)) - zcart=np.transpose(z1d.reshape(V.nz,V.ny,V.nx)) - - r=np.sqrt(xcart[:,0,0]**2+ycart[:,0,0]**2) - theta=np.unwrap(np.arctan2(ycart[0,:,0],xcart[0,:,0])) - z=zcart[0,0,:] - - s=fid.readline() # CELL_DATA (NX-1)(NY-1)(NZ-1) - slist=s.split() - data_type=str(slist[0],'utf-8') - if(data_type != "CELL_DATA"): + x1d = points[::3] + y1d = points[1::3] + z1d = points[2::3] + + xcart = np.transpose(x1d.reshape(V.nz, V.ny, V.nx)) + ycart = np.transpose(y1d.reshape(V.nz, V.ny, V.nx)) + zcart = np.transpose(z1d.reshape(V.nz, V.ny, V.nx)) + + r = np.sqrt(xcart[:, 0, 0] ** 2 + ycart[:, 0, 0] ** 2) + theta = np.unwrap(np.arctan2(ycart[0, :, 0], xcart[0, :, 0])) + z = zcart[0, 0, :] + + s = fid.readline() # CELL_DATA (NX-1)(NY-1)(NZ-1) + slist = s.split() + data_type = str(slist[0], "utf-8") + if data_type != "CELL_DATA": print("ERROR: this routine expect CELL DATA as produced by PLUTO.") fid.close() return 0 - s=fid.readline() # Line feed + s = fid.readline() # Line feed # Perform averaging on coordinate system to get cell centers # The file contains face coordinates, so we extrapolate to get the cell center coordinates. - if V.nx>1: - V.nx=V.nx-1 - V.x=0.5*(r[1:]+r[:-1]) + if V.nx > 1: + V.nx = V.nx - 1 + V.x = 0.5 * (r[1:] + r[:-1]) else: - V.x=r - if V.ny>1: - V.ny=V.ny-1 - V.y=(0.5*(theta[1:]+theta[:-1])+np.pi)%(2.0*np.pi)-np.pi + V.x = r + if V.ny > 1: + V.ny = V.ny - 1 + V.y = (0.5 * (theta[1:] + theta[:-1]) + np.pi) % (2.0 * np.pi) - np.pi else: - V.y=theta - if V.nz>1: - V.nz=V.nz-1 - V.z=0.5*(z[1:]+z[:-1]) + V.y = theta + if V.nz > 1: + V.nz = V.nz - 1 + V.z = 0.5 * (z[1:] + z[:-1]) else: - V.z=z - + V.z = z while 1: - s=fid.readline() # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) - #print repr(s) - if len(s)<2: # leave if end of file + s = ( + fid.readline() + ) # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) + # print repr(s) + if len(s) < 2: # leave if end of file break - slist=s.split() - datatype=str(slist[0],'utf-8') - varname=str(slist[1],'utf-8') + slist = s.split() + datatype = str(slist[0], "utf-8") + varname = str(slist[1], "utf-8") if datatype == "SCALARS": fid.readline() # LOOKUP TABLE - V.data[varname] = np.transpose(np.fromfile(fid,dt,V.nx*V.ny*V.nz).reshape(V.nz,V.ny,V.nx)) + V.data[varname] = np.transpose( + np.fromfile(fid, dt, V.nx * V.ny * V.nz).reshape(V.nz, V.ny, V.nx) + ) elif datatype == "VECTORS": - Q=np.fromfile(fid,dt,3*V.nx*V.ny*V.nz) + Q = np.fromfile(fid, dt, 3 * V.nx * V.ny * V.nz) - V.data[varname+'_X']=np.transpose(Q[::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Y']=np.transpose(Q[1::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Z']=np.transpose(Q[2::3].reshape(V.nz,V.ny,V.nx)) + V.data[varname + "_X"] = np.transpose(Q[::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Y"] = np.transpose(Q[1::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Z"] = np.transpose(Q[2::3].reshape(V.nz, V.ny, V.nx)) else: print("ERROR: Unknown datatype %s" % datatype) - break; + break - fid.readline() #extra line feed + fid.readline() # extra line feed fid.close() return V + # Read a vtk file def readVTKSpherical(filename): try: - fid=open(filename,"rb") + fid = open(filename, "rb") except: print("Can't open file") return 0 # define our datastructure - V=DataStructure() + V = DataStructure() # raw data which will be read from the file - V.data={} + V.data = {} - #print("Hello") + # print("Hello") # datatype we read - dt=np.dtype(">f") # Big endian single precision floats + dt = np.dtype(">f") # Big endian single precision floats - s=fid.readline() # VTK DataFile Version x.x - s=fid.readline() # Comments + s = fid.readline() # VTK DataFile Version x.x + s = fid.readline() # Comments - s=fid.readline() # BINARY - s=fid.readline() # DATASET RECTILINEAR_GRID - slist=s.split() - grid_type=str(slist[1],'utf-8') - if(grid_type != "STRUCTURED_GRID"): + s = fid.readline() # BINARY + s = fid.readline() # DATASET RECTILINEAR_GRID + slist = s.split() + grid_type = str(slist[1], "utf-8") + if grid_type != "STRUCTURED_GRID": print("ERROR: Wrong VTK file type.") print("This routine can only open Spherical VTK files.") fid.close() return 0 - s=fid.readline() # DIMENSIONS NX NY NZ - slist=s.split() - V.nx=int(slist[1]) - V.ny=int(slist[2]) - V.nz=int(slist[3]) + s = fid.readline() # DIMENSIONS NX NY NZ + slist = s.split() + V.nx = int(slist[1]) + V.ny = int(slist[2]) + V.nz = int(slist[3]) - if(V.nz==1): - is2d=1 + if V.nz == 1: + is2d = 1 else: - is2d=0 + is2d = 0 - s=fid.readline() # POINTS NXNYNZ float - slist=s.split() - npoints=int(slist[1]) - points=np.fromfile(fid,dt,3*npoints) - s=fid.readline() # EXTRA LINE FEED + s = fid.readline() # POINTS NXNYNZ float + slist = s.split() + npoints = int(slist[1]) + points = np.fromfile(fid, dt, 3 * npoints) + s = fid.readline() # EXTRA LINE FEED - V.points=points + V.points = points - if V.nx*V.ny*V.nz != npoints: + if V.nx * V.ny * V.nz != npoints: print("ERROR: Grid size incompatible with number of points in the data set") return 0 # Reconstruct the spherical coordinate system + x1d = points[::3] + y1d = points[1::3] + z1d = points[2::3] - x1d=points[::3] - y1d=points[1::3] - z1d=points[2::3] + xcart = np.transpose(x1d.reshape(V.nz, V.ny, V.nx)) + ycart = np.transpose(y1d.reshape(V.nz, V.ny, V.nx)) + zcart = np.transpose(z1d.reshape(V.nz, V.ny, V.nx)) - xcart=np.transpose(x1d.reshape(V.nz,V.ny,V.nx)) - ycart=np.transpose(y1d.reshape(V.nz,V.ny,V.nx)) - zcart=np.transpose(z1d.reshape(V.nz,V.ny,V.nx)) - - if(is2d): - r=np.sqrt(xcart[:,0,0]**2+ycart[:,0,0]**2) - phi=np.unwrap(np.arctan2(zcart[0,0,:],xcart[0,0,:])) - theta=np.arccos(ycart[0,:,0]/np.sqrt(xcart[0,:,0]**2+ycart[0,:,0]**2)) + if is2d: + r = np.sqrt(xcart[:, 0, 0] ** 2 + ycart[:, 0, 0] ** 2) + phi = np.unwrap(np.arctan2(zcart[0, 0, :], xcart[0, 0, :])) + theta = np.arccos( + ycart[0, :, 0] / np.sqrt(xcart[0, :, 0] ** 2 + ycart[0, :, 0] ** 2) + ) else: - r=np.sqrt(xcart[:,0,0]**2+ycart[:,0,0]**2+zcart[:,0,0]**2) - phi=np.unwrap(np.arctan2(ycart[0,0,:],xcart[0,0,:])) - theta=np.arccos(zcart[0,:,0]/np.sqrt(xcart[0,:,0]**2+ycart[0,:,0]**2+zcart[0,:,0]**2)) - - - s=fid.readline() # CELL_DATA (NX-1)(NY-1)(NZ-1) - slist=s.split() - data_type=str(slist[0],'utf-8') - if(data_type != "CELL_DATA"): + r = np.sqrt(xcart[:, 0, 0] ** 2 + ycart[:, 0, 0] ** 2 + zcart[:, 0, 0] ** 2) + phi = np.unwrap(np.arctan2(ycart[0, 0, :], xcart[0, 0, :])) + theta = np.arccos( + zcart[0, :, 0] + / np.sqrt(xcart[0, :, 0] ** 2 + ycart[0, :, 0] ** 2 + zcart[0, :, 0] ** 2) + ) + + s = fid.readline() # CELL_DATA (NX-1)(NY-1)(NZ-1) + slist = s.split() + data_type = str(slist[0], "utf-8") + if data_type != "CELL_DATA": print("ERROR: this routine expect CELL DATA as produced by PLUTO.") fid.close() return 0 - s=fid.readline() # Line feed + s = fid.readline() # Line feed # Perform averaging on coordinate system to get cell centers # The file contains face coordinates, so we extrapolate to get the cell center coordinates. - if V.nx>1: - V.nx=V.nx-1 - V.r=0.5*(r[1:]+r[:-1]) + if V.nx > 1: + V.nx = V.nx - 1 + V.r = 0.5 * (r[1:] + r[:-1]) else: - V.x=r - if V.ny>1: - V.ny=V.ny-1 - V.theta=0.5*(theta[1:]+theta[:-1]) + V.x = r + if V.ny > 1: + V.ny = V.ny - 1 + V.theta = 0.5 * (theta[1:] + theta[:-1]) else: - V.y=theta - if V.nz>1: - V.nz=V.nz-1 - V.phi=(0.5*(phi[1:]+phi[:-1])+np.pi)%(2.0*np.pi)-np.pi + V.y = theta + if V.nz > 1: + V.nz = V.nz - 1 + V.phi = (0.5 * (phi[1:] + phi[:-1]) + np.pi) % (2.0 * np.pi) - np.pi else: - V.phi=phi - + V.phi = phi while 1: - s=fid.readline() # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) - #print repr(s) - if len(s)<2: # leave if end of file + s = ( + fid.readline() + ) # SCALARS/VECTORS name data_type (ex: SCALARS imagedata unsigned_char) + # print repr(s) + if len(s) < 2: # leave if end of file break - slist=s.split() - datatype=str(slist[0],'utf-8') - varname=str(slist[1],'utf-8') + slist = s.split() + datatype = str(slist[0], "utf-8") + varname = str(slist[1], "utf-8") if datatype == "SCALARS": fid.readline() # LOOKUP TABLE - V.data[varname] = np.transpose(np.fromfile(fid,dt,V.nx*V.ny*V.nz).reshape(V.nz,V.ny,V.nx)) + V.data[varname] = np.transpose( + np.fromfile(fid, dt, V.nx * V.ny * V.nz).reshape(V.nz, V.ny, V.nx) + ) elif datatype == "VECTORS": - Q=np.fromfile(fid,dt,3*V.nx*V.ny*V.nz) + Q = np.fromfile(fid, dt, 3 * V.nx * V.ny * V.nz) - V.data[varname+'_X']=np.transpose(Q[::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Y']=np.transpose(Q[1::3].reshape(V.nz,V.ny,V.nx)) - V.data[varname+'_Z']=np.transpose(Q[2::3].reshape(V.nz,V.ny,V.nx)) + V.data[varname + "_X"] = np.transpose(Q[::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Y"] = np.transpose(Q[1::3].reshape(V.nz, V.ny, V.nx)) + V.data[varname + "_Z"] = np.transpose(Q[2::3].reshape(V.nz, V.ny, V.nx)) else: print("ERROR: Unknown datatype %s" % datatype) - break; + break - fid.readline() #extra line feed + fid.readline() # extra line feed fid.close() return V diff --git a/test/Pluto/HD/sod/python/sod.py b/test/Pluto/HD/sod/python/sod.py index 90ad62fe0..99e55b7c4 100755 --- a/test/Pluto/HD/sod/python/sod.py +++ b/test/Pluto/HD/sod/python/sod.py @@ -13,7 +13,7 @@ import scipy.optimize -def sound_speed(gamma, pressure, density, dustFrac=0.): +def sound_speed(gamma, pressure, density, dustFrac=0.0): """ Calculate sound speed, scaled by the dust fraction according to: @@ -23,27 +23,28 @@ def sound_speed(gamma, pressure, density, dustFrac=0.): Where :math:`\epsilon` is the dustFrac """ scale = np.sqrt(1 - dustFrac) - return np.sqrt(gamma * pressure/ density) * scale + return np.sqrt(gamma * pressure / density) * scale -def shock_tube_function(p4, p1, p5, rho1, rho5, gamma, dustFrac=0.): + +def shock_tube_function(p4, p1, p5, rho1, rho5, gamma, dustFrac=0.0): """ Shock tube equation """ - z = (p4 / p5 - 1.) + z = p4 / p5 - 1.0 c1 = sound_speed(gamma, p1, rho1, dustFrac) c5 = sound_speed(gamma, p5, rho5, dustFrac) - gm1 = gamma - 1. - gp1 = gamma + 1. - g2 = 2. * gamma + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 + g2 = 2.0 * gamma - fact = gm1 / g2 * (c5 / c1) * z / np.sqrt(1. + gp1 / g2 * z) - fact = (1. - fact) ** (g2 / gm1) + fact = gm1 / g2 * (c5 / c1) * z / np.sqrt(1.0 + gp1 / g2 * z) + fact = (1.0 - fact) ** (g2 / gm1) return p1 * fact - p4 -def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): +def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.0): """ Compute regions :rtype : tuple @@ -70,18 +71,18 @@ def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): p4 = scipy.optimize.fsolve(shock_tube_function, p1, (p1, p5, rho1, rho5, gamma))[0] # compute post-shock density and velocity - z = (p4 / p5 - 1.) + z = p4 / p5 - 1.0 c5 = sound_speed(gamma, p5, rho5, dustFrac) - gm1 = gamma - 1. - gp1 = gamma + 1. + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 gmfac1 = 0.5 * gm1 / gamma gmfac2 = 0.5 * gp1 / gamma - fact = np.sqrt(1. + gmfac2 * z) + fact = np.sqrt(1.0 + gmfac2 * z) u4 = c5 * z / (gamma * fact) - rho4 = rho5 * (1. + gmfac2 * z) / (1. + gmfac1 * z) + rho4 = rho5 * (1.0 + gmfac2 * z) / (1.0 + gmfac1 * z) # shock speed w = c5 * fact @@ -89,11 +90,11 @@ def calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma=1.4, dustFrac=0.): # compute values at foot of rarefaction p3 = p4 u3 = u4 - rho3 = rho1 * (p3 / p1)**(1. / gamma) + rho3 = rho1 * (p3 / p1) ** (1.0 / gamma) return (p1, rho1, u1), (p3, rho3, u3), (p4, rho4, u4), (p5, rho5, u5), w -def calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac=0.): +def calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac=0.0): """ :return: tuple of positions in the following order -> Head of Rarefaction: xhd, Foot of Rarefaction: xft, @@ -125,21 +126,39 @@ def region_states(pl, pr, region1, region3, region4, region5): where the value is a string, obviously """ if pl > pr: - return {'Region 1': region1, - 'Region 2': 'RAREFACTION', - 'Region 3': region3, - 'Region 4': region4, - 'Region 5': region5} + return { + "Region 1": region1, + "Region 2": "RAREFACTION", + "Region 3": region3, + "Region 4": region4, + "Region 5": region5, + } else: - return {'Region 1': region5, - 'Region 2': region4, - 'Region 3': region3, - 'Region 4': 'RAREFACTION', - 'Region 5': region1} - - -def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, - npts, gamma, t, xi, dustFrac=0.): + return { + "Region 1": region5, + "Region 2": region4, + "Region 3": region3, + "Region 4": "RAREFACTION", + "Region 5": region1, + } + + +def create_arrays( + pl, + pr, + xl, + xr, + positions, + state1, + state3, + state4, + state5, + npts, + gamma, + t, + xi, + dustFrac=0.0, +): """ :return: tuple of x, p, rho and u values across the domain of interest """ @@ -148,8 +167,8 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p3, rho3, u3 = state3 p4, rho4, u4 = state4 p5, rho5, u5 = state5 - gm1 = gamma - 1. - gp1 = gamma + 1. + gm1 = gamma - 1.0 + gp1 = gamma + 1.0 x_arr = np.linspace(xl, xr, npts) rho = np.zeros(npts, dtype=float) @@ -163,10 +182,10 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p[i] = p1 u[i] = u1 elif x < xft: - u[i] = 2. / gp1 * (c1 + (x - xi) / t) - fact = 1. - 0.5 * gm1 * u[i] / c1 - rho[i] = rho1 * fact ** (2. / gm1) - p[i] = p1 * fact ** (2. * gamma / gm1) + u[i] = 2.0 / gp1 * (c1 + (x - xi) / t) + fact = 1.0 - 0.5 * gm1 * u[i] / c1 + rho[i] = rho1 * fact ** (2.0 / gm1) + p[i] = p1 * fact ** (2.0 * gamma / gm1) elif x < xcd: rho[i] = rho3 p[i] = p3 @@ -194,10 +213,10 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, p[i] = p3 u[i] = -u3 elif x < xhd: - u[i] = -2. / gp1 * (c1 + (xi - x) / t) - fact = 1. + 0.5 * gm1 * u[i] / c1 - rho[i] = rho1 * fact ** (2. / gm1) - p[i] = p1 * fact ** (2. * gamma / gm1) + u[i] = -2.0 / gp1 * (c1 + (xi - x) / t) + fact = 1.0 + 0.5 * gm1 * u[i] / c1 + rho[i] = rho1 * fact ** (2.0 / gm1) + p[i] = p1 * fact ** (2.0 * gamma / gm1) else: rho[i] = rho1 p[i] = p1 @@ -206,8 +225,7 @@ def create_arrays(pl, pr, xl, xr, positions, state1, state3, state4, state5, return x_arr, p, rho, u -def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, - dustFrac=0.): +def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, dustFrac=0.0): """ Solves the Sod shock tube problem (i.e. riemann problem) of discontinuity across an interface. @@ -248,34 +266,57 @@ def solve(left_state, right_state, geometry, t, gamma=1.4, npts=500, # basic checking if xl >= xr: - print('xl has to be less than xr!') + print("xl has to be less than xr!") exit() if xi >= xr or xi <= xl: - print('xi has in between xl and xr!') + print("xi has in between xl and xr!") exit() # calculate regions - region1, region3, region4, region5, w = \ - calculate_regions(pl, ul, rhol, pr, ur, rhor, gamma, dustFrac) + region1, region3, region4, region5, w = calculate_regions( + pl, ul, rhol, pr, ur, rhor, gamma, dustFrac + ) regions = region_states(pl, pr, region1, region3, region4, region5) # calculate positions - x_positions = calc_positions(pl, pr, region1, region3, w, xi, t, gamma, - dustFrac) - - pos_description = ('Head of Rarefaction', 'Foot of Rarefaction', - 'Contact Discontinuity', 'Shock') + x_positions = calc_positions(pl, pr, region1, region3, w, xi, t, gamma, dustFrac) + + pos_description = ( + "Head of Rarefaction", + "Foot of Rarefaction", + "Contact Discontinuity", + "Shock", + ) positions = dict(zip(pos_description, x_positions, strict=True)) # create arrays - x, p, rho, u = create_arrays(pl, pr, xl, xr, x_positions, - region1, region3, region4, region5, - npts, gamma, t, xi, dustFrac) - - energy = p/(rho * (gamma - 1.0)) - rho_total = rho/(1.0 - dustFrac) - val_dict = {'x':x, 'p':p, 'rho':rho, 'u':u, 'energy':energy, - 'rho_total':rho_total} + x, p, rho, u = create_arrays( + pl, + pr, + xl, + xr, + x_positions, + region1, + region3, + region4, + region5, + npts, + gamma, + t, + xi, + dustFrac, + ) + + energy = p / (rho * (gamma - 1.0)) + rho_total = rho / (1.0 - dustFrac) + val_dict = { + "x": x, + "p": p, + "rho": rho, + "u": u, + "energy": energy, + "rho_total": rho_total, + } return positions, regions, val_dict diff --git a/test/Pluto/HD/sod/python/testidefix.py b/test/Pluto/HD/sod/python/testidefix.py index 239bb1c86..bdd6daf15 100755 --- a/test/Pluto/HD/sod/python/testidefix.py +++ b/test/Pluto/HD/sod/python/testidefix.py @@ -16,15 +16,14 @@ from scipy.interpolate import interp1d parser = argparse.ArgumentParser() -parser.add_argument("-noplot", - default=False, - help="disable plotting", - action="store_true") +parser.add_argument( + "-noplot", default=False, help="disable plotting", action="store_true" +) -args, unknown=parser.parse_known_args() +args, unknown = parser.parse_known_args() -V=idfx.readVTKCart('../data.0002.vtk') +V = idfx.readVTKCart("../data.0002.vtk") gamma = 1.4 npts = 5000 @@ -34,42 +33,48 @@ # t is the time evolution for which positions and states in tube should be calculated # gamma denotes specific heat # note that gamma and npts are default parameters (1.4 and 500) in solve function -positions, regions, values = sod.solve(left_state=(1, 1, 0), right_state=(0.1, 0.125, 0.), - geometry=(0., 1., 0.5), t=0.2, gamma=gamma, npts=npts) +positions, regions, values = sod.solve( + left_state=(1, 1, 0), + right_state=(0.1, 0.125, 0.0), + geometry=(0.0, 1.0, 0.5), + t=0.2, + gamma=gamma, + npts=npts, +) # Finally, let's plot solutions -p = values['p'] -rho = values['rho'] -u = values['u'] -x= values['x'] +p = values["p"] +rho = values["rho"] +u = values["u"] +x = values["x"] -solinterp=interp1d(x,p) +solinterp = interp1d(x, p) -if(not args.noplot): +if not args.noplot: plt.figure(1) - plt.plot(x,rho) - plt.plot(V.x,V.data['rho'][:,0,0],'+',markersize=2) - plt.title('Density') + plt.plot(x, rho) + plt.plot(V.x, V.data["rho"][:, 0, 0], "+", markersize=2) + plt.title("Density") plt.figure(2) - plt.plot(x,u) - plt.plot(V.x,V.data['vx1'][:,0,0],'+',markersize=2) - plt.title('Velocity') + plt.plot(x, u) + plt.plot(V.x, V.data["vx1"][:, 0, 0], "+", markersize=2) + plt.title("Velocity") plt.figure(3) - plt.plot(x,p) - plt.plot(V.x,V.data['prs'][:,0,0],'+',markersize=2) - plt.title('Pressure') + plt.plot(x, p) + plt.plot(V.x, V.data["prs"][:, 0, 0], "+", markersize=2) + plt.title("Pressure") plt.ioff() plt.show() -error=np.mean(np.fabs(V.data['prs'][:,0,0]-solinterp(V.x))) -print("Error=%e"%error) -if error<1e-2: +error = np.mean(np.fabs(V.data["prs"][:, 0, 0] - solinterp(V.x))) +print("Error=%e" % error) +if error < 1e-2: print("SUCCESS!") sys.exit(0) else: diff --git a/test/SelfGravity/DustyCollapse/python/testidefix.py b/test/SelfGravity/DustyCollapse/python/testidefix.py index 83ec380ac..1ace55c5b 100644 --- a/test/SelfGravity/DustyCollapse/python/testidefix.py +++ b/test/SelfGravity/DustyCollapse/python/testidefix.py @@ -6,18 +6,19 @@ sys.path.append(os.getenv("IDEFIX_DIR")) from pytools.vtk_io import readVTK -G=6.6743e-11 -M=1e16 #mass of spheric clump -r0=1e4 #radius of spheric clump -rmax = 3e4 #right edge of simulation box -d=M/(4*np.pi*r0**3/3) #density of spheric clump -phi0 = -22.247666667 #gravitationnal potential at rmax +G = 6.6743e-11 +M = 1e16 # mass of spheric clump +r0 = 1e4 # radius of spheric clump +rmax = 3e4 # right edge of simulation box +d = M / (4 * np.pi * r0**3 / 3) # density of spheric clump +phi0 = -22.247666667 # gravitationnal potential at rmax + def potential(r): retv = np.empty_like(r) - interior = (r0.01*plateau[-1]: + if np.abs(dsty - plateau[-1]) > 0.01 * plateau[-1]: return np.mean(plateau) else: plateau.append(dsty) return "Error : the whole density distribution is approximately constant !" + # Isolating density plateau -plateau=get_plateau(rho) +plateau = get_plateau(rho) # Calculating absolute error -r_th=time/tff # Theoretical ratio -eta = np.arccos((plateau/rho0)**(-1./6.)) -r_num = 2./np.pi*(eta + 1./2.*np.sin(2.*eta)) # Numerical ratio -error = np.abs(r_num-r_th) # Absolute error +r_th = time / tff # Theoretical ratio +eta = np.arccos((plateau / rho0) ** (-1.0 / 6.0)) +r_num = 2.0 / np.pi * (eta + 1.0 / 2.0 * np.sin(2.0 * eta)) # Numerical ratio +error = np.abs(r_num - r_th) # Absolute error # Print the result of the test -print("Error=%e"%error) -if error<2.0e-3: +print("Error=%e" % error) +if error < 2.0e-3: print("SUCCESS!") sys.exit(0) else: diff --git a/test/SelfGravity/UniformCollapse/testme.py b/test/SelfGravity/UniformCollapse/testme.py index f011cd211..123f417d6 100755 --- a/test/SelfGravity/UniformCollapse/testme.py +++ b/test/SelfGravity/UniformCollapse/testme.py @@ -4,6 +4,7 @@ @author: glesur """ + import os import sys @@ -11,32 +12,33 @@ import pytools.idfx_test as tst -name="dump.0001.dmp" +name = "dump.0001.dmp" + +tolerance = 1e-13 -tolerance=1e-13 def testMe(test): - test.configure() - test.compile() - inifiles=["idefix.ini"] + test.configure() + test.compile() + inifiles = ["idefix.ini"] - # loop on all the ini files for this test - for ini in inifiles: - test.run(inputFile=ini) - test.standardTest() + # loop on all the ini files for this test + for ini in inifiles: + test.run(inputFile=ini) + test.standardTest() -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) if not test.all: - if(test.check): - test.standardTest() - else: - testMe(test) + if test.check: + test.standardTest() + else: + testMe(test) else: - test.noplot = True - test.vectPot=False - test.single=False - test.reconstruction=2 - test.mpi=False - testMe(test) + test.noplot = True + test.vectPot = False + test.single = False + test.reconstruction = 2 + test.mpi = False + testMe(test) diff --git a/test/utils/columnDensity/testme.py b/test/utils/columnDensity/testme.py index 4197a936e..b0a6b5737 100755 --- a/test/utils/columnDensity/testme.py +++ b/test/utils/columnDensity/testme.py @@ -4,13 +4,14 @@ @author: glesur """ + import os import sys sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) test.configure() test.compile() diff --git a/test/utils/dumpImage/testme.py b/test/utils/dumpImage/testme.py index 4197a936e..b0a6b5737 100755 --- a/test/utils/dumpImage/testme.py +++ b/test/utils/dumpImage/testme.py @@ -4,13 +4,14 @@ @author: glesur """ + import os import sys sys.path.append(os.getenv("IDEFIX_DIR")) import pytools.idfx_test as tst -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) test.configure() test.compile() diff --git a/test/utils/lookupTable/testme.py b/test/utils/lookupTable/testme.py index 1bc69a8f2..c02f2b1c3 100755 --- a/test/utils/lookupTable/testme.py +++ b/test/utils/lookupTable/testme.py @@ -4,36 +4,36 @@ @author: glesur """ + import os import sys sys.path.append(os.getenv("IDEFIX_DIR")) import numpy as np -#from scipy.interpolate import RegularGridInterpolator +# from scipy.interpolate import RegularGridInterpolator import pytools.idfx_test as tst def MakeNumpyFile(): - x=np.arange(1,10,1.0) - y=np.arange(5,10,1.0) - z=np.arange(2,5,1.0) - - xp, yp, zp = np.meshgrid(x,y,z,indexing='ij') + x = np.arange(1, 10, 1.0) + y = np.arange(5, 10, 1.0) + z = np.arange(2, 5, 1.0) - data=xp+2*yp-zp + xp, yp, zp = np.meshgrid(x, y, z, indexing="ij") - np.save("x.npy",x) - np.save("y.npy",y) - np.save("z.npy",z) - np.save("data.npy",data) - # show the expected result - #f=RegularGridInterpolator((x, y, z), data) - #print(f([2.7,7.4,3.9])) + data = xp + 2 * yp - zp + np.save("x.npy", x) + np.save("y.npy", y) + np.save("z.npy", z) + np.save("data.npy", data) + # show the expected result + # f=RegularGridInterpolator((x, y, z), data) + # print(f([2.7,7.4,3.9])) -test=tst.idfxTest(__file__) +test = tst.idfxTest(__file__) MakeNumpyFile() test.configure() From 86f46ff753234b438f42c9256623f0e9a9318162 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 17 Aug 2026 10:43:05 +0200 Subject: [PATCH 118/144] Bug: Coarsening+Viscosity (#397) * fix the computation of velocity gradients in the viscosity module when coarsening is enabled. --- src/fluid/viscosity.cpp | 174 +++++++++++++++++++++++++++++----------- 1 file changed, 126 insertions(+), 48 deletions(-) diff --git a/src/fluid/viscosity.cpp b/src/fluid/viscosity.cpp index 038976dd2..5d6d8a65a 100644 --- a/src/fluid/viscosity.cpp +++ b/src/fluid/viscosity.cpp @@ -111,9 +111,9 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D IdefixArray1D x1l = this->data->xl[IDIR]; IdefixArray1D x2l = this->data->xl[JDIR]; IdefixArray1D x3l = this->data->xl[KDIR]; - IdefixArray1D dx1 = this->data->dx[IDIR]; - IdefixArray1D dx2 = this->data->dx[JDIR]; - IdefixArray1D dx3 = this->data->dx[KDIR]; + IdefixArray1D dx1Array = this->data->dx[IDIR]; + IdefixArray1D dx2Array = this->data->dx[JDIR]; + IdefixArray1D dx3Array = this->data->dx[KDIR]; // Fargo variables use to correct energy fluxes #if HAVE_ENERGY @@ -129,6 +129,14 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D IdefixArray1D tanx2m = this->data->tanx2m; #endif + // Coarsening parameters + bool haveGridCoarsening = data->haveGridCoarsening != GridCoarsening::disabled; + bool haveGridCoarseningX1 = data->coarseningDirection[IDIR]; + bool haveGridCoarseningX2 = data->coarseningDirection[JDIR]; + bool haveGridCoarseningX3 = data->coarseningDirection[KDIR]; + auto coarseningLevelX1 = data->coarseningLevel[IDIR]; + auto coarseningLevelX2 = data->coarseningLevel[JDIR]; + auto coarseningLevelX3 = data->coarseningLevel[KDIR]; HydroModuleStatus haveViscosity = this->status.status; @@ -201,18 +209,42 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D etaC2 = eta2 = eta2Constant; } - EXPAND( dVxi = D_DX_I(Vc,VX1)/dx1(i); , - dVyi = D_DX_I(Vc,VX2)/dx1(i); , - dVzi = D_DX_I(Vc,VX3)/dx1(i); ) + // Compute spacing + real dx1 = dx1Array(i); + real dx2 = dx2Array(j); + real dx3 = dx3Array(k); + + // Correct spacing for grid coarsening + + if(haveGridCoarsening) { + if(haveGridCoarseningX1) { + const int factor = 1 << (coarseningLevelX1(k,j) - 1); + dx1 *= factor; + } + + if(haveGridCoarseningX2) { + const int factor = 1 << (coarseningLevelX2(k,i) - 1); + dx2 *= factor; + } + + if(haveGridCoarseningX3) { + const int factor = 1 << (coarseningLevelX3(j,i) - 1); + dx3 *= factor; + } + } + + EXPAND( dVxi = D_DX_I(Vc,VX1)/dx1; , + dVyi = D_DX_I(Vc,VX2)/dx1; , + dVzi = D_DX_I(Vc,VX3)/dx1; ) #if DIMENSIONS >= 2 - EXPAND( dVxj = D_DY_I(Vc,VX1)/dx2(j); , - dVyj = D_DY_I(Vc,VX2)/dx2(j); , - dVzj = D_DY_I(Vc,VX3)/dx2(j); ) + EXPAND( dVxj = D_DY_I(Vc,VX1)/dx2; , + dVyj = D_DY_I(Vc,VX2)/dx2; , + dVzj = D_DY_I(Vc,VX3)/dx2; ) #if DIMENSIONS == 3 - dVxk = D_DZ_I(Vc,VX1)/dx3(k); - dVyk = D_DZ_I(Vc,VX2)/dx3(k); - dVzk = D_DZ_I(Vc,VX3)/dx3(k); + dVxk = D_DZ_I(Vc,VX1)/dx3; + dVyk = D_DZ_I(Vc,VX2)/dx3; + dVzk = D_DZ_I(Vc,VX3)/dx3; #endif #endif @@ -234,14 +266,14 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D tau_xy = eta1*(dVxj + dVyi); SELECT( , , - tau_xz = eta1*0.5*(x1(i)+x1(i-1))/dx1(i) + tau_xz = eta1*0.5*(x1(i)+x1(i-1))/dx1 *(Vc(VX3,k,j,i)/x1(i) - Vc(VX3,k,j,i-1)/x1(i-1)); ) tau_xz = eta1*(dVxk + dVzi); // compute tau_zz at cell center - divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1(i) + Vc(VX1,k,j,i)/x1(i), - +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j) , + divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1 + Vc(VX1,k,j,i)/x1(i), + +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2 , ); tau_zz = 2.0*etaC1*Vc(VX1,k,j,i)/x1(i) + (etaC2 - (2.0/3.0)*etaC1)*divV; @@ -269,14 +301,14 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D // compute tau_yy at cell center - divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1(i) + Vc(VX1,k,j,i)/x1(i), - +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j)/x1(i) , - +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3(k) ); + divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1 + Vc(VX1,k,j,i)/x1(i), + +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2/x1(i) , + +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3 ); #if DIMENSIONS == 1 tau_yy = 2.0*etaC1*( Vc(VX1,k,j,i)/x1(i)) + (etaC2 - (2.0/3.0)*etaC1)*divV; #else - tau_yy = 2.0*etaC1*( 0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j)/x1(i) + tau_yy = 2.0*etaC1*( 0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2/x1(i) + Vc(VX1,k,j,i)/x1(i)) + (etaC2 - (2.0/3.0)*etaC1)*divV; #endif @@ -325,14 +357,14 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D // Compute tau_yy and tau_zz at cell center - divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1(i) + 2.0*Vc(VX1,k,j,i)/x1(i), - +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j)/x1(i) + divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1 + 2.0*Vc(VX1,k,j,i)/x1(i), + +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2/x1(i) +Vc(VX2,k,j,i)/x1(i)*tan_1 , - +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3(k)/x1(i)*s_1 ); + +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3/x1(i)*s_1 ); tau_yy = Vc(VX1,k,j,i)/x1(i); #if DIMENSIONS >= 2 - tau_yy += 0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j)/x1(i); + tau_yy += 0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2/x1(i); #endif tau_yy = 2.0*etaC1*tau_yy + (etaC2-2.0/3.0*etaC1)*divV; @@ -341,7 +373,7 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D tau_zz += Vc(VX2,k,j,i)*tan_1/x1(i); #endif #if DIMENSIONS == 3 - tau_zz += 0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3(k)/x1(i)*s_1; + tau_zz += 0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3/x1(i)*s_1; #endif tau_zz = 2.0*etaC1*tau_zz + (etaC2-2.0/3.0*etaC1)*divV; @@ -426,18 +458,41 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D etaC2 = eta2 = eta2Constant; } - EXPAND( dVxi = D_DX_J(Vc,VX1)/dx1(i); , - dVyi = D_DX_J(Vc,VX2)/dx1(i); , - dVzi = D_DX_J(Vc,VX3)/dx1(i); ) + // Compute spacing + real dx1 = dx1Array(i); + real dx2 = dx2Array(j); + real dx3 = dx3Array(k); + + // Correct spacing for grid coarsening + if(haveGridCoarsening) { + if(haveGridCoarseningX1) { + const int factor = 1 << (coarseningLevelX1(k,j) - 1); + dx1 *= factor; + } - EXPAND( dVxj = D_DY_J(Vc,VX1)/dx2(j); , - dVyj = D_DY_J(Vc,VX2)/dx2(j); , - dVzj = D_DY_J(Vc,VX3)/dx2(j); ) + if(haveGridCoarseningX2) { + const int factor = 1 << (coarseningLevelX2(k,i) - 1); + dx2 *= factor; + } + + if(haveGridCoarseningX3) { + const int factor = 1 << (coarseningLevelX3(j,i) - 1); + dx3 *= factor; + } + } + + EXPAND( dVxi = D_DX_J(Vc,VX1)/dx1; , + dVyi = D_DX_J(Vc,VX2)/dx1; , + dVzi = D_DX_J(Vc,VX3)/dx1; ) + + EXPAND( dVxj = D_DY_J(Vc,VX1)/dx2; , + dVyj = D_DY_J(Vc,VX2)/dx2; , + dVzj = D_DY_J(Vc,VX3)/dx2; ) #if DIMENSIONS == 3 - dVxk = D_DZ_J(Vc,VX1)/dx3(k); - dVyk = D_DZ_J(Vc,VX2)/dx3(k); - dVzk = D_DZ_J(Vc,VX3)/dx3(k); + dVxk = D_DZ_J(Vc,VX1)/dx3; + dVyk = D_DZ_J(Vc,VX2)/dx3; + dVzk = D_DZ_J(Vc,VX3)/dx3; #endif #if GEOMETRY == CARTESIAN @@ -508,8 +563,8 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D + dVzk/x1(i)*s_1 ); // tau_xy is initially cell centered since it is involved in the source term - tau_xy = etaC1*( 0.5*(Vc(VX1,k,j+1,i)-Vc(VX1,k,j-1,i))/x1(i)/dx2(j) - +0.5*(Vc(VX2,k,j,i+1)-Vc(VX2,k,j,i-1))/dx1(i) + tau_xy = etaC1*( 0.5*(Vc(VX1,k,j+1,i)-Vc(VX1,k,j-1,i))/x1(i)/dx2 + +0.5*(Vc(VX2,k,j,i+1)-Vc(VX2,k,j,i-1))/dx1 - Vc(VX2,k,j,i)/x1(i)); tau_yy = 2.0*eta1*(dVyj/x1(i) + vx1i/x1(i)) + (eta2 - (2.0/3.0)*eta1)*divV; @@ -539,17 +594,17 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D s_1 = ONE_F/s_1; } - divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1(i) + 2.0*Vc(VX1,k,j,i)/x1(i), - +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2(j)/x1(i) + divV = D_EXPAND( 0.5*(Vc(VX1,k,j,i+1) - Vc(VX1,k,j,i-1))/dx1 + 2.0*Vc(VX1,k,j,i)/x1(i), + +0.5*(Vc(VX2,k,j+1,i) - Vc(VX2,k,j-1,i))/dx2/x1(i) +Vc(VX2,k,j,i)/x1(i)*tan_1 , - +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3(k)/x1(i)*s_1 ); + +0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3/x1(i)*s_1 ); tau_zz = Vc(VX1,k,j,i)/x1(i); #if COMPONENTS >= 2 tau_zz += Vc(VX2,k,j,i)/x1(i)*tan_1; #endif #if DIMENSIONS == 3 - tau_zz += 0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3(k)/x1(i)*s_1; + tau_zz += 0.5*(Vc(VX3,k+1,j,i) - Vc(VX3,k-1,j,i))/dx3/x1(i)*s_1; #endif tau_zz = 2*eta1*tau_zz + (eta2-2.0/3.0*eta1)*divV; @@ -639,15 +694,38 @@ void Viscosity::AddViscousFlux(int dir, const real t, const IdefixArray4D etaC2 = eta2 = eta2Constant; } - dVxi = D_DX_K(Vc,VX1)/dx1(i); - dVyi = D_DX_K(Vc,VX2)/dx1(i); - dVzi = D_DX_K(Vc,VX3)/dx1(i); - dVxj = D_DY_K(Vc,VX1)/dx2(j); - dVyj = D_DY_K(Vc,VX2)/dx2(j); - dVzj = D_DY_K(Vc,VX3)/dx2(j); - dVxk = D_DZ_K(Vc,VX1)/dx3(k); - dVyk = D_DZ_K(Vc,VX2)/dx3(k); - dVzk = D_DZ_K(Vc,VX3)/dx3(k); + // Compute spacing + real dx1 = dx1Array(i); + real dx2 = dx2Array(j); + real dx3 = dx3Array(k); + + // Correct spacing for grid coarsening + if(haveGridCoarsening) { + if(haveGridCoarseningX1) { + const int factor = 1 << (coarseningLevelX1(k,j) - 1); + dx1 *= factor; + } + + if(haveGridCoarseningX2) { + const int factor = 1 << (coarseningLevelX2(k,i) - 1); + dx2 *= factor; + } + + if(haveGridCoarseningX3) { + const int factor = 1 << (coarseningLevelX3(j,i) - 1); + dx3 *= factor; + } + } + + dVxi = D_DX_K(Vc,VX1)/dx1; + dVyi = D_DX_K(Vc,VX2)/dx1; + dVzi = D_DX_K(Vc,VX3)/dx1; + dVxj = D_DY_K(Vc,VX1)/dx2; + dVyj = D_DY_K(Vc,VX2)/dx2; + dVzj = D_DY_K(Vc,VX3)/dx2; + dVxk = D_DZ_K(Vc,VX1)/dx3; + dVyk = D_DZ_K(Vc,VX2)/dx3; + dVzk = D_DZ_K(Vc,VX3)/dx3; #if GEOMETRY == CARTESIAN divV = dVxi + dVyj + dVzk; From 1e2356281e4f566e190d8a8785ad5cdd80de426e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Tue, 18 Aug 2026 16:45:58 +0200 Subject: [PATCH 119/144] test: Fix missing propagation of return status when calling pytest in ./test.py (#399) * test: Fix missing protagation of return status when calling pytest in ./test.py * fix: fix an issue coming from the previous refactoring about accessing a GPU buffer on CPU * fix: Fix some warnings about unused variabled blocking the test suite * test: fix utils/lookupTable test by adding possibility to call a python function from testme.json * fix: communication issue introduced during the comm refactoring in recent commit of PR #385. * fix: add missing new file testmelib.py in test/utils/lookupTable --- doc/source/testing/testLauncher.rst | 33 ++++++++ pytools/idfx_test_run.py | 78 +++++++++++++++++-- .../RiemannSolver/MHDsolvers/storeFlux.hpp | 4 +- src/fluid/boundary/axis.cpp | 11 +-- .../constrainedTransport/EMFexchange.hpp | 12 +-- src/mpi/buffer.hpp | 3 +- test/utils/lookupTable/testme.json | 3 +- test/utils/lookupTable/testme.py | 25 +----- test/utils/lookupTable/testmelib.py | 19 +++++ 9 files changed, 145 insertions(+), 43 deletions(-) create mode 100644 test/utils/lookupTable/testmelib.py diff --git a/doc/source/testing/testLauncher.rst b/doc/source/testing/testLauncher.rst index ffb80ef9f..febc0cb8d 100644 --- a/doc/source/testing/testLauncher.rst +++ b/doc/source/testing/testLauncher.rst @@ -191,6 +191,12 @@ In addition there is some extra keys which are dedicated to the json interpretat * - ``multirun`` - ``{}`` - See the multi-run section below. + * - ``callPyFunctionBefore`` + - + - Call a python function before executing the test (see dedicated section at the end of this file). + * - ``callPyFunctionAfter`` + - + - Call a python function after executing the test (see dedicated section at the end of this file). Looping over parameters ----------------------- @@ -374,6 +380,33 @@ They are described like : }, } +Calling a Python function +------------------------- + +In some cases (example in ``test/utils/lookupTable``) you might need to call a custom +python function before running the test to prepare the data or after the test to perform +some extra check. + +You can simply implement the functions you want to call in the python file in the test +directory (ideally named ``testmelib.py``) : + +.. code-block:: python + + def callMeAtStart(): + print("This is called at test start !") + + def callMeAtEnd(): + print("This is called at test end !") + +And add the keys in ``testme.json``: + +.. code-block:: json + + "default": { + "callPyFunctionBefore": "testmelib.py:callMeAtStart", + "callPyFunctionAfter": "testmelib.py:callMeAtEnd" + } + Using the idfxTest options -------------------------- diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index 250716125..be2e2bb58 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -7,6 +7,7 @@ import copy import glob +import importlib import json import os import sys @@ -135,6 +136,58 @@ def genTests(self) -> list: # ok return result + def buildPyHooks(self, config: dict) -> dict: + # init + result = {} + key: str + + # extract and build dict + for key, value in config.items(): + if key.startswith("callPyFunction"): + when = key.replace("callPyFunction", "") + result[when] = value + + # ok + return result + + # https://docs.python.org/3/library/importlib.html#importing-a-source-file-directly + def importFromPath(self, moduleName: str, filePath: str): + spec = importlib.util.spec_from_file_location(moduleName, filePath) + module = importlib.util.module_from_spec(spec) + # sys.modules[moduleName] = module + spec.loader.exec_module(module) + return module + + def callPyHook(self, dir: str, hooks: dict, name: str) -> None: + # nothing to do + if name not in hooks: + return + + # split file:funcName + params = hooks[name].split(":", 1) + filePath = params[0] + funcName = params[1] + + # complete + fileFullPath = os.path.join(dir, filePath) + + # log + print("************** CALLING PY FUNCTION ****************") + print(f"Hook: {name}") + print(f"HookValue: {hooks[name]}") + print(f"Import {fileFullPath}") + print(f"Call: {funcName}") + print("***************************************************") + + # import the module + module = self.importFromPath("idefix_test_py_hooks", fileFullPath) + + # get function + function = getattr(module, funcName) + + # call it + function() + def run(self, config: dict) -> None: # clone before modify to not modity for caller config = copy.deepcopy(config) @@ -155,6 +208,7 @@ def run(self, config: dict) -> None: nonRegressionTestIni = config.get("nonRegressionTestIni", None) check_file_produced = config.get("check_file_produced", []) problemDir = os.path.dirname(testfile) + pyHooks = self.buildPyHooks(config) # cleanup some keyword not handled at the # level of idx_test so we don't perturbate it @@ -169,6 +223,12 @@ def run(self, config: dict) -> None: del config["nonRegressionTest"] if "nonRegressionTestIni" in config: del config["nonRegressionTestIni"] + for hook in pyHooks: + del config[f"callPyFunction{hook}"] + + # call hook before + with moveInDir(problemDir): + self.callPyHook(problemDir, pyHooks, "Before") # if switch from test, rebuild the runner (a runner make for one dir) if self.currentTestFile != testfile: @@ -189,11 +249,16 @@ def run(self, config: dict) -> None: ) # check produced - for file in check_file_produced: - if not os.path.exists(file) and not self.currentTestRunner.fake: - raise Exception( - f"Don't find expected file to be produced by the run : {file} !" - ) + with moveInDir(problemDir): + for file in check_file_produced: + if not os.path.exists(file) and not self.currentTestRunner.fake: + raise Exception( + f"Don't find expected file to be produced by the run : {file} !" + ) + + # call hook after + with moveInDir(problemDir): + self.callPyHook(problemDir, pyHooks, "After") def _runNonRegression( self, @@ -365,7 +430,7 @@ def main(self, all: bool = False): os.environ["IDEFIX_TEST_FILTER_SUBDIR"] = idefixTest.filterSubdir if idefixTest.all: - pytest.main( + status = pytest.main( [ "-v", "--no-header", @@ -375,6 +440,7 @@ def main(self, all: bool = False): + idefixTest.remainingArgs + [self.parentScritFile] ) + sys.exit(status) else: raise NotImplementedError("Not yet supported !") # elif self.check: diff --git a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp index b376befe0..e4152dcdb 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp @@ -55,8 +55,8 @@ KOKKOS_FORCEINLINE_FUNCTION void K_StoreHLL( const int i, const int j, const int const IdefixArray3D &dL, const IdefixArray3D &dR) { EXPAND( , - constexpr int Xt = (DIR == IDIR ? MX2 : MX1); , - constexpr int Xb = (DIR == KDIR ? MX2 : MX3); ) + [[maybe_unused]] constexpr int Xt = (DIR == IDIR ? MX2 : MX1); , + [[maybe_unused]] constexpr int Xb = (DIR == KDIR ? MX2 : MX3); ) real ar = std::fmax(ZERO_F, sr); real al = std::fmin(ZERO_F, sl); diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index 45ea49ea5..a5153d361 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -392,7 +392,8 @@ void Axis::ExchangeMPI(int side) { idfx::pushRegion("Axis::ExchangeMPI"); #ifdef WITH_MPI // Load the buffers with data - int ibeg,iend,jbeg,jend,kbeg,kend,offset; + [[maybe_unused]] int ibeg,iend,jbeg,jend,kbeg,kend; + int offset; int ny; Buffer bufferSend = this->bufferSend; IdefixArray1D map = this->mapVars; @@ -491,12 +492,12 @@ void Axis::ExchangeMPI(int side) { //unpack Vs face-centered BoundingBox recvBoxVsIdir = baseBox; recvBoxVsIdir[IDIR][1] += 1; - bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs(IDIR), recvBoxVsIdir); + bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs, recvBoxVsIdir); //unpack Vs face-centered BoundingBox recvBoxVsKdir = baseBox; recvBoxVsKdir[KDIR][1] += 1; - bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs(KDIR), recvBoxVsKdir); + bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs, recvBoxVsKdir); } } else if(side==right) { //unpack Vc on right part @@ -514,14 +515,14 @@ void Axis::ExchangeMPI(int side) { recvBoxVsIdir[IDIR][1] += 1; recvBoxVsIdir[JDIR][0] += offset; recvBoxVsIdir[JDIR][1] += offset; - bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs(IDIR), recvBoxVsIdir); + bufferRecv.UnpackJDirSymetric(Vs, IDIR, sVs, recvBoxVsIdir); //unpack Vs face-centered on right part BoundingBox recvBoxVsKdir = baseBox; recvBoxVsKdir[KDIR][1] += 1; recvBoxVsKdir[JDIR][0] += offset; recvBoxVsKdir[JDIR][1] += offset; - bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs(KDIR), recvBoxVsKdir); + bufferRecv.UnpackJDirSymetric(Vs, KDIR, sVs, recvBoxVsKdir); } // MHD } diff --git a/src/fluid/constrainedTransport/EMFexchange.hpp b/src/fluid/constrainedTransport/EMFexchange.hpp index aad123346..179783802 100644 --- a/src/fluid/constrainedTransport/EMFexchange.hpp +++ b/src/fluid/constrainedTransport/EMFexchange.hpp @@ -75,7 +75,7 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 sendBoxEy[KDIR][1] += 1; sendBoxEy[IDIR][0] = iright; sendBoxEy[IDIR][1] = iright + 1; - BufferRight.Pack(ez, sendBoxEy); + BufferRight.Pack(ey, sendBoxEy); #endif // Wait for completion before sending out everything @@ -239,11 +239,11 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 baseBox[KDIR][1] = data->end[KDIR]; //extend by one the end on jdir && take the ghost on k - BoundingBox sendBoxEz = baseBox; - sendBoxEz[JDIR][1] += 1; - sendBoxEz[KDIR][0] = kright; - sendBoxEz[KDIR][1] = kright + 1; - BufferRight.Pack(ez, sendBoxEz); + BoundingBox sendBoxEx = baseBox; + sendBoxEx[JDIR][1] += 1; + sendBoxEx[KDIR][0] = kright; + sendBoxEx[KDIR][1] = kright + 1; + BufferRight.Pack(ex, sendBoxEx); //extend by one the end on idir && take the ghost on k BoundingBox sendBoxEy = baseBox; diff --git a/src/mpi/buffer.hpp b/src/mpi/buffer.hpp index 35164355b..b045b86e7 100644 --- a/src/mpi/buffer.hpp +++ b/src/mpi/buffer.hpp @@ -165,7 +165,7 @@ class Buffer { void UnpackJDirSymetric(IdefixArray4D& out, const int var, - const int symMultiplier, + IdefixArray1D& SymMap, BoundingBox box) { const int ni = box[IDIR][1]-box[IDIR][0]; const int ninj = (box[JDIR][1]-box[JDIR][0])*ni; @@ -183,6 +183,7 @@ class Buffer { KOKKOS_LAMBDA (int k, int j, int i) { const int jinverted = jend-(j-jbeg)-1; const int arrIndex = i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset; + const int symMultiplier = SymMap(var); out(var,k,jinverted,i) = symMultiplier * arr(arrIndex); }); diff --git a/test/utils/lookupTable/testme.json b/test/utils/lookupTable/testme.json index 100e561d8..d012528b4 100644 --- a/test/utils/lookupTable/testme.json +++ b/test/utils/lookupTable/testme.json @@ -4,6 +4,7 @@ "ini": "idefix.ini", "nonRegressionTest": false, "standardTest": false, - "tolerance": 0 + "tolerance": 0, + "callPyFunctionBefore": "testmelib.py:MakeNumpyFile" } } diff --git a/test/utils/lookupTable/testme.py b/test/utils/lookupTable/testme.py index c02f2b1c3..133ea61b4 100755 --- a/test/utils/lookupTable/testme.py +++ b/test/utils/lookupTable/testme.py @@ -9,32 +9,13 @@ import sys sys.path.append(os.getenv("IDEFIX_DIR")) -import numpy as np - # from scipy.interpolate import RegularGridInterpolator -import pytools.idfx_test as tst - - -def MakeNumpyFile(): - x = np.arange(1, 10, 1.0) - y = np.arange(5, 10, 1.0) - z = np.arange(2, 5, 1.0) - - xp, yp, zp = np.meshgrid(x, y, z, indexing="ij") - - data = xp + 2 * yp - zp - - np.save("x.npy", x) - np.save("y.npy", y) - np.save("z.npy", z) - np.save("data.npy", data) - # show the expected result - # f=RegularGridInterpolator((x, y, z), data) - # print(f([2.7,7.4,3.9])) +import testmelib +import pytools.idfx_test as tst test = tst.idfxTest(__file__) -MakeNumpyFile() +testmelib.MakeNumpyFile() test.configure() test.compile() diff --git a/test/utils/lookupTable/testmelib.py b/test/utils/lookupTable/testmelib.py new file mode 100644 index 000000000..b41266147 --- /dev/null +++ b/test/utils/lookupTable/testmelib.py @@ -0,0 +1,19 @@ +import numpy as np + + +def MakeNumpyFile(): + x = np.arange(1, 10, 1.0) + y = np.arange(5, 10, 1.0) + z = np.arange(2, 5, 1.0) + + xp, yp, zp = np.meshgrid(x, y, z, indexing="ij") + + data = xp + 2 * yp - zp + + np.save("x.npy", x) + np.save("y.npy", y) + np.save("z.npy", z) + np.save("data.npy", data) + # show the expected result + # f=RegularGridInterpolator((x, y, z), data) + # print(f([2.7,7.4,3.9])) From b6136e4b3e3e37019e002d8ece692a12b2befe1b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Wed, 19 Aug 2026 09:44:43 +0200 Subject: [PATCH 120/144] TST/DEP: update minimal Python requirements (#393) --- test/python_requirements.txt | 13 ++++++------- 1 file changed, 6 insertions(+), 7 deletions(-) diff --git a/test/python_requirements.txt b/test/python_requirements.txt index 6419c74af..bfa7c53cd 100644 --- a/test/python_requirements.txt +++ b/test/python_requirements.txt @@ -1,13 +1,12 @@ -# note: version requirements are indicative and tests # should be able to run with +# note: version requirements are indicative and tests should be able to run with # older versions of our dependencies, though it is not guaranteed. -# minimally require last versions available for Python 2.7 -numpy>=1.16.6 -matplotlib>=2.2.5 -scipy>=1.2.3 - -# note that no version of inifix supports Python older than 3.6 +# minimally require earliest versions available for Python 3.10 +numpy>=1.21.1 +matplotlib>=3.5.0 +scipy>=1.7.2 inifix>=0.11.2 + pybind11 >= 3.0.4 # To run the test suite, we can use pytest, mostly any version # 6.0 is the one available on system available on debian-11 From f604897b84c30c3fed960eb526a7497c38ac43c2 Mon Sep 17 00:00:00 2001 From: Alankar Dutta Date: Wed, 19 Aug 2026 10:33:34 +0200 Subject: [PATCH 121/144] Fixing issues related to linking parallel hdf5 on cmake (#391) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Fix parallel HDF5 detection when found via CMake config package find_package(HDF5) can resolve through the HDF5-provided CMake config package (config mode), which does not set HDF5_IS_PARALLEL. The previous 'if(NOT HDF5_IS_PARALLEL)' check then wrongly failed for a genuinely parallel HDF5 build. Detect parallel support robustly: prefer imported targets (hdf5::hdf5 / HDF5::HDF5), fall back to the FindHDF5 module, and determine parallelism from HDF5_IS_PARALLEL/HDF5_C_IS_PARALLEL, 'h5cc -showconfig', or an H5Pset_fapl_mpio compile+link probe. * Silence unused-variable warnings with [[maybe_unused]] Mark variables that are unused in some build configurations as [[maybe_unused]]: the MPI buffer index locals in Axis::ExchangeMPI and tot_dim in the DIMENSIONS==2 branch of Xdmf::Write. * Apply suggestions from code review Minor Co-pilot suggested fixes Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> * Minor typo fix * [ENH] refactor of parallel hdf5 detection --------- Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> Co-authored-by: Sébastien Valat --- CMakeLists.txt | 20 +++++++++-- cmake/CheckHdf5ParallelSupport.cmake | 50 ++++++++++++++++++++++++++++ src/fluid/showConfig.hpp | 2 +- src/output/xdmf.cpp | 2 +- 4 files changed, 69 insertions(+), 5 deletions(-) create mode 100644 cmake/CheckHdf5ParallelSupport.cmake diff --git a/CMakeLists.txt b/CMakeLists.txt index fad0058ba..1b2c05ef3 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -42,6 +42,7 @@ include(ReplaceIdefixSource) include(AddIdefixSource) include(SetIdefixProperty) include(SetRequiredBuildSettingsForGCC8) +include(CheckHdf5ParallelSupport) #Idefix requires Cuda Lambdas (experimental) if(Kokkos_ENABLE_CUDA) @@ -113,12 +114,25 @@ if(Idefix_HDF5) PUBLIC src/output/xdmf.cpp PUBLIC src/output/xdmf.hpp ) - find_package(HDF5 REQUIRED) - target_link_libraries(idefix "${HDF5_LIBRARIES}") + # Prefer imported targets (matches older working behavior), then fall back. + find_package(HDF5 QUIET COMPONENTS C) + if(NOT HDF5_FOUND) + find_package(HDF5 REQUIRED MODULE COMPONENTS C) + endif() + + set(_idefix_hdf5_link_items "${HDF5_LIBRARIES}") + if(TARGET hdf5::hdf5) + set(_idefix_hdf5_link_items hdf5::hdf5) + elseif(TARGET HDF5::HDF5) + set(_idefix_hdf5_link_items HDF5::HDF5) + endif() + + target_link_libraries(idefix ${_idefix_hdf5_link_items}) message(STATUS "Found HDF5 include directories: ${HDF5_INCLUDE_DIRS}") target_include_directories(idefix PUBLIC "${HDF5_INCLUDE_DIRS}") if(Idefix_MPI) - if(NOT HDF5_IS_PARALLEL) + CheckHdf5ParallelSupport("${_idefix_hdf5_link_items}") + if(NOT IDEFIX_HDF5_IS_PARALLEL) message(FATAL_ERROR "Parallel HDF5 required for Idefix_MPI but the found HDF5 library does not support it") endif() endif() diff --git a/cmake/CheckHdf5ParallelSupport.cmake b/cmake/CheckHdf5ParallelSupport.cmake new file mode 100644 index 000000000..aae651a17 --- /dev/null +++ b/cmake/CheckHdf5ParallelSupport.cmake @@ -0,0 +1,50 @@ +include(CheckCSourceCompiles) + +# Check whether the HDF5 library found by find_package(HDF5) supports parallel +# (MPI-IO) access, and store the result in IDEFIX_HDF5_IS_PARALLEL in the +# caller's scope. +# +# Usage: CheckHdf5ParallelSupport() +# where is the list of HDF5 targets/libraries to link against. +# +# Some CMake/HDF5 combinations do not reliably set HDF5_IS_PARALLEL (e.g. when +# HDF5 is found via its CMake config package rather than the FindHDF5 module). +# Combine metadata checks with a compile+link probe for the MPI-IO symbols to +# reliably detect parallel HDF5. +function(CheckHdf5ParallelSupport hdf5_link_items) + set(_idefix_hdf5_is_parallel FALSE) + if(HDF5_IS_PARALLEL OR HDF5_C_IS_PARALLEL) + set(_idefix_hdf5_is_parallel TRUE) + endif() + + if(NOT _idefix_hdf5_is_parallel AND DEFINED HDF5_C_COMPILER_EXECUTABLE) + execute_process( + COMMAND "${HDF5_C_COMPILER_EXECUTABLE}" -showconfig + OUTPUT_VARIABLE _idefix_hdf5_showconfig + ERROR_QUIET + ) + if(_idefix_hdf5_showconfig MATCHES "Parallel HDF5:[ \t]*yes") + set(_idefix_hdf5_is_parallel TRUE) + endif() + endif() + + set(CMAKE_REQUIRED_INCLUDES ${HDF5_INCLUDE_DIRS} ${MPI_C_INCLUDE_DIRS}) + set(CMAKE_REQUIRED_LIBRARIES ${hdf5_link_items} MPI::MPI_C) + check_c_source_compiles( + "#include + #include + int main(void) { + hid_t plist = H5Pcreate(H5P_FILE_ACCESS); + H5Pset_fapl_mpio(plist, MPI_COMM_WORLD, MPI_INFO_NULL); + H5Pclose(plist); + return 0; + }" + IDEFIX_HDF5_HAS_MPI_IO + ) + + if(IDEFIX_HDF5_HAS_MPI_IO) + set(_idefix_hdf5_is_parallel TRUE) + endif() + + set(IDEFIX_HDF5_IS_PARALLEL ${_idefix_hdf5_is_parallel} PARENT_SCOPE) +endfunction() diff --git a/src/fluid/showConfig.hpp b/src/fluid/showConfig.hpp index f3a144304..0f8b64ed9 100644 --- a/src/fluid/showConfig.hpp +++ b/src/fluid/showConfig.hpp @@ -60,7 +60,7 @@ void Fluid::ShowConfig() { << ": Ohmic resistivity ENABLED with user-defined resistivity function." << std::endl; if(!ohmicDiffusivityFunc) { - IDEFIX_ERROR("No user-defined Ihmic resistivity function has been enrolled."); + IDEFIX_ERROR("No user-defined Ohmic resistivity function has been enrolled."); } } else { IDEFIX_ERROR("Unknown Ohmic resistivity mode"); diff --git a/src/output/xdmf.cpp b/src/output/xdmf.cpp index 4e7ff6843..f08819003 100644 --- a/src/output/xdmf.cpp +++ b/src/output/xdmf.cpp @@ -295,7 +295,7 @@ int Xdmf::Write() { #if DIMENSIONS == 1 [[maybe_unused]] int tot_dim = 1; #elif DIMENSIONS == 2 - int tot_dim = 2; + [[maybe_unused]] int tot_dim = 2; #elif DIMENSIONS == 3 [[maybe_unused]] int tot_dim = 3; #endif From 8d8508a71d9ee6447e48da3af337bfbddc301028 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Wed, 19 Aug 2026 15:46:40 +0200 Subject: [PATCH 122/144] github: update the action version dependencies to fix some warnings about nodejs-20 instead of nodejs-24. (#400) --- .github/workflows/idefix-ci-doc.yml | 2 +- .github/workflows/idefix-ci-jobs.yml | 26 +++++++++++++------------- .github/workflows/idefix-ci.yml | 8 ++++---- 3 files changed, 18 insertions(+), 18 deletions(-) diff --git a/.github/workflows/idefix-ci-doc.yml b/.github/workflows/idefix-ci-doc.yml index 7422be2f3..2d04e9e4e 100644 --- a/.github/workflows/idefix-ci-doc.yml +++ b/.github/workflows/idefix-ci-doc.yml @@ -16,7 +16,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: persist-credentials: false - name: install doxygen diff --git a/.github/workflows/idefix-ci-jobs.yml b/.github/workflows/idefix-ci-jobs.yml index ab2b73247..4c3b54715 100644 --- a/.github/workflows/idefix-ci-jobs.yml +++ b/.github/workflows/idefix-ci-jobs.yml @@ -28,7 +28,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -47,7 +47,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -64,7 +64,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -87,7 +87,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -109,7 +109,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -125,7 +125,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -141,7 +141,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -163,7 +163,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -187,7 +187,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -203,7 +203,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -223,7 +223,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -237,7 +237,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false @@ -255,7 +255,7 @@ jobs: runs-on: self-hosted steps: - name: Check out repo - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: submodules: recursive persist-credentials: false diff --git a/.github/workflows/idefix-ci.yml b/.github/workflows/idefix-ci.yml index 50fd26eee..8e1a03635 100644 --- a/.github/workflows/idefix-ci.yml +++ b/.github/workflows/idefix-ci.yml @@ -17,14 +17,14 @@ jobs: if: ${{ github.repository == 'idefix-code/idefix' || github.repository == 'glesur/idefix' }} runs-on: ubuntu-latest steps: - - uses: actions/checkout@f43a0e5ff2bd294095638e18286ca9a3d1956744 # v3.6.0 + - uses: actions/checkout@3d3c42e5aac5ba805825da76410c181273ba90b1 # v7.0.1 with: persist-credentials: false - - uses: actions/setup-python@7f4fc3e22c37d6ff65e88745f38bd3157c663f7c # v4.9.1 + - uses: actions/setup-python@ece7cb06caefa5fff74198d8649806c4678c61a1 # v6.3.0 with: python-version: 3.x - - uses: pre-commit/action@646c83fcd040023954eafda54b4db0192ce70507 # v3.0.0 - - uses: pre-commit-ci/lite-action@50143aaf27e2c42e75a5e06185a471d9582e89df # v1.0.0 + - uses: pre-commit/action@2c7b3805fd2a0fd8c1884dcaebf91fc102a13ecd # v3.0.1 + - uses: pre-commit-ci/lite-action@5d6cc0eb514c891a40562a58a8e71576c5c7fb43 # v1.1.0 if: always() icc-jobs: From 73255b09c4c07b71f0f0355d2a1fba1c27fcadae Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 26 Aug 2026 12:00:54 +0200 Subject: [PATCH 123/144] Fix: Kokkos 5 performances on AMD (#402) - Constrain Kokkos parallel_for range kernels via LaunchBounds<256> in idefix_for wrappers to mitigate AMD register spilling. - Replace the generated-in-source version.hpp mechanism with CMake-generated headers (version.h, compiler_info.h) and update outputs/version printing to use them. - Add Idefix_SUPPRESS_FMA and a SuppressFMA.cmake helper to disable FMA contraction across toolchains; update the Python test harness to enable it for bitwise-stable comparisons. --------- Co-authored-by: Geoffroy Lesur Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --- CMakeLists.txt | 33 +++++++++--- cmake/SuppressFMA.cmake | 102 +++++++++++++++++++++++++++++++++++ pytools/idfx_test.py | 8 ++- src/compiler_info.h.in | 17 ++++++ src/dataBlock/dumpToFile.cpp | 4 +- src/input.cpp | 12 +++-- src/loop.hpp | 8 +-- src/output/dump.cpp | 4 +- src/output/vtk.cpp | 4 +- src/output/xdmf.cpp | 4 +- src/version.h.in | 19 +++++++ 11 files changed, 187 insertions(+), 28 deletions(-) create mode 100644 cmake/SuppressFMA.cmake create mode 100644 src/compiler_info.h.in create mode 100644 src/version.h.in diff --git a/CMakeLists.txt b/CMakeLists.txt index 1b2c05ef3..ed2276839 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -16,6 +16,7 @@ option(Idefix_DEBUG "Enable Idefix debug features (makes the code very slow)" OF option(Idefix_RUNTIME_CHECKS "Enable runtime sanity checks" OFF) option(Idefix_WERROR "Treat compiler warnings as errors" OFF) option(Idefix_PYTHON "Enable python bindings (requires pybind11)" OFF) +option(Idefix_SUPPRESS_FMA "Disable FMA (fused multiply-add) contraction/codegen. Useful for code validation across architectures." OFF) set(Idefix_PROBLEM_DIR "${CMAKE_BINARY_DIR}" CACHE STRING "Problem directory to build for.") set(Idefix_CXX_FLAGS "" CACHE STRING "Additional compiler/linker flag") set(Idefix_DEFS "definitions.hpp" CACHE FILEPATH "Problem definition header file") @@ -43,6 +44,7 @@ include(AddIdefixSource) include(SetIdefixProperty) include(SetRequiredBuildSettingsForGCC8) include(CheckHdf5ParallelSupport) +include(SuppressFMA) #Idefix requires Cuda Lambdas (experimental) if(Kokkos_ENABLE_CUDA) @@ -58,6 +60,8 @@ include_directories(${Kokkos_INCLUDE_DIRS_RET}) # Add Idefix CXX Flags add_compile_options(${Idefix_CXX_FLAGS}) + + # Add filesystem libraries for GCC8 set_required_build_settings_for_GCC8() @@ -181,15 +185,15 @@ endif() if(Idefix_EVOLVE_VECTOR_POTENTIAL) add_compile_definitions("EVOLVE_VECTOR_POTENTIAL") endif() -#update version.hpp if possible + +# determine idefix version from git git_describe(GIT_SHA1) set(Idefix_VERSION ${Idefix_VERSION_MAJOR}.${Idefix_VERSION_MINOR}.${Idefix_VERSION_PATCH}-${GIT_SHA1}) -file(WRITE ${CMAKE_SOURCE_DIR}/src/version.hpp "#define IDEFIX_GIT_COMMIT \"${GIT_SHA1}\"\n") -file(APPEND ${CMAKE_SOURCE_DIR}/src/version.hpp "#define IDEFIX_VERSION_MAJOR \"${Idefix_VERSION_MAJOR}\"\n") -file(APPEND ${CMAKE_SOURCE_DIR}/src/version.hpp "#define IDEFIX_VERSION_MINOR \"${Idefix_VERSION_MINOR}\"\n") -file(APPEND ${CMAKE_SOURCE_DIR}/src/version.hpp "#define IDEFIX_VERSION_PATCH \"${Idefix_VERSION_PATCH}\"\n") -file(APPEND ${CMAKE_SOURCE_DIR}/src/version.hpp "#define IDEFIX_VERSION \"${Idefix_VERSION}\"\n") - +configure_file( + ${CMAKE_SOURCE_DIR}/src/version.h.in + ${CMAKE_BINARY_DIR}/build/generated/version.h + @ONLY +) if(NOT ${Idefix_DEFS} STREQUAL "definitions.hpp") add_compile_definitions("DEFINITIONS_FILE=\"${Idefix_DEFS}\"") @@ -269,6 +273,21 @@ target_include_directories(idefix PUBLIC target_link_libraries(idefix Kokkos::kokkos) +# Generate header with compiler information (name, flags, path) +configure_file( + ${CMAKE_SOURCE_DIR}/src/compiler_info.h.in + ${CMAKE_BINARY_DIR}/build/generated/compiler_info.h + @ONLY +) +# Make sure the generated header is on the include path +target_include_directories(idefix PRIVATE ${CMAKE_BINARY_DIR}/build/generated) + +# disable FMA if needed +if(Idefix_SUPPRESS_FMA) + message(STATUS "FMA (fused multiply-add) contraction/codegen is disabled") + target_suppress_fma(idefix) +endif() + message(STATUS "Idefix final configuration") if(Idefix_EVOLVE_VECTOR_POTENTIAL) message(STATUS " MHD: ${Idefix_MHD} (Vector potential)") diff --git a/cmake/SuppressFMA.cmake b/cmake/SuppressFMA.cmake new file mode 100644 index 000000000..18dc10d46 --- /dev/null +++ b/cmake/SuppressFMA.cmake @@ -0,0 +1,102 @@ +#[[============================================================================ + SuppressFMA.cmake + + Provides an option and a function to optionally disable fused + multiply-add (FMA) code generation / contraction for a Kokkos-based CXX + target. + + Kokkos wraps the real device compiler behind nvcc_wrapper (CUDA) or + hipcc (HIP), which makes CMAKE_CXX_COMPILER_ID report the *underlying + host* compiler (e.g. "GNU" or "Clang") instead of "NVIDIA" or "Clang + as HIP". Backend detection therefore relies on the Kokkos_ENABLE_* + variables exported by KokkosConfig.cmake / set by the Kokkos build, + and only falls back to CMAKE_CXX_COMPILER_ID for the plain host + compilers (no CUDA/HIP backend active): + + - Kokkos_ENABLE_HIP ON -> AMD HIP (hipcc, clang-based) : -ffp-contract=off + - Kokkos_ENABLE_CUDA ON -> NVIDIA nvcc (via nvcc_wrapper) : --fmad=false + - otherwise, CMAKE_CXX_COMPILER_ID selects among: + GNU : gcc/g++ + Intel : classic icc/icpc + IntelLLVM : Intel oneAPI icx/icpx + Clang : LLVM clang++ + AppleClang : Xcode clang++ + NVHPC : NVIDIA HPC SDK (nvc++), e.g. for OpenMPTarget/OpenACC + + Usage (after find_package(Kokkos) so Kokkos_ENABLE_* are defined): + include(SuppressFMA.cmake) + add_library(mylib source.cpp) + target_link_libraries(mylib PUBLIC Kokkos::kokkos) + target_suppress_fma(mylib) + +============================================================================]] + +include_guard(GLOBAL) + +# Determine the CXX FMA-suppression flags for the active Kokkos backend / +# CXX compiler. Returns the list of flags (possibly empty) via out_var. +function(_fma_suppression_flags_cxx out_var) + set(flags "") + set(id "${CMAKE_CXX_COMPILER_ID}") + + # Kokkos backend takes priority: nvcc_wrapper/hipcc hide the real + # device compiler from CMAKE_CXX_COMPILER_ID. + if(Kokkos_ENABLE_HIP) + set(flags "-ffp-contract=off") + + elseif(Kokkos_ENABLE_CUDA) + set(flags "--fmad=false") + + elseif(id STREQUAL "GNU") + include(CheckCXXCompilerFlag) + check_cxx_compiler_flag("-mno-fma" IDEFIX_HAS_MNO_FMA) + set(flags "-ffp-contract=off") + if(IDEFIX_HAS_MNO_FMA) + list(APPEND flags "-mno-fma") + endif() + elseif(id MATCHES "^(Clang|AppleClang|CrayClang)$") + set(flags "-ffp-contract=off") + + elseif(id STREQUAL "Intel") + # Intel classic compiler + set(flags "-fp-model=precise" "-no-fma") + + elseif(id STREQUAL "IntelLLVM") + # Intel oneAPI compiler (clang-based) + set(flags "-ffp-contract=off" "-fp-model=strict") + + elseif(id STREQUAL "NVHPC") + # NVIDIA HPC SDK (formerly PGI), e.g. OpenMPTarget/OpenACC backend + set(flags "-Mnofma") # untested + endif() + + set(${out_var} "${flags}" PARENT_SCOPE) +endfunction() + +# target_suppress_fma() +# +# Applies compiler-specific FMA-suppression flags to 's CXX +# sources, but only when the SUPPRESS_FMA option is ON. Safe to call +# unconditionally. +function(target_suppress_fma target) + + if(NOT TARGET ${target}) + message(FATAL_ERROR "target_suppress_fma: '${target}' is not a target") + endif() + + _fma_suppression_flags_cxx(cxx_flags) + + if(cxx_flags) + foreach(flag IN LISTS cxx_flags) + target_compile_options(${target} PRIVATE + $<$:${flag}> + ) + endforeach() + else() + message(VERBOSE + "target_suppress_fma: no FMA-suppression flag known for " + "CXX compiler '${CMAKE_CXX_COMPILER_ID}' " + "(Kokkos_ENABLE_CUDA=${Kokkos_ENABLE_CUDA}, " + "Kokkos_ENABLE_HIP=${Kokkos_ENABLE_HIP}) (target ${target})") + endif() +endfunction() diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index ac72d6dde..ffbd0de33 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -225,21 +225,19 @@ def _genCmakeCommand(self, definitionFile=""): if self.cuda: comm.append("-DKokkos_ENABLE_CUDA=ON") - # disable fmad operations on Cuda to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=--fmad=false") # disable Async cuda malloc for tests performed on old UCX implementations comm.append("-DKokkos_ENABLE_IMPL_CUDA_MALLOC_ASYNC=OFF") if self.intel: # disable fmad operations on Cuda to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=-fp-model=strict") comm.append("-DCMAKE_CXX_COMPILER=icpx") comm.append("-DCMAKE_C_COMPILER=icx") if self.hip: comm.append("-DKokkos_ENABLE_HIP=ON") - # disable fmad operations on HIP to make it compatible with CPU arithmetics - comm.append("-DIdefix_CXX_FLAGS=-ffp-contract=off") + + # disable FMA for testing so that we have the same results on CPU and GPU (otherwise, the results are not bitwise identical) + comm.append("-DIdefix_SUPPRESS_FMA=ON") # if we use single precision if self.single: diff --git a/src/compiler_info.h.in b/src/compiler_info.h.in new file mode 100644 index 000000000..140eafd79 --- /dev/null +++ b/src/compiler_info.h.in @@ -0,0 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef COMPILER_INFO_H +#define COMPILER_INFO_H + +namespace CompilerInfo { + inline constexpr const char* name = "@CMAKE_CXX_COMPILER_ID@"; + inline constexpr const char* version = "@CMAKE_CXX_COMPILER_VERSION@"; + inline constexpr const char* path = "@CMAKE_CXX_COMPILER@"; +} + +#endif diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index f20dde838..305b417a7 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -9,8 +9,8 @@ #include #include "../idefix.hpp" #include "dataBlock.hpp" -#include "version.hpp" #include "fluid.hpp" +#include "version.h" #define NAMESIZE 16 #define HEADERSIZE 128 @@ -78,7 +78,7 @@ void DataBlock::DumpToFile(std::string filebase) { // Write Header char header[HEADERSIZE]; - std::snprintf(header, HEADERSIZE, "Idefix %s Debug DataBlock", IDEFIX_VERSION); + std::snprintf(header, HEADERSIZE, "Idefix %s Debug DataBlock", VersionInfo::version); fwrite (header, sizeof(char), HEADERSIZE, fileHdl); // Write Vc diff --git a/src/input.cpp b/src/input.cpp index 336414953..6be052f66 100644 --- a/src/input.cpp +++ b/src/input.cpp @@ -18,8 +18,9 @@ #include "idefix.hpp" #include "input.hpp" -#include "version.hpp" #include "profiler.hpp" +#include "version.h" +#include "compiler_info.h" // Flag will be set if a signal has been received bool Input::abortRequested = false; @@ -415,7 +416,10 @@ void Input::PrintOptions() { } void Input::PrintVersion() { - idfx::cout << " Idefix version " << IDEFIX_VERSION << std::endl; - idfx::cout << " Built against Kokkos " << KOKKOS_VERSION << std::endl; - idfx::cout << " Compiled on " << __DATE__ << " at " << __TIME__ << std::endl; + idfx::cout << "Idefix version " << VersionInfo::version << std::endl; + idfx::cout << "Built against Kokkos " << KOKKOS_VERSION << std::endl; + idfx::cout << "Compiled on " << __DATE__ << " at " << __TIME__ << std::endl; + idfx::cout << "Compiler name: " << CompilerInfo::name << std::endl; + idfx::cout << "Compiler version: " << CompilerInfo::version << std::endl; + idfx::cout << "Compiler path: " << CompilerInfo::path << std::endl; } diff --git a/src/loop.hpp b/src/loop.hpp index 42192fa84..319ad8553 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -85,7 +85,7 @@ inline void idefix_for(const std::string & NAME, idfx::pushRegion("idefix_for("+NAME+")"); #endif const int NI = IE - IB; - Kokkos::parallel_for(NAME, NI, + Kokkos::parallel_for(NAME, Kokkos::RangePolicy>(0, NI), KOKKOS_LAMBDA (const int& IDX) { int i = IDX; i += IB; @@ -112,7 +112,7 @@ inline void idefix_for(const std::string & NAME, const int NJ = JE - JB; const int NI = IE - IB; const int NJNI = NJ * NI; - Kokkos::parallel_for(NAME, NJNI, + Kokkos::parallel_for(NAME, Kokkos::RangePolicy>(0, NJNI), KOKKOS_LAMBDA (const int& IDX) { int j = IDX / NI; int i = IDX - j*NI; @@ -172,7 +172,7 @@ inline void idefix_for(const std::string & NAME, const int NI = IE - IB; const int NKNJNI = NK*NJ*NI; const int NJNI = NJ * NI; - Kokkos::parallel_for(NAME,NKNJNI, + Kokkos::parallel_for(NAME,Kokkos::RangePolicy>(0, NKNJNI), KOKKOS_LAMBDA (const int& IDX) { int k = IDX / NJNI; int j = (IDX - k*NJNI) / NI; @@ -259,7 +259,7 @@ inline void idefix_for(const std::string & NAME, const int NNNKNJNI = NN*NK*NJ*NI; const int NKNJNI = NK*NJ*NI; const int NJNI = NJ * NI; - Kokkos::parallel_for(NAME,NNNKNJNI, + Kokkos::parallel_for(NAME,Kokkos::RangePolicy>(0, NNNKNJNI), KOKKOS_LAMBDA (const int& IDX) { int n = IDX / NKNJNI; int k = (IDX - n*NKNJNI) / NJNI; diff --git a/src/output/dump.cpp b/src/output/dump.cpp index 96a40b548..d20eec265 100644 --- a/src/output/dump.cpp +++ b/src/output/dump.cpp @@ -20,11 +20,11 @@ #include #include #include "dump.hpp" -#include "version.hpp" #include "dataBlockHost.hpp" #include "gridHost.hpp" #include "output.hpp" #include "fluid.hpp" +#include "version.h" // Max size of array name #define NAMESIZE 16 @@ -880,7 +880,7 @@ int Dump::Write(Output& output) { char header[HEADERSIZE]; std::snprintf(header, HEADERSIZE, "Idefix %s Dump Data %s endian", - IDEFIX_VERSION, endian.c_str()); + VersionInfo::version, endian.c_str()); WriteString(fileHdl, header, HEADERSIZE); for(int dir = 0; dir < 3 ; dir++) { diff --git a/src/output/vtk.cpp b/src/output/vtk.cpp index 98e4c2577..fb04e03de 100644 --- a/src/output/vtk.cpp +++ b/src/output/vtk.cpp @@ -20,12 +20,12 @@ #else error "Missing the header." #endif -#include "version.hpp" #include "idefix.hpp" #include "dataBlock.hpp" #include "gridHost.hpp" #include "output.hpp" #include "fluid.hpp" +#include "version.h" #define VTK_RECTILINEAR_GRID 14 #define VTK_STRUCTURED_GRID 35 @@ -385,7 +385,7 @@ void Vtk::WriteHeader(IdfxFileHandler fvtk, real time) { 2. Header ------------------------------------------- */ - ssheader << "Idefix " << IDEFIX_VERSION << " VTK Data" << std::endl; + ssheader << "Idefix " << VersionInfo::version << " VTK Data" << std::endl; /* ------------------------------------------ 3. File format diff --git a/src/output/xdmf.cpp b/src/output/xdmf.cpp index f08819003..7d559a6d6 100644 --- a/src/output/xdmf.cpp +++ b/src/output/xdmf.cpp @@ -21,11 +21,11 @@ #endif #include "xdmf.hpp" -#include "version.hpp" #include "idefix.hpp" #include "dataBlockHost.hpp" #include "gridHost.hpp" #include "output.hpp" +#include "version.h" // Whether or not we write the time in the XDMF file #define WRITE_TIME @@ -526,7 +526,7 @@ void Xdmf::WriteHeader( dimstr = 1; - ssheader << "Idefix " << IDEFIX_VERSION << " XDMF Data"; + ssheader << "Idefix " << VersionInfo::version << " XDMF Data"; strspace = H5Screate_simple(1, &dimstr, NULL); string_type = H5Tcopy(H5T_C_S1); H5Tset_size(string_type, strlen( ssheader.str().c_str() )); diff --git a/src/version.h.in b/src/version.h.in new file mode 100644 index 000000000..5561658aa --- /dev/null +++ b/src/version.h.in @@ -0,0 +1,19 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef VERSION_H +#define VERSION_H + +namespace VersionInfo { + inline constexpr const char* gitCommit = "@GIT_SHA1@"; + inline constexpr const char* versionMajor = "@Idefix_VERSION_MAJOR@"; + inline constexpr const char* versionMinor = "@Idefix_VERSION_MINOR@"; + inline constexpr const char* versionPatch = "@Idefix_VERSION_PATCH@"; + inline constexpr const char* version = "@Idefix_VERSION@"; +} + +#endif From 9344820d267dec383b5750464e2ed25d65cd6bd0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Thu, 27 Aug 2026 20:51:26 +0200 Subject: [PATCH 124/144] MPI gpu-direct: make it optional and have fallback solution with device-host explicit transfers (#389) * gpu-direct: handle communications when MPI GPU DIRECT is not there/available. --------- Co-authored-by: Geoffroy Lesur --- CMakeLists.txt | 26 + doc/source/faq.rst | 3 + doc/source/reference/makefile.rst | 6 + pytools/idfx_test.py | 21 + src/fluid/boundary/axis.cpp | 31 +- src/fluid/boundary/axis.hpp | 12 +- .../constrainedTransport/EMFexchange.hpp | 25 +- .../constrainedTransport.hpp | 84 +-- .../enforceEMFBoundary.hpp | 14 +- src/mpi/buffer.hpp | 38 +- src/mpi/commArray.hpp | 224 ++++++++ src/mpi/exchanger.cpp | 64 ++- src/mpi/exchanger.hpp | 4 +- src/mpi/mpi.cpp | 32 +- src/mpi/mpi.hpp | 1 + src/mpi/mpiWrapper.hpp | 505 ++++++++++++++++++ src/output/slice.cpp | 2 +- src/output/vtk.cpp | 2 +- src/pydefix.cpp | 22 +- src/timeIntegrator.cpp | 2 +- src/utils/column.cpp | 15 +- src/utils/column.hpp | 3 +- src/utils/lookupTable.hpp | 8 +- test/MHD/AxisFluxTube/testme.json | 18 +- 24 files changed, 991 insertions(+), 171 deletions(-) create mode 100644 src/mpi/commArray.hpp create mode 100644 src/mpi/mpiWrapper.hpp diff --git a/CMakeLists.txt b/CMakeLists.txt index ed2276839..02cede629 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -16,6 +16,9 @@ option(Idefix_DEBUG "Enable Idefix debug features (makes the code very slow)" OF option(Idefix_RUNTIME_CHECKS "Enable runtime sanity checks" OFF) option(Idefix_WERROR "Treat compiler warnings as errors" OFF) option(Idefix_PYTHON "Enable python bindings (requires pybind11)" OFF) +option(Idefix_MPI_GPU_DIRECT "Enable usage of GPU direct to avoid CPU-GPU copies for MPI messages." ON) +option(Idefix_MPI_GPU_FORCE_COPY "When GPU_DIRECT is disabled, force using transfers for validation purpose." OFF) +mark_as_advanced(Idefix_MPI_GPU_FORCE_TRANSFERS) option(Idefix_SUPPRESS_FMA "Disable FMA (fused multiply-add) contraction/codegen. Useful for code validation across architectures." OFF) set(Idefix_PROBLEM_DIR "${CMAKE_BINARY_DIR}" CACHE STRING "Problem directory to build for.") set(Idefix_CXX_FLAGS "" CACHE STRING "Additional compiler/linker flag") @@ -36,6 +39,10 @@ set_property(CACHE Idefix_PRECISION PROPERTY STRINGS Double Single) set(Idefix_LOOP_PATTERN "Default" CACHE STRING "Loop pattern for idefix_for") set_property(CACHE Idefix_LOOP_PATTERN PROPERTY STRINGS Default SIMD Range MDRange TeamPolicy TeamPolicyInnerVector) +set(Idefix_MPI_MODE "Persistent" CACHE STRING "MPI communication mode to use.") +set_property(CACHE Idefix_MPI_MODE PROPERTY STRINGS Persistent Blocking NonBlocking) +mark_as_advanced(Idefix_MPI_MODE) + # load git revision tools list(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/cmake/") include(GetGitRevisionDescription) @@ -109,6 +116,10 @@ if(Idefix_MPI) add_subdirectory(src/mpi) endif() +if (Idefix_MPI_GPU_DIRECT) + add_compile_definitions("WITH_MPI_GPU_DIRECT") +endif() + if(Idefix_HDF5) add_compile_definitions("WITH_HDF5") if(Idefix_MPI) @@ -245,6 +256,20 @@ if(${Idefix_PRECISION} STREQUAL "Single") add_compile_definitions("SINGLE_PRECISION") endif() +# MPI mode +if(${Idefix_MPI_MODE} STREQUAL "Persistent") + add_compile_definitions("COMMUNICATION_MODE_PERSISTENT") +elseif(${Idefix_MPI_MODE} STREQUAL "NonBlocking") + add_compile_definitions("COMMUNICATION_MODE_NON_BLOCKING") +else(NOT ${Idefix_MPI_MODE} STREQUAL "Blocking") + message(ERROR "Unknown MPI communication mode : Idefix_MPI_MODE=${Idefix_MPI_MODE}") +endif() + +# GPU direct disabled and force transfers +if (${Idefix_MPI_GPU_FORCE_COPY}) + add_compile_definitions("WITH_GPU_FORCE_COPY") +endif() + target_include_directories(idefix PUBLIC "${Idefix_PROBLEM_DIR_ABS}" ) @@ -297,6 +322,7 @@ endif() message(STATUS " MPI: ${Idefix_MPI}") message(STATUS " HDF5: ${Idefix_HDF5}") message(STATUS " Python: ${Idefix_PYTHON}") +message(STATUS " GPU direct: ${Idefix_MPI_GPU_DIRECT}") message(STATUS " Reconstruction: ${Idefix_RECONSTRUCTION}") message(STATUS " Precision: ${Idefix_PRECISION}") message(STATUS " Version: ${Idefix_VERSION}") diff --git a/doc/source/faq.rst b/doc/source/faq.rst index 4dd198318..c1df8bdb9 100644 --- a/doc/source/faq.rst +++ b/doc/source/faq.rst @@ -27,6 +27,9 @@ I have a complex setup, and have written some functions in separate .cpp files. I want to run on the GPUs of xxx machine, how do I proceed? Check the examples in :ref:`setupExamples` +I don't have a CUDA or HIP aware MPI with GPU DIRECT support, how I can run *Idefix* ? + You can look at the compile option `-DIdefix_MPI_GPU_DIRECT=OFF` in :ref:`makefile` to disable GPU DIRECT usage. Note that this will decrease performances. + Compilation ----------- diff --git a/doc/source/reference/makefile.rst b/doc/source/reference/makefile.rst index 8f58ceedb..fa83b4935 100644 --- a/doc/source/reference/makefile.rst +++ b/doc/source/reference/makefile.rst @@ -1,3 +1,5 @@ +.. _makefile: + Code configuration with Cmake ============================= @@ -33,6 +35,10 @@ Several options can be enabled from the command line (or are accessible with ``c ``-D Idefix_MPI=ON`` Enable MPI parallelisation. Requires an MPI library. When used in conjonction with CUDA (Nvidia GPUs), a CUDA-aware MPI library is required by *Idefix*. +``-D Idefix_MPI_GPU_DIRECT=OFF`` + Disable the usage of MPI GPU direct for inter-process communication. In this case it uses a copy between GPU and GPU before and after making communications. + It is usefull if your MPI is not GPU-aware. Note that this option decreases performances. + ``-D Idefix_DEFS=foo.hpp`` Specify a particular filename to be used in place of the default problem file ``definitions.hpp`` diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index ffbd0de33..de907848d 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -92,6 +92,20 @@ def __init__(self, current_test_file, name=""): parser.add_argument("-mpi", help="Enable MPI", action="store_true") + parser.add_argument( + "-mpiMode", + default="Persistent", + choices=["Default", "Persistent", "NonBlocking", "Blocking"], + help="MPI communication mode to use (Default)", + type=str, + ) + + parser.add_argument( + "-mpiGpuForceCopy", + action="store_true", + help="Disable MPI GPU direct and force memory transfers for validation purpose.", + ) + parser.add_argument( "-all", help="Do all test suite (otherwise, just do the test with the current configuration)", @@ -266,6 +280,13 @@ def _genCmakeCommand(self, definitionFile=""): else: comm.append("-DIdefix_MPI=OFF") + if self.mpiMode != "Default": + comm.append(f"-DIdefix_MPI_MODE={self.mpiMode}") + + if self.mpiGpuForceCopy: + comm.append("-DIdefix_MPI_GPU_DIRECT=OFF") + comm.append("-DIdefix_MPI_GPU_FORCE_COPY=ON") + if self.reconstruction == 2: comm.append("-DIdefix_RECONSTRUCTION=Linear") elif self.reconstruction == 3: diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index a5153d361..c0b00cb36 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -25,7 +25,7 @@ void Axis::ShowConfig() { void Axis::SymmetrizeEx1Side(int jref, IdefixArray3D Ex1) { #if DIMENSIONS == 3 - IdefixArray1D Ex1Avg = this->Ex1Avg; + auto Ex1Avg = this->Ex1Avg.deviceView(); idefix_for("Ex1_ini",0,data->np_tot[IDIR], KOKKOS_LAMBDA(int i) { @@ -40,7 +40,7 @@ void Axis::SymmetrizeEx1Side(int jref, IdefixArray3D Ex1) { #ifdef WITH_MPI Kokkos::fence(); // sum along all of the processes on the same r - MPI_Allreduce(MPI_IN_PLACE, Ex1Avg.data(), data->np_tot[IDIR], realMPI, + idfx::MPI_Allreduce(MPI_IN_PLACE, this->Ex1Avg, data->np_tot[IDIR], realMPI, MPI_SUM, data->mygrid->AxisComm); #endif } @@ -88,7 +88,8 @@ void Axis::RegularizeCurrentSide(int side) { jc = data->end[JDIR]-1; sign = -1; } - IdefixArray1D BAvg = this->Ex1Avg; + auto BAvg = this->Ex1Avg.deviceView(); + auto BAvgComm = this->Ex1Avg; IdefixArray1D x1 = data->x[IDIR]; IdefixArray1D dx3 = data->dx[KDIR]; IdefixArray1D dx2 = data->dx[JDIR]; @@ -107,7 +108,7 @@ void Axis::RegularizeCurrentSide(int side) { #ifdef WITH_MPI Kokkos::fence(); // sum along all of the processes on the same r - MPI_Allreduce(MPI_IN_PLACE, BAvg.data(), data->np_tot[IDIR], realMPI, + MPI_Allreduce(MPI_IN_PLACE, BAvgComm, data->np_tot[IDIR], realMPI, MPI_SUM, data->mygrid->AxisComm); #endif } @@ -169,7 +170,7 @@ void Axis::FixBx2sAxis(int side) { // Compute the values of Bx and By that are consistent with BX2 along the axis #if DIMENSIONS == 3 IdefixArray4D Vs = this->Vs; - IdefixArray2D BAvg = this->BAvg; + auto BAvg = this->BAvg.deviceView(); IdefixArray1D phi = data->x[KDIR]; int jin = 0; @@ -208,7 +209,7 @@ void Axis::FixBx2sAxis(int side) { Kokkos::fence(); #ifdef WITH_MPI // sum along all of the processes on the same r - MPI_Allreduce(MPI_IN_PLACE, BAvg.data(), 2*data->np_tot[IDIR], realMPI, + idfx::MPI_Allreduce(MPI_IN_PLACE, this->BAvg, 2*data->np_tot[IDIR], realMPI, MPI_SUM, data->mygrid->AxisComm); #endif } @@ -392,7 +393,6 @@ void Axis::ExchangeMPI(int side) { idfx::pushRegion("Axis::ExchangeMPI"); #ifdef WITH_MPI // Load the buffers with data - [[maybe_unused]] int ibeg,iend,jbeg,jend,kbeg,kend; int offset; int ny; Buffer bufferSend = this->bufferSend; @@ -409,7 +409,7 @@ void Axis::ExchangeMPI(int side) { MPI_Status recvStatus; double tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Start(&recvRequest)); + MPI_SAFE_CALL(idfx::MPI_Start(&recvRequest)); idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Coordinates of the ghost region which needs to be transfered @@ -471,8 +471,8 @@ void Axis::ExchangeMPI(int side) { Kokkos::fence(); tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Start(&sendRequest)); - MPI_Wait(&recvRequest,&recvStatus); + MPI_SAFE_CALL(idfx::MPI_Start(&sendRequest)); + idfx::MPI_Wait(&recvRequest,&recvStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Unpack @@ -526,8 +526,7 @@ void Axis::ExchangeMPI(int side) { } // MHD } - MPI_Wait(&sendRequest, &sendStatus); - + idfx::MPI_Wait(&sendRequest, &sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; @@ -594,11 +593,11 @@ void Axis::InitMPI() { MPI_SAFE_CALL(MPI_Cart_shift(data->mygrid->AxisComm,0,data->mygrid->nproc[KDIR]/2, &procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(bufferSend.data(), bufferSend.Size(), realMPI, procSend, - 650, data->mygrid->AxisComm, &sendRequest)); + MPI_SAFE_CALL(idfx::MPI_Send_init(bufferSend.commView(), bufferSend.Size(), + realMPI, procSend, 650, data->mygrid->AxisComm, &sendRequest)); - MPI_SAFE_CALL(MPI_Recv_init(bufferRecv.data(), bufferRecv.Size(), realMPI, procRecv, - 650, data->mygrid->AxisComm, &recvRequest)); + MPI_SAFE_CALL(idfx::MPI_Recv_init(bufferRecv.commView(), bufferRecv.Size(), + realMPI, procRecv, 650, data->mygrid->AxisComm, &recvRequest)); #endif idfx::popRegion(); diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index 390a628ce..ad2389fe9 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -57,8 +57,8 @@ class Axis { enum {faceTop, faceBot}; #ifdef WITH_MPI - MPI_Request sendRequest; - MPI_Request recvRequest; + idfx::MPI_Request_1D sendRequest; + idfx::MPI_Request_1D recvRequest; Buffer bufferSend; Buffer bufferRecv; @@ -71,8 +71,8 @@ class Axis { #endif void InitMPI(); - IdefixArray1D Ex1Avg; - IdefixArray2D BAvg; + idfx::IdefixCommArray1D Ex1Avg; + idfx::IdefixCommArray2D BAvg; bool haveCurrent; IdefixArray2D JAvg; IdefixArray1D symmetryVc; @@ -155,8 +155,8 @@ Axis::Axis(Boundary *boundary) { } Kokkos::deep_copy(symmetryVs, symmetryVsHost); - this->Ex1Avg = IdefixArray1D("Axis:Ex1Avg",data->np_tot[IDIR]); - this->BAvg = IdefixArray2D("Axis:BxAvg",data->np_tot[IDIR],2); + this->Ex1Avg = idfx::IdefixCommArray1D("Axis:Ex1Avg",data->np_tot[IDIR]); + this->BAvg = idfx::IdefixCommArray2D("Axis:BxAvg",data->np_tot[IDIR],2); if(haveCurrent) { this->JAvg = IdefixArray2D("Axis:JAvg",data->np_tot[IDIR],3); } diff --git a/src/fluid/constrainedTransport/EMFexchange.hpp b/src/fluid/constrainedTransport/EMFexchange.hpp index 179783802..22fbb58e8 100644 --- a/src/fluid/constrainedTransport/EMFexchange.hpp +++ b/src/fluid/constrainedTransport/EMFexchange.hpp @@ -41,7 +41,7 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 MPI_Status recvStatus[2]; double tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX1)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, recvRequestX1)); idfx::mpiCallsTimer += MPI_Wtime() - tStart; BoundaryType lbound = data->lbound[IDIR]; @@ -82,11 +82,10 @@ void ConstrainedTransport::ExchangeX1(IdefixArray3D ey, IdefixArray3 Kokkos::fence(); tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX1)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, sendRequestX1)); // Wait for buffers to be received - - MPI_Waitall(2,recvRequestX1,recvStatus); - MPI_Waitall(2, sendRequestX1, sendStatus); + idfx::MPI_Waitall(2,recvRequestX1,recvStatus); + idfx::MPI_Waitall(2, sendRequestX1, sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Unpack @@ -130,7 +129,7 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 double tStart = MPI_Wtime(); MPI_Status sendStatus[2]; MPI_Status recvStatus[2]; - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX2)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, recvRequestX2)); idfx::mpiCallsTimer += MPI_Wtime() - tStart; BoundaryType lbound = data->lbound[JDIR]; @@ -169,10 +168,10 @@ void ConstrainedTransport::ExchangeX2(IdefixArray3D ex, IdefixArray3 Kokkos::fence(); tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX2)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, sendRequestX2)); // Wait for buffers to be received - MPI_Waitall(2, recvRequestX2, recvStatus); - MPI_Waitall(2, sendRequestX2, sendStatus); + idfx::MPI_Waitall(2, recvRequestX2, recvStatus); + idfx::MPI_Waitall(2, sendRequestX2, sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Unpack @@ -216,7 +215,7 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 double tStart = MPI_Wtime(); MPI_Status sendStatus[2]; MPI_Status recvStatus[2]; - MPI_SAFE_CALL(MPI_Startall(2, recvRequestX3)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, recvRequestX3)); idfx::mpiCallsTimer += MPI_Wtime() - tStart; BoundaryType lbound = data->lbound[KDIR]; @@ -256,10 +255,10 @@ void ConstrainedTransport::ExchangeX3(IdefixArray3D ex, IdefixArray3 Kokkos::fence(); tStart = MPI_Wtime(); - MPI_SAFE_CALL(MPI_Startall(2, sendRequestX3)); + MPI_SAFE_CALL(idfx::MPI_Startall(2, sendRequestX3)); // Wait for buffers to be received - MPI_Waitall(2, recvRequestX3, recvStatus); - MPI_Waitall(2, sendRequestX3, sendStatus); + idfx::MPI_Waitall(2, recvRequestX3, recvStatus); + idfx::MPI_Waitall(2, sendRequestX3, sendStatus); idfx::mpiCallsTimer += MPI_Wtime() - tStart; // Unpack diff --git a/src/fluid/constrainedTransport/constrainedTransport.hpp b/src/fluid/constrainedTransport/constrainedTransport.hpp index ab83b23bc..5f07a6fdd 100644 --- a/src/fluid/constrainedTransport/constrainedTransport.hpp +++ b/src/fluid/constrainedTransport/constrainedTransport.hpp @@ -68,9 +68,9 @@ class ConstrainedTransport { IdefixArray3D Ex3; // Helper arrays for shearing box - IdefixArray2D sbEyL; - IdefixArray2D sbEyR; - IdefixArray2D sbEyRL; + idfx::IdefixCommArray2D sbEyL; + idfx::IdefixCommArray2D sbEyR; + idfx::IdefixCommArray2D sbEyRL; // Range of existence @@ -137,12 +137,12 @@ class ConstrainedTransport { int bufferSizeX3; // Requests for MPI persistent communications - MPI_Request sendRequestX1[2]; - MPI_Request sendRequestX2[2]; - MPI_Request sendRequestX3[2]; - MPI_Request recvRequestX1[2]; - MPI_Request recvRequestX2[2]; - MPI_Request recvRequestX3[2]; + idfx::MPI_Request_1D sendRequestX1[2]; + idfx::MPI_Request_1D sendRequestX2[2]; + idfx::MPI_Request_1D sendRequestX3[2]; + idfx::MPI_Request_1D recvRequestX1[2]; + idfx::MPI_Request_1D recvRequestX2[2]; + idfx::MPI_Request_1D recvRequestX3[2]; Kokkos::Timer timer; // Internal MPI timer #endif @@ -188,9 +188,9 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr // Allocate shearing box arrays if(hydro->haveShearingBox == true) { - sbEyL = IdefixArray2D("EMF_sbEyL", data->np_tot[KDIR], data->np_tot[JDIR]); - sbEyR = IdefixArray2D("EMF_sbEyR", data->np_tot[KDIR], data->np_tot[JDIR]); - sbEyRL = IdefixArray2D("EMF_sbEyRL", data->np_tot[KDIR], data->np_tot[JDIR]); + sbEyL = idfx::IdefixCommArray2D("EMF_sbEyL", data->np_tot[KDIR], data->np_tot[JDIR]); + sbEyR = idfx::IdefixCommArray2D("EMF_sbEyR", data->np_tot[KDIR], data->np_tot[JDIR]); + sbEyRL = idfx::IdefixCommArray2D("EMF_sbEyRL", data->np_tot[KDIR], data->np_tot[JDIR]); } D_EXPAND( ez = IdefixArray3D("EMF_ez", @@ -331,11 +331,11 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr if(data->rbound[IDIR] == shearingbox ) procSend = MPI_PROC_NULL; if(data->lbound[IDIR] == shearingbox ) procRecv = MPI_PROC_NULL; - MPI_SAFE_CALL(MPI_Send_init(BufferSendX1[faceRight].data(), bufferSizeX1, realMPI, procSend, 100, - mygrid->CartComm, &sendRequestX1[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX1[faceRight].commView(), bufferSizeX1, + realMPI, procSend, 100, mygrid->CartComm, &sendRequestX1[faceRight])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX1[faceLeft].data(), bufferSizeX1, realMPI, procRecv, 100, - mygrid->CartComm, &recvRequestX1[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX1[faceLeft].commView(), bufferSizeX1, + realMPI, procRecv, 100, mygrid->CartComm, &recvRequestX1[faceLeft])); // Send to the left // We receive from procRecv, and we send to procSend @@ -344,52 +344,52 @@ ConstrainedTransport::ConstrainedTransport(Input &input, Fluid *hydr if(data->lbound[IDIR] == shearingbox ) procSend = MPI_PROC_NULL; if(data->rbound[IDIR] == shearingbox ) procRecv = MPI_PROC_NULL; - MPI_SAFE_CALL(MPI_Send_init(BufferSendX1[faceLeft].data(), bufferSizeX1, realMPI, procSend, 101, - mygrid->CartComm, &sendRequestX1[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX1[faceLeft].commView(), bufferSizeX1, + realMPI, procSend, 101, mygrid->CartComm, &sendRequestX1[faceLeft])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX1[faceRight].data(), bufferSizeX1, realMPI, procRecv, 101, - mygrid->CartComm, &recvRequestX1[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX1[faceRight].commView(), bufferSizeX1, + realMPI, procRecv, 101, mygrid->CartComm, &recvRequestX1[faceRight])); #if DIMENSIONS >= 2 // We receive from procRecv, and we send to procSend MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,1,&procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(BufferSendX2[faceRight].data(), bufferSizeX2, realMPI, procSend, 200, - mygrid->CartComm, &sendRequestX2[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX2[faceRight].commView(), bufferSizeX2, + realMPI, procSend, 200, mygrid->CartComm, &sendRequestX2[faceRight])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX2[faceLeft].data(), bufferSizeX2, realMPI, procRecv, 200, - mygrid->CartComm, &recvRequestX2[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX2[faceLeft].commView(), bufferSizeX2, + realMPI, procRecv, 200, mygrid->CartComm, &recvRequestX2[faceLeft])); // Send to the left // We receive from procRecv, and we send to procSend MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,1,-1,&procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(BufferSendX2[faceLeft].data(), bufferSizeX2, realMPI, procSend, 201, - mygrid->CartComm, &sendRequestX2[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX2[faceLeft].commView(), bufferSizeX2, + realMPI, procSend, 201, mygrid->CartComm, &sendRequestX2[faceLeft])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX2[faceRight].data(), bufferSizeX2, realMPI, procRecv, 201, - mygrid->CartComm, &recvRequestX2[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX2[faceRight].commView(), bufferSizeX2, + realMPI, procRecv, 201, mygrid->CartComm, &recvRequestX2[faceRight])); #endif #if DIMENSIONS == 3 // We receive from procRecv, and we send to procSend MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,1,&procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(BufferSendX3[faceRight].data(), bufferSizeX3, realMPI, procSend, 300, - mygrid->CartComm, &sendRequestX3[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX3[faceRight].commView(), bufferSizeX3, + realMPI, procSend, 300, mygrid->CartComm, &sendRequestX3[faceRight])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX3[faceLeft].data(), bufferSizeX3, realMPI, procRecv, 300, - mygrid->CartComm, &recvRequestX3[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX3[faceLeft].commView(), bufferSizeX3, + realMPI, procRecv, 300, mygrid->CartComm, &recvRequestX3[faceLeft])); // Send to the left // We receive from procRecv, and we send to procSend MPI_SAFE_CALL(MPI_Cart_shift(mygrid->CartComm,2,-1,&procRecv,&procSend )); - MPI_SAFE_CALL(MPI_Send_init(BufferSendX3[faceLeft].data(), bufferSizeX3, realMPI, procSend, 301, - mygrid->CartComm, &sendRequestX3[faceLeft])); + MPI_SAFE_CALL(idfx::MPI_Send_init(BufferSendX3[faceLeft].commView(), bufferSizeX3, + realMPI, procSend, 301, mygrid->CartComm, &sendRequestX3[faceLeft])); - MPI_SAFE_CALL(MPI_Recv_init(BufferRecvX3[faceRight].data(), bufferSizeX3, realMPI, procRecv, 301, - mygrid->CartComm, &recvRequestX3[faceRight])); + MPI_SAFE_CALL(idfx::MPI_Recv_init(BufferRecvX3[faceRight].commView(), bufferSizeX3, + realMPI, procRecv, 301, mygrid->CartComm, &recvRequestX3[faceRight])); #endif #endif // WITH_MPI @@ -409,17 +409,17 @@ ConstrainedTransport::~ConstrainedTransport() { // Properly clean up the mess idfx::cout << "Emf: Cleaning up MPI persistent communication channels" << std::endl; for(int i=0 ; i< 2; i++) { - MPI_Request_free( &sendRequestX1[i]); - MPI_Request_free( &recvRequestX1[i]); + idfx::MPI_Request_free( &sendRequestX1[i]); + idfx::MPI_Request_free( &recvRequestX1[i]); #if DIMENSIONS >= 2 - MPI_Request_free( &sendRequestX2[i]); - MPI_Request_free( &recvRequestX2[i]); + idfx::MPI_Request_free( &sendRequestX2[i]); + idfx::MPI_Request_free( &recvRequestX2[i]); #endif #if DIMENSIONS == 3 - MPI_Request_free( &sendRequestX3[i]); - MPI_Request_free( &recvRequestX3[i]); + idfx::MPI_Request_free( &sendRequestX3[i]); + idfx::MPI_Request_free( &recvRequestX3[i]); #endif } #endif diff --git a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp index 9d3d6913f..b35bec9fa 100644 --- a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp +++ b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp @@ -108,9 +108,9 @@ void ConstrainedTransport::SymmetrizeEMFShearingBox() { idfx::pushRegion("Emf::EnforceEMFBoundary"); #if MHD == YES - IdefixArray2D sbEyL = this->sbEyL; - IdefixArray2D sbEyR = this->sbEyR; - IdefixArray2D sbEyRL = this->sbEyRL; + auto sbEyL = this->sbEyL.deviceView(); + auto sbEyR = this->sbEyR.deviceView(); + auto sbEyRL = this->sbEyRL.deviceView(); IdefixArray3D ey = this->ey; @@ -142,16 +142,16 @@ void ConstrainedTransport::SymmetrizeEMFShearingBox() { // We send to our left (which, by periodicity, is the right end of the domain) // our value of sbEyL and get Kokkos::fence(); - MPI_Sendrecv(sbEyL.data(), size, realMPI, procLeft, 2001, - sbEyR.data(), size, realMPI, procLeft, 2002, + idfx::MPI_Sendrecv(this->sbEyL, size, realMPI, procLeft, 2001, + this->sbEyR, size, realMPI, procLeft, 2002, data->mygrid->CartComm, &status ); } if(data->rbound[IDIR]==shearingbox) { Kokkos::fence(); // We send to our right (which, by periodicity, is the left end (=beginning) // of the domain) our value of sbEyR and get sbEyL - MPI_Sendrecv(sbEyR.data(), size, realMPI, procRight, 2002, - sbEyL.data(), size, realMPI, procRight, 2001, + idfx::MPI_Sendrecv(this->sbEyR, size, realMPI, procRight, 2002, + this->sbEyL, size, realMPI, procRight, 2001, data->mygrid->CartComm, &status ); } } diff --git a/src/mpi/buffer.hpp b/src/mpi/buffer.hpp index b045b86e7..f4f4f423a 100644 --- a/src/mpi/buffer.hpp +++ b/src/mpi/buffer.hpp @@ -10,6 +10,7 @@ #include "idefix.hpp" #include "arrays.hpp" +#include "mpiWrapper.hpp" using BoundingBox = std::array,3>; @@ -17,7 +18,9 @@ using BoundingBox = std::array,3>; class Buffer { public: Buffer() = default; - explicit Buffer(size_t size): pointer{0}, array{IdefixArray1D("BufferArray",size)} {}; + explicit Buffer(size_t size) + : pointer{0} + , array{IdefixArray1D("BufferArray",size)} {} // Compute the size of a bounding box static size_t ComputeBoxSize(BoundingBox box) { @@ -27,16 +30,20 @@ class Buffer { return(ninjnk); } - void* data() { - return(array.data()); + void* deviceData() { + return(array.deviceView().data()); } - const IdefixArray1D & getArray(void) const { + IdefixArray1D & deviceView(void) { + return this->array.deviceView(); + } + + idfx::IdefixCommArray1D & commView(void) { return this->array; } int Size() { - return(array.size()); + return(array.deviceView().size()); } void ResetPointer() { @@ -55,7 +62,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("LoadBuffer3D",kbeg,kend,jbeg,jend,ibeg,iend, KOKKOS_LAMBDA (int k, int j, int i) { arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(k,j,i); @@ -79,7 +86,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("LoadBuffer4D_var",kbeg,kend,jbeg,jend,ibeg,iend, KOKKOS_LAMBDA (int k, int j, int i) { arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ) = in(var, k,j,i); @@ -102,7 +109,7 @@ class Buffer { const int jend = box[JDIR][1]; const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("LoadBuffer4D_map",0,map.size(), kbeg,kend, @@ -128,7 +135,7 @@ class Buffer { const int jend = box[JDIR][1]; const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("UnLoadBuffer3D",kbeg,kend,jbeg,jend,ibeg,iend, KOKKOS_LAMBDA (int k, int j, int i) { @@ -153,7 +160,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("UnLoadBuffer4D_var",kbeg,kend,jbeg,jend,ibeg,iend, KOKKOS_LAMBDA (int k, int j, int i) { out(var,k,j,i) = arr(i-ibeg + (j-jbeg)*ni + (k-kbeg)*ninj + offset ); @@ -178,7 +185,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("UnLoadBuffer4D_var_sym",kbeg,kend,jbeg,jend,ibeg,iend, KOKKOS_LAMBDA (int k, int j, int i) { const int jinverted = jend-(j-jbeg)-1; @@ -205,7 +212,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("UnLoadBuffer4D_map",0,map.size(), kbeg,kend, jbeg,jend, @@ -233,7 +240,7 @@ class Buffer { const int kend = box[KDIR][1]; const int offset = this->pointer; - auto arr = this->array; + auto arr = this->array.deviceView(); idefix_for("UnLoadBuffer4D_map_sym",0,map.size(), kbeg,kend, jbeg,jend, @@ -248,10 +255,9 @@ class Buffer { this->pointer += ninjnk*map.size(); } - private: - size_t pointer; - IdefixArray1D array; + size_t pointer{0}; + idfx::IdefixCommArray1D array{}; }; #endif // MPI_BUFFER_HPP_ diff --git a/src/mpi/commArray.hpp b/src/mpi/commArray.hpp new file mode 100644 index 000000000..3856c7e8c --- /dev/null +++ b/src/mpi/commArray.hpp @@ -0,0 +1,224 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef MPI_COMMARRAY_HPP_ +#define MPI_COMMARRAY_HPP_ + +//To enable to force transfers and validate that it is working in any conditions. +//#define WITH_GPU_FORCE_COPY + +#ifdef WITH_MPI + #include +#endif //WITH_MPI + +#include +#include +#include + +#include "idefix.hpp" + +namespace idfx { + +/** + * Provide a specific array used for MPI communications. It embeds the standard + * array as usual, and also optionally a communication copy on the host, depending + * if we have access to WITH_MPI_GPU_DIRECT or not. + */ +template +class IdefixCommArrayGpuDirect { + public: + template + explicit IdefixCommArrayGpuDirect(Args... args) + :deviceArray(args...) + {} + + /** + * Acces as a simple device view for use in kokkos kernels + * (because need to not carry the host part). + */ + T & deviceView(void) { + return this->deviceArray; + } + + /** + * Acces as a simple communication view for use in communication routines. + */ + T commView(void) { + return this->deviceArray; + } + + /** + * If needed, transfers the data from the device to the host to be ready to make + * a communication. + */ + void syncCommData(void) {} + + /** + * If needed, transfers the data from the device to the host to be ready to make + * a communication. + */ + void syncCommDataAsync(void) {} + + /** + * If needed, transerts the data to the device after a communication to be ready + * to use it. + */ + void syncDeviceData(void) {} + + /** + * If needed, transerts the data to the device after a communication to be ready + * to use it. + */ + void syncDeviceDataAsync(void) {} + + /** + * Get access to the communication array. It will be either on host or device + * depending on the WITH_MPI_GPU_DIRECT configuration. + */ + void * commData(void) { + return this->deviceArray.data(); + } + + private: + /** + * Device buffer containing the device side of the data to use for communications. + * This where the computation are done. Then it is transfered to/from the communication + * buffer if needed. + */ + T deviceArray; +}; + +/** + * Provide a specific array used for MPI communications. It embeds the standard + * array as usual, and also optionally a communication copy on the host, depending + * if we have access to WITH_MPI_GPU_DIRECT or not. + */ +template +class IdefixCommArrayNoGpuDirect { + public: + template + explicit IdefixCommArrayNoGpuDirect(Args... args) + :deviceArray(args...) + ,commArray(initCommArray(this->deviceArray)) + {} + + /** + * Acces as a simple device view for use in kokkos kernels + * (because need to not carry the host part). + */ + T & deviceView(void) { + return this->deviceArray; + } + + /** + * Acces as a simple communication view for use in communication routines. + */ + typename T::host_mirror_type & commView(void) { + return this->commArray; + } + + /** + * If needed, transfers the data from the device to the host to be ready to make + * a communication. + */ + void syncCommData(void) { + Kokkos::deep_copy(this->commArray, this->deviceArray); + } + + /** + * If needed, transfers the data from the device to the host to be ready to make + * a communication. + */ + void syncCommDataAsync(void) { + Kokkos::deep_copy(Kokkos::DefaultExecutionSpace(), this->commArray, this->deviceArray); + } + + /** + * If needed, transerts the data to the device after a communication to be ready + * to use it. + */ + void syncDeviceData(void) { + Kokkos::deep_copy(this->deviceArray, this->commArray); + } + + /** + * If needed, transerts the data to the device after a communication to be ready + * to use it. + */ + void syncDeviceDataAsync(void) { + Kokkos::deep_copy(Kokkos::DefaultExecutionSpace(), this->deviceArray, this->commArray); + } + + /** + * Get access to the communication array. It will be either on host or device + * depending on the WITH_MPI_GPU_DIRECT configuration. + */ + void * commData(void) { + return this->commArray.data(); + } + + private: + static typename T::host_mirror_type initCommArray(T & deviceArray) { + #ifdef WITH_GPU_FORCE_COPY + //for validation purpose, force the transfers by using a copy anytime. + return Kokkos::create_mirror(deviceArray); + #else + //if no GPU DIRECT, it creates a copy only if deviceArray is on GPU, + //if on host, it just reference it + return Kokkos::create_mirror_view(deviceArray); + #endif + } + + private: + /** + * Device buffer containing the device side of the data to use for communications. + * This where the computation are done. Then it is transfered to/from the communication + * buffer if needed. + */ + T deviceArray; + /** + * Buffer to contain a copy of the data on host if required. If WITH_MPI_GPU_DIRECT + * is enabled it directly points the device buffer as no copy is required. + */ + typename T::host_mirror_type commArray; +}; + +#ifdef WITH_MPI_GPU_DIRECT + template using IdefixCommArray = IdefixCommArrayGpuDirect; +#else + template using IdefixCommArray = IdefixCommArrayNoGpuDirect; +#endif + +/** Wrap the idefix 1D array to use it for communication purpose. */ +template using IdefixCommArray1D = IdefixCommArray< IdefixArray1D >; +/** Wrap the idefix 2D array to use it for communication purpose. */ +template using IdefixCommArray2D = IdefixCommArray< IdefixArray2D >; +/** Wrap the idefix 3D array to use it for communication purpose. */ +template using IdefixCommArray3D = IdefixCommArray< IdefixArray3D >; +/** Wrap the idefix 4D array to use it for communication purpose. */ +template using IdefixCommArray4D = IdefixCommArray< IdefixArray4D >; + +template +struct Idefix_MPI_Request { + IdefixCommArray commArray; + #ifdef WITH_MPI + MPI_Request request; + #endif //WITH_MPI +}; + +/** Wrap the idefix 1D array to use it for communication purpose. */ +template using MPI_Request_1D = Idefix_MPI_Request< IdefixArray1D >; +/** Wrap the idefix 2D array to use it for communication purpose. */ +template using MPI_Request_2D = Idefix_MPI_Request< IdefixArray2D >; +/** Wrap the idefix 3D array to use it for communication purpose. */ +template using MPI_Request_3D = Idefix_MPI_Request< IdefixArray3D >; +/** Wrap the idefix 4D array to use it for communication purpose. */ +template using MPI_Request_4D = Idefix_MPI_Request< IdefixArray4D >; + +} // namespace idfx + +#endif // MPI_COMMARRAY_HPP_ diff --git a/src/mpi/exchanger.cpp b/src/mpi/exchanger.cpp index 033ce4041..7f377c2ac 100644 --- a/src/mpi/exchanger.cpp +++ b/src/mpi/exchanger.cpp @@ -12,8 +12,11 @@ #include "grid.hpp" #include "arrays.hpp" -//#define MPI_NON_BLOCKING -#define MPI_PERSISTENT +#if defined(COMMUNICATION_MODE_NON_BLOCKING) + #define MPI_NON_BLOCKING +#elif defined(COMMUNICATION_MODE_PERSISTENT) + #define MPI_PERSISTENT +#endif //COMMUNICATION_MODE_* int Exchanger::nInstances = 0; @@ -129,22 +132,22 @@ void Exchanger::Init( // X1-dir exchanges // We receive from procRecv, and we send to procSend - MPI_Send_init(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, + idfx::MPI_Send_init(BufferSend[faceRight].commView(), bufferSizeSend[faceRight], realMPI, procSend[faceRight], thisInstance*2, grid->CartComm, &sendRequest[faceRight]); - MPI_Recv_init(BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, + idfx::MPI_Recv_init(BufferRecv[faceLeft].commView(), bufferSizeRecv[faceLeft], realMPI, procRecv[faceLeft],thisInstance*2, grid->CartComm, &recvRequest[faceLeft]); // Send to the left // We receive from procRecv, and we send to procSend - MPI_Send_init(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, + idfx::MPI_Send_init(BufferSend[faceLeft].commView(), bufferSizeSend[faceLeft], realMPI, procSend[faceLeft],thisInstance*2+1, grid->CartComm, &sendRequest[faceLeft]); - MPI_Recv_init(BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, + idfx::MPI_Recv_init(BufferRecv[faceRight].commView(), bufferSizeRecv[faceRight], realMPI, procRecv[faceRight], thisInstance*2+1, grid->CartComm, &recvRequest[faceRight]); @@ -163,8 +166,8 @@ Exchanger::~Exchanger() { // Properly clean up the mess #ifdef MPI_PERSISTENT for(int i=0 ; i< 2; i++) { - MPI_Request_free( &sendRequest[i]); - MPI_Request_free( &recvRequest[i]); + idfx::MPI_Request_free( &sendRequest[i]); + idfx::MPI_Request_free( &recvRequest[i]); } #endif isInitialized = false; @@ -189,7 +192,7 @@ void Exchanger::Exchange(IdefixArray4D Vc, IdefixArray4D Vs) { MPI_Status sendStatus[2]; MPI_Status recvStatus[2]; - MPI_Startall(2, recvRequest); + idfx::MPI_Startall(2, recvRequest); idfx::mpiCallsTimer += MPI_Wtime() - tStart; #endif myTimer += MPI_Wtime(); @@ -211,65 +214,68 @@ void Exchanger::Exchange(IdefixArray4D Vc, IdefixArray4D Vs) { Kokkos::fence(); myTimer -= MPI_Wtime(); tStart = MPI_Wtime(); + #ifdef MPI_PERSISTENT - MPI_Startall(2, sendRequest); + idfx::MPI_Startall(2, sendRequest); // Wait for buffers to be received - MPI_Waitall(2,recvRequest,recvStatus); + idfx::MPI_Waitall(2, recvRequest, recvStatus); #else #ifdef MPI_NON_BLOCKING MPI_Status sendStatus[2]; MPI_Status recvStatus[2]; - MPI_Request sendRequest[2]; - MPI_Request recvRequest[2]; + idfx::MPI_Request_1D sendRequest[2]; + idfx::MPI_Request_1D recvRequest[2]; // We receive from procRecv, and we send to procSend - MPI_Isend(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, - procSend[faceRight], 100, mygrid->CartComm, &sendRequest[0]); + idfx::MPI_Isend(BufferSend[faceRight].commView(), bufferSizeSend[faceRight], realMPI, + procSend[faceRight], 100, grid->CartComm, &sendRequest[0]); - MPI_Irecv(BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, - procRecv[faceLeft], 100, mygrid->CartComm, &recvRequest[0]); + idfx::MPI_Irecv(BufferRecv[faceLeft].commView(), bufferSizeRecv[faceLeft], realMPI, + procRecv[faceLeft], 100, grid->CartComm, &recvRequest[0]); // Send to the left // We receive from procRecv, and we send to procSend - MPI_Isend(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, - procSend[faceLeft], 101, mygrid->CartComm, &sendRequest[1]); + idfx::MPI_Isend(BufferSend[faceLeft].commView(), bufferSizeSend[faceLeft], realMPI, + procSend[faceLeft], 101, grid->CartComm, &sendRequest[1]); - MPI_Irecv(BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, - procRecv[faceRight], 101, mygrid->CartComm, &recvRequest[1]); + idfx::MPI_Irecv(BufferRecv[faceRight].commView(), bufferSizeRecv[faceRight], realMPI, + procRecv[faceRight], 101, grid->CartComm, &recvRequest[1]); // Wait for recv to complete (we don't care about the sends) - MPI_Waitall(2, recvRequest, recvStatus); + idfx::MPI_Waitall(2, recvRequest, recvStatus); #else MPI_Status status; // Send to the right // We receive from procRecv, and we send to procSend - MPI_Sendrecv(BufferSend[faceRight].data(), bufferSizeSend[faceRight], realMPI, + idfx::MPI_Sendrecv(BufferSend[faceRight].commView(), bufferSizeSend[faceRight], realMPI, procSend[faceRight], 100, - BufferRecv[faceLeft].data(), bufferSizeRecv[faceLeft], realMPI, + BufferRecv[faceLeft].commView(), bufferSizeRecv[faceLeft], realMPI, procRecv[faceLeft], 100, grid->CartComm, &status); // Send to the left // We receive from procRecv, and we send to procSend - MPI_Sendrecv(BufferSend[faceLeft].data(), bufferSizeSend[faceLeft], realMPI, + idfx::MPI_Sendrecv(BufferSend[faceLeft].commView(), bufferSizeSend[faceLeft], realMPI, procSend[faceLeft], 101, - BufferRecv[faceRight].data(), bufferSizeRecv[faceRight], realMPI, + BufferRecv[faceRight].commView(), bufferSizeRecv[faceRight], realMPI, procRecv[faceRight], 101, grid->CartComm, &status); #endif #endif myTimer += MPI_Wtime(); -idfx::mpiCallsTimer += MPI_Wtime() - tStart; + // Unpack BufferLeft=BufferRecv[faceLeft]; BufferRight=BufferRecv[faceRight]; +idfx::mpiCallsTimer += MPI_Wtime() - tStart; + BufferLeft.ResetPointer(); BufferRight.ResetPointer(); @@ -292,11 +298,11 @@ if(recvRight) { myTimer -= MPI_Wtime(); #ifdef MPI_NON_BLOCKING // Wait for the sends if they have not yet completed - MPI_Waitall(2, sendRequest, sendStatus); + idfx::MPI_Waitall(2, sendRequest, sendStatus); #endif #ifdef MPI_PERSISTENT - MPI_Waitall(2, sendRequest, sendStatus); + idfx::MPI_Waitall(2, sendRequest, sendStatus); #endif myTimer += MPI_Wtime(); bytesSentOrReceived += (bufferSizeRecv[faceLeft] diff --git a/src/mpi/exchanger.hpp b/src/mpi/exchanger.hpp index 2e1affcb0..d5b53e123 100644 --- a/src/mpi/exchanger.hpp +++ b/src/mpi/exchanger.hpp @@ -72,8 +72,8 @@ class Exchanger { bool haveVs{false}; // Requests for MPI persistent communications - MPI_Request sendRequest[2]; - MPI_Request recvRequest[2]; + idfx::MPI_Request_1D sendRequest[2]; + idfx::MPI_Request_1D recvRequest[2]; Grid *grid; }; diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp index d0759199a..75c45c0f7 100644 --- a/src/mpi/mpi.cpp +++ b/src/mpi/mpi.cpp @@ -123,19 +123,21 @@ void Mpi::ExchangeX3(IdefixArray4D Vc, IdefixArray4D Vs) { void Mpi::CheckConfig() { idfx::pushRegion("Mpi::CheckConfig"); // compile time check - #ifdef KOKKOS_ENABLE_CUDA + #if defined(KOKKOS_ENABLE_CUDA) && defined(WITH_MPI_GPU_DIRECT) #if defined(MPIX_CUDA_AWARE_SUPPORT) && !MPIX_CUDA_AWARE_SUPPORT - #error Your MPI library is not CUDA Aware (check Idefix requirements). + #error Your MPI library is not CUDA Aware (check Idefix requirements). \ + You can look on Idefix cmake option -DIdefix_MPI_GPU_DIRECT=OFF to skip \ + this requirement (will be slower). #endif #endif /* MPIX_CUDA_AWARE_SUPPORT */ // Run-time check that we can do a reduce on device arrays - IdefixArray1D src("MPIChecksrc",1); - IdefixArray1D::host_mirror_type srcHost = Kokkos::create_mirror_view(src); + idfx::IdefixCommArray1D src("MPIChecksrc",1); + IdefixArray1D::host_mirror_type srcHost = Kokkos::create_mirror_view(src.deviceView()); if(idfx::prank == 0) { srcHost(0) = 0; - Kokkos::deep_copy(src, srcHost); + Kokkos::deep_copy(src.deviceView(), srcHost); } if(idfx::psize > 1) { @@ -155,15 +157,15 @@ void Mpi::CheckConfig() { MPI_Status status; int ierrSend, ierrRecv; if(idfx::prank == 0) { - ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, idfx::prank+1, 1, MPI_COMM_WORLD); - ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::psize-1, 1, MPI_COMM_WORLD, &status); + ierrSend = idfx::MPI_Send(src, 1, MPI_INT64_T, idfx::prank+1, 1, MPI_COMM_WORLD); + ierrRecv = idfx::MPI_Recv(src, 1, MPI_INT64_T, idfx::psize-1, 1, MPI_COMM_WORLD, &status); } else { - ierrRecv = MPI_Recv(src.data(), 1, MPI_INT64_T, idfx::prank-1, 1, MPI_COMM_WORLD, &status); + ierrRecv = idfx::MPI_Recv(src, 1, MPI_INT64_T, idfx::prank-1, 1, MPI_COMM_WORLD, &status); // Add our own rank to the data - Kokkos::deep_copy(srcHost, src); + Kokkos::deep_copy(srcHost, src.deviceView()); srcHost(0) += idfx::prank; - Kokkos::deep_copy(src, srcHost); - ierrSend = MPI_Send(src.data(), 1, MPI_INT64_T, (idfx::prank+1)%idfx::psize, 1, + Kokkos::deep_copy(src.deviceView(), srcHost); + ierrSend = idfx::MPI_Send(src, 1, MPI_INT64_T, (idfx::prank+1)%idfx::psize, 1, MPI_COMM_WORLD); } @@ -190,6 +192,12 @@ void Mpi::CheckConfig() { #else errmsg << "Check your MPI library configuration." << std::endl; #endif + #if defined(KOKKKOS_ENABLE_CUDA) || defined(KOKKOS_ENABLE_HIP) + errmsg << "GPU-aware MPI is required to communicate GPU buffers directly. " + "You can disable this requirement by configuring Idefix with " + "-DIdefix_MPI_GPU_DIRECT=OFF, which falls back to staging " + "data through host memory (this will be slower)." << std::endl; + #endif errmsg << "Error: " << e.what() << std::endl; IDEFIX_ERROR(errmsg); } @@ -199,7 +207,7 @@ void Mpi::CheckConfig() { } // Check that we have the proper end result - Kokkos::deep_copy(srcHost, src); + Kokkos::deep_copy(srcHost, src.deviceView()); int64_t size = static_cast(idfx::psize); int64_t rank = static_cast(idfx::prank); int64_t result = rank == 0 ? size*(size-1)/2 : rank*(rank+1)/2; diff --git a/src/mpi/mpi.hpp b/src/mpi/mpi.hpp index b8f929326..41f13be68 100644 --- a/src/mpi/mpi.hpp +++ b/src/mpi/mpi.hpp @@ -17,6 +17,7 @@ #include "grid.hpp" #include "buffer.hpp" #include "exchanger.hpp" +#include "mpiWrapper.hpp" class DataBlock; diff --git a/src/mpi/mpiWrapper.hpp b/src/mpi/mpiWrapper.hpp new file mode 100644 index 000000000..71cc5b265 --- /dev/null +++ b/src/mpi/mpiWrapper.hpp @@ -0,0 +1,505 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// Copyright(C) Geoffroy R. J. Lesur +// and other code contributors +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + +#ifndef MPI_MPIWRAPPER_HPP_ +#define MPI_MPIWRAPPER_HPP_ + +#ifdef WITH_MPI + #include +#endif //WITH_MPI + +#include +#include +#include + +#include "idefix.hpp" +#include "commArray.hpp" + +namespace idfx { + +#ifdef WITH_MPI + +/** + * Provide a wrapper of the standard MPI_Sendrecv by handling an idefix + * communication array. It will automate the process of transfering the data + * to the host if required (when WITH_MPI_GPU_DIRECT is disabled). + */ +template +int MPI_Sendrecv(IdefixCommArray & sendbuf, int sendcount, MPI_Datatype sendtype, + int dest, int sendtag, IdefixCommArray &recvbuf, int recvcount, + MPI_Datatype recvtype, int source, int recvtag, MPI_Comm comm, MPI_Status *status) { + //check size + assert(sendbuf.span() == sendcount); + assert(sendbuf.span_is_contiguous()); + assert(recvbuf.span() == sendcount); + assert(recvbuf.span_is_contiguous()); + + //make a local allocation if needed + sendbuf.syncCommData(); + + //make the communication + const int result = ::MPI_Sendrecv(sendbuf.commData(), sendcount, sendtype, dest, sendtag, + recvbuf.commData(), recvcount, recvtype, source, recvtag, + comm, status); + + //copy back if needed + recvbuf.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_Send_init() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Send_init(IdefixCommArray & buf, int count, MPI_Datatype datatype, int dest, + int tag, MPI_Comm comm, Idefix_MPI_Request *request) { + //check + assert(request != nullptr); + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //store the values + request->commArray = buf; + + //call MPI + const int result = ::MPI_Send_init(buf.commData(), count, datatype, + dest, tag, comm, &request->request); + + //ok + return result; +} + +/** + * Overlad the MPI_Recv_init() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Recv_init(IdefixCommArray & buf, int count, MPI_Datatype datatype, int + source, int tag, MPI_Comm comm, Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //store the values + request->commArray = buf; + + //call MPI + const int result = ::MPI_Recv_init(buf.commData(), count, datatype, + source, tag, comm, &request->request); + + //ok + return result; +} + +/** + * Overlad the MPI_Request_free() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Request_free(Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + + //call MPI + return ::MPI_Request_free(&request->request); +} + +/** + * Overlad the MPI_Startall() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Startall(int count, Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + assert(count >= 0); + + //sync the copies in async mode + for (size_t i = 0 ; i < count ; i++) { + request[i].commArray.syncCommDataAsync(); + } + + //wait transfers to be done + Kokkos::fence(); + + //launch the comms + int final_result = 0; + for (size_t i = 0 ; i < count ; i++) { + const int result = ::MPI_Start(&request[i].request); + if (result < 0) + final_result = result; + } + + //ok + return final_result; +} + +/** + * Overlad the MPI_Waitall() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Waitall(int count, Idefix_MPI_Request* request, + MPI_Status *array_of_statuses) { + //check + assert(request != nullptr); + assert(count >= 0); + + //wait the comms + int final_result = 0; + for (size_t i = 0 ; i < count ; i++) { + const int result = ::MPI_Wait(&request[i].request, &array_of_statuses[i]); + if (result < 0) + final_result = result; + } + + //sync the copies in async mode + for (size_t i = 0 ; i < count ; i++) { + request[i].commArray.syncDeviceDataAsync(); + } + + //wait transfers to be done + Kokkos::fence(); + + //ok + return final_result; +} + +/** + * Overlad the MPI_Start() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Start(Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + + //sync the copies in async mode + request->commArray.syncCommData(); + + //call MPI + return ::MPI_Start(&request->request); +} + +/** + * Overlad the MPI_Wait() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Wait(Idefix_MPI_Request* request, MPI_Status *array_of_statuses) { + //check + assert(request != nullptr); + + //wait the comms + const int result = ::MPI_Wait(&request->request, array_of_statuses); + + //sync the copies in async mode + request->commArray.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_Send() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Send(IdefixCommArray & buf, int count, MPI_Datatype datatype, int + dest, int tag, MPI_Comm comm) { + //check + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //sync + buf.syncCommData(); + + //call MPI + const int result = ::MPI_Send(buf.commData(), count, datatype, + dest, tag, comm); + + //ok + return result; +} + +/** + * Overlad the MPI_Send() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Send(const std::array & buf, int count, MPI_Datatype datatype, + int dest, int tag, MPI_Comm comm) { + //call MPI + return ::MPI_Send(buf.data(), count, datatype, dest, tag, comm); +} + +/** + * Overlad the MPI_Send() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Send(const Kokkos::View & buf, int count, + MPI_Datatype datatype, int dest, int tag, MPI_Comm comm) { + //check + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //call MPI + return ::MPI_Send(buf.data(), count, datatype, dest, tag, comm); +} + +/** + * Overlad the MPI_Recv() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Recv(IdefixCommArray & buf, int count, MPI_Datatype datatype, int + source, int tag, MPI_Comm comm, MPI_Status * status) { + //check + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //call MPI + const int result = ::MPI_Recv(buf.commData(), count, datatype, + source, tag, comm, status); + + //sync + buf.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_Recv() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Recv(std::array & buf, int count, MPI_Datatype datatype, int + source, int tag, MPI_Comm comm, MPI_Status * status) { + //call MPI + return ::MPI_Recv(buf.data(), count, datatype, source, tag, comm, status); +} + +/** + * Overlad the MPI_Recv() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Recv(Kokkos::View & buf, int count, + MPI_Datatype datatype, int source, int tag, MPI_Comm comm, MPI_Status * status) { + //check + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //call MPI + return ::MPI_Recv(buf.data(), count, datatype, source, tag, comm, status); +} + +/** + * Overlad the MPI_Isend() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Isend(IdefixCommArray & buf, int count, MPI_Datatype datatype, int + source, int tag, MPI_Comm comm, Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //store the values + request->commArray = buf; + + //sync + buf.syncCommData(); + + //call MPI + const int result = ::MPI_Isend(buf.commData(), count, datatype, + source, tag, comm, &request->request); + + //ok + return result; +} + +/** + * Overlad the MPI_Irecv() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Irecv(IdefixCommArray & buf, int count, MPI_Datatype datatype, int + source, int tag, MPI_Comm comm, Idefix_MPI_Request* request) { + //check + assert(request != nullptr); + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //store the values + request->commArray = buf; + + //call MPI + const int result = ::MPI_Irecv(buf.commData(), count, datatype, + source, tag, comm, &request->request); + + //ok + return result; +} + +/** + * Overlad the MPI_Bcast() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Bcast(IdefixCommArray & buffer, int count, MPI_Datatype datatype, int root, + MPI_Comm comm) { + //check + assert(buffer.span() == count); + assert(buffer.span_is_contiguous()); + + //get current rank + int rank = -1; + const int status = ::MPI_Comm_rank(comm, &rank); + assert(status == MPI_SUCCESS); + + //sync + if (rank == root) + buffer.syncCommData(); + + //call MPI + const int result = ::MPI_Bcast(buffer.commData(), count, datatype, root, comm); + + //sync back + if (rank != root) + buffer.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_Bcast() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Bcast(IdefixHostArray1D & buffer, int count, MPI_Datatype datatype, int root, + MPI_Comm comm) { + //check + assert(buffer.span() == count); + assert(buffer.span_is_contiguous()); + + //call MPI + const int result = ::MPI_Bcast(buffer.data(), count, datatype, root, comm); + + //ok + return result; +} + +/** + * Overlad the MPI_Allreduce() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Allreduce(IdefixCommArray & sendbuf, IdefixCommArray & recvbuf, int count, + MPI_Datatype datatype, MPI_Op op, MPI_Comm comm) { + //check + assert(sendbuf.span() == count); + assert(sendbuf.span_is_contiguous()); + assert(recvbuf.span() == count); + assert(recvbuf.span_is_contiguous()); + + sendbuf.syncCommData(); + + //call MPI + const int result = ::MPI_Allreduce(sendbuf.commData(), recvbuf.commData(), count, datatype, + op, comm); + + //sync back + recvbuf.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_Allreduce() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Allreduce(void * sendbuf, IdefixHostArray3D & recvbuf, int count, + MPI_Datatype datatype, MPI_Op op, MPI_Comm comm) { + //check + assert(recvbuf.span() == count); + assert(recvbuf.span_is_contiguous()); + + //call MPI + const int result = ::MPI_Allreduce(sendbuf, recvbuf.data(), count, datatype, op, comm); + + //ok + return result; +} + +/** + * Overlad the MPI_Allreduce() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Allreduce(void * sendbuf, IdefixCommArray & recvbuf, int count, + MPI_Datatype datatype, MPI_Op op, MPI_Comm comm) { + //check + assert(recvbuf.span() == count); + assert(recvbuf.span_is_contiguous()); + + //call MPI + const int result = ::MPI_Allreduce(sendbuf, recvbuf.commData(), count, datatype, op, comm); + + //sync back + recvbuf.syncDeviceData(); + + //ok + return result; +} + +/** + * Overlad the MPI_File_write_all() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_File_write_all(MPI_File fh, const IdefixHostArray4D & buf, int count, + MPI_Datatype datatype, MPI_Status* status) { + //check + assert(buf.span() == count); + assert(buf.span_is_contiguous()); + + //call MPI + const int result = ::MPI_File_write_all(fh, buf.data(), count, datatype, status); + + //ok + return result; +} + +/** + * Overlad the MPI_Gather() function to handle an idefix communication array. It will automate the + * CPU / GPU transfers if the array in on GPU and WITH_MPI_GPU_DIRECT is disabled. + */ +template +int MPI_Gather(const void* sendbuf, int sendcount, MPI_Datatype + sendtype, std::vector & recvbuf, int recvcount, MPI_Datatype recvtype, + int root, MPI_Comm comm) { + assert(recvcount <= recvbuf.size()); + return ::MPI_Gather(sendbuf, sendcount, sendtype, recvbuf.data(), recvcount, + recvtype, root, comm); +} + +#endif //WITH_MPI + +} // namespace idfx + +#endif // MPI_MPIWRAPPER_HPP_ diff --git a/src/output/slice.cpp b/src/output/slice.cpp index 98caa5c21..b6e8709ec 100644 --- a/src/output/slice.cpp +++ b/src/output/slice.cpp @@ -162,7 +162,7 @@ void Slice::CheckForWrite(DataBlock &data, bool force) { }}} #ifdef WITH_MPI Kokkos::fence(); - MPI_Allreduce(MPI_IN_PLACE, arrOut.data(), + idfx::MPI_Allreduce(MPI_IN_PLACE, arrOut, arrOut.extent(0)*arrOut.extent(1)*arrOut.extent(2)*arrOut.extent(3), realMPI, MPI_SUM, avgComm); #endif diff --git a/src/output/vtk.cpp b/src/output/vtk.cpp index fb04e03de..664e97b39 100644 --- a/src/output/vtk.cpp +++ b/src/output/vtk.cpp @@ -50,7 +50,7 @@ void Vtk::WriteHeaderNodes(IdfxFileHandler fvtk) { int size_int = static_cast(size); MPI_SAFE_CALL(MPI_File_set_view(fvtk, this->offset, MPI_FLOAT, this->nodeView, "native", MPI_INFO_NULL)); - MPI_SAFE_CALL(MPI_File_write_all(fvtk, node_coord.data(), size_int, + MPI_SAFE_CALL(idfx::MPI_File_write_all(fvtk, node_coord, size_int, MPI_FLOAT, MPI_STATUS_IGNORE)); this->offset += sizeof(float)*(nx1+ioffset)*(nx2+joffset)*(nx3+koffset)*3; #else diff --git a/src/pydefix.cpp b/src/pydefix.cpp index f7044af71..457faa4eb 100644 --- a/src/pydefix.cpp +++ b/src/pydefix.cpp @@ -96,15 +96,15 @@ py::array_t GatherIdefixArray(IdefixHostArray3D #ifdef WITH_MPI MPI_Status status; // Fetch the local array size - MPI_Recv(np_int.data(), 3, MPI_INT, rank, 010, MPI_COMM_WORLD, &status); - MPI_Recv(np_tot.data(), 3, MPI_INT, rank, 011, MPI_COMM_WORLD, &status); - MPI_Recv(beg.data(), 3, MPI_INT, rank, 012, MPI_COMM_WORLD, &status); - MPI_Recv(gbeg.data(), 3, MPI_INT, rank, 013, MPI_COMM_WORLD, &status); + idfx::MPI_Recv(np_int, 3, MPI_INT, rank, 010, MPI_COMM_WORLD, &status); + idfx::MPI_Recv(np_tot, 3, MPI_INT, rank, 011, MPI_COMM_WORLD, &status); + idfx::MPI_Recv(beg, 3, MPI_INT, rank, 012, MPI_COMM_WORLD, &status); + idfx::MPI_Recv(gbeg, 3, MPI_INT, rank, 013, MPI_COMM_WORLD, &status); buf = IdefixHostArray3D("pydefix::tempArray", np_tot[KDIR],np_tot[JDIR],np_tot[IDIR]); // Fetch data - MPI_Recv(buf.data(), np_tot[IDIR]*np_tot[JDIR]*np_tot[KDIR], + idfx::MPI_Recv(buf, np_tot[IDIR]*np_tot[JDIR]*np_tot[KDIR], realMPI, rank, 014, MPI_COMM_WORLD,&status); #else IDEFIX_ERROR("Can't deal with psize>1 without MPI."); @@ -147,11 +147,11 @@ py::array_t GatherIdefixArray(IdefixHostArray3D } #ifdef WITH_MPI // send the local array size - MPI_Send(np_int.data(), 3, MPI_INT, 0, 010, MPI_COMM_WORLD); - MPI_Send(np_tot.data(), 3, MPI_INT, 0, 011, MPI_COMM_WORLD); - MPI_Send(beg.data(), 3, MPI_INT, 0, 012, MPI_COMM_WORLD); - MPI_Send(gbeg.data(), 3, MPI_INT, 0, 013, MPI_COMM_WORLD); - MPI_Send(in.data(), np_tot[IDIR]*np_tot[JDIR]*np_tot[KDIR], realMPI, 0, 014, MPI_COMM_WORLD); + idfx::MPI_Send(np_int, 3, MPI_INT, 0, 010, MPI_COMM_WORLD); + idfx::MPI_Send(np_tot, 3, MPI_INT, 0, 011, MPI_COMM_WORLD); + idfx::MPI_Send(beg, 3, MPI_INT, 0, 012, MPI_COMM_WORLD); + idfx::MPI_Send(gbeg, 3, MPI_INT, 0, 013, MPI_COMM_WORLD); + idfx::MPI_Send(in, np_tot[IDIR]*np_tot[JDIR]*np_tot[KDIR], realMPI, 0, 014, MPI_COMM_WORLD); #else IDEFIX_ERROR("Can't deal with psize>1 without MPI."); #endif @@ -159,7 +159,7 @@ py::array_t GatherIdefixArray(IdefixHostArray3D // All is transfered #ifdef WITH_MPI if(broadcast) { - MPI_Bcast(out.data(), out.extent(0)*out.extent(1)*out.extent(2), realMPI, 0, MPI_COMM_WORLD); + idfx::MPI_Bcast(out, out.extent(0)*out.extent(1)*out.extent(2), realMPI, 0, MPI_COMM_WORLD); } #endif diff --git a/src/timeIntegrator.cpp b/src/timeIntegrator.cpp index 7079700d9..79298a0f6 100644 --- a/src/timeIntegrator.cpp +++ b/src/timeIntegrator.cpp @@ -199,7 +199,7 @@ double TimeIntegrator::ComputeBalance() { #ifdef WITH_MPI const double allowedImbalance = 20.0; std::vector computeLogPerCore(idfx::psize); - MPI_Gather(&computeLastLog, 1, MPI_DOUBLE, computeLogPerCore.data(), 1, MPI_DOUBLE, 0, + idfx::MPI_Gather(&computeLastLog, 1, MPI_DOUBLE, computeLogPerCore, 1, MPI_DOUBLE, 0, MPI_COMM_WORLD); computeLastLog = 0; // reset timer for all cores if(idfx::prank==0) { diff --git a/src/utils/column.cpp b/src/utils/column.cpp index 4657abc55..dadac1976 100644 --- a/src/utils/column.cpp +++ b/src/utils/column.cpp @@ -16,6 +16,7 @@ #include "grid.hpp" #include "dataBlock.hpp" #include "dataBlockHost.hpp" +#include "mpiWrapper.hpp" Column::Column(int dir, int sign, DataBlock *data) : direction(dir), sign(sign) { @@ -35,13 +36,13 @@ Column::Column(int dir, int sign, DataBlock *data) // allocate helper array if(dir == IDIR) { - localSum = IdefixArray2D("localSum",np_tot[KDIR], np_tot[JDIR]); + localSum = idfx::IdefixCommArray2D("localSum",np_tot[KDIR], np_tot[JDIR]); } if(dir == JDIR) { - localSum = IdefixArray2D("localSum",np_tot[KDIR], np_tot[IDIR]); + localSum = idfx::IdefixCommArray2D("localSum",np_tot[KDIR], np_tot[IDIR]); } if(dir == KDIR) { - localSum = IdefixArray2D("localSum",np_tot[JDIR], np_tot[IDIR]); + localSum = idfx::IdefixCommArray2D("localSum",np_tot[JDIR], np_tot[IDIR]); } #ifdef WITH_MPI // Create sub-MPI communicator dedicated to scan @@ -78,7 +79,7 @@ void Column::ComputeColumn(IdefixArray4D in, const int var) { auto column = this->ColumnArray; auto dV = this->Volume; auto A = this->Area; - auto localSum = this->localSum; + auto localSum = this->localSum.deviceView(); if(direction==IDIR) { // Inspired from loop.hpp @@ -133,7 +134,7 @@ void Column::ComputeColumn(IdefixArray4D in, const int var) { MPI_Status status; // Get the cumulative sum from previous processes Kokkos::fence(); - MPI_Recv(localSum.data(), size, realMPI, src, 20, ColumnComm, &status); + idfx::MPI_Recv(this->localSum, size, realMPI, src, 20, ColumnComm, &status); // Add this to our cumulative sum idefix_for("Addsum",kb,ke,jb,je,ib,ie, KOKKOS_LAMBDA(int k, int j, int i) { @@ -164,7 +165,7 @@ void Column::ComputeColumn(IdefixArray4D in, const int var) { } // And send it Kokkos::fence(); - MPI_Send(localSum.data(),size, realMPI, dst, 20, ColumnComm); + idfx::MPI_Send(this->localSum,size, realMPI, dst, 20, ColumnComm); } // MPIrank small enough #endif // If we need it backwards @@ -194,7 +195,7 @@ void Column::ComputeColumn(IdefixArray4D in, const int var) { #ifdef WITH_MPI Kokkos::fence(); - MPI_Bcast(localSum.data(),size, realMPI, MPIsize-1, ColumnComm); + idfx::MPI_Bcast(this->localSum,size, realMPI, MPIsize-1, ColumnComm); #endif // All substract the local column from the full column diff --git a/src/utils/column.hpp b/src/utils/column.hpp index 43383cbe6..8e2e619dd 100644 --- a/src/utils/column.hpp +++ b/src/utils/column.hpp @@ -13,6 +13,7 @@ #include "idefix.hpp" #include "dataBlock.hpp" +#include "commArray.hpp" @@ -59,7 +60,7 @@ class Column { IdefixArray3D Area; IdefixArray3D Volume; - IdefixArray2D localSum; + idfx::IdefixCommArray2D localSum; #ifdef WITH_MPI Mpi mpi; // Mpi object when WITH_MPI is set MPI_Comm ColumnComm; diff --git a/src/utils/lookupTable.hpp b/src/utils/lookupTable.hpp index 72d13a838..a71b42412 100644 --- a/src/utils/lookupTable.hpp +++ b/src/utils/lookupTable.hpp @@ -392,10 +392,10 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB #ifdef WITH_MPI // Share with the others - MPI_Bcast(xinHost.data(), xinHost.extent(0), realMPI, 0, MPI_COMM_WORLD); - MPI_Bcast(dimensionsHost.data(), dimensionsHost.extent(0), MPI_INT, 0, MPI_COMM_WORLD); - MPI_Bcast(offsetHost.data(), offsetHost.extent(0), MPI_INT, 0, MPI_COMM_WORLD); - MPI_Bcast(dataHost.data(),dataHost.extent(0), realMPI, 0, MPI_COMM_WORLD); + idfx::MPI_Bcast(xinHost, xinHost.extent(0), realMPI, 0, MPI_COMM_WORLD); + idfx::MPI_Bcast(dimensionsHost, dimensionsHost.extent(0), MPI_INT, 0, MPI_COMM_WORLD); + idfx::MPI_Bcast(offsetHost, offsetHost.extent(0), MPI_INT, 0, MPI_COMM_WORLD); + idfx::MPI_Bcast(dataHost,dataHost.extent(0), realMPI, 0, MPI_COMM_WORLD); #endif // Copy to target diff --git a/test/MHD/AxisFluxTube/testme.json b/test/MHD/AxisFluxTube/testme.json index f5d074770..2ff1e570f 100644 --- a/test/MHD/AxisFluxTube/testme.json +++ b/test/MHD/AxisFluxTube/testme.json @@ -1,5 +1,5 @@ { - "namings": "ini,mpi", + "namings": "ini,mpi,mpiGpuForceCopy,mpiMode", "default": { "dumpname": "dump.0001.dmp", "noplot": true, @@ -12,7 +12,21 @@ "variants": [ { "ini": ["idefix.ini","idefix-coarsening.ini"], - "mpi": [false, true] + "mpi": [false, true], + "mpiGpuForceCopy": false, + "mpiMode": "Default" + }, + { + "ini": ["idefix.ini"], + "mpi": true, + "mpiGpuForceCopy": [true], + "mpiMode": ["Persistent"] + }, + { + "ini": ["idefix.ini"], + "mpi": true, + "mpiGpuForceCopy": [false, true], + "mpiMode": ["NonBlocking", "Blocking"] } ] } From fa22d208c3c4ded50a97fd87c868861fa6f3e99c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Fri, 28 Aug 2026 16:27:23 +0200 Subject: [PATCH 125/144] fix: typo in documentation + issue in pytest configuration (#404) * doc: fix typo in test runner documentation (tests => test) * test: fix issue when generating the .junit.xml report (the output stream is not there for failed tests). --- doc/source/testing/testLauncher.rst | 6 +++--- pytest.ini | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/doc/source/testing/testLauncher.rst b/doc/source/testing/testLauncher.rst index febc0cb8d..33b8e7ba5 100644 --- a/doc/source/testing/testLauncher.rst +++ b/doc/source/testing/testLauncher.rst @@ -32,12 +32,12 @@ To run the test you can basically : # Run all tests ./test.py - # Run all tests in ./tests/HD - ./test.py -subdir=./tests/HD + # Run all tests in ./test/HD + ./test.py -subdir=./test/HD # Select in more details the tests containing the "single" keyword # See pytest documentation for the exact advanced semantic - ./test.py -subdir=./tests/HD -k single + ./test.py -subdir=./test/HD -k single # Run in verbose ./test.py -v diff --git a/pytest.ini b/pytest.ini index 33a7f2a95..98983edc4 100644 --- a/pytest.ini +++ b/pytest.ini @@ -2,5 +2,5 @@ markers= default: Test to run by default. python_files="test_*.py" -junit_logging="all" -junit_log_passing_tests=false +junit_logging=all +junit_log_passing_tests=False From 3903fba56a6568a250151196a8d94353a0b2b3b0 Mon Sep 17 00:00:00 2001 From: Alankar Dutta Date: Mon, 31 Aug 2026 11:58:19 +0200 Subject: [PATCH 126/144] Enable parsing of 1D column data and interpolation in functional space using `LookupTable` object (#401) * Allow 1D lookup tables to be read as columns of a CSV file * LookupTable interpolation on function space * Add accessors to the neighbours used by the LookupTable interpolation * Cache the neighbour search between Get and the neighbour getters * generate irregular grid to test the lookupTable generic neighbour search * Use a dichotomy instead of linear search for faster lookup search in large tables * added test helpers for clarity. Should be replaced by proper unit test library (note in this PR though) --------- Co-authored-by: Geoffroy Lesur --- doc/source/programmingguide.rst | 195 ++++++++- src/real_types.hpp | 4 + src/utils/lookupTable.hpp | 511 +++++++++++++++++++--- test/utils/lookupTable/main.cpp | 544 +++++++++++++++++++++--- test/utils/lookupTable/testmelib.py | 20 +- test/utils/lookupTable/toto1Dcolumn.csv | 5 + test/utils/lookupTable/toto1Dlog.csv | 6 + 7 files changed, 1158 insertions(+), 127 deletions(-) create mode 100644 test/utils/lookupTable/toto1Dcolumn.csv create mode 100644 test/utils/lookupTable/toto1Dlog.csv diff --git a/doc/source/programmingguide.rst b/doc/source/programmingguide.rst index 6f65742bc..d8f989df7 100644 --- a/doc/source/programmingguide.rst +++ b/doc/source/programmingguide.rst @@ -489,7 +489,36 @@ For the CSV constructor, ``nDim`` can only have the values 1 or 2. .. note:: The input CSV file is allowed to contain comments, starting with "#". Any character following - "#" is ignored by the ``LookupTable`` class. + "#" is ignored by the ``LookupTable`` class. Hence, a line starting with "#" is entirely ignored, + and so are empty lines and lines made only of white spaces. Comments and blank lines can therefore + be inserted anywhere in the file, including before the first line of the table. + +By default, the coordinates and the data are read as *lines* of the CSV file, as in the examples above. For 1D lookup +tables, they can also be read as *columns* of the CSV file, using the optional argument ``readColumns`` of the constructor: + +.. code-block:: c++ + + template + LookupTable::LookupTable(std::string filename, char delimiter, + bool errorIfOutOfBound, bool readColumns); + +With ``readColumns=true``, the 1D lookup table is read from the two first columns of the file, the first one +giving the coordinates and the second one the data: + +.. list-table:: example1D_col.csv + :widths: 25 25 + :header-rows: 0 + + * - x\ :sub:`1` + - data\ :sub:`1` + * - x\ :sub:`2` + - data\ :sub:`2` + * - x\ :sub:`3` + - data\ :sub:`3` + +.. note:: + ``readColumns`` is only available for 1D lookup tables. 2D lookup tables are always read as lines, + following the layout of ``example2D.csv`` above. Numpy constructor @@ -507,6 +536,60 @@ the constructor expects a vector of size ``nDim`` of .npy files for the 1D coord Note that the template parameter ``nDim`` should match the number of dimensions of the numpy array stored in the file ``dataSet``. +Interpolation in function space ++++++++++++++++++++++++++++++++ + +By default, ``LookupTable`` performs a multi-linear interpolation directly on the coordinates ``x`` and the data +of the table. For data spanning several orders of magnitude (cooling tables, opacity tables, etc...), it is often +more accurate to interpolate the data in *function space*, i.e. to interpolate ``func(data)`` as a function of +``func(x)``, and to transform the interpolated value back with the inverse function ``invFunc``. This is enabled with +the optional argument ``interpolateInFuncSpace`` accepted by each of the constructors: + +.. code-block:: c++ + + // 1D CSV table read as columns, interpolated in log space + LookupTable<1> table("cooling.csv", ',', true, true, true); + + // 3D numpy table, interpolated in log space + LookupTable<3> tablenpy(coordinates, "data.npy", true, true); + +When this option is enabled, ``func`` is applied to the coordinates and to the data when the table is constructed +(so that ``xinHost``, ``xinDev``, ``dataHost`` and ``dataDev`` all store transformed values), the interpolation is +performed in that space, and ``Get`` and ``GetHost`` return ``invFunc`` of the interpolated value. The coordinates +passed to ``Get`` and ``GetHost``, as well as the value they return, are therefore always expressed in the original +(untransformed) space. + +``func`` and ``invFunc`` default to the natural logarithm and the exponential (the functors ``LookupTableLog`` and +``LookupTableExp``). They can be changed when the lookup table is created, using the two optional template parameters +of ``LookupTable``, which expect functors defining ``operator()(const real)``. This operator should be decorated with +``KOKKOS_INLINE_FUNCTION``, so that the transformation can be used both on the host and on the device: + +.. code-block:: c++ + + // A user-defined transformation and its inverse + struct MyLog10 { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(log10(x)); + } + }; + + struct MyPow10 { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(pow(10.0,x)); + } + }; + + // A 1D CSV table interpolated in log10 space + LookupTable<1, MyLog10, MyPow10> table("cooling.csv", ',', true, true, true); + +Instances of these functors can also be given as the last two arguments of the constructors, which is useful when the +transformation carries a state (e.g. a tunable exponent). + +.. warning:: + The transformation is applied to every coordinate and to every element of the data. Since the default transformation + is the natural logarithm, the whole table should be strictly positive when the default ``func`` is used, otherwise + ``LookupTable`` triggers an error while it is being constructed. + Using the lookup table ++++++++++++++++++++++ @@ -536,6 +619,116 @@ The ``Get`` and ``GetHost`` functions expect a C array of size ``nDim`` and retu real result = csv.GetHost(y); +Accessing the neighbours used for the interpolation ++++++++++++++++++++++++++++++++++++++++++++++++++++ + +In addition to the interpolated value, ``LookupTable`` can return the elements of the table which surround the +requested coordinates, i.e. the ones the interpolation is computed from. This is useful to implement a custom +interpolation or reconstruction (e.g. a power law between two nodes), to estimate a local slope, or simply to +check which part of the table is being used. Four methods are available, ``GetNeighbours`` and ``GetNeighboursIndx`` +on the device, and ``GetNeighboursHost`` and ``GetNeighboursIndxHost`` on the host: + +.. code-block:: c++ + + // Coordinates and data of the neighbours (device and host) + void GetNeighbours(const real x[nDim], real xN[2*nDim], real dataN[1 << nDim]); + void GetNeighboursHost(const real x[nDim], real xN[2*nDim], real dataN[1 << nDim]); + + // Indices of the same neighbours (device and host) + void GetNeighboursIndx(const real x[nDim], int idx[nDim], int dataIdx[1 << nDim]); + void GetNeighboursIndxHost(const real x[nDim], int idx[nDim], int dataIdx[1 << nDim]); + +These methods do not return anything, but they fill the arrays which are given to them: + +* ``xN[2*n]`` and ``xN[2*n+1]`` are the two coordinates of the table bracketing ``x[n]`` along the dimension ``n``. +* ``dataN[v]`` is the data on the vertex ``v`` of the cell surrounding ``x``. Since a cell of a ``nDim`` table has + ``2^nDim`` vertices, ``dataN`` has ``1 << nDim`` elements. The bit ``n`` of ``v`` tells whether the vertex is on + the right (1) or on the left (0) of the dimension ``n``: in 2D, ``dataN[0]``, ``dataN[1]``, ``dataN[2]`` and + ``dataN[3]`` are therefore the data in (x\ :sub:`i`, y\ :sub:`j`), (x\ :sub:`i+1`, y\ :sub:`j`), + (x\ :sub:`i`, y\ :sub:`j+1`) and (x\ :sub:`i+1`, y\ :sub:`j+1`). +* ``idx[n]`` is the index of the left neighbour along the dimension ``n`` (the right one being ``idx[n]+1``). +* ``dataIdx[v]`` is the index of the vertex ``v`` in the data array of the table, following the same convention as + ``dataN``, so that ``dataN[v]`` and ``dataHost(dataIdx[v])`` refer to the same element. + +For instance, the 2D table ``example2D.csv`` above, interpolated in (x=2.1, y=3.5), gives: + +.. code-block:: c++ + + real x[2]; + x[0] = 2.1; + x[1] = 3.5; + + real xN[4]; // 2 coordinates for each of the 2 dimensions + real dataN[4]; // 2^2 vertices + int idx[2]; + int dataIdx[4]; + + csv.GetNeighboursHost(x, xN, dataN); + csv.GetNeighboursIndxHost(x, idx, dataIdx); + + // xN[0] and xN[1] now bracket x[0], while xN[2] and xN[3] bracket x[1], and the interpolated + // value returned by csv.GetHost(x) can be recomputed from dataN: + real dx = (x[0]-xN[0])/(xN[1]-xN[0]); + real dy = (x[1]-xN[2])/(xN[3]-xN[2]); + real value = (1-dx)*(1-dy)*dataN[0] + dx*(1-dy)*dataN[1] + + (1-dx)*dy*dataN[2] + dx*dy*dataN[3]; + +The same methods without the ``Host`` suffix can be called from within an ``idefix_for`` loop, the arrays being then +local to the loop. + +Both ``Get`` and the methods above search the table for the cell surrounding the requested coordinates. When the +interpolated value *and* its neighbours are needed for the same coordinates, this search can be performed only once, +by handing the same ``LookupTableSearchCache`` structure to each of them: whichever is called first searches the +table and stores the result in the structure, and the ones called next reuse it instead of searching the table again. +The order in which they are called is irrelevant, ``Get`` can fill the structure for ``GetNeighbours`` and +``GetNeighboursIndx``, or the other way around. + +.. code-block:: c++ + + idefix_for("loop",0, 10, KOKKOS_LAMBDA (int i) { + real x[2]; + x[0] = 2.1; + x[1] = 3.5; + + // The search performed by Get is stored in neighbours... + LookupTableSearchCache<2> neighbours; + real value = csv.Get(x, neighbours); + + // ... and is reused by the two methods below, which do not search the table again + real xN[4]; + real dataN[4]; + int idx[2]; + int dataIdx[4]; + csv.GetNeighbours(x, neighbours, xN, dataN); + csv.GetNeighboursIndx(x, neighbours, idx, dataIdx); + }); + +The very same methods are available on the host, as ``GetHost``, ``GetNeighboursHost`` and ``GetNeighboursIndxHost``. +The structure gives access to the search itself, ``neighbours.idx[n]`` being the index of the left neighbour along +the dimension ``n``, and ``neighbours.delta[n]`` the elementary ratio used to weight the two neighbours of that +dimension. + +.. note:: + The stored search is only reused when the coordinates it was computed for are the ones being requested. Calling + ``GetNeighbours`` or ``GetNeighboursIndx`` with different coordinates simply searches the table again, and updates + the structure accordingly, so that a ``LookupTableSearchCache`` can be reused from one point to the next. + +.. warning:: + The ``LookupTableSearchCache`` structure is declared *per thread*, and not by the lookup table itself: when it is used inside an + ``idefix_for`` loop, it should be declared *inside* the loop, so that each thread has its own copy. A lookup table + is shared by all of the threads of a loop, and can therefore not store anything of the sort itself. + +.. note:: + When the table is interpolated in function space (see above), ``xN`` and ``dataN`` are returned in the original + space of the table, i.e. ``invFunc`` is applied to the values which are stored in ``xin`` and ``data``. The + indices returned by ``GetNeighboursIndx`` are of course not affected by the transformation. + +.. note:: + The search of the neighbours follows exactly the same rules as ``Get``: an out of bound coordinate triggers an + error when ``errorIfOutOfBound`` is enabled, and is otherwise clamped to the closest cell of the table. If one of + the requested coordinates is a nan, ``xN`` and ``dataN`` are filled with nans, and ``idx`` and ``dataIdx`` with -1. + + .. note:: Usage examples are provided in `test/utils/lookupTable`. diff --git a/src/real_types.hpp b/src/real_types.hpp index 440c7aac9..988ca1675 100644 --- a/src/real_types.hpp +++ b/src/real_types.hpp @@ -33,6 +33,8 @@ #define TAN(x) tanf(x) #define SIN(x) sinf(x) #define COS(x) cosf(x) +#define LOG(x) logf(x) +#define EXP(x) expf(x) #define COPYSIGN(x,y) copysignf(x,y) #define ISNAN(x) isnanf(x) #define FMOD(x,y) fmodf(x,y) @@ -52,6 +54,8 @@ #define TAN(x) tan(x) #define SIN(x) sin(x) #define COS(x) cos(x) +#define LOG(x) log(x) +#define EXP(x) exp(x) #define COPYSIGN(x,y) copysign(x,y) #define ISNAN(x) isnan(x) #define FMOD(x,y) fmod(x,y) diff --git a/src/utils/lookupTable.hpp b/src/utils/lookupTable.hpp index a71b42412..b97c9a56e 100644 --- a/src/utils/lookupTable.hpp +++ b/src/utils/lookupTable.hpp @@ -14,18 +14,82 @@ #include "lookupTable.hpp" #include "npy.hpp" +// Default transformation (and its inverse) used when the lookup table interpolates in function +// space: the interpolation is then performed on log(x) and log(data), and the interpolated value +// is transformed back with exp. +// Any functor exposing a KOKKOS_INLINE_FUNCTION operator()(const real) can be used instead, so +// that the transformation is available both on the host and on the device. +struct LookupTableLog { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(LOG(x)); + } +}; + +struct LookupTableExp { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(EXP(x)); + } +}; + +// Neighbours of a point of a lookup table, as they are found by the search performed by Get: +// idx[n] is the index of the left neighbour along the dimension n, and delta[n] is the elementary +// ratio used to weight the two neighbours of that dimension. +// Get (and GetHost) fill this structure when it is given as an argument, and GetNeighbours and +// GetNeighboursIndx then reuse the search it contains instead of performing it a second time +// (which is only done when they are called with the same coordinates: they search the table again +// as usual when a different x is requested). +// This structure is kept by the caller, so that it is thread-private when it is declared inside +// an idefix_for loop. The lookup table itself is shared by all of the threads of a loop, and can +// therefore not be used to store anything of the sort. template +struct LookupTableSearchCache { + real x[kDim]; // coordinates for which the neighbours below were computed + int idx[kDim]; // index of the left neighbour along each dimension + real delta[kDim]; // elementary ratio between the two neighbours of each dimension + bool valid{false}; // whether the neighbours above have been successfully computed + + // Check whether this structure already holds the neighbours of the coordinates xIn. + // The comparison is a bit-exact "==" on purpose: this is meant to catch the case where the + // caller passes back literally the same x it just queried (e.g. Get then GetNeighbours on the + // same iteration), not to approximate "close enough" coordinates. Do not replace this with a + // tolerance-based comparison, or two distinct nearby queries could wrongly reuse a stale search. + KOKKOS_INLINE_FUNCTION + bool Matches(const real xIn[kDim]) const { + if(!valid) return(false); + for(int n = 0 ; n < kDim ; n++) { + if(x[n] != xIn[n]) return(false); + } + return(true); + } +}; + +template class LookupTable { public: LookupTable() = default; - LookupTable(std::string filename, char delimiter, bool errorIfOutOfBound = true); + // Constructor from a CSV/ASCII file. + // By default (readColumns=false), the arrays are read as *lines* of the input file: + // 1D: 1st line = coordinates (xinHost), 2nd line = data (dataHost) + // 2D: 1st line = coordinates of the 1st dimension, then each line starts with the + // coordinate of the 2nd dimension, followed by the data of that line. + // For 1D tables only, the arrays can also be read as *columns* of the input file by setting + // readColumns=true: + // 1st column = coordinates (xinHost), 2nd column = data (dataHost) + // All of the constructors accept the optional argument interpolateInFuncSpace: when it is set + // to true, the coordinates and the data are stored as func(x) and func(data), the interpolation + // is performed in that space, and Get returns invFunc of the interpolated value (see below). + LookupTable(std::string filename, char delimiter, bool errorIfOutOfBound = true, + bool readColumns = false, bool interpolateInFuncSpace = false, + TFunc func = TFunc(), TInvFunc invFunc = TInvFunc()); LookupTable(std::vector filenames, std::string dataSet, - bool errorIfOutOfBound = true); + bool errorIfOutOfBound = true, bool interpolateInFuncSpace = false, + TFunc func = TFunc(), TInvFunc invFunc = TInvFunc()); template LookupTable(Kokkos::View array, std::array,kDim>, - bool errorIfOutOfBound = true); + bool errorIfOutOfBound = true, bool interpolateInFuncSpace = false, + TFunc func = TFunc(), TInvFunc invFunc = TInvFunc()); IdefixArray1D dimensionsDev; IdefixArray1D offsetDev; // Actually sum_(n-1) (dimensions) @@ -40,20 +104,62 @@ class LookupTable { bool errorIfOutOfBound{true}; - // Generic getter for all kinds of input arrays + // When enabled, the table is interpolated in function space: xin and data store func(x) and + // func(data), and Get returns invFunc(interpolated value). func and invFunc are stored by + // value, so that they are available on the device as well as on the host. + bool interpolateInFuncSpace{false}; + TFunc func; + TInvFunc invFunc; + + // Transform the coordinates and the data of the table in function space. + // This is called on the host by the constructors, before the arrays are copied on the device. + void ToFuncSpace() { + for(int i = 0 ; i < xinHost.extent(0) ; i++) { + xinHost(i) = func(xinHost(i)); + if(!std::isfinite(xinHost(i))) { + IDEFIX_ERROR("LookupTable: the transformation of the coordinates in function space " + "produced invalid values (with the default log, the coordinates of the " + "table should all be strictly positive)"); + } + } + for(int i = 0 ; i < dataHost.extent(0) ; i++) { + dataHost(i) = func(dataHost(i)); + if(!std::isfinite(dataHost(i))) { + IDEFIX_ERROR("LookupTable: the transformation of the data in function space " + "produced invalid values (with the default log, the data of the " + "table should all be strictly positive)"); + } + } + } + + // --------------------------------------------------------------------------------------------- + // Implementation details below: these generic (Tint/Treal-templated) helpers are shared by the + // public Get/GetHost/GetNeighbours*/GetNeighboursIndx* entry points declared further down, which + // simply instantiate them with the device or host storage. They are not meant to be called + // directly, hence kept private; make this public again if another translation unit genuinely + // needs the generic (host-or-device) form directly. + // --------------------------------------------------------------------------------------------- + private: + // Search of the bracketing indices used by the interpolation, for all kinds of input arrays. + // On output, idx[n] is the index of the left neighbour along the dimension n (so that the + // interpolation is performed between xin(offset(n)+idx[n]) and xin(offset(n)+idx[n]+1)), and + // delta[n] is the elementary ratio used to weight these two neighbours. + // Returns false when the requested coordinates contain nans, and true otherwise. + // This is the only place that performs the actual search: Get, GetNeighbours and + // GetNeighboursIndx all reach it through GetIndices below, so that a bug fix here never + // needs to be duplicated elsewhere. template KOKKOS_INLINE_FUNCTION - real Get(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, Treal &data) const { - // Fetch function that should be called inside idefix_loop - int idx[kDim]; - real delta[kDim]; - + bool GetIndices(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, + int idx[kDim], real delta[kDim]) const { for(int n = 0 ; n < kDim ; n++) { real xstart = xin(offset(n)); real xend = xin(offset(n)+dimensions(n)-1); - real x_n = x[n]; + // When interpolating in function space, xin already stores func(x), so the coordinate + // we are looking for should be transformed accordingly + real x_n = interpolateInFuncSpace ? func(x[n]) : x[n]; - if(std::isnan(x_n)) return(NAN); + if(std::isnan(x_n)) return(false); // Compute index of closest element assuming even distribution int i; @@ -82,16 +188,20 @@ class LookupTable { // Check if resulting bounding elements are correct if(xin(offset(n) + i) > x_n || xin(offset(n) + i+1) < x_n) { // Nop, so the points are not evenly distributed - // Search for the correct index (a dicotomy would be more appropriate...) - - i = 0; - while(xin(offset(n) + i) < x_n && i < dimensions(n)-1 ) { - i++; + // Search for the correct index with a dichotomy + int ileft = 0; + int iright = dimensions(n)-1; + while(iright-ileft>1) { + int imid = (ileft + iright) / 2; + if(xin(offset(n) + imid) <= x_n) { + ileft = imid; + } else { + iright = imid; + } } - i = i-1; // i is overestimated by one + i = ileft; } } - // Store the index idx[n] = i; @@ -99,33 +209,190 @@ class LookupTable { delta[n] = (x_n - xin(offset(n) + i) ) / (xin(offset(n) + i+1) - xin(offset(n) + i)); } - // De a linear interpolation from the neightbouring points to get our value. + return(true); + } + + // Index in the data array of the vertex "vertex" of the neighbours. Each bit of "vertex" tells + // whether we are on the right (1) or on the left (0) of the corresponding dimension, so that + // there are 2^kDim vertices surrounding the point we are interpolating. + template + KOKKOS_INLINE_FUNCTION + int GetDataIndex(Tint &dimensions, const int idx[kDim], const unsigned int vertex) const { + int index = 0; + for(unsigned int m = 0 ; m < kDim ; m++) { + index = index * dimensions(m); + unsigned int myBit = 1 << m; + // If bit is set, we're doing the right vertex, otherwise we're doing the left vertex + if((vertex & myBit) > 0) { + index += idx[m]+1; + } else { + index += idx[m]; + } + } + return(index); + } + + // Fill "searchCache" with the neighbours of x, unless it already holds them (in which case the + // table is not searched again). This is what allows Get, GetNeighbours and GetNeighboursIndx to + // share a single search when they are called successively with the same coordinates. + template + KOKKOS_INLINE_FUNCTION + void SearchNeighbours(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, + LookupTableSearchCache &searchCache) const { + // Nothing to do if the neighbours of these very coordinates are already known + if(searchCache.Matches(x)) return; + + searchCache.valid = GetIndices(x, dimensions, offset, xin, searchCache.idx, searchCache.delta); + for(int n = 0 ; n < kDim ; n++) { + searchCache.x[n] = x[n]; + } + } + + // Generic getter which stores in "searchCache" the elements of the table it used, so that a + // subsequent call to GetNeighbours or GetNeighboursIndx with the same coordinates does not + // search the table again + template + KOKKOS_INLINE_FUNCTION + real Get(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, Treal &data, + LookupTableSearchCache &searchCache) const { + SearchNeighbours(x, dimensions, offset, xin, searchCache); + + if(!searchCache.valid) return(NAN); + + // Do a linear interpolation from the neightbouring points to get our value. real value = 0; // loop on all of the vertices of the neighbours for(unsigned int n = 0 ; n < (1 << kDim) ; n++) { - int index = 0; real weight = 1.0; for(unsigned int m = 0 ; m < kDim ; m++) { - index = index * dimensions(m); unsigned int myBit = 1 << m; // If bit is set, we're doing the right vertex, otherwise we're doing the left vertex if((n & myBit) > 0) { // We're on the right - weight = weight*delta[m]; - index += idx[m]+1; + weight = weight*searchCache.delta[m]; } else { // We're on the left - weight = weight*(1-delta[m]); - index += idx[m]; + weight = weight*(1-searchCache.delta[m]); } } - value = value + weight*data(index); + value = value + weight*data(GetDataIndex(dimensions, searchCache.idx, n)); } + // The interpolation was performed on func(data), so we transform the result back + if(interpolateInFuncSpace) value = invFunc(value); + return(value); } + // Generic getter for all kinds of input arrays. + // Implemented as a thin delegation to the neighbours-caching overload below, using a throwaway + // searchCache structure: LookupTableSearchCache is a small stack-only POD (no allocation), so + // this costs nothing extra while guaranteeing the two overloads can never disagree on the result. + template + KOKKOS_INLINE_FUNCTION + real Get(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, Treal &data) const { + LookupTableSearchCache searchCache; + return Get(x, dimensions, offset, xin, data, searchCache); + } + + // Generic getter for the neighbours used by the interpolation, for all kinds of input arrays. + // On output, xN[2*n] and xN[2*n+1] are the coordinates bracketing x[n] along the dimension n, + // and dataN[v] is the data at the vertex v of these neighbours (see GetDataIndex for the + // convention on v). When the table is interpolated in function space, both are returned in the + // original space of the table (i.e. invFunc is applied to the values stored in the table). + // All of the outputs are set to nan when the requested coordinates contain nans. + template + KOKKOS_INLINE_FUNCTION + void GetNeighbours(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, Treal &data, + real xN[2*kDim], real dataN[1 << kDim]) const { + LookupTableSearchCache searchCache; + GetNeighbours(x, dimensions, offset, xin, data, searchCache, xN, dataN); + } + + // Same as above, but the search is stored in (and reused from) "searchCache": the table is only + // searched again when "searchCache" does not already hold the neighbours of x, e.g. because it + // was filled by a previous call to Get with these very same coordinates. + template + KOKKOS_INLINE_FUNCTION + void GetNeighbours(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, Treal &data, + LookupTableSearchCache &searchCache, + real xN[2*kDim], real dataN[1 << kDim]) const { + // Reuse GetNeighboursIndx for the search and the idx -> flat data offset bookkeeping, so that + // logic only lives in one place (GetDataIndex/GetNeighboursIndx). + int idx[kDim]; + int dataIdx[1 << kDim]; + GetNeighboursIndx(x, dimensions, offset, xin, searchCache, idx, dataIdx); + + if(!searchCache.valid) { + for(int n = 0 ; n < 2*kDim ; n++) xN[n] = NAN; + for(unsigned int n = 0 ; n < (1 << kDim) ; n++) dataN[n] = NAN; + return; + } + + // Coordinates of the neighbours along each dimension + for(int n = 0 ; n < kDim ; n++) { + xN[2*n] = xin(offset(n) + idx[n]); + xN[2*n+1] = xin(offset(n) + idx[n]+1); + if(interpolateInFuncSpace) { + xN[2*n] = invFunc(xN[2*n]); + xN[2*n+1] = invFunc(xN[2*n+1]); + } + } + + // Data on each vertex of the neighbours + for(unsigned int n = 0 ; n < (1 << kDim) ; n++) { + dataN[n] = data(dataIdx[n]); + if(interpolateInFuncSpace) dataN[n] = invFunc(dataN[n]); + } + } + + // Generic getter for the indices of the neighbours used by the interpolation, for all kinds of + // input arrays. On output, idx[n] is the index of the left neighbour along the dimension n + // (the right one being idx[n]+1), and dataIdx[v] is the index in the data array of the vertex v + // of these neighbours (see GetDataIndex for the convention on v). + // All of the outputs are set to -1 when the requested coordinates contain nans. + template + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndx(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, + LookupTableSearchCache &searchCache, + int idx[kDim], int dataIdx[1 << kDim]) const { + SearchNeighbours(x, dimensions, offset, xin, searchCache); + + if(!searchCache.valid) { + for(int n = 0 ; n < kDim ; n++) idx[n] = -1; + for(unsigned int n = 0 ; n < (1 << kDim) ; n++) dataIdx[n] = -1; + return; + } + + for(int n = 0 ; n < kDim ; n++) { + idx[n] = searchCache.idx[n]; + } + for(unsigned int n = 0 ; n < (1 << kDim) ; n++) { + dataIdx[n] = GetDataIndex(dimensions, searchCache.idx, n); + } + } + + +// Same as above, but the search is not stored in a caller-supplied structure: a throwaway +// LookupTableSearchCache is created and filled, and then discarded. + template + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndx(const real x[kDim], Tint &dimensions, Tint &offset, Treal &xin, + int idx[kDim], int dataIdx[1 << kDim]) const { + LookupTableSearchCache searchCache; + GetNeighboursIndx(x, dimensions, offset, xin, searchCache, idx, dataIdx); + } + + + + // ----------------------------------------------------------------------------------------- + // Public interface: each of Get/GetNeighbours/GetNeighboursIndx below is a thin one-line + // dispatch to the generic (private) implementation above, selecting device or host storage, + // and optionally reusing a caller-supplied LookupTableSearchCache cache. None of them contains + // any interpolation logic of its own. + // ----------------------------------------------------------------------------------------- + public: // Getter on device KOKKOS_INLINE_FUNCTION real Get(const real x[kDim]) const { @@ -137,14 +404,86 @@ class LookupTable { real GetHost(const real x[kDim]) const { return(Get(x, dimensionsHost, offsetHost, xinHost, dataHost)); } + + // Getter for the neighbours used by the interpolation, on device + KOKKOS_INLINE_FUNCTION + void GetNeighbours(const real x[kDim], real xN[2*kDim], real dataN[1 << kDim]) const { + GetNeighbours(x, dimensionsDev, offsetDev, xinDev, dataDev, xN, dataN); + } + + // Getter for the neighbours used by the interpolation, on Host + KOKKOS_INLINE_FUNCTION + void GetNeighboursHost(const real x[kDim], real xN[2*kDim], real dataN[1 << kDim]) const { + GetNeighbours(x, dimensionsHost, offsetHost, xinHost, dataHost, xN, dataN); + } + + // Getter for the indices of the neighbours used by the interpolation, on device + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndx(const real x[kDim], int idx[kDim], int dataIdx[1 << kDim]) const { + GetNeighboursIndx(x, dimensionsDev, offsetDev, xinDev, idx, dataIdx); + } + + // Getter for the indices of the neighbours used by the interpolation, on Host + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndxHost(const real x[kDim], int idx[kDim], int dataIdx[1 << kDim]) const { + GetNeighboursIndx(x, dimensionsHost, offsetHost, xinHost, idx, dataIdx); + } + + // Getter on device, which stores the neighbours it used in "neighbours". Giving that same + // structure to GetNeighbours or GetNeighboursIndx below then avoids searching the table twice. + KOKKOS_INLINE_FUNCTION + real Get(const real x[kDim], LookupTableSearchCache &neighbours) const { + return(Get(x, dimensionsDev, offsetDev, xinDev, dataDev, neighbours)); + } + + // Getter on Host, which stores the neighbours it used in "neighbours" + KOKKOS_INLINE_FUNCTION + real GetHost(const real x[kDim], LookupTableSearchCache &neighbours) const { + return(Get(x, dimensionsHost, offsetHost, xinHost, dataHost, neighbours)); + } + + // Getter for the neighbours used by the interpolation, on device, reusing the search stored in + // "neighbours" when it was performed for these very same coordinates + KOKKOS_INLINE_FUNCTION + void GetNeighbours(const real x[kDim], LookupTableSearchCache &neighbours, + real xN[2*kDim], real dataN[1 << kDim]) const { + GetNeighbours(x, dimensionsDev, offsetDev, xinDev, dataDev, neighbours, xN, dataN); + } + + // Getter for the neighbours used by the interpolation, on Host, reusing the search stored in + // "neighbours" when it was performed for these very same coordinates + KOKKOS_INLINE_FUNCTION + void GetNeighboursHost(const real x[kDim], LookupTableSearchCache &neighbours, + real xN[2*kDim], real dataN[1 << kDim]) const { + GetNeighbours(x, dimensionsHost, offsetHost, xinHost, dataHost, neighbours, xN, dataN); + } + + // Getter for the indices of the neighbours, on device, reusing the search stored in + // "neighbours" when it was performed for these very same coordinates + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndx(const real x[kDim], LookupTableSearchCache &searchCache, + int idx[kDim], int dataIdx[1 << kDim]) const { + GetNeighboursIndx(x, dimensionsDev, offsetDev, xinDev, searchCache, idx, dataIdx); + } + + // Getter for the indices of the neighbours, on Host, reusing the search stored in + // "neighbours" when it was performed for these very same coordinates + KOKKOS_INLINE_FUNCTION + void GetNeighboursIndxHost(const real x[kDim], LookupTableSearchCache &neighbours, + int idx[kDim], int dataIdx[1 << kDim]) const { + GetNeighboursIndx(x, dimensionsHost, offsetHost, xinHost, neighbours, idx, dataIdx); + } }; -template -LookupTable::LookupTable(std::vector filenames, +template +LookupTable::LookupTable(std::vector filenames, std::string dataSet, - bool errOOB) { + bool errOOB, bool funcSpace, TFunc funcIn, TInvFunc invFuncIn) { idfx::pushRegion("LookupTable::LookupTable"); this->errorIfOutOfBound = errOOB; + this->interpolateInFuncSpace = funcSpace; + this->func = funcIn; + this->invFunc = invFuncIn; std::vector shape; bool fortran_order; @@ -177,7 +516,7 @@ LookupTable::LookupTable(std::vector filenames, } // Allocate the required memory - //Allocate arrays so that the data fits in it + // Allocate arrays so that the data fits in it this->xinDev = IdefixArray1D ("Table_x", sizeTotal); this->dimensionsDev = IdefixArray1D ("Table_dim", kDim); this->offsetDev = IdefixArray1D ("Table_offset", kDim); @@ -233,6 +572,9 @@ LookupTable::LookupTable(std::vector filenames, } } + // Transform the table in function space if required + if(this->interpolateInFuncSpace) this->ToFuncSpace(); + // Copy to target Kokkos::deep_copy(this->xinDev ,xinHost); Kokkos::deep_copy(this->dimensionsDev, dimensionsHost); @@ -244,13 +586,23 @@ LookupTable::LookupTable(std::vector filenames, // Constructor from CSV file -template -LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB) { +// The coordinates and the data are read as lines of the input file, unless readColumns is set +// to true, in which case they are read as columns of the input file (1D tables only, see the +// declaration of the class for a description of both layouts). +template +LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB, + bool readColumns, bool funcSpace, TFunc funcIn, TInvFunc invFuncIn) { idfx::pushRegion("LookupTable::LookupTable"); this->errorIfOutOfBound = errOOB; + this->interpolateInFuncSpace = funcSpace; + this->func = funcIn; + this->invFunc = invFuncIn; if(kDim>2) { IDEFIX_ERROR("CSV files are only compatible with 1D and 2D tables"); } + if(kDim>1 && readColumns) { + IDEFIX_ERROR("CSV files can only be read as columns for 1D tables"); + } // Only 1 process loads the file // Size of the array int size[2]; @@ -265,21 +617,18 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB if(file.is_open()) { std::string line, lineWithComments; - bool firstLine = true; - int nx = -1; + // Full content of the file, stored as a list of lines, each line being a list of values + std::vector> fileContent; while(std::getline(file, lineWithComments)) { // get rid of comments (starting with #) line = lineWithComments.substr(0, lineWithComments.find("#",0)); if (line.empty()) continue; // skip blank line - char firstChar = line.find_first_not_of(" "); + std::size_t firstChar = line.find_first_not_of(" "); if (firstChar == std::string::npos) continue; // line is all white space // Walk the line - bool firstColumn=true; - if(kDim == 1) firstColumn = false; - - std::vector dataLine; - dataLine.clear(); + std::vector lineVector; + lineVector.clear(); // make the line a string stream, and get all of the values separated by a delimiter std::stringstream str(line); std::string valueString; @@ -294,31 +643,62 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB << "\" cannot be converted to real." << std::endl; IDEFIX_ERROR(errmsg); } - if(firstLine) { - xVector.push_back(value); - } else if(firstColumn) { - yVector.push_back(value); - firstColumn = false; - } else { - dataLine.push_back(value); - } + lineVector.push_back(value); } // We have finished the line - if(firstLine) { - nx = xVector.size(); - firstLine=false; - } else { - if(dataLine.size() != nx) { + fileContent.push_back(lineVector); + // When read as lines, a 1D table is fully described by the first two lines of the file, + // so we stop reading what's after them + if(kDim < 2 && !readColumns && fileContent.size() == 2) break; + } + file.close(); + // End of file reached + + if(fileContent.size() < 2) { + IDEFIX_ERROR("LookupTable: The input CSV file should contain at least two lines"); + } + + // Dispatch the content of the file in the coordinate and data containers. + // Note that dataVector is always indexed as dataVector[j][i], where i (resp. j) is the + // index along the 1st (resp. 2nd) dimension of the table. + if(readColumns) { + // (1D tables only) the coordinates are stored in the 1st column of the input file, + // while the data is stored in its 2nd column + dataVector.push_back(std::vector()); + for(int i = 0 ; i < fileContent.size() ; i++) { + if(fileContent[i].size() < 2) { + IDEFIX_ERROR("LookupTable: The input CSV file should have at least two columns " + "when the table is read as columns"); + } + xVector.push_back(fileContent[i][0]); + dataVector[0].push_back(fileContent[i][1]); + } + } else { + // (default) the arrays are stored as lines of the input file + // 1st line always gives the coordinates of the 1st dimension + xVector = fileContent[0]; + const int nx = xVector.size(); + if(kDim < 2) { + // 2nd line is the data + if(fileContent[1].size() != nx) { IDEFIX_ERROR("LookupTable: The number of columns in the input CSV " "file should be constant"); } - dataVector.push_back(dataLine); - firstLine = false; - if(kDim < 2) break; // Stop reading what's after the first two lines + dataVector.push_back(fileContent[1]); + } else { + // each of the following lines starts with the coordinate of the 2nd dimension, + // followed by the data of that line + for(int j = 1 ; j < fileContent.size() ; j++) { + if(fileContent[j].size() != nx+1) { + IDEFIX_ERROR("LookupTable: The number of columns in the input CSV " + "file should be constant"); + } + yVector.push_back(fileContent[j][0]); + dataVector.push_back(std::vector(fileContent[j].begin()+1, + fileContent[j].end())); + } } } - file.close(); - // End of file reached } else { std::stringstream errmsg; errmsg << "LookupTable: Unable to open file " << filename << std::endl; @@ -398,6 +778,9 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB idfx::MPI_Bcast(dataHost,dataHost.extent(0), realMPI, 0, MPI_COMM_WORLD); #endif + // Transform the table in function space if required + if(this->interpolateInFuncSpace) this->ToFuncSpace(); + // Copy to target Kokkos::deep_copy(this->xinDev ,xinHost); Kokkos::deep_copy(this->dimensionsDev, dimensionsHost); @@ -426,13 +809,16 @@ LookupTable::LookupTable(std::string filename, char delimiter, bool errOOB // Constructor from IdefixHostArray -template +template template -LookupTable::LookupTable(Kokkos::View array, +LookupTable::LookupTable(Kokkos::View array, std::array,kDim> x, - bool errOOB) { + bool errOOB, bool funcSpace, TFunc funcIn, TInvFunc invFuncIn) { idfx::pushRegion("LookupTable::LookupTable"); this->errorIfOutOfBound = errOOB; + this->interpolateInFuncSpace = funcSpace; + this->func = funcIn; + this->invFunc = invFuncIn; std::vector shape(kDim); for(int i = 0 ; i < kDim ; i++) shape[i] = x[i].extent(0); @@ -504,6 +890,9 @@ LookupTable::LookupTable(Kokkos::View array, } } + // Transform the table in function space if required + if(this->interpolateInFuncSpace) this->ToFuncSpace(); + // Copy to target Kokkos::deep_copy(this->xinDev ,xinHost); Kokkos::deep_copy(this->dimensionsDev, dimensionsHost); diff --git a/test/utils/lookupTable/main.cpp b/test/utils/lookupTable/main.cpp index 1fc660cd6..d13c47e02 100644 --- a/test/utils/lookupTable/main.cpp +++ b/test/utils/lookupTable/main.cpp @@ -10,6 +10,87 @@ // minimal skeleton to use idfx basic functions void testReduction(); +// Custom transformation (and its inverse) to check that the functions used for the interpolation +// in function space can be changed when the lookup table is created +struct MyLog10 { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(log10(x)); + } +}; + +struct MyPow10 { + KOKKOS_INLINE_FUNCTION real operator() (const real x) const { + return(pow(10.0,x)); + } +}; + +// --------------------------------------------------------------------------------------------- +// Small test helpers, so that each check below states what it verifies and why it failed, instead +// of every failure printing an undifferentiated "ERROR!!" that has to be traced back to the last +// banner that was printed. +// --------------------------------------------------------------------------------------------- +namespace { + +void Banner(const std::string &what) { + idfx::cout << "--------------------------------------" << std::endl; + idfx::cout << what << std::endl; +} + +void Success() { + idfx::cout << "Success" << std::endl; +} + +// Exact equality: used for values that should reproduce bit-for-bit (e.g. requesting a table node +// directly, or comparing an int index), matching what the original tests checked with a plain !=. +template +void CheckEqual(T got, T expected, const std::string &what) { + if(got != expected) { + idfx::cerr << "ERROR!! " << what << ": got " << got << ", expected " << expected << std::endl; + exit(1); + } +} + +// Element-wise exact equality over a small fixed-size array (neighbour coordinates/data/indices). +template +void CheckArrayEqual(const T *got, const T *expected, int n, const std::string &what) { + for(int i = 0 ; i < n ; i++) { + if(got[i] != expected[i]) { + idfx::cerr << "ERROR!! " << what << " (element " << i << "): got " << got[i] + << ", expected " << expected[i] << std::endl; + exit(1); + } + } +} + +// Tolerance-based equality, for values obtained through interpolation. +void CheckClose(real got, real expected, real tol, const std::string &what) { + if(std::fabs(got - expected) > tol) { + idfx::cerr << std::scientific; + idfx::cerr << "ERROR!! " << what << ": got " << got << ", expected " << expected + << " (|diff|=" << std::fabs(got - expected) << ", tol=" << tol << ")" << std::endl; + exit(1); + } +} + +void CheckTrue(bool cond, const std::string &what) { + if(!cond) { + idfx::cerr << "ERROR!! " << what << std::endl; + exit(1); + } +} + +// Expected bracketing neighbours of the 2D CSV table (toto.csv) around (x=2.1, y=3.5): x brackets +// [2,3], y brackets [3,4], and the data on the four surrounding vertices is 5,6,6,7. This is +// checked from several angles across the file below (Get vs GetNeighbours vs GetNeighboursIndx, +// host vs device, cached vs uncached search), so it is defined once here instead of being +// retyped as magic numbers in every block. +const real kXN2D[4] = {2.0, 3.0, 3.0, 4.0}; +const real kDataN2D[4] = {5.0, 6.0, 6.0, 7.0}; +const int kIdx2D[2] = {0, 1}; +const int kDataIdx2D[4] = {1, 4, 2, 5}; +const real kValue2D = 5.6; // csv.Get({2.1, 3.5}) + +} // namespace // main function int main( int argc, char* argv[] ) @@ -35,8 +116,8 @@ int main( int argc, char* argv[] ) { idfx::initialize(); - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Testing 2D CSV file on device." << std::endl; + + Banner("Testing 2D CSV file on device."); IdefixArray1D arr = IdefixArray1D("Test",1); IdefixArray1D::host_mirror_type arrHost = Kokkos::create_mirror_view(arr); @@ -50,33 +131,20 @@ int main( int argc, char* argv[] ) }); Kokkos::deep_copy(arrHost , arr); - idfx::cout << "result="<1e-13) { - idfx::cerr << std::scientific; - idfx::cerr << "ERROR!!" << std::endl; - idfx::cerr << arrHost(0)-5.6; - exit(1); - } - idfx::cout << "Success" << std::endl; + CheckClose(arrHost(0), kValue2D, 1e-13, "2D CSV, device"); + Success(); - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Testing 2D CSV file on Host." << std::endl; + Banner("Testing 2D CSV file on Host."); real x[2]; x[0] = 2.1; x[1] = 3.5; real result = csv.GetHost(x); idfx::cout << "result="<1e-13) { - idfx::cerr << std::scientific; - idfx::cerr << "ERROR!!" << std::endl; - idfx::cerr << result-5.6; - exit(1); - } - idfx::cout << "Success" << std::endl; + CheckClose(result, kValue2D, 1e-13, "2D CSV, host"); + Success(); - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Testing 1D CSV file on device." << std::endl; + Banner("Testing 1D CSV file on device."); // Read 1D CSV File LookupTable<1> csv1D("toto1D.csv",','); @@ -87,30 +155,403 @@ int main( int argc, char* argv[] ) }); Kokkos::deep_copy(arrHost , arr); - idfx::cout << "result="< csv1Dcolumn("toto1Dcolumn.csv",',', true, true); + + idefix_for("loop",0, 1, KOKKOS_LAMBDA (int i) { + real x[1]; + x[0] = 2.1; + arr(i) = csv1Dcolumn.Get(x); + }); + + Kokkos::deep_copy(arrHost , arr); + idfx::cout << "result="< csv1Dlin("toto1Dlog.csv",',', true, true); + LookupTable<1> csv1Dlog("toto1Dlog.csv",',', true, true, true); + // the transformation and its inverse can also be chosen when the table is created + LookupTable<1, MyLog10, MyPow10> csv1Dlog10("toto1Dlog.csv",',', true, true, true); + + idefix_for("loop",0, 1, KOKKOS_LAMBDA (int i) { + real x[1]; + x[0] = 3.0; + arr(i) = csv1Dlog.Get(x); + }); + Kokkos::deep_copy(arrHost , arr); + idfx::cout << "result="< xNdev = IdefixArray1D("xN",4); + IdefixArray1D dataNdev = IdefixArray1D("dataN",4); + IdefixArray1D idxDev = IdefixArray1D("idx",2); + IdefixArray1D dataIdxDev = IdefixArray1D("dataIdx",4); + + idefix_for("neighbours",0, 1, KOKKOS_LAMBDA (int i) { + real xq[2]; + xq[0] = 2.1; + xq[1] = 3.5; + real xN[4]; + real dataN[4]; + int idx[2]; + int dataIdx[4]; + csv.GetNeighbours(xq, xN, dataN); + csv.GetNeighboursIndx(xq, idx, dataIdx); + for(int n = 0 ; n < 4 ; n++) { + xNdev(n) = xN[n]; + dataNdev(n) = dataN[n]; + dataIdxDev(n) = dataIdx[n]; + } + idxDev(0) = idx[0]; + idxDev(1) = idx[1]; + }); + + auto xNHost = Kokkos::create_mirror_view(xNdev); + auto dataNHost = Kokkos::create_mirror_view(dataNdev); + auto idxHost = Kokkos::create_mirror_view(idxDev); + auto dataIdxHost = Kokkos::create_mirror_view(dataIdxDev); + Kokkos::deep_copy(xNHost, xNdev); + Kokkos::deep_copy(dataNHost, dataNdev); + Kokkos::deep_copy(idxHost, idxDev); + Kokkos::deep_copy(dataIdxHost, dataIdxDev); + + idfx::cout << "2D: x=" << xNHost(0) << "," << xNHost(1) << " y=" << xNHost(2) << "," + << xNHost(3) << " data=" << dataNHost(0) << "," << dataNHost(1) << "," + << dataNHost(2) << "," << dataNHost(3) << " idx=" << idxHost(0) << "," + << idxHost(1) << std::endl; + real xN[4], dataN[4]; + int idx[2], dataIdx[4]; + for(int n = 0 ; n < 4 ; n++) { xN[n] = xNHost(n); dataN[n] = dataNHost(n); } + idx[0] = idxHost(0); idx[1] = idxHost(1); + for(int n = 0 ; n < 4 ; n++) dataIdx[n] = dataIdxHost(n); + CheckArrayEqual(xN, kXN2D, 4, "2D neighbours (device), coordinates"); + CheckArrayEqual(dataN, kDataN2D, 4, "2D neighbours (device), data"); + CheckArrayEqual(idx, kIdx2D, 2, "2D neighbours (device), idx"); + CheckArrayEqual(dataIdx, kDataIdx2D, 4, "2D neighbours (device), dataIdx"); + Success(); + } + + Banner("Testing the 1D neighbours on the edges of the table."); + { + // toto1D.csv holds x=1,2,3 and data=2,4,6. Whatever the requested value, we expect the two + // neighbours bracketing it, i.e. the last two nodes when we sit on the upper edge + real xq[1]; + real xN[2]; + real dataN[2]; + real expected[3][2] = {{1.0,2.0}, {2.0,3.0}, {2.0,3.0}}; + real xRequest[3] = {1.0, 2.0, 3.0}; + for(int n = 0 ; n < 3 ; n++) { + xq[0] = xRequest[n]; + csv1D.GetNeighboursHost(xq, xN, dataN); + idfx::cout << "x=" << xq[0] << " -> neighbours " << xN[0] << "," << xN[1] + << " (data " << dataN[0] << "," << dataN[1] << ")" << std::endl; + CheckArrayEqual(xN, expected[n], 2, "1D edge neighbours, coordinates"); + CheckTrue(xN[0] <= xq[0] && xN[1] >= xq[0], + "1D edge neighbours do not bracket the requested value"); + } + Success(); + } + + Banner("Testing the reuse of the search between Get and GetNeighbours on Host."); + { + real xq[2]; + xq[0] = 2.1; + xq[1] = 3.5; + // The neighbours found by Get are stored in nb... + LookupTableSearchCache<2> nb; + result = csv.GetHost(xq, nb); + CheckClose(result, kValue2D, 1e-13, "Get-then-GetNeighbours (host), value"); + CheckTrue(nb.valid, "Get-then-GetNeighbours (host), search validity"); + CheckArrayEqual(nb.idx, kIdx2D, 2, "Get-then-GetNeighbours (host), cached idx"); + + // ... and are reused (not computed again) by the getters below + real xN[4]; + real dataN[4]; + int idx[2]; + int dataIdx[4]; + csv.GetNeighboursHost(xq, nb, xN, dataN); + csv.GetNeighboursIndxHost(xq, nb, idx, dataIdx); + CheckArrayEqual(xN, kXN2D, 4, "Get-then-GetNeighbours (host), coordinates"); + CheckArrayEqual(dataN, kDataN2D, 4, "Get-then-GetNeighbours (host), data"); + CheckArrayEqual(idx, kIdx2D, 2, "Get-then-GetNeighbours (host), idx"); + CheckArrayEqual(dataIdx, kDataIdx2D, 4, "Get-then-GetNeighbours (host), dataIdx"); + + // Check that the table is really not searched again for the same coordinates: we corrupt + // the stored search, and check that the corrupted result is the one which is used + nb.idx[0] = 1; + csv.GetNeighboursIndxHost(xq, nb, idx, dataIdx); + CheckEqual(idx[0], 1, "Get-then-GetNeighbours (host): the stored search was not reused"); + + // ... while different coordinates trigger a new search, as usual + real xq2[2]; + xq2[0] = 2.9; + xq2[1] = 2.5; + csv.GetNeighboursIndxHost(xq2, nb, idx, dataIdx); + CheckTrue(idx[0] == 0 && idx[1] == 0, + "Get-then-GetNeighbours (host): different coordinates did not trigger a new search"); + Success(); + } + + Banner("Testing the search performed by GetNeighbours first, and reused by Get, on Host."); + { + real xq[2]; + xq[0] = 2.1; + xq[1] = 3.5; + + // No call to Get yet: GetNeighbours searches the table as usual, and stores the result + LookupTableSearchCache<2> nb; + real xN[4]; + real dataN[4]; + csv.GetNeighboursHost(xq, nb, xN, dataN); + CheckTrue(nb.valid, "GetNeighbours-then-Get (host), search validity"); + CheckArrayEqual(nb.idx, kIdx2D, 2, "GetNeighbours-then-Get (host), cached idx"); + CheckArrayEqual(xN, kXN2D, 4, "GetNeighbours-then-Get (host), coordinates"); + CheckArrayEqual(dataN, kDataN2D, 4, "GetNeighbours-then-Get (host), data"); + + // Get now reuses that search for the same coordinates + result = csv.GetHost(xq, nb); + CheckClose(result, kValue2D, 1e-13, "GetNeighbours-then-Get (host), value"); + + // Same check as before, the other way around: we corrupt the ratio stored by + // GetNeighbours, and check that Get uses it instead of computing it again. + // With delta[0]=0.5 instead of 0.1, the interpolation gives (5+6+6+7)/4=6 + nb.delta[0] = 0.5; + result = csv.GetHost(xq, nb); + CheckClose(result, 6.0, 1e-13, + "GetNeighbours-then-Get (host): the stored search was not reused by Get"); + + // ... while different coordinates make Get search the table again + real xq2[2]; + xq2[0] = 2.9; + xq2[1] = 2.5; + result = csv.GetHost(xq2, nb); + CheckClose(result, csv.GetHost(xq2), 1e-13, + "GetNeighbours-then-Get (host): different coordinates did not trigger a new search"); + CheckEqual(nb.idx[1], 0, + "GetNeighbours-then-Get (host): different coordinates did not trigger a new search"); + + // The same holds when the search comes from GetNeighboursIndx, here on the 1D table + LookupTableSearchCache<1> nb1D; + real xq1[1]; + xq1[0] = 2.1; + int idx1[1]; + int dataIdx1[2]; + csv1D.GetNeighboursIndxHost(xq1, nb1D, idx1, dataIdx1); + CheckTrue(nb1D.valid, "GetNeighboursIndx-then-Get (host, 1D), search validity"); + CheckEqual(idx1[0], 1, "GetNeighboursIndx-then-Get (host, 1D), idx"); + nb1D.delta[0] = 0.0; // x is now on the left neighbour, so we expect its data + result = csv1D.GetHost(xq1, nb1D); + CheckClose(result, 4.0, 1e-13, + "GetNeighboursIndx-then-Get (host, 1D): the stored search was not reused by Get"); + Success(); } - idfx::cout << "Success" << std::endl; - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Testing 3D npy file on device." << std::endl; + Banner("Testing the reuse of the search between Get and GetNeighbours on device."); + { + IdefixArray1D xNdev = IdefixArray1D("xN",4); + IdefixArray1D dataNdev = IdefixArray1D("dataN",4); + IdefixArray1D idxDev = IdefixArray1D("idx",2); + IdefixArray1D dataIdxDev = IdefixArray1D("dataIdx",4); + + idefix_for("neighbours",0, 1, KOKKOS_LAMBDA (int i) { + real xq[2]; + xq[0] = 2.1; + xq[1] = 3.5; + // the structure is local to the loop, and is therefore private to each thread + LookupTableSearchCache<2> nb; + real xN[4]; + real dataN[4]; + int idx[2]; + int dataIdx[4]; + arr(i) = csv.Get(xq, nb); + csv.GetNeighbours(xq, nb, xN, dataN); + csv.GetNeighboursIndx(xq, nb, idx, dataIdx); + for(int n = 0 ; n < 4 ; n++) { + xNdev(n) = xN[n]; + dataNdev(n) = dataN[n]; + dataIdxDev(n) = dataIdx[n]; + } + idxDev(0) = idx[0]; + idxDev(1) = idx[1]; + }); + + Kokkos::deep_copy(arrHost , arr); + auto xNHost = Kokkos::create_mirror_view(xNdev); + auto dataNHost = Kokkos::create_mirror_view(dataNdev); + auto idxHost = Kokkos::create_mirror_view(idxDev); + auto dataIdxHost = Kokkos::create_mirror_view(dataIdxDev); + Kokkos::deep_copy(xNHost, xNdev); + Kokkos::deep_copy(dataNHost, dataNdev); + Kokkos::deep_copy(idxHost, idxDev); + Kokkos::deep_copy(dataIdxHost, dataIdxDev); + + // Same test on device, but with GetNeighbours called first and Get reusing its search. + // The ratio stored by GetNeighbours is corrupted in between, so that a value of 6 (instead + // of 5.6) proves that Get did not search the table again + IdefixArray1D valuesDev = IdefixArray1D("values",2); + idefix_for("neighboursFirst",0, 1, KOKKOS_LAMBDA (int i) { + real xq[2]; + xq[0] = 2.1; + xq[1] = 3.5; + LookupTableSearchCache<2> nb; + real xN[4]; + real dataN[4]; + // no call to Get yet: the search is performed here for the first time + csv.GetNeighbours(xq, nb, xN, dataN); + valuesDev(0) = csv.Get(xq, nb); + nb.delta[0] = 0.5; + valuesDev(1) = csv.Get(xq, nb); + }); + auto valuesHost = Kokkos::create_mirror_view(valuesDev); + Kokkos::deep_copy(valuesHost, valuesDev); + idfx::cout << "neighbours first: value=" << valuesHost(0) + << " (with a corrupted stored search)=" << valuesHost(1) << std::endl; + CheckClose(valuesHost(0), kValue2D, 1e-13, + "GetNeighbours-then-Get (device): the stored search was not reused by Get"); + CheckClose(valuesHost(1), 6.0, 1e-13, + "GetNeighbours-then-Get (device): the stored search was not reused by Get"); + + idfx::cout << "value=" << arrHost(0) << " x=" << xNHost(0) << "," << xNHost(1) + << " y=" << xNHost(2) << "," << xNHost(3) + << " data=" << dataNHost(0) << "," << dataNHost(1) << "," << dataNHost(2) + << "," << dataNHost(3) << " idx=" << idxHost(0) << "," << idxHost(1) << std::endl; + CheckClose(arrHost(0), kValue2D, 1e-13, "Get-then-GetNeighbours (device), value"); + real xN[4], dataN[4]; + int idx[2], dataIdx[4]; + for(int n = 0 ; n < 4 ; n++) { xN[n] = xNHost(n); dataN[n] = dataNHost(n); } + idx[0] = idxHost(0); idx[1] = idxHost(1); + for(int n = 0 ; n < 4 ; n++) dataIdx[n] = dataIdxHost(n); + CheckArrayEqual(xN, kXN2D, 4, "Get-then-GetNeighbours (device), coordinates"); + CheckArrayEqual(dataN, kDataN2D, 4, "Get-then-GetNeighbours (device), data"); + CheckArrayEqual(idx, kIdx2D, 2, "Get-then-GetNeighbours (device), idx"); + CheckArrayEqual(dataIdx, kDataIdx2D, 4, "Get-then-GetNeighbours (device), dataIdx"); + Success(); + } + + Banner("Testing 3D npy file on device."); // Read npy File std::vector coords({"x.npy","y.npy","z.npy"}); @@ -125,36 +566,21 @@ int main( int argc, char* argv[] ) }); Kokkos::deep_copy(arrHost , arr); - idfx::cout << "result="<1e-13) { - idfx::cerr << std::scientific; - idfx::cerr << "ERROR!!" << std::endl; - idfx::cerr << arrHost(0)-13.6; - exit(1); - } - idfx::cout << "Success" << std::endl; - - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Testing 3D npy file on host." << std::endl; + CheckClose(arrHost(0), 13.6, 1e-13, "3D npy, device"); + Success(); + Banner("Testing 3D npy file on host."); real y[3]; y[0] = 2.7; y[1] = 7.4; y[2] = 3.9; result = csvnpy.GetHost(y); - idfx::cout << "result="<< result << std::endl; - if(std::fabs(result - 13.6)>1e-13) { - idfx::cerr << std::scientific; - idfx::cerr << "ERROR!!" << std::endl; - idfx::cerr << result-13.6; - exit(1); - } - idfx::cout << "Success" << std::endl; - idfx::cout << "--------------------------------------" << std::endl; - idfx::cout << "Done." << std::endl; + CheckClose(result, 13.6, 1e-13, "3D npy, host"); + Success(); + Banner("Done."); } Kokkos::finalize(); #ifdef WITH_MPI diff --git a/test/utils/lookupTable/testmelib.py b/test/utils/lookupTable/testmelib.py index b41266147..5a5b942af 100644 --- a/test/utils/lookupTable/testmelib.py +++ b/test/utils/lookupTable/testmelib.py @@ -1,11 +1,15 @@ import numpy as np +from scipy.interpolate import RegularGridInterpolator def MakeNumpyFile(): - x = np.arange(1, 10, 1.0) - y = np.arange(5, 10, 1.0) - z = np.arange(2, 5, 1.0) + x = 2 ** np.arange(np.log2(1), np.log2(10), 0.2) + y = 2 ** np.arange(np.log2(5), np.log2(10), 0.2) + z = 2 ** np.arange(np.log2(2), np.log2(5), 0.2) + print(x) + print(y) + print(z) xp, yp, zp = np.meshgrid(x, y, z, indexing="ij") data = xp + 2 * yp - zp @@ -14,6 +18,10 @@ def MakeNumpyFile(): np.save("y.npy", y) np.save("z.npy", z) np.save("data.npy", data) - # show the expected result - # f=RegularGridInterpolator((x, y, z), data) - # print(f([2.7,7.4,3.9])) + f = RegularGridInterpolator((x, y, z), data) + return f([2.7, 7.4, 3.9]) + + +if __name__ == "__main__": + f = MakeNumpyFile() + print("expected result:%f", f) diff --git a/test/utils/lookupTable/toto1Dcolumn.csv b/test/utils/lookupTable/toto1Dcolumn.csv new file mode 100644 index 000000000..291aa31cb --- /dev/null +++ b/test/utils/lookupTable/toto1Dcolumn.csv @@ -0,0 +1,5 @@ +# test csv file, same 1D table as toto1D.csv, but stored as columns + +1.0, 2.0 +2.0, 4.0 +3.0, 6.0 diff --git a/test/utils/lookupTable/toto1Dlog.csv b/test/utils/lookupTable/toto1Dlog.csv new file mode 100644 index 000000000..2cb5d5d51 --- /dev/null +++ b/test/utils/lookupTable/toto1Dlog.csv @@ -0,0 +1,6 @@ +# test csv file, power law data = x^2 stored as columns +# used to test the interpolation in function space + +1.0, 1.0 +2.0, 4.0 +4.0, 16.0 From 289197c6db7348712d21a857bc6b00cf6e68881e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Mon, 31 Aug 2026 12:00:02 +0200 Subject: [PATCH 127/144] doc: add documentation for pydefix in virtualenv (#365) * add documentation for pydefix in virtualenv --- doc/source/modules/pydefix.rst | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) diff --git a/doc/source/modules/pydefix.rst b/doc/source/modules/pydefix.rst index d359810e7..d02f34fa8 100644 --- a/doc/source/modules/pydefix.rst +++ b/doc/source/modules/pydefix.rst @@ -104,6 +104,9 @@ The python script `pydefix_example.py` initializes the initial condition of the Troubleshooting --------------- +Pybind11 not found by cmake +++++++++++++++++++++++++++++ + It during configuration stage, you get:: CMake Error at CMakeLists.txt:122 (find_package): @@ -125,3 +128,19 @@ You can then exit the interpreter and set the pybind11_DIR environement variable export pybind11_DIR=env/lib/python3.10/site-packages/pybind11 you can then run cmake which should be able to find pybind11, and compile the code. + +Using pydefix in a virtual environment ++++++++++++++++++++++++++++++++++++++++ +If you use pydefix in a python virtual environment (venv), pydefix might not detect your environment and fail to find pybind11 or other +python packages in your venv. This typically results in a python error "xxxx module not found" when you run Idefix with pydefix. + +The fix is to force the following environement variables (replace XX by your python version) before launching Idefix: + +```bash +export PYTHONPATH=$(python3 -c "import sys; print(':'.join(x for x in sys.path if x))") +``` + +.. warning:: + This is a dirty patch to fix an issue actually caused by pybind11. A better solution would be to fix pybind11 to properly detect virtual environments. + Note that you *should never* set the PYTHONPATH variable globally in your system (i.e. in .bashrc), but only in the terminal where you launch Idefix with pydefix. + The reader may check the dedicated `pydefix PR for details `_. From 110ab0291968b0c46158d848938dcfb453682162 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Cl=C3=A9ment=20Robert?= Date: Mon, 31 Aug 2026 13:57:07 +0100 Subject: [PATCH 128/144] TST: require inifile to be Pluto/Idefix valid (#394) * TST/DEP: update minimal Python requirements * TST: require inifile to be Pluto/Idefix valid --------- Co-authored-by: Geoffroy Lesur --- test/MHD/Coarsening/python/testidefix.py | 2 +- test/MHD/MTI/python/testidefix.py | 2 +- test/MHD/clessTDiffusion/python/testidefix.py | 2 +- test/MHD/sphBragTDiffusion/python/testidefix.py | 2 +- test/MHD/sphBragViscosity/python/testidefix.py | 2 +- test/python_requirements.txt | 2 +- 6 files changed, 6 insertions(+), 6 deletions(-) diff --git a/test/MHD/Coarsening/python/testidefix.py b/test/MHD/Coarsening/python/testidefix.py index d901d805a..32b60711b 100755 --- a/test/MHD/Coarsening/python/testidefix.py +++ b/test/MHD/Coarsening/python/testidefix.py @@ -34,7 +34,7 @@ s = line.split() inputFile = s[5][:-1] -input = inifix.load("../" + inputFile) +input = inifix.load(f"../{inputFile}", sections="require") componentDir = input["Setup"]["direction"][0] spatialDir = input["Setup"]["direction"][1] diff --git a/test/MHD/MTI/python/testidefix.py b/test/MHD/MTI/python/testidefix.py index 28c721619..278366eb9 100644 --- a/test/MHD/MTI/python/testidefix.py +++ b/test/MHD/MTI/python/testidefix.py @@ -16,7 +16,7 @@ n = 1 # fondamental mode -conf = inifix.load("../idefix.ini") +conf = inifix.load("../idefix.ini", sections="require") Pr = conf["Setup"]["pr"] ksi = conf["Setup"]["ksi"] diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py index b68a52bad..fac2d084f 100644 --- a/test/MHD/clessTDiffusion/python/testidefix.py +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -7,7 +7,7 @@ from pytools.vtk_io import readVTK -conf = inifix.load("../idefix.ini") +conf = inifix.load("../idefix.ini", sections="require") gamma = conf["Hydro"]["gamma"] kappa = conf["Hydro"]["bragTDiffusion"][-1] diff --git a/test/MHD/sphBragTDiffusion/python/testidefix.py b/test/MHD/sphBragTDiffusion/python/testidefix.py index f96cbe6af..2cd3655dd 100644 --- a/test/MHD/sphBragTDiffusion/python/testidefix.py +++ b/test/MHD/sphBragTDiffusion/python/testidefix.py @@ -7,7 +7,7 @@ from pytools.vtk_io import readVTK -conf = inifix.load("../idefix.ini") +conf = inifix.load("../idefix.ini", sections="require") amplitude = conf["Setup"]["amplitude"] gamma = conf["Hydro"]["gamma"] kappa = conf["Hydro"]["bragTDiffusion"][-1] diff --git a/test/MHD/sphBragViscosity/python/testidefix.py b/test/MHD/sphBragViscosity/python/testidefix.py index 84c60dfc6..05ae619c0 100644 --- a/test/MHD/sphBragViscosity/python/testidefix.py +++ b/test/MHD/sphBragViscosity/python/testidefix.py @@ -8,7 +8,7 @@ from pytools.vtk_io import readVTK -conf = inifix.load("../idefix.ini") +conf = inifix.load("../idefix.ini", sections="require") amplitude = conf["Setup"]["amplitude"] time_step = conf["Output"]["vtk"] diff --git a/test/python_requirements.txt b/test/python_requirements.txt index bfa7c53cd..5b8c6ba7c 100644 --- a/test/python_requirements.txt +++ b/test/python_requirements.txt @@ -5,7 +5,7 @@ numpy>=1.21.1 matplotlib>=3.5.0 scipy>=1.7.2 -inifix>=0.11.2 +inifix>=5.1.0 pybind11 >= 3.0.4 # To run the test suite, we can use pytest, mostly any version From ec7751b685050d7ee34f98624e095ed09d86dca5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Wed, 2 Sep 2026 21:22:04 +0200 Subject: [PATCH 129/144] test: add usage of jsonschema to validate testme.json files and get more understandable errors. (#405) * test: add usage of jsonschema to validate the testme.json file and get more understandable errors. * test: add testme.json format validation in the pre-commit + improve the error messages of test.py + make it faster to start. --- .pre-commit-config.yaml | 20 +++ pytools/idfx_test.py | 6 + pytools/idfx_test_run.py | 62 ++++++- pytools/testme.schema.json | 157 ++++++++++++++++++ test.py | 8 + test/HD/ShearingBox/testme.json | 2 +- test/HD/ViscousDisk/testme.json | 2 +- test/HD/ViscousFlowPastCylinder/testme.json | 2 +- test/HD/thermalDiffusion/testme.json | 2 +- test/MHD/AmbipolarCshock3D/testme.json | 4 +- test/MHD/FargoMHDSpherical/testme.json | 2 +- test/MHD/LinearWaveTest/testme.json | 2 +- test/MHD/OrszagTang/testme.json | 2 +- test/MHD/OrszagTang3D/testme.json | 2 +- test/MHD/ShearingBox/testme.json | 2 +- test/Planet/PlanetMigration2D/testme.json | 2 +- test/Planet/PlanetPlanetRK42D/testme.json | 2 +- test/Planet/PlanetSpiral2D/testme.json | 2 +- test/Planet/PlanetTorque3D/testme.json | 2 +- test/Planet/PlanetsIsActiveRK52D/testme.json | 2 +- test/SelfGravity/JeansInstability/testme.json | 2 +- test/SelfGravity/RandomSphere/testme.json | 2 +- test/python_requirements.txt | 1 + 23 files changed, 266 insertions(+), 24 deletions(-) create mode 100644 pytools/testme.schema.json diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index ddd79ae61..632f9abb9 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -57,3 +57,23 @@ repos: hooks: - id: cpplint args: [--counting=detailed, --exclude=test/*] + + - repo: https://github.com/python-jsonschema/check-jsonschema + rev: 0.38.0 + hooks: + - id: check-jsonschema + files: ^test/.*/testme.json$ + args: ["--schemafile", "pytools/testme.schema.json"] + + - repo: local + hooks: + - id: pytest + name: testme.json validation + entry: ./test.py --validate-testme-jsons + language: python + files: ^test/.*/testme.json$ + pass_filenames: false + additional_dependencies: + - matplotlib >= 3.5.0 + - pytest >= 6.0 + - jsonschema >= 4.26.0 diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index de907848d..99f052884 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -141,6 +141,12 @@ def __init__(self, current_test_file, name=""): action="store_true", ) + parser.add_argument( + "--validate-testme-jsons", + help="Only validate the testme.json files.", + action="store_true", + ) + parser.add_argument( "--help-pytest", help="Display the options you can transmit directly to pytest in addition to the specific to idefix tests.", diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index be2e2bb58..f968745f9 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -13,6 +13,7 @@ import sys from contextlib import contextmanager +import jsonschema import pytest # idefix test class @@ -45,14 +46,38 @@ def __init__(self, parentScriptFile: str): self.currentTestRunner: tst.idfxTest = None self.parentScritFile = parentScriptFile self.filterSubdir = os.environ.get("IDEFIX_TEST_FILTER_SUBDIR", "./test/") + self.testmeSchema = self._loadTestmeSchema() + + def _loadTestmeSchema(self) -> dict: + scriptDir = os.path.dirname(__file__) + schemaPath = os.path.join(scriptDir, "testme.schema.json") + with open(schemaPath, "r") as fp: + return json.load(fp) def _validateNaming(self, namings: str, autoExtracted: str, file: str): names = namings.split(",") - for n in autoExtracted.split(","): - if not n in names: - raise Exception( - f"Naming parameter list not match the auto-detectection, some are missinge. You gave : '{names}', detected '{autoExtracted}' into {file}" - ) + names_sorted = namings.split(",") + autoNames = autoExtracted.split(",") + autoNames_sorted = autoExtracted.split(",") + + # quick compare + names_sorted.sort() + autoNames_sorted.sort() + + # check and if error check in details to report + if names_sorted != autoNames_sorted: + for n in autoNames: + if n not in names: + raise Exception( + f"Naming parameter list not match the auto-detectection, some are missing : '{n}'\n" + f"You gave : '{names}', detected '{autoNames}' into {file}" + ) + for n in names: + if n not in autoNames: + raise Exception( + f"Naming parameter list not match the auto-detectection, some are missing : '{n}'.\n" + f"You gave : '{names}', detected '{autoNames}' into {file}" + ) def _makeVariableArgAsList(self, namings: str, variants) -> list: # make as a list @@ -98,6 +123,23 @@ def genTests(self) -> list: with open(testfilePath, "r") as fp: # load test = json.load(fp) + + # validate via jsonschema + try: + jsonschema.validate(instance=test, schema=self.testmeSchema) + except jsonschema.ValidationError as e: + print() + print( + "--------------- testme.json format error ---------------" + ) + print(f"Invalid format for : {testfilePath}\n{e}") + print( + "--------------------------------------------------------" + ) + print() + raise Exception(f"{testfilePath} format error !") from e + + # build generator idefixTestGenerator = IdefixDirTestGenerator( testfilePath, testfileDir ) @@ -130,7 +172,7 @@ def genTests(self) -> list: ) except Exception as e: raise Exception( - f"Fail to generate tests from {testfileRelPath}" + f"Fail to generate tests from {testfileRelPath}.\n{e}" ) from e # ok @@ -423,6 +465,14 @@ def _runNonRegSingleRun( f"Dump file {file} was overwritten on restart" ) + def validateTestmeJsons(self) -> bool: + try: + self.genTests() + except Exception as e: + print(f"{e}") + return False + return True + def main(self, all: bool = False): if all: sys.argv.append("-all") diff --git a/pytools/testme.schema.json b/pytools/testme.schema.json new file mode 100644 index 000000000..7ea0b3872 --- /dev/null +++ b/pytools/testme.schema.json @@ -0,0 +1,157 @@ +{ + "title": "testme", + "description": "Schema to validate the testme.json files in the test suite of Idefix.", + "type": "object", + "properties": { + "namings": { + "type": "string" + }, + "default": { "$ref": "#/$defs/config" }, + "variants": { + "type": "array", + "items": { + "type": "object", + "additionalProperties": false, + "properties": { + "ini": { + "anyOf": [ + { "type": "string" }, + { "type": "array", "items": { "type": "string" } } + ] + }, + "definitionFile": { + "anyOf": [ + { "type": "string" }, + { "type": "array", "items": { "type": "string" } } + ] + }, + "dumpname": { + "anyOf": [ + { "type": "string" }, + { "type": "array", "items": { "type": "string" } } + ] + }, + "tolerance": { + "anyOf": [ + { "type": "number" }, + { "type": "array", "items": { "type": "number" } } + ] + }, + "nonRegressionTest": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "standardTest": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "noplot": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "reconstruction": { + "anyOf": [ + { "type": "integer" }, + { "type": "array", "items": { "type": "integer" } } + ] + }, + "dec": { "type": "array", "items": { "type": "number"} }, + "single": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "vectPot": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "mpi": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "mpiGpuForceCopy": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "mpiMode": { + "anyOf": [ + { "enum": ["Default", "Persistent", "Blocking", "NonBlocking" ] }, + { "type": "array", "items": { "enum": ["Default", "Persistent", "Blocking", "NonBlocking" ] } } + ] + }, + "restart": { + "anyOf": [ + { "type": "boolean" }, + { "type": "array", "items": { "type": "boolean" } } + ] + }, + "callPyFunctionBefore": { + "anyOf": [ + { "type": "string" }, + { "type": "array", "items": { "type": "string" } } + ] + }, + "callPyFunctionAfter": { + "anyOf": [ + { "type": "string" }, + { "type": "array", "items": { "type": "string" } } + ] + }, + "check_file_produced": { "type": "array", "items": { "type": "string"} }, + "restart_no_overwrite": { "type": "array", "items": { "type": "string"} }, + "multirun": { + "type": "array", + "items": { "$ref": "#/$defs/config" } + } + } + } + } + }, + "when": { + "type": "object", + "properties": { + "condition": { "$ref": "#/$defs/config" }, + "apply": { "$ref": "#/$defs/config" } + } + }, + "$defs": { + "config": { + "type": "object", + "additionalProperties": false, + "properties": { + "ini": { "type": "string" }, + "definitionFile": { "type": "string" }, + "dumpname": { "type": "string" }, + "tolerance": { "type": "number" }, + "nonRegressionTest": { "type": "boolean" }, + "standardTest": { "type": "boolean" }, + "noplot": { "type": "boolean" }, + "reconstruction": { "type": "integer" }, + "dec": { "type": "array", "items": { "type": "number"} }, + "single": { "type": "boolean" }, + "vectPot": { "type": "boolean" }, + "mpi": { "type": "boolean" }, + "mpiGpuForceCopy": { "type": "boolean" }, + "mpiMode": { "enum": ["Default", "Persistent", "Blocking", "NonBlocking" ] }, + "restart": { "type": "boolean" }, + "callPyFunctionBefore": { "type": "string" }, + "callPyFunctionAfter": { "type": "string" }, + "check_file_produced": { "type": "array", "items": { "type": "string"} }, + "restart_no_overwrite": { "type": "array", "items": { "type": "string"} } + } + } + } +} diff --git a/test.py b/test.py index 1bb6768fe..a680be613 100755 --- a/test.py +++ b/test.py @@ -18,6 +18,14 @@ gblIdefixPytestRunner = IdexPytestRunner(__file__) +# if called directly as a script +if __name__ == "__main__" and "--validate-testme-jsons" in sys.argv: + if gblIdefixPytestRunner.validateTestmeJsons(): + sys.exit(0) + else: + sys.exit(1) + + # define the pytest test @pytest.mark.parametrize("config", gblIdefixPytestRunner.genTests()) def test_idefix_build_run_check(config): diff --git a/test/HD/ShearingBox/testme.json b/test/HD/ShearingBox/testme.json index 802c6ce33..b492bec19 100644 --- a/test/HD/ShearingBox/testme.json +++ b/test/HD/ShearingBox/testme.json @@ -6,7 +6,7 @@ "reconstruction": 2, "single": false, "mpi": false, - "dec": ["2","1","2"], + "dec": [2,1,2], "tolerance": 1e-15 }, "variants": [ diff --git a/test/HD/ViscousDisk/testme.json b/test/HD/ViscousDisk/testme.json index a25a09e4b..6cba24198 100644 --- a/test/HD/ViscousDisk/testme.json +++ b/test/HD/ViscousDisk/testme.json @@ -6,7 +6,7 @@ "reconstruction": 2, "single": false, "mpi": false, - "dec": ["2","1","2"], + "dec": [2,1,2], "tolerance": 3e-15 }, "variants": [ diff --git a/test/HD/ViscousFlowPastCylinder/testme.json b/test/HD/ViscousFlowPastCylinder/testme.json index 519a01ca4..2fb79fda3 100644 --- a/test/HD/ViscousFlowPastCylinder/testme.json +++ b/test/HD/ViscousFlowPastCylinder/testme.json @@ -5,7 +5,7 @@ "noplot": true, "reconstruction": 2, "single": false, - "dec": ["2","2"], + "dec": [2,2], "tolerance": 3e-14 }, "variants": [ diff --git a/test/HD/thermalDiffusion/testme.json b/test/HD/thermalDiffusion/testme.json index 8fd07a94a..a62b140a9 100644 --- a/test/HD/thermalDiffusion/testme.json +++ b/test/HD/thermalDiffusion/testme.json @@ -6,7 +6,7 @@ "reconstruction": 2, "single": false, "mpi": false, - "dec": ["2","1","2"], + "dec": [2,1,2], "tolerance": 0 }, "variants": [ diff --git a/test/MHD/AmbipolarCshock3D/testme.json b/test/MHD/AmbipolarCshock3D/testme.json index 96c8bff2a..22f9df910 100644 --- a/test/MHD/AmbipolarCshock3D/testme.json +++ b/test/MHD/AmbipolarCshock3D/testme.json @@ -12,12 +12,12 @@ "ini": ["idefix.ini","idefix-rkl.ini"], "mpi": [false], "vectPot": [false, true], - "dec": ["2","1","1"] + "dec": [2,1,1] },{ "ini": ["idefix.ini","idefix-rkl.ini"], "mpi": [true], "vectPot": [false], - "dec": ["2","1","1"], + "dec": [2,1,1], "tolerance": 3e-14 } ], diff --git a/test/MHD/FargoMHDSpherical/testme.json b/test/MHD/FargoMHDSpherical/testme.json index 8943f0ce5..70748b449 100644 --- a/test/MHD/FargoMHDSpherical/testme.json +++ b/test/MHD/FargoMHDSpherical/testme.json @@ -5,7 +5,7 @@ "noplot": true, "single": false, "reconstruction": 2, - "dec": ["2","2","2"], + "dec": [2,2,2], "standardTest": false, "tolerance": 1e-14 }, diff --git a/test/MHD/LinearWaveTest/testme.json b/test/MHD/LinearWaveTest/testme.json index dd56af87f..b552fb8f7 100644 --- a/test/MHD/LinearWaveTest/testme.json +++ b/test/MHD/LinearWaveTest/testme.json @@ -3,7 +3,7 @@ "default": { "dumpname": "dump.0001.dmp", "noplot": true, - "dec": ["2","2","2"], + "dec": [2,2,2], "tolerance": 2e-13 }, "variants": [ diff --git a/test/MHD/OrszagTang/testme.json b/test/MHD/OrszagTang/testme.json index b455db40d..a2a5b478a 100644 --- a/test/MHD/OrszagTang/testme.json +++ b/test/MHD/OrszagTang/testme.json @@ -3,7 +3,7 @@ "default": { "dumpname": "dump.0001.dmp", "noplot": true, - "dec": ["2","2"], + "dec": [2,2], "tolerance": 1e-12, "standardTest": false }, diff --git a/test/MHD/OrszagTang3D/testme.json b/test/MHD/OrszagTang3D/testme.json index 8bebdb77e..fac783064 100644 --- a/test/MHD/OrszagTang3D/testme.json +++ b/test/MHD/OrszagTang3D/testme.json @@ -3,7 +3,7 @@ "default": { "dumpname": "dump.0001.dmp", "reconstruction": 2, - "dec": ["2","2","2"], + "dec": [2,2,2], "standardTest": false, "tolerance": 1e-13 }, diff --git a/test/MHD/ShearingBox/testme.json b/test/MHD/ShearingBox/testme.json index 7166c3e86..e347fa894 100644 --- a/test/MHD/ShearingBox/testme.json +++ b/test/MHD/ShearingBox/testme.json @@ -5,7 +5,7 @@ "noplot": true, "single": false, "reconstruction": 2, - "dec": ["2","1","2"], + "dec": [2,1,2], "tolerance": 1e-14 }, "variants": [ diff --git a/test/Planet/PlanetMigration2D/testme.json b/test/Planet/PlanetMigration2D/testme.json index fa0c71fbc..af4f84b43 100644 --- a/test/Planet/PlanetMigration2D/testme.json +++ b/test/Planet/PlanetMigration2D/testme.json @@ -7,7 +7,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2","2"], + "dec": [2,2], "tolerance": 1e-13 }, "variants": [ diff --git a/test/Planet/PlanetPlanetRK42D/testme.json b/test/Planet/PlanetPlanetRK42D/testme.json index 458fecd6b..ece6aa2d6 100644 --- a/test/Planet/PlanetPlanetRK42D/testme.json +++ b/test/Planet/PlanetPlanetRK42D/testme.json @@ -7,7 +7,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2","2"], + "dec": [2,2], "tolerance": 1e-13 }, "variants": [ diff --git a/test/Planet/PlanetSpiral2D/testme.json b/test/Planet/PlanetSpiral2D/testme.json index fa0c71fbc..af4f84b43 100644 --- a/test/Planet/PlanetSpiral2D/testme.json +++ b/test/Planet/PlanetSpiral2D/testme.json @@ -7,7 +7,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2","2"], + "dec": [2,2], "tolerance": 1e-13 }, "variants": [ diff --git a/test/Planet/PlanetTorque3D/testme.json b/test/Planet/PlanetTorque3D/testme.json index 5ef1ba03f..8cb617f9c 100644 --- a/test/Planet/PlanetTorque3D/testme.json +++ b/test/Planet/PlanetTorque3D/testme.json @@ -6,7 +6,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2","2","2"], + "dec": [2,2,2], "tolerance": 1e-13 }, "variants": [ diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.json b/test/Planet/PlanetsIsActiveRK52D/testme.json index 1f7e49ebf..3f219b916 100644 --- a/test/Planet/PlanetsIsActiveRK52D/testme.json +++ b/test/Planet/PlanetsIsActiveRK52D/testme.json @@ -6,7 +6,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2","2"], + "dec": [2,2], "nonRegressionTest": false, "tolerance": 1e-13 }, diff --git a/test/SelfGravity/JeansInstability/testme.json b/test/SelfGravity/JeansInstability/testme.json index cdcfaa60c..ba620fb6b 100644 --- a/test/SelfGravity/JeansInstability/testme.json +++ b/test/SelfGravity/JeansInstability/testme.json @@ -6,7 +6,7 @@ "vectPot": false, "single": false, "reconstruction": 2, - "dec": ["2"], + "dec": [2], "nonRegressionTest": false, "tolerance": 1e-13 }, diff --git a/test/SelfGravity/RandomSphere/testme.json b/test/SelfGravity/RandomSphere/testme.json index a3b2fbe94..20128b31e 100644 --- a/test/SelfGravity/RandomSphere/testme.json +++ b/test/SelfGravity/RandomSphere/testme.json @@ -3,7 +3,7 @@ "default": { "dumpname": "dump.0001.dmp", "noplot": true, - "dec": ["2","2","1"], + "dec": [2,2,1], "nonRegressionTest": false, "tolerance": 0 }, diff --git a/test/python_requirements.txt b/test/python_requirements.txt index 5b8c6ba7c..9ff69aedb 100644 --- a/test/python_requirements.txt +++ b/test/python_requirements.txt @@ -11,3 +11,4 @@ pybind11 >= 3.0.4 # To run the test suite, we can use pytest, mostly any version # 6.0 is the one available on system available on debian-11 pytest >= 6.0 +jsonschema >= 4.26.0 From e9827297e0e650524ced2dd73c40c57257a0381e Mon Sep 17 00:00:00 2001 From: nscepi <63753204+nscepi@users.noreply.github.com> Date: Thu, 3 Sep 2026 08:51:57 +0200 Subject: [PATCH 130/144] Move CheckNan to end of loop on stages in timeIntegrator (#403) * Move CheckNan to end of loop on stages in timeIntegrator CheckNan was previously located after EvolveStage. However, EvolveStage updates the conservative variables and CheckNan checks the primitive variables. This reports the detection of a NaN to the next cycle. By moving CheckNan to the end of the loop on stages in timeIntegrator, so after the ConsToPrim, this PR ensures that we detect the NaN at the right cycle. * [pre-commit.ci lite] apply automatic fixes * Move CheckNan at end of integration cycle * Update pre-commit config --------- Co-authored-by: pre-commit-ci-lite[bot] <117423508+pre-commit-ci-lite[bot]@users.noreply.github.com> --- src/timeIntegrator.cpp | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/src/timeIntegrator.cpp b/src/timeIntegrator.cpp index 79298a0f6..e3f6949ed 100644 --- a/src/timeIntegrator.cpp +++ b/src/timeIntegrator.cpp @@ -306,14 +306,6 @@ void TimeIntegrator::Cycle(DataBlock &data) { // evolve dt accordingly data.t += data.dt; - // Look for Nans every now and then (this actually cost a lot of time on GPUs - // because streams are divergent) - if(ncycles%checkNanPeriodicity==0) { - if(data.CheckNan()>0) { - throw std::runtime_error(std::string("Nan found after integration cycle")); - } - } - // Compute next time_step during first stage if(stage==0) { if(!haveFixedDt) { @@ -353,6 +345,7 @@ void TimeIntegrator::Cycle(DataBlock &data) { // Add back fargo velocity so that boundary conditions are applied on the total V if(data.haveFargo) data.fargo->AddVelocity(data.t); } + ///////////////////////////////////////////////// // END STAGES LOOP // ///////////////////////////////////////////////// @@ -381,6 +374,14 @@ void TimeIntegrator::Cycle(DataBlock &data) { // Launch user step last data.LaunchUserStepLast(); + // Look for Nans every now and then (this actually cost a lot of time on GPUs + // because streams are divergent) + if(ncycles%checkNanPeriodicity==0) { + if(data.CheckNan()>0) { + throw std::runtime_error(std::string("Nan found after integration cycle")); + } + } + // Update current time (should have already been done, but this gets rid of roundoff errors) data.t=t0+data.dt; From 5787cac5ec6023cb344772f184eca9307a8568af Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Thu, 3 Sep 2026 20:53:57 +0200 Subject: [PATCH 131/144] Add conservation test to OT and OT3D (#407) * check conserved quantities --- test/MHD/OrszagTang/idefix-hll.ini | 7 +-- .../MHD/OrszagTang/idefix-hlld-arithmetic.ini | 7 +-- test/MHD/OrszagTang/idefix-hlld-hll.ini | 7 +-- test/MHD/OrszagTang/idefix-hlld-hlld.ini | 7 +-- test/MHD/OrszagTang/idefix-hlld-uct0.ini | 7 +-- test/MHD/OrszagTang/idefix-hlld.ini | 7 +-- test/MHD/OrszagTang/idefix-tvdlf.ini | 7 +-- test/MHD/OrszagTang/idefix.ini | 7 +-- test/MHD/OrszagTang/setup.cpp | 44 ++++++++++++++++++- test/MHD/OrszagTang3D/idefix.ini | 7 +-- test/MHD/OrszagTang3D/setup.cpp | 44 ++++++++++++++++++- 11 files changed, 121 insertions(+), 30 deletions(-) diff --git a/test/MHD/OrszagTang/idefix-hll.ini b/test/MHD/OrszagTang/idefix-hll.ini index 4f13fd972..707f35605 100644 --- a/test/MHD/OrszagTang/idefix-hll.ini +++ b/test/MHD/OrszagTang/idefix-hll.ini @@ -18,6 +18,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-hlld-arithmetic.ini b/test/MHD/OrszagTang/idefix-hlld-arithmetic.ini index 8a656d7b3..0c62cfcc5 100644 --- a/test/MHD/OrszagTang/idefix-hlld-arithmetic.ini +++ b/test/MHD/OrszagTang/idefix-hlld-arithmetic.ini @@ -19,6 +19,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-hlld-hll.ini b/test/MHD/OrszagTang/idefix-hlld-hll.ini index b396e9917..26ae64973 100644 --- a/test/MHD/OrszagTang/idefix-hlld-hll.ini +++ b/test/MHD/OrszagTang/idefix-hlld-hll.ini @@ -19,6 +19,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-hlld-hlld.ini b/test/MHD/OrszagTang/idefix-hlld-hlld.ini index 5e158b939..8f82d6f8e 100644 --- a/test/MHD/OrszagTang/idefix-hlld-hlld.ini +++ b/test/MHD/OrszagTang/idefix-hlld-hlld.ini @@ -19,6 +19,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-hlld-uct0.ini b/test/MHD/OrszagTang/idefix-hlld-uct0.ini index 23646b96f..b0d637d74 100644 --- a/test/MHD/OrszagTang/idefix-hlld-uct0.ini +++ b/test/MHD/OrszagTang/idefix-hlld-uct0.ini @@ -19,6 +19,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-hlld.ini b/test/MHD/OrszagTang/idefix-hlld.ini index cf6d5cbfd..449d941f4 100644 --- a/test/MHD/OrszagTang/idefix-hlld.ini +++ b/test/MHD/OrszagTang/idefix-hlld.ini @@ -18,6 +18,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix-tvdlf.ini b/test/MHD/OrszagTang/idefix-tvdlf.ini index ec9ffe85e..62cf6d280 100644 --- a/test/MHD/OrszagTang/idefix-tvdlf.ini +++ b/test/MHD/OrszagTang/idefix-tvdlf.ini @@ -18,6 +18,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/idefix.ini b/test/MHD/OrszagTang/idefix.ini index 0e7421843..2ecc050ec 100644 --- a/test/MHD/OrszagTang/idefix.ini +++ b/test/MHD/OrszagTang/idefix.ini @@ -18,6 +18,7 @@ X2-beg periodic X2-end periodic [Output] -vtk 0.5 -dmp 0.5 -log 100 +analysis 0.1 +vtk 0.5 +dmp 0.5 +log 100 diff --git a/test/MHD/OrszagTang/setup.cpp b/test/MHD/OrszagTang/setup.cpp index 50c981c18..b337ff6bf 100644 --- a/test/MHD/OrszagTang/setup.cpp +++ b/test/MHD/OrszagTang/setup.cpp @@ -9,13 +9,53 @@ generators on different architectures. **/ /*********************************************/ - +void CheckConservation(DataBlock &data) { + static real firstCall{true}; + static std::array consArray; + data.hydro->ConvertPrimToCons(); + auto Uc = data.hydro->Uc; + auto dV = data.dV; + //idfx::cout << "Analysis: checking conserved quantities..." << std::endl; + #ifdef SINGLE_PRECISION + const real threshold = 1e-4; + #else + const real threshold = 1e-13; + #endif + for(int nv = 0 ; nv < DefaultPhysics::nvar ; nv++) { + real cons = 0; + idefix_reduce("Conserved quantity reduction", + data.beg[KDIR], data.end[KDIR], + data.beg[JDIR], data.end[JDIR], + data.beg[IDIR], data.end[IDIR], + KOKKOS_LAMBDA (int k, int j, int i, real &c) { + c += dV(k,j,i)*Uc(nv,k,j,i); + }, + Kokkos::Sum(cons)); + #ifdef WITH_MPI + MPI_Allreduce(MPI_IN_PLACE, &cons, 1, realMPI, MPI_SUM, MPI_COMM_WORLD); + #endif + if(firstCall) { + consArray[nv] = cons; + } else { + real err = std::fabs((consArray[nv]-cons)); + if(err>threshold) { + std::stringstream str; + str << "Quantity " << data.hydro->VcName[nv] << " is not conserved" << std::endl; + std::cout << "Error on " << data.hydro->VcName[nv] << " is " << err << std::endl; + std::cout << "Original=" << consArray[nv] << " New=" << cons << std::endl; + IDEFIX_ERROR(str); + } + } + } + firstCall=false; + //idfx::cout << "Analysis: done." << std::endl; +} // Default constructor // Initialisation routine. Can be used to allocate // Arrays or variables which are used later on Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { - + output.EnrollAnalysis(&CheckConservation); } // This routine initialize the flow diff --git a/test/MHD/OrszagTang3D/idefix.ini b/test/MHD/OrszagTang3D/idefix.ini index 1021bd335..5551b23f8 100644 --- a/test/MHD/OrszagTang3D/idefix.ini +++ b/test/MHD/OrszagTang3D/idefix.ini @@ -22,6 +22,7 @@ X3-beg periodic X3-end periodic [Output] -vtk 0.2 -dmp 0.2 -log 10 +vtk 0.2 +dmp 0.2 +log 10 +analysis 0.1 diff --git a/test/MHD/OrszagTang3D/setup.cpp b/test/MHD/OrszagTang3D/setup.cpp index a6927a132..abbc78534 100644 --- a/test/MHD/OrszagTang3D/setup.cpp +++ b/test/MHD/OrszagTang3D/setup.cpp @@ -11,11 +11,53 @@ generators on different architectures. Output* myOutput; int outnum; -// Analysis function + +void CheckConservation(DataBlock &data) { + static real firstCall{true}; + static std::array consArray; + data.hydro->ConvertPrimToCons(); + auto Uc = data.hydro->Uc; + auto dV = data.dV; + //idfx::cout << "Analysis: checking conserved quantities..." << std::endl; + #ifdef SINGLE_PRECISION + const real threshold = 2e-4; + #else + const real threshold = 1e-13; + #endif + for(int nv = 0 ; nv < DefaultPhysics::nvar ; nv++) { + real cons = 0; + idefix_reduce("Conserved quantity reduction", + data.beg[KDIR], data.end[KDIR], + data.beg[JDIR], data.end[JDIR], + data.beg[IDIR], data.end[IDIR], + KOKKOS_LAMBDA (int k, int j, int i, real &c) { + c += dV(k,j,i)*Uc(nv,k,j,i); + }, + Kokkos::Sum(cons)); + #ifdef WITH_MPI + MPI_Allreduce(MPI_IN_PLACE, &cons, 1, realMPI, MPI_SUM, MPI_COMM_WORLD); + #endif + if(firstCall) { + consArray[nv] = cons; + } else { + real err = std::fabs((consArray[nv]-cons)); + if(err>threshold) { + std::stringstream str; + str << "Quantity " << data.hydro->VcName[nv] << " is not conserved" << std::endl; + std::cout << "Error on " << data.hydro->VcName[nv] << " is " << err << std::endl; + std::cout << "Original=" << consArray[nv] << " New=" << cons << std::endl; + IDEFIX_ERROR(str); + } + } + } + firstCall=false; + //idfx::cout << "Analysis: done." << std::endl; +} // Initialisation routine. Can be used to allocate // Arrays or variables which are used later on Setup::Setup(Input &input, Grid &grid, DataBlock &data, Output &output) { + output.EnrollAnalysis(&CheckConservation); } // This routine initialize the flow From 6ef3da052a128810c32a1a3027ba3024dfcb0cb1 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Tue, 8 Sep 2026 16:48:54 +0200 Subject: [PATCH 132/144] Keep Inter-cell flux (#337) * keep Flux array in each direction (increase memory footprint, but easier post-treatment) --- src/fluid/RiemannSolver/riemannSolver.hpp | 4 ---- src/fluid/addNonIdealMHDFlux.hpp | 3 +-- src/fluid/calcParabolicFlux.hpp | 8 ++++---- src/fluid/calcRightHandSide.hpp | 4 ++-- src/fluid/evolveStage.hpp | 6 +++--- src/fluid/fluid.hpp | 12 ++++++++---- src/rkl/rkl.hpp | 12 +++++------- test/MHD/AmbipolarWind/setup.cpp | 2 +- test/SelfGravity/UniformCollapse/setup.cpp | 2 +- 9 files changed, 25 insertions(+), 28 deletions(-) diff --git a/src/fluid/RiemannSolver/riemannSolver.hpp b/src/fluid/RiemannSolver/riemannSolver.hpp index abb70eed5..b6c1e6f11 100644 --- a/src/fluid/RiemannSolver/riemannSolver.hpp +++ b/src/fluid/RiemannSolver/riemannSolver.hpp @@ -70,7 +70,6 @@ class RiemannSolver { IdefixArray4D Vc; IdefixArray4D Vs; - IdefixArray4D Flux; IdefixArray3D cMax; Fluid* hydro; DataBlock *data; @@ -90,7 +89,6 @@ class RiemannSolver { template RiemannSolver::RiemannSolver(Input &input, Fluid* hydro) : Vc{hydro->Vc}, Vs{hydro->Vs}, - Flux{hydro->FluxRiemann}, cMax{hydro->cMax}, hydro{hydro}, data{hydro->data} @@ -148,8 +146,6 @@ RiemannSolver::RiemannSolver(Input &input, Fluid* hydro) : Vc{hydro- mySolver = HLL_DUST; } - - // Shock flattening this->haveShockFlattening = input.CheckEntry(std::string(Phys::prefix),"shockFlattening")>=0; // Init shock flattening diff --git a/src/fluid/addNonIdealMHDFlux.hpp b/src/fluid/addNonIdealMHDFlux.hpp index 52c281d2d..9ae6af304 100644 --- a/src/fluid/addNonIdealMHDFlux.hpp +++ b/src/fluid/addNonIdealMHDFlux.hpp @@ -19,8 +19,7 @@ void Fluid::AddNonIdealMHDFlux(const real t) { if constexpr(Phys::mhd) { int ioffset,joffset,koffset; - - IdefixArray4D Flux = this->FluxRiemann; + IdefixArray4D Flux = this->FluxRiemann[dir]; IdefixArray4D Vc = this->Vc; IdefixArray4D Vs = this->Vs; IdefixArray3D dMax = this->dMax; diff --git a/src/fluid/calcParabolicFlux.hpp b/src/fluid/calcParabolicFlux.hpp index a8c6761c0..8713f9107 100644 --- a/src/fluid/calcParabolicFlux.hpp +++ b/src/fluid/calcParabolicFlux.hpp @@ -42,7 +42,7 @@ void Fluid::CalcParabolicFlux(const real t) { if(data->haveFargo && viscosityStatus.isExplicit) { data->fargo->AddVelocityFluid(t,this); } - this->viscosity->AddViscousFlux(dir,t, this->FluxRiemann); + this->viscosity->AddViscousFlux(dir,t, this->FluxRiemann[dir]); // Remove back Fargo velocity if(data->haveFargo && viscosityStatus.isExplicit) { @@ -53,18 +53,18 @@ void Fluid::CalcParabolicFlux(const real t) { // Add thermal diffusion if( (thermalDiffusionStatus.isExplicit && (!data->rklCycle)) || (thermalDiffusionStatus.isRKL && data->rklCycle)) { - this->thermalDiffusion->AddDiffusiveFlux(dir,t, this->FluxRiemann); + this->thermalDiffusion->AddDiffusiveFlux(dir,t, this->FluxRiemann[dir]); } if( (bragViscosityStatus.isExplicit && (!data->rklCycle)) || (bragViscosityStatus.isRKL && data->rklCycle)) { - this->bragViscosity->AddBragViscousFlux(dir,t, this->FluxRiemann); + this->bragViscosity->AddBragViscousFlux(dir,t, this->FluxRiemann[dir]); } // Add braginskii thermal diffusion if( (bragThermalDiffusionStatus.isExplicit && (!data->rklCycle)) || (bragThermalDiffusionStatus.isRKL && data->rklCycle)) { - this->bragThermalDiffusion->AddBragDiffusiveFlux(dir,t, this->FluxRiemann); + this->bragThermalDiffusion->AddBragDiffusiveFlux(dir,t, this->FluxRiemann[dir]); } idfx::popRegion(); diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index 0a0d3e194..a68f56d0f 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -21,7 +21,7 @@ struct Fluid_CorrectFluxFunctor { explicit Fluid_CorrectFluxFunctor (Fluid *hydro, real dt) { Uc = hydro->Uc; Vc = hydro->Vc; - Flux = hydro->FluxRiemann; + Flux = hydro->FluxRiemann[dir]; A = hydro->data->A[dir]; dV = hydro->data->dV; x1m = hydro->data->xl[IDIR]; @@ -205,7 +205,7 @@ struct Fluid_CalcRHSFunctor { explicit Fluid_CalcRHSFunctor (Fluid *hydro, real dt) { Uc = hydro->Uc; Vc = hydro->Vc; - Flux = hydro->FluxRiemann; + Flux = hydro->FluxRiemann[dir]; A = hydro->data->A[dir]; dV = hydro->data->dV; x1m = hydro->data->xl[IDIR]; diff --git a/src/fluid/evolveStage.hpp b/src/fluid/evolveStage.hpp index 31dae5b7d..b0a467ba4 100644 --- a/src/fluid/evolveStage.hpp +++ b/src/fluid/evolveStage.hpp @@ -14,20 +14,20 @@ template template void Fluid::LoopDir(const real t, const real dt) { // Step 2: compute the intercell flux with our Riemann solver, store the resulting InvDt - this->rSolver->template CalcFlux(this->FluxRiemann); + this->rSolver->template CalcFlux(this->FluxRiemann[dir]); // Step 2.5: compute intercell parabolic flux when needed if(haveExplicitParabolicTerms) CalcParabolicFlux(t); // If we have tracers, compute the tracer intercell flux if(haveTracer) { - this->tracer->template CalcFlux(this->FluxRiemann); + this->tracer->template CalcFlux(this->FluxRiemann[dir]); } // Step 3: compute the resulting evolution of the conserved variables, stored in Uc CalcRightHandSide(t,dt); if(haveTracer) { - this->tracer->template CalcRightHandSide(this->FluxRiemann,t ,dt); + this->tracer->template CalcRightHandSide(this->FluxRiemann[dir],t ,dt); } // Recursive: do next dimension diff --git a/src/fluid/fluid.hpp b/src/fluid/fluid.hpp index 44cace6bf..9e0615dee 100644 --- a/src/fluid/fluid.hpp +++ b/src/fluid/fluid.hpp @@ -67,7 +67,7 @@ class Fluid { void EvolveStage(const real, const real); void ResetStage(); void ShowConfig(); - IdefixArray4D GetFlux() {return this->FluxRiemann;} + IdefixArray4D GetFlux(int dir) {return this->FluxRiemann.at(dir);} int CheckNan(); // Our boundary conditions @@ -182,7 +182,7 @@ class Fluid { // Required by time integrator IdefixArray3D InvDt; - IdefixArray4D FluxRiemann; + std::array,DIMENSIONS> FluxRiemann; IdefixArray3D dMax; // Maximum diffusion speed std::unique_ptr> rSolver; @@ -539,8 +539,12 @@ Fluid::Fluid(Grid &grid, Input &input, DataBlock *datain, int n) { data->np_tot[KDIR], data->np_tot[JDIR], data->np_tot[IDIR]); dMax = IdefixArray3D(prefix+"_dMax", data->np_tot[KDIR], data->np_tot[JDIR], data->np_tot[IDIR]); - FluxRiemann = IdefixArray4D(prefix+"_FluxRiemann", Phys::nvar+nTracer, - data->np_tot[KDIR], data->np_tot[JDIR], data->np_tot[IDIR]); + + for(int i = 0 ; i < DIMENSIONS ; i++) { + FluxRiemann[i] = IdefixArray4D(prefix+"_FluxRiemann_X"+std::to_string(i), + Phys::nvar+nTracer, + data->np_tot[KDIR], data->np_tot[JDIR], data->np_tot[IDIR]); + } if constexpr(Phys::mhd) { Vs = IdefixArray4D(prefix+"_Vs", DIMENSIONS, diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 6f22de6f5..8288cd0fa 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -30,7 +30,7 @@ class RKLegendre { RKLegendre(Input &, Fluid*); void Cycle(); void ResetStage(); - void ResetFlux(); + void ResetFlux(int dir); void EvolveStage(real); template void CalcParabolicRHS(real); void ComputeDt(); @@ -556,9 +556,9 @@ void RKLegendre::Cycle() { template -void RKLegendre::ResetFlux() { +void RKLegendre::ResetFlux(int dir) { idfx::pushRegion("RKLegendre::ResetFlux"); - IdefixArray4D Flux = hydro->FluxRiemann; + IdefixArray4D Flux = hydro->FluxRiemann[dir]; IdefixArray1D vars = this->varList; idefix_for("RKL_ResetFlux", 0,nvarRKL, @@ -577,7 +577,6 @@ template struct RKLegendre_ResetStageFunctor { explicit RKLegendre_ResetStageFunctor(RKLegendre *rkl) { dU = rkl->dU; - Flux = rkl->hydro->FluxRiemann; vars = rkl->varList; stage = rkl->stage; nvar = rkl->nvarRKL; @@ -597,7 +596,6 @@ struct RKLegendre_ResetStageFunctor { } IdefixArray4D dU; - IdefixArray4D Flux; IdefixArray1D vars; IdefixArray4D dA, dB; IdefixArray3D ex,ey,ez; @@ -681,7 +679,7 @@ void RKLegendre::ComputeDt() { template template void RKLegendre::LoopDir(real t) { - ResetFlux(); + ResetFlux(dir); // CalcParabolicFlux hydro->template CalcParabolicFlux(t); @@ -725,7 +723,7 @@ template void RKLegendre::CalcParabolicRHS(real t) { idfx::pushRegion("RKLegendre::CalcParabolicRHS"); - IdefixArray4D Flux = hydro->FluxRiemann; + IdefixArray4D Flux = hydro->FluxRiemann[dir]; IdefixArray3D A = data->A[dir]; IdefixArray3D dV = data->dV; IdefixArray1D x1m = data->xl[IDIR]; diff --git a/test/MHD/AmbipolarWind/setup.cpp b/test/MHD/AmbipolarWind/setup.cpp index 892eeea27..99b45ba8f 100644 --- a/test/MHD/AmbipolarWind/setup.cpp +++ b/test/MHD/AmbipolarWind/setup.cpp @@ -335,7 +335,7 @@ void EmfBoundary(DataBlock& data, const real t) { } void FluxBoundary(DataBlock & data, int dir, BoundarySide side, const real t) { - IdefixArray4D Flux = data.hydro->FluxRiemann; + IdefixArray4D Flux = data.hydro->FluxRiemann[dir]; if( dir==IDIR && side == left) { int iref = data.beg[IDIR]; diff --git a/test/SelfGravity/UniformCollapse/setup.cpp b/test/SelfGravity/UniformCollapse/setup.cpp index 6f773a153..22f4a34d6 100644 --- a/test/SelfGravity/UniformCollapse/setup.cpp +++ b/test/SelfGravity/UniformCollapse/setup.cpp @@ -65,7 +65,7 @@ void FluxBoundary(Fluid *hydro, int dir, BoundarySide side, cons if((dir==IDIR) && (side == left)) { // Loading needed data DataBlock &data = *hydro->data; - IdefixArray4D Flux = hydro->FluxRiemann; + IdefixArray4D Flux = hydro->FluxRiemann[dir]; real halfDt = data.dt/2.; // RK2, dt is actually half at each flux calculation int iref = data.nghost[IDIR]; real rin = data.xbeg[IDIR]; From 8e4f8db1b7bc0fb9059e40cf2d152ed8e6f5d5b7 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Fri, 18 Sep 2026 14:58:05 +0200 Subject: [PATCH 133/144] ensure shearing box test also analyse B (#412) * ensure shearing box test also analyse B * add B field in the validation of the shearing box test. Adjust tolerance accordingly. --- test/MHD/ShearingBox/analysis.cpp | 11 ++++++----- test/MHD/ShearingBox/analysis.hpp | 3 ++- test/MHD/ShearingBox/python/testidefix.py | 17 +++++++++++++++-- 3 files changed, 23 insertions(+), 8 deletions(-) diff --git a/test/MHD/ShearingBox/analysis.cpp b/test/MHD/ShearingBox/analysis.cpp index 95102b993..c227c3fa8 100644 --- a/test/MHD/ShearingBox/analysis.cpp +++ b/test/MHD/ShearingBox/analysis.cpp @@ -58,7 +58,8 @@ double Analysis::ShwaveAmplitude(const int field, const int nx, const int ny, const int nz, - const real t) + const real t, + const real phaseShift = 0.0) /* * compute the weighted average: int dphi dz rho *infield/int dphi dz rho * @@ -74,7 +75,7 @@ double Analysis::ShwaveAmplitude(const int field, real z = d->x[KDIR](k); real wave = sin(2.0*M_PI*( (nx-ny*shear*t)*x + ny*y - + nz*z)); + + nz*z ) + 2*phaseShift*M_PI); q += wave*d->Vc(field,k,j,i); } } @@ -159,9 +160,9 @@ void Analysis::PerformAnalysis(DataBlock &data) { WriteField(ShwaveAmplitude(VX1, 0, 1, 2, data.t) ); WriteField(ShwaveAmplitude(VX2, 0, 1, 2, data.t) ); WriteField(ShwaveAmplitude(VX3, 0, 1, 2, data.t) ); - WriteField(ShwaveAmplitude(BX1, 0, 1, 2, data.t) ); - WriteField(ShwaveAmplitude(BX2, 0, 1, 2, data.t) ); - WriteField(ShwaveAmplitude(BX3, 0, 1, 2, data.t) ); + WriteField(ShwaveAmplitude(BX1, 0, 1, 2, data.t, -0.25)); + WriteField(ShwaveAmplitude(BX2, 0, 1, 2, data.t, -0.25)); + WriteField(ShwaveAmplitude(BX3, 0, 1, 2, data.t, -0.25)); if(idfx::prank==0) { diff --git a/test/MHD/ShearingBox/analysis.hpp b/test/MHD/ShearingBox/analysis.hpp index 8b65c4317..3a0633f37 100644 --- a/test/MHD/ShearingBox/analysis.hpp +++ b/test/MHD/ShearingBox/analysis.hpp @@ -25,7 +25,8 @@ class Analysis { const int, const int, const int, - const real); + const real, + const real); DataBlockHost *d; Grid *grid; diff --git a/test/MHD/ShearingBox/python/testidefix.py b/test/MHD/ShearingBox/python/testidefix.py index 6f75c6af7..559c6c6ff 100755 --- a/test/MHD/ShearingBox/python/testidefix.py +++ b/test/MHD/ShearingBox/python/testidefix.py @@ -64,7 +64,7 @@ def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): args, unknown = parser.parse_known_args() -# initial condition: vr=1, rest is 0, mode initial is nx=0, ny=1, nz=5) +# initial condition: vr=1, rest is 0, mode initial is nx=0, ny=1, nz=2) y = solve_ivp( rhs, [0, 30], @@ -103,6 +103,9 @@ def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): (V["vx"] / v0 - y.sol(V["t"])[0, :]) ** 2 + (V["vy"] / v0 - y.sol(V["t"])[1, :]) ** 2 + (V["vz"] / v0 - y.sol(V["t"])[2, :]) ** 2 + + (V["bx"] / v0 - y.sol(V["t"])[3, :]) ** 2 + + (V["by"] / v0 - y.sol(V["t"])[4, :]) ** 2 + + (V["bz"] / v0 - y.sol(V["t"])[5, :]) ** 2 ) @@ -122,6 +125,16 @@ def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): plt.legend() plt.xlabel("t") + plt.figure(2) + plt.plot(V["t"], V["bx"] / v0, "r-", label=r"$b_{R}$") + plt.plot(V["t"], y.sol(V["t"])[3, :], "r--") + plt.plot(V["t"], V["by"] / v0, "b-", label=r"$b_{\varphi}$") + plt.plot(V["t"], y.sol(V["t"])[4, :], "b--") + plt.plot(V["t"], V["bz"] / v0, "g-", label=r"$b_{z}$") + plt.plot(V["t"], y.sol(V["t"])[5, :], "g--") + plt.legend() + plt.xlabel("t") + # plot error plt.figure() plt.semilogy(V["t"], error) @@ -134,7 +147,7 @@ def rhs(t, y, Omega, q, B0y, B0z, k0x, k0y, k0z): err = np.mean(error) print("Error=", err) -if err < 0.03: +if err < 0.04: print("SUCCESS") sys.exit(0) else: From c46e4971d7980b33bf71ab19d2b49a5db485f474 Mon Sep 17 00:00:00 2001 From: ScatteredComet <120208759+ScatteredComet@users.noreply.github.com> Date: Fri, 18 Sep 2026 20:08:29 +0100 Subject: [PATCH 134/144] fix spelling error (#411) --- doc/source/index.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/source/index.rst b/doc/source/index.rst index 2cea98cdb..b3be783b1 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -20,7 +20,7 @@ algorithm is essentially the same (but with some major modification to its struc ================ Requirements ================ -*Idefix* is written is standard C++20 and does not rely on any external library in serial (non MPI). +*Idefix* is written in standard C++20 and does not rely on any external library in serial (non MPI). Compiler *Idefix* requires a C++20 compatible compiler. It has been tested successfully with GCC (>11), Intel compiler suite (>2022) and From f0403bb9c047fe8934956409824a890c7f60d781 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?S=C3=A9bastien=20Valat?= Date: Wed, 23 Sep 2026 16:52:32 +0200 Subject: [PATCH 135/144] copyrights: update copyright headers in all files of the project (#410) header: introduce a script to update the source file headers with licence & authors (imported from MALT : MALloc Tracker) --- .pre-commit-config.yaml | 12 - CMakeLists.txt | 18 + cmake/AddIdefixSource.cmake | 14 + cmake/CheckHdf5ParallelSupport.cmake | 14 + cmake/GetGitRevisionDescription.cmake | 14 + cmake/GetGitRevisionDescription.cmake.in | 14 + cmake/ReplaceIdefixSource.cmake | 14 + cmake/SetIdefixProperty.cmake | 14 + cmake/SetRequiredBuildSettingsForGCC8.cmake | 14 + cmake/SuppressFMA.cmake | 14 + doc/Makefile | 14 + doc/source/_static/my_theme.css | 14 + doc/source/conf.py | 15 + doc/source/plot_idefix_bench.py | 16 + make_tarballs.py | 15 + pytools/dump_io.py | 15 + pytools/idfx_io.py | 16 + pytools/idfx_test.py | 16 + pytools/idfx_test_gen.py | 14 +- pytools/idfx_test_run.py | 14 +- pytools/sod.py | 15 + pytools/tests/test_idfx_test_gen.py | 14 +- pytools/tests/test_idfx_test_run.py | 14 +- pytools/update_file_headers.json | 202 ++++++ pytools/update_file_headers.py | 666 ++++++++++++++++++ pytools/vtk_io.py | 16 + ruff.toml | 14 + scripts/ci/run-tests | 15 + src/CMakeLists.txt | 14 + src/arrays.hpp | 9 +- src/compiler_info.h.in | 9 +- src/dataBlock/CMakeLists.txt | 16 + src/dataBlock/coarsen.cpp | 9 +- src/dataBlock/dataBlock.cpp | 12 +- src/dataBlock/dataBlock.hpp | 11 +- src/dataBlock/dataBlockHost.cpp | 12 +- src/dataBlock/dataBlockHost.hpp | 11 +- src/dataBlock/dumpToFile.cpp | 13 +- src/dataBlock/evolveStage.cpp | 11 +- src/dataBlock/fargo.cpp | 10 +- src/dataBlock/fargo.hpp | 10 +- src/dataBlock/makeGeometry.cpp | 11 +- src/dataBlock/planetarySystem/CMakeLists.txt | 14 + src/dataBlock/planetarySystem/planet.cpp | 10 +- src/dataBlock/planetarySystem/planet.hpp | 9 +- .../planetarySystem/planetStructs.hpp | 9 +- .../planetarySystem/planetarySystem.cpp | 10 +- .../planetarySystem/planetarySystem.hpp | 9 +- src/dataBlock/stateContainer.cpp | 10 +- src/dataBlock/stateContainer.hpp | 10 +- src/dataBlock/validation.cpp | 11 +- src/error.cpp | 9 +- src/error.hpp | 11 +- src/fluid/CMakeLists.txt | 14 + src/fluid/RiemannSolver/CMakeLists.txt | 13 + .../RiemannSolver/Dustsolvers/CMakeLists.txt | 14 + .../RiemannSolver/Dustsolvers/hllDust.hpp | 9 +- .../RiemannSolver/HDsolvers/CMakeLists.txt | 14 + src/fluid/RiemannSolver/HDsolvers/hllHD.hpp | 11 +- src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp | 11 +- src/fluid/RiemannSolver/HDsolvers/roeHD.hpp | 11 +- src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp | 11 +- .../RiemannSolver/MHDsolvers/CMakeLists.txt | 14 + src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp | 11 +- .../RiemannSolver/MHDsolvers/hlldMHD.hpp | 11 +- src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp | 11 +- .../RiemannSolver/MHDsolvers/storeFlux.hpp | 10 +- .../RiemannSolver/MHDsolvers/tvdlfMHD.hpp | 11 +- src/fluid/RiemannSolver/calcFlux.hpp | 9 +- .../RiemannSolver/extrapolateToFaces.hpp | 9 +- src/fluid/RiemannSolver/flux.hpp | 9 +- src/fluid/RiemannSolver/riemannSolver.hpp | 10 +- src/fluid/RiemannSolver/shockFlattening.hpp | 9 +- src/fluid/RiemannSolver/slopeLimiter.hpp | 10 +- src/fluid/addNonIdealMHDFlux.hpp | 9 +- src/fluid/addSourceTerms.hpp | 9 +- src/fluid/boundary/CMakeLists.txt | 14 + src/fluid/boundary/axis.cpp | 13 +- src/fluid/boundary/axis.hpp | 10 +- src/fluid/boundary/boundary.hpp | 10 +- src/fluid/braginskii/CMakeLists.txt | 14 + src/fluid/braginskii/bragThermalDiffusion.cpp | 11 +- src/fluid/braginskii/bragThermalDiffusion.hpp | 11 +- src/fluid/braginskii/bragViscosity.cpp | 11 +- src/fluid/braginskii/bragViscosity.hpp | 10 +- src/fluid/calcCurrent.hpp | 13 +- src/fluid/calcParabolicFlux.hpp | 11 +- src/fluid/calcRightHandSide.hpp | 10 +- src/fluid/checkDivB.hpp | 11 +- src/fluid/checkNan.hpp | 11 +- src/fluid/coarsenFlow.hpp | 10 +- src/fluid/constrainedTransport/CMakeLists.txt | 14 + .../constrainedTransport/EMFexchange.hpp | 11 +- .../constrainedTransport/calcCornerEmf.hpp | 11 +- .../constrainedTransport/calcNonidealEMF.hpp | 11 +- .../constrainedTransport/calcRiemannEmf.hpp | 9 +- .../constrainedTransport.hpp | 11 +- .../enforceEMFBoundary.hpp | 10 +- .../enforceVectorPotentialBoundary.hpp | 9 +- .../constrainedTransport/evolveMagField.hpp | 11 +- .../evolveVectorPotential.hpp | 9 +- src/fluid/convertConsToPrim.hpp | 9 +- src/fluid/drag.cpp | 9 +- src/fluid/drag.hpp | 9 +- src/fluid/enroll.hpp | 9 +- src/fluid/eos/CMakeLists.txt | 14 + src/fluid/eos/eos.hpp | 9 +- src/fluid/eos/eos_adiabatic.hpp | 9 +- src/fluid/eos/eos_isothermal.hpp | 9 +- src/fluid/eos/eos_template.hpp | 9 +- src/fluid/evolveStage.hpp | 9 +- src/fluid/fluid.hpp | 9 +- src/fluid/fluid_defs.hpp | 11 +- src/fluid/showConfig.hpp | 10 +- src/fluid/thermalDiffusion.cpp | 9 +- src/fluid/thermalDiffusion.hpp | 9 +- src/fluid/tracer/CMakeLists.txt | 14 + src/fluid/tracer/tracer.cpp | 9 +- src/fluid/tracer/tracer.hpp | 9 +- src/fluid/viscosity.cpp | 10 +- src/fluid/viscosity.hpp | 9 +- src/global.cpp | 12 +- src/global.hpp | 10 +- src/gravity/CMakeLists.txt | 14 + src/gravity/gravity.cpp | 10 +- src/gravity/gravity.hpp | 9 +- src/gravity/laplacian.cpp | 11 +- src/gravity/laplacian.hpp | 9 +- src/gravity/selfGravity.cpp | 9 +- src/gravity/selfGravity.hpp | 9 +- src/grid.cpp | 12 +- src/grid.hpp | 10 +- src/gridHost.cpp | 13 +- src/gridHost.hpp | 11 +- src/idefix.hpp | 11 +- src/input.cpp | 10 +- src/input.hpp | 11 +- src/loop.hpp | 11 +- src/macros.hpp | 11 +- src/main.cpp | 12 +- src/mpi/CMakeLists.txt | 14 + src/mpi/buffer.hpp | 10 +- src/mpi/commArray.hpp | 9 +- src/mpi/exchanger.cpp | 10 +- src/mpi/exchanger.hpp | 10 +- src/mpi/mpi.cpp | 10 +- src/mpi/mpi.hpp | 10 +- src/mpi/mpiWrapper.hpp | 9 +- src/output/CMakeLists.txt | 15 + src/output/dump.cpp | 12 +- src/output/dump.hpp | 12 +- src/output/output.cpp | 12 +- src/output/output.hpp | 11 +- src/output/scalarField.hpp | 9 +- src/output/slice.cpp | 12 +- src/output/slice.hpp | 11 +- src/output/vtk.cpp | 14 +- src/output/vtk.hpp | 11 +- src/output/xdmf.cpp | 11 +- src/output/xdmf.hpp | 11 +- src/physics.hpp | 9 +- src/profiler.cpp | 9 +- src/profiler.hpp | 9 +- src/pydefix.cpp | 10 +- src/pydefix.hpp | 9 +- src/real_types.hpp | 12 +- src/reduce.hpp | 9 +- src/rkl/CMakeLists.txt | 14 + src/rkl/rkl.hpp | 10 +- src/setup.cpp | 9 +- src/setup.hpp | 11 +- src/timeIntegrator.cpp | 14 +- src/timeIntegrator.hpp | 12 +- src/units.cpp | 9 +- src/units.hpp | 9 +- src/utils/CMakeLists.txt | 14 + src/utils/bigEndian.hpp | 9 +- src/utils/column.cpp | 10 +- src/utils/column.hpp | 10 +- src/utils/dumpImage.cpp | 11 +- src/utils/dumpImage.hpp | 10 +- src/utils/iterativesolver/CMakeLists.txt | 14 + src/utils/iterativesolver/bicgstab.hpp | 9 +- src/utils/iterativesolver/cg.hpp | 9 +- src/utils/iterativesolver/iterativesolver.hpp | 9 +- src/utils/iterativesolver/jacobi.hpp | 9 +- src/utils/iterativesolver/minres.hpp | 9 +- src/utils/lookupTable.hpp | 11 +- src/utils/npy.hpp | 10 +- src/utils/vector.hpp | 9 +- src/version.h.in | 9 +- test.py | 14 + test/Dust/DustEnergy/definitions.hpp | 14 + test/Dust/DustEnergy/python/testidefix.py | 14 + test/Dust/DustEnergy/setup.cpp | 14 + test/Dust/DustEnergy/testme.py | 14 + test/Dust/DustyShock/definitions.hpp | 14 + test/Dust/DustyShock/python/testidefix.py | 15 + test/Dust/DustyShock/setup.cpp | 14 + test/Dust/DustyShock/testme.py | 14 + test/Dust/DustyWave/definitions.hpp | 14 + test/Dust/DustyWave/python/testidefix.py | 15 + test/Dust/DustyWave/setup.cpp | 14 + test/Dust/DustyWave/testme.py | 14 + test/Dust/FargoPlanet/definitions.hpp | 14 + test/Dust/FargoPlanet/setup.cpp | 14 + .../Dust/StreamingInstability/definitions.hpp | 14 + test/Dust/StreamingInstability/setup.cpp | 14 + test/HD/FargoPlanet/definitions.hpp | 14 + test/HD/FargoPlanet/setup.cpp | 14 + test/HD/FargoPlanet/testme.py | 14 + test/HD/KHI/definitions.hpp | 14 + test/HD/KHI/setup.cpp | 14 + test/HD/MachReflection/definitions.hpp | 14 + test/HD/MachReflection/setup.cpp | 14 + test/HD/MachReflection/testme.py | 14 + test/HD/RWI-cavity/definitions.hpp | 14 + test/HD/RWI-cavity/setup.cpp | 15 + .../SedovBlastWave/definitions-spherical.hpp | 14 + .../HD/SedovBlastWave/definitions-unequal.hpp | 14 + test/HD/SedovBlastWave/definitions.hpp | 14 + .../python/1Dsolution/definitions.hpp | 13 + .../python/1Dsolution/setup.cpp | 14 + test/HD/SedovBlastWave/python/testidefix.py | 15 + test/HD/SedovBlastWave/setup.cpp | 14 + test/HD/SedovBlastWave/testme.py | 14 + test/HD/ShearingBox/CMakeLists.txt | 14 + test/HD/ShearingBox/analysis.cpp | 14 + test/HD/ShearingBox/analysis.hpp | 14 + test/HD/ShearingBox/definitions.hpp | 14 + test/HD/ShearingBox/python/testidefix.py | 15 + test/HD/ShearingBox/setup.cpp | 14 + test/HD/ShearingBox/testme.py | 14 + test/HD/VSI/definitions.hpp | 14 + test/HD/VSI/setup.cpp | 15 + test/HD/ViscousDisk/definitions.hpp | 14 + test/HD/ViscousDisk/python/testidefix.py | 14 + test/HD/ViscousDisk/setup.cpp | 14 + test/HD/ViscousDisk/testme.py | 14 + .../ViscousFlowPastCylinder/definitions.hpp | 14 + test/HD/ViscousFlowPastCylinder/setup.cpp | 14 + test/HD/ViscousFlowPastCylinder/testme.py | 14 + test/HD/sod-iso/definitions.hpp | 14 + test/HD/sod-iso/python/testidefix.py | 15 + test/HD/sod-iso/setup.cpp | 15 + test/HD/sod-iso/testme.py | 14 + test/HD/sod/definitions.hpp | 14 + test/HD/sod/pydefix_example.py | 15 + test/HD/sod/python/testidefix.py | 15 + test/HD/sod/setup.cpp | 14 + test/HD/sod/testme.py | 14 + test/HD/thermalDiffusion/definitions.hpp | 14 + test/HD/thermalDiffusion/python/testidefix.py | 14 + test/HD/thermalDiffusion/setup.cpp | 14 + test/HD/thermalDiffusion/testme.py | 14 + test/IO/dump/CMakeLists.txt | 14 + test/IO/dump/definitions.hpp | 14 + test/IO/dump/setup.cpp | 14 + test/IO/dump/testme.py | 15 + test/IO/pydefix/CMakeLists.txt | 14 + test/IO/pydefix/definitions.hpp | 14 + test/IO/pydefix/pydefix_example.py | 15 + test/IO/pydefix/testme.py | 14 + test/IO/xdmf/CMakeLists.txt | 14 + test/IO/xdmf/definitions.hpp | 14 + test/IO/xdmf/setup.cpp | 14 + test/IO/xdmf/testme.py | 14 + test/MHD/AmbipolarCshock/CMakeLists.txt | 14 + test/MHD/AmbipolarCshock/definitions.hpp | 14 + test/MHD/AmbipolarCshock/python/testidefix.py | 14 + test/MHD/AmbipolarCshock/setup.cpp | 14 + test/MHD/AmbipolarCshock/testme.py | 14 + test/MHD/AmbipolarCshock3D/CMakeLists.txt | 14 + test/MHD/AmbipolarCshock3D/definitions.hpp | 14 + .../AmbipolarCshock3D/python/testidefix.py | 14 + test/MHD/AmbipolarCshock3D/setup.cpp | 14 + test/MHD/AmbipolarCshock3D/testme.py | 14 + test/MHD/AmbipolarShearingBox/CMakeLists.txt | 14 + test/MHD/AmbipolarShearingBox/definitions.hpp | 14 + .../AmbipolarShearingBox/python/testidefix.py | 15 + test/MHD/AmbipolarShearingBox/setup.cpp | 15 + test/MHD/AmbipolarWind/CMakeLists.txt | 14 + test/MHD/AmbipolarWind/definitions.hpp | 14 + test/MHD/AmbipolarWind/setup.cpp | 14 + test/MHD/AxisFluxTube/CMakeLists.txt | 14 + test/MHD/AxisFluxTube/definitions.hpp | 14 + .../AxisFluxTube/python/checkAxisBounds.py | 14 + test/MHD/AxisFluxTube/setup.cpp | 14 + test/MHD/AxisFluxTube/testme.py | 14 + test/MHD/Coarsening/CMakeLists.txt | 15 + test/MHD/Coarsening/definitions.hpp | 15 + test/MHD/Coarsening/python/testidefix.py | 16 + test/MHD/Coarsening/setup.cpp | 15 + test/MHD/Coarsening/testme.py | 15 + test/MHD/FargoMHDSpherical/CMakeLists.txt | 14 + test/MHD/FargoMHDSpherical/definitions.hpp | 14 + test/MHD/FargoMHDSpherical/setup.cpp | 14 + test/MHD/FargoMHDSpherical/testme.py | 14 + test/MHD/FieldLoop/CMakeLists.txt | 14 + test/MHD/FieldLoop/definitions.hpp | 14 + test/MHD/FieldLoop/setup.cpp | 14 + test/MHD/HallDisk/CMakeLists.txt | 14 + test/MHD/HallDisk/definitions.hpp | 14 + test/MHD/HallDisk/setup.cpp | 15 + test/MHD/HallWhistler/CMakeLists.txt | 14 + test/MHD/HallWhistler/definitions.hpp | 14 + test/MHD/HallWhistler/python/testidefix.py | 14 + test/MHD/HallWhistler/setup.cpp | 14 + test/MHD/HallWhistler/testme.py | 14 + test/MHD/LinearWaveTest/CMakeLists.txt | 14 + test/MHD/LinearWaveTest/definitions.hpp | 14 + test/MHD/LinearWaveTest/python/testidefix.py | 14 + test/MHD/LinearWaveTest/setup.cpp | 14 + test/MHD/LinearWaveTest/testme.py | 14 + test/MHD/MTI/CMakeLists.txt | 14 + test/MHD/MTI/analysis.cpp | 14 + test/MHD/MTI/analysis.hpp | 14 + test/MHD/MTI/definitions.hpp | 14 + test/MHD/MTI/python/testidefix.py | 15 + test/MHD/MTI/setup.cpp | 15 + test/MHD/MTI/testme.py | 14 + test/MHD/OrszagTang/CMakeLists.txt | 14 + test/MHD/OrszagTang/definitions.hpp | 14 + test/MHD/OrszagTang/setup.cpp | 14 + test/MHD/OrszagTang/testme.py | 14 + test/MHD/OrszagTang3D/CMakeLists.txt | 14 + test/MHD/OrszagTang3D/definitions.hpp | 14 + test/MHD/OrszagTang3D/setup.cpp | 14 + test/MHD/OrszagTang3D/testme.py | 14 + test/MHD/ResistiveAlfvenWave/CMakeLists.txt | 14 + test/MHD/ResistiveAlfvenWave/definitions.hpp | 14 + .../ResistiveAlfvenWave/python/testidefix.py | 15 + test/MHD/ResistiveAlfvenWave/setup.cpp | 15 + test/MHD/ResistiveAlfvenWave/testme.py | 14 + test/MHD/RotorCartesian/CMakeLists.txt | 14 + test/MHD/RotorCartesian/definitions.hpp | 14 + test/MHD/RotorCartesian/setup.cpp | 14 + test/MHD/RotorPolar/CMakeLists.txt | 14 + test/MHD/RotorPolar/definitions.hpp | 14 + test/MHD/RotorPolar/setup.cpp | 14 + test/MHD/ShearingBox/CMakeLists.txt | 14 + test/MHD/ShearingBox/analysis.cpp | 14 + test/MHD/ShearingBox/analysis.hpp | 14 + test/MHD/ShearingBox/definitions.hpp | 14 + test/MHD/ShearingBox/python/testidefix.py | 14 + test/MHD/ShearingBox/setup.cpp | 14 + test/MHD/ShearingBox/testme.py | 14 + test/MHD/advectionOBlique/CMakeLists.txt | 14 + test/MHD/advectionOBlique/definitions.hpp | 14 + test/MHD/advectionOBlique/setup.cpp | 14 + test/MHD/clessTDiffusion/CMakeLists.txt | 14 + test/MHD/clessTDiffusion/definitions.hpp | 14 + test/MHD/clessTDiffusion/python/testidefix.py | 15 + test/MHD/clessTDiffusion/setup.cpp | 15 + test/MHD/clessTDiffusion/testme.py | 14 + test/MHD/disk/CMakeLists.txt | 14 + test/MHD/disk/definitions.hpp | 14 + test/MHD/disk/setup.cpp | 15 + test/MHD/diskSpherical/CMakeLists.txt | 14 + test/MHD/diskSpherical/definitions.hpp | 14 + test/MHD/diskSpherical/setup.cpp | 15 + test/MHD/sod-iso/CMakeLists.txt | 14 + test/MHD/sod-iso/definitions.hpp | 14 + test/MHD/sod-iso/setup.cpp | 15 + test/MHD/sod-iso/testme.py | 14 + test/MHD/sod/CMakeLists.txt | 14 + test/MHD/sod/definitions.hpp | 14 + test/MHD/sod/setup.cpp | 15 + test/MHD/sod/testme.py | 14 + test/MHD/sphBragTDiffusion/CMakeLists.txt | 14 + test/MHD/sphBragTDiffusion/definitions.hpp | 14 + .../sphBragTDiffusion/python/testidefix.py | 14 + test/MHD/sphBragTDiffusion/setup.cpp | 14 + test/MHD/sphBragTDiffusion/testme.py | 14 + test/MHD/sphBragViscosity/CMakeLists.txt | 14 + test/MHD/sphBragViscosity/definitions.hpp | 14 + .../sphBragViscosity/noDivBragViscosity.cpp | 9 +- .../MHD/sphBragViscosity/python/testidefix.py | 15 + test/MHD/sphBragViscosity/setup.cpp | 14 + test/MHD/sphBragViscosity/testme.py | 14 + test/Planet/Planet3Body/definitions.hpp | 14 + test/Planet/Planet3Body/python/testidefix.py | 14 + test/Planet/Planet3Body/setup.cpp | 14 + test/Planet/Planet3Body/testme.py | 14 + test/Planet/PlanetMigration2D/definitions.hpp | 14 + .../PlanetMigration2D/python/testidefix.py | 14 + test/Planet/PlanetMigration2D/setup.cpp | 14 + test/Planet/PlanetMigration2D/testme.py | 14 + test/Planet/PlanetPlanetRK42D/definitions.hpp | 14 + .../PlanetPlanetRK42D/python/testidefix.py | 14 + test/Planet/PlanetPlanetRK42D/setup.cpp | 14 + test/Planet/PlanetPlanetRK42D/testme.py | 14 + test/Planet/PlanetSpiral2D/definitions.hpp | 13 + .../PlanetSpiral2D/python/testidefix.py | 14 + test/Planet/PlanetSpiral2D/setup.cpp | 14 + test/Planet/PlanetSpiral2D/testme.py | 14 + test/Planet/PlanetTorque3D/definitions.hpp | 14 + .../PlanetTorque3D/python/testidefix.py | 14 + test/Planet/PlanetTorque3D/setup.cpp | 14 + test/Planet/PlanetTorque3D/testme.py | 14 + .../PlanetsIsActiveRK52D/definitions.hpp | 14 + .../PlanetsIsActiveRK52D/python/testidefix.py | 14 + test/Planet/PlanetsIsActiveRK52D/setup.cpp | 14 + test/Planet/PlanetsIsActiveRK52D/testme.py | 14 + test/Pluto/HD/FargoPlanet/definitions.h | 14 + test/Pluto/HD/FargoPlanet/eos.c | 14 + test/Pluto/HD/FargoPlanet/init.c | 14 + test/Pluto/HD/MachReflection/definitions.h | 14 + test/Pluto/HD/MachReflection/init.c | 15 + test/Pluto/HD/PlanetDisk/definitions.h | 14 + test/Pluto/HD/PlanetDisk/eos.c | 14 + test/Pluto/HD/PlanetDisk/init.c | 14 + test/Pluto/HD/PlanetDisk3D/definitions.h | 14 + test/Pluto/HD/PlanetDisk3D/eos.c | 14 + test/Pluto/HD/PlanetDisk3D/init.c | 14 + .../HD/ViscousFlowPastCylinder/definitions.h | 14 + test/Pluto/HD/ViscousFlowPastCylinder/init.c | 14 + .../ViscousFlowPastCylinder/userdef_output.c | 14 + .../HD/ViscousFlowPastCylinder/visc_nu.c | 14 + test/Pluto/HD/sod/definitions.h | 14 + test/Pluto/HD/sod/init.c | 14 + test/Pluto/HD/sod/python/idefixTools.py | 15 + test/Pluto/HD/sod/python/sod.py | 15 + test/Pluto/HD/sod/python/testidefix.py | 15 + test/Pluto/MHD/OrszagTang/definitions.h | 14 + test/Pluto/MHD/OrszagTang/init.c | 14 + test/Pluto/MHD/sod-iso/definitions.h | 14 + test/Pluto/MHD/sod-iso/init.c | 15 + test/Pluto/MHD/sod/definitions.h | 14 + test/Pluto/MHD/sod/init.c | 15 + .../SelfGravity/DustyCollapse/definitions.hpp | 14 + .../DustyCollapse/python/testidefix.py | 15 + test/SelfGravity/DustyCollapse/setup.cpp | 14 + test/SelfGravity/DustyCollapse/testme.py | 14 + .../JeansInstability/definitions.hpp | 14 + .../JeansInstability/python/testidefix.py | 14 + test/SelfGravity/JeansInstability/setup.cpp | 14 + test/SelfGravity/JeansInstability/testme.py | 14 + test/SelfGravity/RandomSphere/definitions.hpp | 14 + .../RandomSphere/python/testidefix.py | 14 + test/SelfGravity/RandomSphere/setup.cpp | 14 + test/SelfGravity/RandomSphere/testme.py | 14 + .../RandomSphereCartesian/definitions.hpp | 14 + .../python/testidefix.py | 14 + .../RandomSphereCartesian/setup.cpp | 14 + .../RandomSphereCartesian/testme.py | 14 + .../UniformCollapse/CMakeLists.txt | 14 + .../UniformCollapse/definitions.hpp | 14 + .../UniformCollapse/python/testidefix.py | 14 + test/SelfGravity/UniformCollapse/setup.cpp | 15 + test/SelfGravity/UniformCollapse/testme.py | 14 + test/checks_examples.sh | 13 + test/skeleton/CMakeLists.txt | 14 + test/skeleton/definitions.hpp | 14 + test/skeleton/main.cpp | 14 + test/utils/columnDensity/definitions.hpp | 14 + test/utils/columnDensity/setup.cpp | 14 + test/utils/columnDensity/testme.py | 14 + test/utils/dumpImage/CMakeLists.txt | 14 + test/utils/dumpImage/definitions.hpp | 14 + test/utils/dumpImage/setup.cpp | 15 + test/utils/dumpImage/testme.py | 15 + test/utils/lookupTable/CMakeLists.txt | 14 + test/utils/lookupTable/definitions.hpp | 14 + test/utils/lookupTable/main.cpp | 15 + test/utils/lookupTable/testme.py | 15 + test/utils/lookupTable/testmelib.py | 15 + 467 files changed, 6711 insertions(+), 172 deletions(-) create mode 100644 pytools/update_file_headers.json create mode 100755 pytools/update_file_headers.py diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 632f9abb9..85672b3c4 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -40,18 +40,6 @@ repos: hooks: - id: inifix-format - - repo: https://github.com/Lucas-C/pre-commit-hooks - rev: v1.5.5 - hooks: - - id: remove-tabs # auto-fix tab/space mixing - - id: insert-license - files: ^(src/).*\.(hpp|cpp)$ - args: - - --license-filepath - - src/license_header.txt - - --comment-style - - // - - repo: https://gitlab.com/daverona/pre-commit/cpp rev: 0.8.0 hooks: diff --git a/CMakeLists.txt b/CMakeLists.txt index 02cede629..a54905501 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,3 +1,21 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file CMakeLists.txt +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2026) +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# - Alankar Dutta (MPA Garching - 2023 - 2026) +# - Nicolas Aunai (LPP - 2024) +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + cmake_minimum_required(VERSION 3.16) if (NOT CMAKE_BUILD_TYPE) set(CMAKE_BUILD_TYPE "Release" CACHE STRING "" FORCE) diff --git a/cmake/AddIdefixSource.cmake b/cmake/AddIdefixSource.cmake index 8991e4907..328ddcb0c 100644 --- a/cmake/AddIdefixSource.cmake +++ b/cmake/AddIdefixSource.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/AddIdefixSource.cmake +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + function(add_idefix_source _new_source) message(STATUS " Adding problem-specific source file ${_new_source}") target_sources(idefix PUBLIC ${_new_source}) diff --git a/cmake/CheckHdf5ParallelSupport.cmake b/cmake/CheckHdf5ParallelSupport.cmake index aae651a17..262d086cd 100644 --- a/cmake/CheckHdf5ParallelSupport.cmake +++ b/cmake/CheckHdf5ParallelSupport.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/CheckHdf5ParallelSupport.cmake +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Alankar Dutta (MPA Garching - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + include(CheckCSourceCompiles) # Check whether the HDF5 library found by find_package(HDF5) supports parallel diff --git a/cmake/GetGitRevisionDescription.cmake b/cmake/GetGitRevisionDescription.cmake index 81b5844be..0999f53bc 100644 --- a/cmake/GetGitRevisionDescription.cmake +++ b/cmake/GetGitRevisionDescription.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/GetGitRevisionDescription.cmake +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # - Returns a version string from Git # # These functions force a re-configure on each git commit so that you can diff --git a/cmake/GetGitRevisionDescription.cmake.in b/cmake/GetGitRevisionDescription.cmake.in index 66eee6377..1eee216c8 100644 --- a/cmake/GetGitRevisionDescription.cmake.in +++ b/cmake/GetGitRevisionDescription.cmake.in @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/GetGitRevisionDescription.cmake.in +# +# Last modified : 08/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # # Internal file for GetGitRevisionDescription.cmake # diff --git a/cmake/ReplaceIdefixSource.cmake b/cmake/ReplaceIdefixSource.cmake index 80000b0b3..d48f4cbab 100644 --- a/cmake/ReplaceIdefixSource.cmake +++ b/cmake/ReplaceIdefixSource.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/ReplaceIdefixSource.cmake +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + function(replace_idefix_source _old_source _new_source) get_target_property(fullsource idefix SOURCES) list(FILTER fullsource INCLUDE REGEX ${_old_source}) diff --git a/cmake/SetIdefixProperty.cmake b/cmake/SetIdefixProperty.cmake index 22c77c10c..dc32c5605 100644 --- a/cmake/SetIdefixProperty.cmake +++ b/cmake/SetIdefixProperty.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/SetIdefixProperty.cmake +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + function(set_idefix_property _property_name _property_value) message(STATUS " Explicitely setting ${_property_name} = ${_property_value}") set(${_property_name} ${_property_value} CACHE STRING "Overridden by custom setup in CMakeLists.txt" FORCE) diff --git a/cmake/SetRequiredBuildSettingsForGCC8.cmake b/cmake/SetRequiredBuildSettingsForGCC8.cmake index bb389298a..852fc0a4c 100644 --- a/cmake/SetRequiredBuildSettingsForGCC8.cmake +++ b/cmake/SetRequiredBuildSettingsForGCC8.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/SetRequiredBuildSettingsForGCC8.cmake +# +# Last modified : 11/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # The std::filesystem functions are part of the C++17 standard, but GCC8 # does not store them in libstdc++ but in libstdc++-fs. This function # ensure that we link to this additional library when using GCC8 diff --git a/cmake/SuppressFMA.cmake b/cmake/SuppressFMA.cmake index 18dc10d46..e22399703 100644 --- a/cmake/SuppressFMA.cmake +++ b/cmake/SuppressFMA.cmake @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file cmake/SuppressFMA.cmake +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + #[[============================================================================ SuppressFMA.cmake diff --git a/doc/Makefile b/doc/Makefile index d0c3cbf10..ac6f669e8 100644 --- a/doc/Makefile +++ b/doc/Makefile @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file doc/Makefile +# +# Last modified : 09/2020 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # Minimal makefile for Sphinx documentation # diff --git a/doc/source/_static/my_theme.css b/doc/source/_static/my_theme.css index 827056226..961556641 100644 --- a/doc/source/_static/my_theme.css +++ b/doc/source/_static/my_theme.css @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file doc/source/_static/my_theme.css +// +// Last modified : 04/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + .wy-nav-content { max-width: 1024px !important; } diff --git a/doc/source/conf.py b/doc/source/conf.py index 1c772f493..b6806b800 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file doc/source/conf.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # Configuration file for the Sphinx documentation builder. # # This file only contains a selection of the most common options. For a full diff --git a/doc/source/plot_idefix_bench.py b/doc/source/plot_idefix_bench.py index 7810751ef..1d8896523 100644 --- a/doc/source/plot_idefix_bench.py +++ b/doc/source/plot_idefix_bench.py @@ -1,3 +1,19 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file doc/source/plot_idefix_bench.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Marc Coiffier (IPAG/UGA/CNRS - 2025) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import json import matplotlib.pyplot as plt diff --git a/make_tarballs.py b/make_tarballs.py index df57b94bc..79c64f35c 100644 --- a/make_tarballs.py +++ b/make_tarballs.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file make_tarballs.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import argparse import os import subprocess diff --git a/pytools/dump_io.py b/pytools/dump_io.py index 6c8338428..a084a1f93 100644 --- a/pytools/dump_io.py +++ b/pytools/dump_io.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/dump_io.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2022 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Fri Nov 27 22:07:47 2020 diff --git a/pytools/idfx_io.py b/pytools/idfx_io.py index e530117a6..95f49b9a0 100644 --- a/pytools/idfx_io.py +++ b/pytools/idfx_io.py @@ -1,3 +1,19 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/idfx_io.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2022 - 2026) +# - Marc Van den Bossche (IAP Postdam - 2024) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import struct import numpy as np diff --git a/pytools/idfx_test.py b/pytools/idfx_test.py index 99f052884..cf16deae1 100644 --- a/pytools/idfx_test.py +++ b/pytools/idfx_test.py @@ -1,3 +1,19 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/idfx_test.py +# +# Last modified : 09/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import argparse import json import os diff --git a/pytools/idfx_test_gen.py b/pytools/idfx_test_gen.py index eaee82917..324c85028 100644 --- a/pytools/idfx_test_gen.py +++ b/pytools/idfx_test_gen.py @@ -1,9 +1,17 @@ -##################################################################################### +###################################################################################### # Idefix MHD astrophysical code -# Copyright(C) Sébastien Valat +# +# Source file pytools/idfx_test_gen.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) # and other code contributors +# # Licensed under CeCILL 2.1 License, see COPYING for more information -##################################################################################### +###################################################################################### import copy diff --git a/pytools/idfx_test_run.py b/pytools/idfx_test_run.py index f968745f9..f4cd4caa8 100644 --- a/pytools/idfx_test_run.py +++ b/pytools/idfx_test_run.py @@ -1,9 +1,17 @@ -##################################################################################### +###################################################################################### # Idefix MHD astrophysical code -# Copyright(C) Sébastien Valat +# +# Source file pytools/idfx_test_run.py +# +# Last modified : 09/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) # and other code contributors +# # Licensed under CeCILL 2.1 License, see COPYING for more information -##################################################################################### +###################################################################################### import copy import glob diff --git a/pytools/sod.py b/pytools/sod.py index 3639825f9..084317a45 100644 --- a/pytools/sod.py +++ b/pytools/sod.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/sod.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + """ Created on Thu Mar 5 11:27:16 2020 diff --git a/pytools/tests/test_idfx_test_gen.py b/pytools/tests/test_idfx_test_gen.py index 11a9603a1..ffa68494a 100644 --- a/pytools/tests/test_idfx_test_gen.py +++ b/pytools/tests/test_idfx_test_gen.py @@ -1,9 +1,17 @@ -##################################################################################### +###################################################################################### # Idefix MHD astrophysical code -# Copyright(C) Sébastien Valat +# +# Source file pytools/tests/test_idfx_test_gen.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) # and other code contributors +# # Licensed under CeCILL 2.1 License, see COPYING for more information -##################################################################################### +###################################################################################### import pytest diff --git a/pytools/tests/test_idfx_test_run.py b/pytools/tests/test_idfx_test_run.py index dfe32ac56..da9702e9e 100644 --- a/pytools/tests/test_idfx_test_run.py +++ b/pytools/tests/test_idfx_test_run.py @@ -1,9 +1,17 @@ -##################################################################################### +###################################################################################### # Idefix MHD astrophysical code -# Copyright(C) Sébastien Valat +# +# Source file pytools/tests/test_idfx_test_run.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) # and other code contributors +# # Licensed under CeCILL 2.1 License, see COPYING for more information -##################################################################################### +###################################################################################### import os diff --git a/pytools/update_file_headers.json b/pytools/update_file_headers.json new file mode 100644 index 000000000..dfe74083e --- /dev/null +++ b/pytools/update_file_headers.json @@ -0,0 +1,202 @@ +{ + "header_keys": { + "PROJECT": "Idefix MHD astrophysical code", + "DATE": "@LAST_EDIT_MONTH_YEAR@", + "LICENSE": "CeCILL-C" + }, + "message": [ + "@PROJECT@", + "", + "Source file @FILE@", + "", + "Last modified : @DATE@", + "", + "Copyright(C) by :", + "@COPYRIGHTS@", + "and other code contributors", + "", + "Licensed under CeCILL 2.1 License, see COPYING for more information" + ], + "width": 86, + "specific": { + }, + "extra_authors": [ + { + "name": "Gaylor Wafflard", + "mail": "gaylor.wafflard@univ-grenoble-alpes.fr", + "commits": [ + "158f2aa3a35148bb2a992ae24bb8f813a5965034", + "18c2b7301334a291b1acfcbed431b71607cb433d", + "1087e858d72fc99f1e37aa2276bfdb79b3007ac4", + "8d13e69a6193db9fd4cdb7ef292033790c54f457", + "d00a8eb17198dfa2b9bd924f1245f7fb00844b22" + ] + } + ], + "authors_name_fixes": { + "pre-commit-ci-lite[bot]": null, + "Geoffroy Lesur geoffroy.lesur@univ-grenoble-alpes.fr": "Geoffroy Lesur", + "nscepi": "Nicolas Scepi", + "Soufiane BAGHDADI": "Soufiane Baghdadi", + "vdbma": "Marc Van den Bossche", + "marc": "Marc Van den Bossche", + "Hal Bal": "Victor Réville" + }, + "replace_mails": { + "sebastien.valat.dev@orange.fr": "sebastien.valat@univ-grenoble-alpes.fr", + "63753204+nscepi@users.noreply.github.com": "nicolas.scepi@univ-grenoble-alpes.fr", + "nicolas.scepi@gmail.com": "nicolas.scepi@univ-grenoble-alpes.fr", + "geoffroy.lesur@obs.ujf-grenoble.fr": "geoffroy.lesur@univ-grenoble-alpes.fr", + "93188557+vdbma@users.noreply.github.com": "mbossche@aip.de", + "vandenbossche.marc@hotmail.com": "mbossche@aip.de", + "victorreville@gmail.com": "vreville@irap.omp.eu", + "cr52@protonmail.com": "clement.robert@univ-grenoble-alpes.fr", + "89980449+Anto6453@users.noreply.github.com": "antonin.borderies@ens-lyon.fr", + "lesur@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "lesurg@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "gelesur@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "glesur@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "glesurg@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "geoffroy@": "geoffroy.lesur@univ-grenoble-alpes.fr", + "cmt.robert@univ-grenoble-alpes.fr": "clement.robert@univ-grenoble-alpes.fr", + "soufiane.baghdadi@meryntech.com": "soufiane.baghdadi@univ-grenoble-alpes.fr" + }, + "affiliation_domains": { + "@irap.omp.eu": "IRAP", + "@univ-grenoble-alpes.fr": "IPAG/UGA/CNRS", + "dutta.alankar@gmail.com": "MPA Garching", + "@aip.de": "IAP Postdam", + "@ens-lyon.fr": "ENS Lyon", + "@lpp.polytechnique.fr": "LPP" + }, + "allow_no_affiliation": false, + "exclude_hashes": [ + ], + "exclude_summary_regexps": [ + "^copyrights:" + ], + "lang": { + "shell": { + "max_line_length": 100, + "open_start": "##", + "open_end": "", + "repeat": "#", + "info_open": "# ", + "close_start": "##", + "close_end": "", + "apply_on": [ + "*.py", + "*.sh", + "*.cmake", + "*.cmake.in", + "*.spec", + "*.ebuild", + "*.sh.in", + "Dockerfile-*", + "CMakeLists.txt", + "options", + "configure", + "PKGBUILD", + "Makefile", + "makefile", + "makefile.rules", + "*.yml", + "*.toml", + "run-tests" + ] + }, + "c": { + "max_line_length": 100, + "open_start": "// ", + "open_end": "", + "repeat": "*", + "info_open": "// ", + "close_start": "// ", + "close_end": "", + "apply_on": [ + "*.c", + "*.cpp", + "*.cxx", + "*.h", + "*.hpp", + "*.hxx", + "*.h.in", + "*.js", + "*.css", + "*.rs", + "*.ts", + "*.scss" + ] + }, + "html": { + "max_line_length": 100, + "open_start": "", + "apply_on": [ + "*.html", + "*.vue" + ] + }, + "fortran": { + "max_line_length": 100, + "open_start": "!", + "open_end": "", + "repeat": "-", + "info_open": "! ", + "close_start": "!", + "close_end": "!", + "apply_on": [ + "*.f90", + "*.f", + "*.F90", + "*.F" + ] + } + }, + "exclude_files": [ + ".version", + "*.yml", + "*.yaml", + "*.gitignore", + ".gitignore", + "*.json", + "*.md", + "Doxyfile", + "*.txt", + "*.xmi", + "*.ini", + "*.bat", + "*.ico", + "*.ttf", + "*.bz2", + "*.ronn", + "*.bowerrc", + "*.png", + "*.webp", + "*.jpg", + "*.jpeg", + "*.jpeg", + "*.rst", + "*.svg", + "*.vtk", + "COPYING", + "CPPLINT.cfg", + ".gitmodules", + ".git-blame-ignore-revs", + "reference", + "src/kokkos", + "*/README", + "*.dmp", + "*.dat", + "*.csv", + "*.npy" + ], + "include_files": [ + "**/CMakeLists.txt", + "CMakeLists.txt" + ] +} diff --git a/pytools/update_file_headers.py b/pytools/update_file_headers.py new file mode 100755 index 000000000..55c61a77f --- /dev/null +++ b/pytools/update_file_headers.py @@ -0,0 +1,666 @@ +#!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/update_file_headers.py +# +# Last modified : 09/2026 +# +# Copyright(C) by : +# - Sebastien Valat (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + +############################################################ +# +# Imported and modified by Sébastien Valat (IPAG/CNRS) +# from MALT (Sébastien Valat) repository. +# +# Original licence is same than this project so it can be reused +# without problems. +# +# - https://github.com/memtt/malt/blob/v1.6.3/dev/update_file_headers.py +# - https://github.com/memtt/malt/blob/v1.6.3/dev/update_file_headers.json +# +############################################################ +# PROJECT : MALT (MALoc Tracker) +# DATE : 09/2025 +# LICENSE : CeCILL-C +# FILE : dev/update_file_headers.py +# ----------------------------------------------------------- +# AUTHOR : Sébastien Valat - 2024 +# AUTHOR : Sébastien Valat (INRIA) - 2025 +############################################################ + +# Usage : +# -------------------------------------------------------------------------------------------------- +# python3 -m venv venv +# source venv/bin/activate +# pip install gitpython +# ./dev/update_file_headers.py --git-all . +# -------------------------------------------------------------------------------------------------- + +############################################################ +# python +import argparse +import datetime +import fnmatch +import itertools +import json +import os +import pathlib +import re +import subprocess +import warnings + +# git +from git import Repo + + +############################################################ +class HeaderPatcher: + def __init__(self, config_file: str) -> None: + # vars + self.config_file = config_file + self.config = {} + + # load + self.load_config(config_file) + + def load_config(self, config_file: str) -> None: + with open(config_file, "r") as fp: + config = json.load(fp) + for id, entry in enumerate(config["exclude_summary_regexps"]): + config["exclude_summary_regexps"][id] = re.compile(entry) + self.config = config + + def get_manual_co_authors(self, commit_hash: str) -> list[dict]: + # get the manual infos + manual_authors: list[dict] = self.config.get("extra_authors", []) + + # build result list + result: list[dict] = [] + + # loop to scan + for author in manual_authors: + for commit in author["commits"]: + if commit == commit_hash: + result.append({"name": author["name"], "mail": author["mail"]}) + + # ok + return result + + def git_load_blame_log(self, file: str) -> list[dict]: + # open git repo + repo = Repo(pathlib.Path(".")) + assert not repo.bare + + # blame + blame = repo.git.blame("HEAD", file, "--porcelain").split("\n") + + # create log + log = [] + + # set default vars to track + commit_hash = "" + commiter_mail = "INIT" + commiter_name = "INIT" + commiter_time = "INIT" + commiter_zone = "INIT" + summary = "INIT" + + # loop on all entries to extract the infos + for entry in blame: + parts = entry.split(" ", maxsplit=1) + key = parts[0] + if len(key) == 40: + commit_hash = key + if key == "summary": + summary = parts[1] + elif key == "author-mail": + commiter_mail = parts[1] + if key == "author": + commiter_name = parts[1] + elif key == "author-time": + commiter_time = parts[1] + elif key == "filename": + commiter_zone = parts[1] + log.append( + { + "mail": commiter_mail, + "name": commiter_name, + "time": commiter_time, + "zone": commiter_zone, + "hash": commit_hash, + "summary": summary, + } + ) + + # search for co-authors to add to commit authors + co_authors = self.get_manual_co_authors(commit_hash) + for co_author in co_authors: + log.append( + { + "mail": "<" + co_author["mail"] + ">", + "name": co_author["name"], + "time": commiter_time, + "zone": commiter_zone, + "hash": commit_hash, + "summary": summary, + } + ) + + # reset vars for next scan + commit_hash = "" + commiter_mail = "INIT" + commiter_name = "INIT" + commiter_time = "INIT" + commiter_zone = "INIT" + summary = "INIT" + else: + # just ignore the other fields + pass + + # ok + return log + + def get_mail_affiliation(self, mail: str) -> str | None: + if mail == "": + return None + domain = "@" + mail.split("@")[1] + username = mail.split("@")[0] + "@" + affiliation_domains = self.config["affiliation_domains"] + if mail in affiliation_domains: + return affiliation_domains[mail] + elif domain in affiliation_domains: + return affiliation_domains[domain] + elif username in affiliation_domains: + return affiliation_domains[username] + else: + return None + + def replace_mail_by_pro_mail(self, mail: str, year: int) -> str: + # get the db entry in config + db: str | list[str] = self.config["replace_mails"] + username = mail.split("@")[0] + "@" + + # check if in + entry = None + if mail in db: + entry = db[mail] + elif username in db: + entry = db[username] + + # if need to replace + if entry is not None: + # direct definition or per year mode + if isinstance(entry, str): + return entry + elif isinstance(entry, list): + for epoc in entry: + started = epoc.get("from", 0) + ended = epoc.get("to", 9999) + if year >= started and year <= ended: + return epoc["mail"] + else: + raise Exception( + f"Invalid format for the field 'replace_mails' : {db[mail]}" + ) + + # ok keep as it is + return mail + + def fix_name(self, name: str) -> str: + authors_name_fixes = self.config["authors_name_fixes"] + if name in authors_name_fixes: + return authors_name_fixes[name] + else: + return name + + def need_skip_blame_entry(self, blame_entry: dict) -> bool: + exclude_hashes = self.config["exclude_hashes"] + + # skip some based on hash + if blame_entry["hash"] in exclude_hashes: + return True + + # skip based on summary (not to get commit which push file headers update) + for regexp in self.config["exclude_summary_regexps"]: + if regexp.match(blame_entry["summary"]): + return True + + # not found, so keep it + return False + + def git_extract_authors_from_history(self, blame_log: list) -> dict: + # build final storage + authors = {} + + # loop on all entries + for entry in itertools.filterfalse(self.need_skip_blame_entry, blame_log): + # extract name & skip if none + name = self.fix_name(entry["name"]) + if name is None: + continue + + # extract date infos + date = datetime.datetime.fromtimestamp(int(entry["time"])) + year = date.year + month = date.month + + # extract author infos + mail = entry["mail"][1:-1].strip() + mail = self.replace_mail_by_pro_mail(mail, year) + author = entry["mail"] + affiliation = self.get_mail_affiliation(mail) + full_name = f"{name} <{mail}>" + + # if no afficiation, warn + if affiliation is None: + if self.config.get("allow_no_affiliation", True): + warnings.warn(f"No affilication found for {entry}", stacklevel=1) + else: + raise Exception(f"No affilication found for {entry}") + + # inject it + if full_name not in authors: + authors[full_name] = { + "name": name, + "full-name": full_name, + "author": author, + "year-start": year, + "year-end": year, + "last-month": month, + "date-start": date, + "mail": mail, + "affiliation": affiliation, + } + + # set entry + auth_entry = authors[full_name] + auth_entry["year-start"] = min(auth_entry["year-start"], year) + auth_entry["year-end"] = max(auth_entry["year-end"], year) + auth_entry["date-start"] = min(auth_entry["date-start"], date) + + # ok + return authors + + def get_last_edit_month_year(self, blame_log: list[str]) -> str: + # vars + last_month = 0 + last_year = 0 + + # loop on all entries + for entry in blame_log: + # apply skip + if self.need_skip_blame_entry(entry): + continue + + date = datetime.datetime.fromtimestamp(int(entry["time"])) + year = date.year + month = date.month + if year > last_year: + last_year = year + last_month = month + elif year == last_year and month > last_month: + last_month = month + + # ok + return f"{last_month:02d}/{last_year:04d}" + + def build_infos(self, filename: str) -> dict: + # build default + infos = { + "header": self.config["header_keys"].copy(), + "origin": None, + "width": self.config["width"], + } + + # set file + infos["header"]["FILE"] = filename + + # apply specific for some files + if filename in self.config["specific"]: + specific = self.config["specific"][filename] + # has external origin + if "origin" in specific: + infos["origin"] = specific["origin"] + # override value (license....) + if "override" in specific: + for key, value in specific["override"].items(): + infos["header"][key] = value + if "width" in specific: + infos["width"] = specific["width"] + + # ok + return infos + + def build_new_file_header( + self, authors_list: list[dict], last_edit: str, infos: dict, lang: dict + ) -> list: + if "message" in self.config: + return self.build_new_file_header_by_message( + authors_list, last_edit, infos, lang + ) + else: + return self.build_new_file_header_by_keys( + authors_list, last_edit, infos, lang + ) + + def build_new_file_header_by_keys( + self, authors_list: list[dict], last_edit: str, infos: dict, lang: dict + ) -> list: + # pattern + info_open = lang["info_open"] + open_start = lang["open_start"] + open_end = lang["open_end"] + close_start = lang["close_start"] + close_end = lang["close_end"] + width = infos["width"] + line_start = ( + open_start + + lang["repeat"] * (width - len(open_start) - len(open_end)) + + open_end + ) + line_end = ( + close_start + + lang["repeat"] * (width - len(close_start) - len(close_end)) + + close_end + ) + + # build new header + header_script = [] + width = infos["width"] + header_script.append(f"{line_start}\n") + for key, value in infos["header"].items(): + fixed_value = value.replace("@LAST_EDIT_MONTH_YEAR@", last_edit) + header_script.append(f"{info_open} {key: <8} : {fixed_value}\n") + header_script.append(f"{info_open}{'-' * (width - len(info_open))}\n") + + # add authors + for author in authors_list: + full_name = author["full-name"] + start = author["year-start"] + end = author["year-end"] + if start == end: + years = str(start) + else: + years = f"{start} - {end}" + header_script.append(f"{info_open} AUTHOR : {full_name} - {years}\n") + + # origin + if infos["origin"]: + header_script.append(info_open + " ORIGIN ".center(width - 1, "-") + "\n") + for key, value in infos["origin"].items(): + header_script.append(f"{info_open} {key: <8} : {value}\n") + + # close + header_script.append(f"{line_end}\n") + + # ok + return header_script + + def build_new_file_header_by_message( + self, authors_list: list[dict], last_edit: str, infos: dict, lang: dict + ) -> list: + # pattern + max_line_length = lang["max_line_length"] + info_open = lang["info_open"] + open_start = lang["open_start"] + open_end = lang["open_end"] + close_start = lang["close_start"] + close_end = lang["close_end"] + width = infos["width"] + line_start = ( + open_start + + lang["repeat"] * (width - len(open_start) - len(open_end)) + + open_end + ) + line_end = ( + close_start + + lang["repeat"] * (width - len(close_start) - len(close_end)) + + close_end + ) + + # build new header + header_script = [] + width = infos["width"] + + # add authors + authors = [] + for author in authors_list: + name = author["name"] + start = author["year-start"] + end = author["year-end"] + email = author["mail"] + affiliation = author["affiliation"] + if start == end: + years = str(start) + else: + years = f"{start} - {end}" + if affiliation: + descr = f"- {name} <{email}> ({affiliation} - {years})" + if len(descr) <= max_line_length: + authors.append(descr) + else: + authors.append(f"- {name} <{email}>") + authors.append(f" ({affiliation} - {years})") + else: + authors.append(f"- {name} <{email}> ({years})") + + # replace in message + msg_line: str + header_script.append(f"{line_start}\n") + for msg_line in self.config["message"]: + for key, value in infos["header"].items(): + fixed_value = value.replace("@LAST_EDIT_MONTH_YEAR@", last_edit) + msg_line = msg_line.replace(f"@{key}@", fixed_value) + if msg_line == "@COPYRIGHTS@": + for author in authors: + header_script.append(f"{info_open}{author}\n") + else: + if msg_line == "": + header_script.append(f"{info_open.strip()}\n") + else: + header_script.append(f"{info_open}{msg_line}\n") + + # close + header_script.append(f"{line_end}\n") + + # ok + return header_script + + def calc_lang(self, filename: str) -> dict: + # get it + lang = self.config["lang"] + fname = os.path.basename(filename) + + # apply filters + for name, params in lang.items(): + apply_on = params["apply_on"] + for selector in apply_on: + if fnmatch.fnmatch(fname, selector): + print(f" - {filename} : apply type {name}") + return params + + # not found + raise Exception(f"Invalid file type : {filename}") + + def patch_header_lines( + self, origin_content: list, new_header: list, width: int, lang: dict + ) -> list: + # build patched + patched_content = None + + # pattern + info_open = lang["info_open"] + open_start = lang["open_start"] + open_end = lang["open_end"] + close_start = lang["close_start"] + close_end = lang["close_end"] + line_start = ( + open_start + + lang["repeat"] * (width - len(open_start) - len(open_end)) + + open_end + ) + line_end = ( + close_start + + lang["repeat"] * (width - len(close_start) - len(close_end)) + + close_end + ) + + # loop on content to find the start of header + for line, value in enumerate(origin_content): + if value == f"{line_start}\n" and ( + f"{info_open} {self.config['message'][0]}" + ): + count = 1 + while origin_content[line + count] != f"{line_end}\n": + count += 1 + del origin_content[line : line + count + 1] + patched_content = ( + origin_content[0:line] + new_header + origin_content[line:] + ) + break + elif line > 10: + break + + # add on top if not present + if len(origin_content) == 0: + patched_content = origin_content + elif not patched_content and origin_content[0][0:2] == "#!": + patched_content = origin_content[0:1] + new_header + origin_content[1:] + elif not patched_content: + patched_content = new_header + origin_content + + # ok + return patched_content + + def order_authors_by_date(self, authors: dict) -> list[dict]: + per_year = {} + for _key, author in authors.items(): + year = author["date-start"] + if not year in per_year: + per_year[year] = [] + per_year[year].append(author) + + result = [] + for year in sorted(per_year.keys()): + auths = sorted(per_year[year], key=lambda author: author["full-name"]) + for author in auths: + result.append(author) + + return result + + def patch_header(self, file: str) -> None: + # extract log + blame_log = self.git_load_blame_log(file) + + # extract authors + authors = self.git_extract_authors_from_history(blame_log) + last_edit = self.get_last_edit_month_year(blame_log) + + # as list + authors_list = self.order_authors_by_date(authors) + + # build infos + infos = self.build_infos(file) + + # get lang + lang = self.calc_lang(file) + + # build header as list of lines + header_script = self.build_new_file_header(authors_list, last_edit, infos, lang) + + # load file + with open(file, "r") as fp: + original_content = fp.readlines() + + # patch + patched_content = self.patch_header_lines( + original_content, header_script, infos["width"], lang + ) + + # save again + with open(file, "w+") as fp: + fp.writelines(patched_content) + + def is_in_include_files(self, filename: str) -> bool: + # check if included + for ipattern in self.config["include_files"]: + if ( + fnmatch.fnmatch(filename, ipattern) + or filename.startswith(ipattern) + or filename == ipattern + ): + return True + return False + + def patch_file(self, filename: str) -> None: + # if exclude + for pattern in self.config["exclude_files"]: + if fnmatch.fnmatch(filename, pattern) or filename.startswith(pattern): + if not self.is_in_include_files(filename): + print(f" - {filename} : EXCLUDED") + return + + # apply + self.patch_header(filename) + + def patch_all_git_files(self, git_dir: str) -> None: + files = subprocess.getoutput("git ls-files").split("\n") + for file in files: + self.patch_file(file) + + +############################################################ +def run_from_args(args): + # load + patcher = HeaderPatcher(args.config) + + # patch + if args.git_all: + patcher.patch_all_git_files(args.FILE) + else: + patcher.patch_file(args.FILE) + + +############################################################ +def config_arg_parser(parser: argparse.ArgumentParser) -> None: + # calc default config path + default_config = os.path.join(os.path.dirname(__file__), "update_file_headers.json") + + # add options + parser.add_argument("FILE", help="File to patch or source dir when using --git-all") + parser.add_argument( + "--git-all", + "-g", + help="Run on all file from GIT. FILE in this case give the GIT dir.", + action="store_true", + ) + parser.add_argument( + "--config", "-c", help="Config file to use", default=default_config + ) + + +############################################################ +def main() -> None: + # define arguments + parser = argparse.ArgumentParser() + config_arg_parser(parser) + + # parse + options = parser.parse_args() + + # run + run_from_args(options) + + # ok + return 0 + + +############################################################ +if __name__ == "__main__": + raise SystemExit(main()) diff --git a/pytools/vtk_io.py b/pytools/vtk_io.py index 6d8041091..061d64c22 100644 --- a/pytools/vtk_io.py +++ b/pytools/vtk_io.py @@ -1,3 +1,19 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file pytools/vtk_io.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2022 - 2026) +# - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + """ Created on Mon Nov 3 15:23:00 2014 diff --git a/ruff.toml b/ruff.toml index 9b6b6c620..b79a1d23e 100644 --- a/ruff.toml +++ b/ruff.toml @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file ruff.toml +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target-version = "py310" [lint] diff --git a/scripts/ci/run-tests b/scripts/ci/run-tests index ebf895035..81764353a 100755 --- a/scripts/ci/run-tests +++ b/scripts/ci/run-tests @@ -1,4 +1,19 @@ #!/usr/bin/env bash +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file scripts/ci/run-tests +# +# Last modified : 06/2026 +# +# Copyright(C) by : +# - Marc Coiffier (IPAG/UGA/CNRS - 2024) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # load ICC compiler env if [ "$IDEFIX_COMPILER" == icc ]; then diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 08dd93c61..d0b714368 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/CMakeLists.txt +# +# Last modified : 04/2025 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### add_subdirectory(fluid) add_subdirectory(dataBlock) diff --git a/src/arrays.hpp b/src/arrays.hpp index 8a8eaea32..6d8989bda 100644 --- a/src/arrays.hpp +++ b/src/arrays.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/arrays.hpp +// +// Last modified : 06/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2022) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/compiler_info.h.in b/src/compiler_info.h.in index 140eafd79..b14e4c400 100644 --- a/src/compiler_info.h.in +++ b/src/compiler_info.h.in @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/compiler_info.h.in +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/CMakeLists.txt b/src/dataBlock/CMakeLists.txt index c3410f41b..3ddf4016d 100644 --- a/src/dataBlock/CMakeLists.txt +++ b/src/dataBlock/CMakeLists.txt @@ -1,3 +1,19 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/dataBlock/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + add_subdirectory(planetarySystem) target_sources(idefix diff --git a/src/dataBlock/coarsen.cpp b/src/dataBlock/coarsen.cpp index 4c6b60ccd..f4b75b9dc 100644 --- a/src/dataBlock/coarsen.cpp +++ b/src/dataBlock/coarsen.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/coarsen.cpp +// +// Last modified : 03/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/dataBlock.cpp b/src/dataBlock/dataBlock.cpp index 2877a8346..3440facac 100644 --- a/src/dataBlock/dataBlock.cpp +++ b/src/dataBlock/dataBlock.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/dataBlock.cpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2025) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/dataBlock.hpp b/src/dataBlock/dataBlock.hpp index 89b745fa5..6d322e7e5 100644 --- a/src/dataBlock/dataBlock.hpp +++ b/src/dataBlock/dataBlock.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/dataBlock.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/dataBlockHost.cpp b/src/dataBlock/dataBlockHost.cpp index c7811b391..0c3293b6a 100644 --- a/src/dataBlock/dataBlockHost.cpp +++ b/src/dataBlock/dataBlockHost.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/dataBlockHost.cpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2025) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/dataBlockHost.hpp b/src/dataBlock/dataBlockHost.hpp index f7dc4041f..0bf4ccd86 100644 --- a/src/dataBlock/dataBlockHost.hpp +++ b/src/dataBlock/dataBlockHost.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/dataBlockHost.hpp +// +// Last modified : 09/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/dumpToFile.cpp b/src/dataBlock/dumpToFile.cpp index 305b417a7..fdac2fb4f 100644 --- a/src/dataBlock/dumpToFile.cpp +++ b/src/dataBlock/dumpToFile.cpp @@ -1,7 +1,18 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/dumpToFile.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Marc Van den Bossche (IAP Postdam - 2024) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/evolveStage.cpp b/src/dataBlock/evolveStage.cpp index c97c9f713..c00c44fec 100644 --- a/src/dataBlock/evolveStage.cpp +++ b/src/dataBlock/evolveStage.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/evolveStage.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2025) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/fargo.cpp b/src/dataBlock/fargo.cpp index 7aa2d26a5..046a11d5f 100644 --- a/src/dataBlock/fargo.cpp +++ b/src/dataBlock/fargo.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/fargo.cpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/fargo.hpp b/src/dataBlock/fargo.hpp index a1efcb2b6..9347f716f 100644 --- a/src/dataBlock/fargo.hpp +++ b/src/dataBlock/fargo.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/fargo.hpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/makeGeometry.cpp b/src/dataBlock/makeGeometry.cpp index ddb9a2101..fc2b8624c 100644 --- a/src/dataBlock/makeGeometry.cpp +++ b/src/dataBlock/makeGeometry.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/makeGeometry.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/planetarySystem/CMakeLists.txt b/src/dataBlock/planetarySystem/CMakeLists.txt index 217cb7050..8be62f30a 100644 --- a/src/dataBlock/planetarySystem/CMakeLists.txt +++ b/src/dataBlock/planetarySystem/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/dataBlock/planetarySystem/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/planet.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/planet.hpp diff --git a/src/dataBlock/planetarySystem/planet.cpp b/src/dataBlock/planetarySystem/planet.cpp index ccbed14e6..a2808b2d2 100644 --- a/src/dataBlock/planetarySystem/planet.cpp +++ b/src/dataBlock/planetarySystem/planet.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/planetarySystem/planet.cpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/planetarySystem/planet.hpp b/src/dataBlock/planetarySystem/planet.hpp index 46b701889..2542adac2 100644 --- a/src/dataBlock/planetarySystem/planet.hpp +++ b/src/dataBlock/planetarySystem/planet.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/planetarySystem/planet.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/planetarySystem/planetStructs.hpp b/src/dataBlock/planetarySystem/planetStructs.hpp index 6440daf8f..156fea612 100644 --- a/src/dataBlock/planetarySystem/planetStructs.hpp +++ b/src/dataBlock/planetarySystem/planetStructs.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/planetarySystem/planetStructs.hpp +// +// Last modified : 06/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/planetarySystem/planetarySystem.cpp b/src/dataBlock/planetarySystem/planetarySystem.cpp index 8d01118db..6370d4d00 100644 --- a/src/dataBlock/planetarySystem/planetarySystem.cpp +++ b/src/dataBlock/planetarySystem/planetarySystem.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/planetarySystem/planetarySystem.cpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/planetarySystem/planetarySystem.hpp b/src/dataBlock/planetarySystem/planetarySystem.hpp index 436ad3d4e..6a2d4bfc8 100644 --- a/src/dataBlock/planetarySystem/planetarySystem.hpp +++ b/src/dataBlock/planetarySystem/planetarySystem.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/planetarySystem/planetarySystem.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/stateContainer.cpp b/src/dataBlock/stateContainer.cpp index 52fff9125..ac87a5cfe 100644 --- a/src/dataBlock/stateContainer.cpp +++ b/src/dataBlock/stateContainer.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/stateContainer.cpp +// +// Last modified : 11/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// - Clément Robert (IPAG/UGA/CNRS - 2022) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/stateContainer.hpp b/src/dataBlock/stateContainer.hpp index b8d9378c5..bb0bd4a78 100644 --- a/src/dataBlock/stateContainer.hpp +++ b/src/dataBlock/stateContainer.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/stateContainer.hpp +// +// Last modified : 11/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// - Clément Robert (IPAG/UGA/CNRS - 2022) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/dataBlock/validation.cpp b/src/dataBlock/validation.cpp index 9ee53e60e..f2819bf1a 100644 --- a/src/dataBlock/validation.cpp +++ b/src/dataBlock/validation.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/dataBlock/validation.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/error.cpp b/src/error.cpp index 5ea3006cf..868de2418 100644 --- a/src/error.cpp +++ b/src/error.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/error.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/error.hpp b/src/error.hpp index 71cf09dd5..3661f16bc 100644 --- a/src/error.hpp +++ b/src/error.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/error.hpp +// +// Last modified : 11/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/CMakeLists.txt b/src/fluid/CMakeLists.txt index f849b22fc..b5d70be2c 100644 --- a/src/fluid/CMakeLists.txt +++ b/src/fluid/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + add_subdirectory(boundary) add_subdirectory(braginskii) add_subdirectory(constrainedTransport) diff --git a/src/fluid/RiemannSolver/CMakeLists.txt b/src/fluid/RiemannSolver/CMakeLists.txt index f9a018736..9099fea25 100644 --- a/src/fluid/RiemannSolver/CMakeLists.txt +++ b/src/fluid/RiemannSolver/CMakeLists.txt @@ -1,3 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/RiemannSolver/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### add_subdirectory(MHDsolvers) add_subdirectory(HDsolvers) diff --git a/src/fluid/RiemannSolver/Dustsolvers/CMakeLists.txt b/src/fluid/RiemannSolver/Dustsolvers/CMakeLists.txt index 0cafdc8d6..6f5a7bb38 100644 --- a/src/fluid/RiemannSolver/Dustsolvers/CMakeLists.txt +++ b/src/fluid/RiemannSolver/Dustsolvers/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/RiemannSolver/Dustsolvers/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/hllDust.hpp ) diff --git a/src/fluid/RiemannSolver/Dustsolvers/hllDust.hpp b/src/fluid/RiemannSolver/Dustsolvers/hllDust.hpp index d55f0ceb7..2bc8da708 100644 --- a/src/fluid/RiemannSolver/Dustsolvers/hllDust.hpp +++ b/src/fluid/RiemannSolver/Dustsolvers/hllDust.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/Dustsolvers/hllDust.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/HDsolvers/CMakeLists.txt b/src/fluid/RiemannSolver/HDsolvers/CMakeLists.txt index 6d3ec5701..5d684e731 100644 --- a/src/fluid/RiemannSolver/HDsolvers/CMakeLists.txt +++ b/src/fluid/RiemannSolver/HDsolvers/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/RiemannSolver/HDsolvers/CMakeLists.txt +# +# Last modified : 09/2021 +# +# Copyright(C) by : +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/hllcHD.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/hllHD.hpp diff --git a/src/fluid/RiemannSolver/HDsolvers/hllHD.hpp b/src/fluid/RiemannSolver/HDsolvers/hllHD.hpp index 89d72d332..276f4e4ce 100644 --- a/src/fluid/RiemannSolver/HDsolvers/hllHD.hpp +++ b/src/fluid/RiemannSolver/HDsolvers/hllHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/HDsolvers/hllHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp b/src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp index e79aac35f..2585fd7a4 100644 --- a/src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp +++ b/src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/HDsolvers/hllcHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/HDsolvers/roeHD.hpp b/src/fluid/RiemannSolver/HDsolvers/roeHD.hpp index 416f99848..b985b40a2 100644 --- a/src/fluid/RiemannSolver/HDsolvers/roeHD.hpp +++ b/src/fluid/RiemannSolver/HDsolvers/roeHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/HDsolvers/roeHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp b/src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp index 597dd0d12..7a389dd16 100644 --- a/src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp +++ b/src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/HDsolvers/tvdlfHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/MHDsolvers/CMakeLists.txt b/src/fluid/RiemannSolver/MHDsolvers/CMakeLists.txt index 4fbac3d94..268318f84 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/CMakeLists.txt +++ b/src/fluid/RiemannSolver/MHDsolvers/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/RiemannSolver/MHDsolvers/CMakeLists.txt +# +# Last modified : 09/2021 +# +# Copyright(C) by : +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/hlldMHD.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/hllMHD.hpp diff --git a/src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp b/src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp index 77253b727..ae4c4b6c3 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/MHDsolvers/hllMHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/MHDsolvers/hlldMHD.hpp b/src/fluid/RiemannSolver/MHDsolvers/hlldMHD.hpp index fa2491c55..7d0237a6b 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/hlldMHD.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/hlldMHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/MHDsolvers/hlldMHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp b/src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp index 633c3ebd8..4395c202d 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/MHDsolvers/roeMHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp index e4152dcdb..d10bb19a9 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/MHDsolvers/storeFlux.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2026) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/MHDsolvers/tvdlfMHD.hpp b/src/fluid/RiemannSolver/MHDsolvers/tvdlfMHD.hpp index b8435d3cd..743c6ada0 100644 --- a/src/fluid/RiemannSolver/MHDsolvers/tvdlfMHD.hpp +++ b/src/fluid/RiemannSolver/MHDsolvers/tvdlfMHD.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/MHDsolvers/tvdlfMHD.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/calcFlux.hpp b/src/fluid/RiemannSolver/calcFlux.hpp index ea5b18741..c23755b87 100644 --- a/src/fluid/RiemannSolver/calcFlux.hpp +++ b/src/fluid/RiemannSolver/calcFlux.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/calcFlux.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/extrapolateToFaces.hpp b/src/fluid/RiemannSolver/extrapolateToFaces.hpp index bb3c99587..c832bad9d 100644 --- a/src/fluid/RiemannSolver/extrapolateToFaces.hpp +++ b/src/fluid/RiemannSolver/extrapolateToFaces.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/extrapolateToFaces.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #ifndef FLUID_RIEMANNSOLVER_EXTRAPOLATETOFACES_HPP_ diff --git a/src/fluid/RiemannSolver/flux.hpp b/src/fluid/RiemannSolver/flux.hpp index 9c5131d88..ee885c465 100644 --- a/src/fluid/RiemannSolver/flux.hpp +++ b/src/fluid/RiemannSolver/flux.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/flux.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/riemannSolver.hpp b/src/fluid/RiemannSolver/riemannSolver.hpp index b6c1e6f11..bffaaa43b 100644 --- a/src/fluid/RiemannSolver/riemannSolver.hpp +++ b/src/fluid/RiemannSolver/riemannSolver.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/riemannSolver.hpp +// +// Last modified : 09/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Marc Van den Bossche (IAP Postdam - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/shockFlattening.hpp b/src/fluid/RiemannSolver/shockFlattening.hpp index df68de766..454b7db06 100644 --- a/src/fluid/RiemannSolver/shockFlattening.hpp +++ b/src/fluid/RiemannSolver/shockFlattening.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/shockFlattening.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/RiemannSolver/slopeLimiter.hpp b/src/fluid/RiemannSolver/slopeLimiter.hpp index 082ed0894..5417eee28 100644 --- a/src/fluid/RiemannSolver/slopeLimiter.hpp +++ b/src/fluid/RiemannSolver/slopeLimiter.hpp @@ -1,9 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/RiemannSolver/slopeLimiter.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** + #ifndef FLUID_RIEMANNSOLVER_SLOPELIMITER_HPP_ #define FLUID_RIEMANNSOLVER_SLOPELIMITER_HPP_ diff --git a/src/fluid/addNonIdealMHDFlux.hpp b/src/fluid/addNonIdealMHDFlux.hpp index 9ae6af304..4bb3d785d 100644 --- a/src/fluid/addNonIdealMHDFlux.hpp +++ b/src/fluid/addNonIdealMHDFlux.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/addNonIdealMHDFlux.hpp +// +// Last modified : 06/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/addSourceTerms.hpp b/src/fluid/addSourceTerms.hpp index e3f745868..0350fab0c 100644 --- a/src/fluid/addSourceTerms.hpp +++ b/src/fluid/addSourceTerms.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/addSourceTerms.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/boundary/CMakeLists.txt b/src/fluid/boundary/CMakeLists.txt index 35f30dff1..8c04f2b3c 100644 --- a/src/fluid/boundary/CMakeLists.txt +++ b/src/fluid/boundary/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/boundary/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/axis.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/axis.hpp diff --git a/src/fluid/boundary/axis.cpp b/src/fluid/boundary/axis.cpp index c0b00cb36..1b6ef30d0 100644 --- a/src/fluid/boundary/axis.cpp +++ b/src/fluid/boundary/axis.cpp @@ -1,7 +1,18 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/boundary/axis.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Marc Van den Bossche (IPAG/UGA/CNRS - 2023) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2024) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/boundary/axis.hpp b/src/fluid/boundary/axis.hpp index ad2389fe9..eb92688e0 100644 --- a/src/fluid/boundary/axis.hpp +++ b/src/fluid/boundary/axis.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/boundary/axis.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/boundary/boundary.hpp b/src/fluid/boundary/boundary.hpp index 4065cc60d..56c7cac20 100644 --- a/src/fluid/boundary/boundary.hpp +++ b/src/fluid/boundary/boundary.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/boundary/boundary.hpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/braginskii/CMakeLists.txt b/src/fluid/braginskii/CMakeLists.txt index 8e2198c23..8b6414014 100644 --- a/src/fluid/braginskii/CMakeLists.txt +++ b/src/fluid/braginskii/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/braginskii/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/bragThermalDiffusion.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/bragThermalDiffusion.cpp diff --git a/src/fluid/braginskii/bragThermalDiffusion.cpp b/src/fluid/braginskii/bragThermalDiffusion.cpp index f251d0b0c..6bd32d170 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.cpp +++ b/src/fluid/braginskii/bragThermalDiffusion.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/braginskii/bragThermalDiffusion.cpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Victor Réville (IRAP - 2024 - 2025) +// - Jean Kempf (IRAP - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/braginskii/bragThermalDiffusion.hpp b/src/fluid/braginskii/bragThermalDiffusion.hpp index 116ff9a03..065976614 100644 --- a/src/fluid/braginskii/bragThermalDiffusion.hpp +++ b/src/fluid/braginskii/bragThermalDiffusion.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/braginskii/bragThermalDiffusion.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Victor Réville (IRAP - 2024 - 2025) +// - Jean Kempf (IRAP - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/braginskii/bragViscosity.cpp b/src/fluid/braginskii/bragViscosity.cpp index e53ab2c65..7f6d363b1 100644 --- a/src/fluid/braginskii/bragViscosity.cpp +++ b/src/fluid/braginskii/bragViscosity.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/braginskii/bragViscosity.cpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Jean Kempf (IRAP - 2025) +// - Victor Réville (IRAP - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/braginskii/bragViscosity.hpp b/src/fluid/braginskii/bragViscosity.hpp index 5340110a8..4e7acfbb1 100644 --- a/src/fluid/braginskii/bragViscosity.hpp +++ b/src/fluid/braginskii/bragViscosity.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/braginskii/bragViscosity.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Jean Kempf (IRAP - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/calcCurrent.hpp b/src/fluid/calcCurrent.hpp index 1f57560a0..14a47ade6 100644 --- a/src/fluid/calcCurrent.hpp +++ b/src/fluid/calcCurrent.hpp @@ -1,9 +1,20 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/calcCurrent.hpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** + #ifndef FLUID_CALCCURRENT_HPP_ #define FLUID_CALCCURRENT_HPP_ diff --git a/src/fluid/calcParabolicFlux.hpp b/src/fluid/calcParabolicFlux.hpp index 8713f9107..68e1c065e 100644 --- a/src/fluid/calcParabolicFlux.hpp +++ b/src/fluid/calcParabolicFlux.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/calcParabolicFlux.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #ifndef FLUID_CALCPARABOLICFLUX_HPP_ diff --git a/src/fluid/calcRightHandSide.hpp b/src/fluid/calcRightHandSide.hpp index a68f56d0f..acbc66f03 100644 --- a/src/fluid/calcRightHandSide.hpp +++ b/src/fluid/calcRightHandSide.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/calcRightHandSide.hpp +// +// Last modified : 11/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/checkDivB.hpp b/src/fluid/checkDivB.hpp index 6e47d4c8c..f5ddcd67b 100644 --- a/src/fluid/checkDivB.hpp +++ b/src/fluid/checkDivB.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/checkDivB.hpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/checkNan.hpp b/src/fluid/checkNan.hpp index 0e8890725..654e01eba 100644 --- a/src/fluid/checkNan.hpp +++ b/src/fluid/checkNan.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/checkNan.hpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2024) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/coarsenFlow.hpp b/src/fluid/coarsenFlow.hpp index b1bf79eaa..0ce030d9a 100644 --- a/src/fluid/coarsenFlow.hpp +++ b/src/fluid/coarsenFlow.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/coarsenFlow.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/CMakeLists.txt b/src/fluid/constrainedTransport/CMakeLists.txt index 7d99b805c..d9ce0c658 100644 --- a/src/fluid/constrainedTransport/CMakeLists.txt +++ b/src/fluid/constrainedTransport/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/constrainedTransport/CMakeLists.txt +# +# Last modified : 12/2025 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/calcCornerEmf.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/calcNonidealEMF.hpp diff --git a/src/fluid/constrainedTransport/EMFexchange.hpp b/src/fluid/constrainedTransport/EMFexchange.hpp index 22fbb58e8..fd6eb555c 100644 --- a/src/fluid/constrainedTransport/EMFexchange.hpp +++ b/src/fluid/constrainedTransport/EMFexchange.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/EMFexchange.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/calcCornerEmf.hpp b/src/fluid/constrainedTransport/calcCornerEmf.hpp index 0a998aa52..8b04ab2a8 100644 --- a/src/fluid/constrainedTransport/calcCornerEmf.hpp +++ b/src/fluid/constrainedTransport/calcCornerEmf.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/calcCornerEmf.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #ifndef FLUID_CONSTRAINEDTRANSPORT_CALCCORNEREMF_HPP_ diff --git a/src/fluid/constrainedTransport/calcNonidealEMF.hpp b/src/fluid/constrainedTransport/calcNonidealEMF.hpp index 2253e33d1..2ca5834e1 100644 --- a/src/fluid/constrainedTransport/calcNonidealEMF.hpp +++ b/src/fluid/constrainedTransport/calcNonidealEMF.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/calcNonidealEMF.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/calcRiemannEmf.hpp b/src/fluid/constrainedTransport/calcRiemannEmf.hpp index 2779ffbab..5a56f0519 100644 --- a/src/fluid/constrainedTransport/calcRiemannEmf.hpp +++ b/src/fluid/constrainedTransport/calcRiemannEmf.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/calcRiemannEmf.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/constrainedTransport.hpp b/src/fluid/constrainedTransport/constrainedTransport.hpp index 5f07a6fdd..6d53e86b6 100644 --- a/src/fluid/constrainedTransport/constrainedTransport.hpp +++ b/src/fluid/constrainedTransport/constrainedTransport.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/constrainedTransport.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp index b35bec9fa..3f2163850 100644 --- a/src/fluid/constrainedTransport/enforceEMFBoundary.hpp +++ b/src/fluid/constrainedTransport/enforceEMFBoundary.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/enforceEMFBoundary.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp index 3019edfd8..7d7b966be 100644 --- a/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp +++ b/src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/enforceVectorPotentialBoundary.hpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025 - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/constrainedTransport/evolveMagField.hpp b/src/fluid/constrainedTransport/evolveMagField.hpp index 01aa8a6ec..0a013d8c1 100644 --- a/src/fluid/constrainedTransport/evolveMagField.hpp +++ b/src/fluid/constrainedTransport/evolveMagField.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/evolveMagField.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #ifndef FLUID_CONSTRAINEDTRANSPORT_EVOLVEMAGFIELD_HPP_ diff --git a/src/fluid/constrainedTransport/evolveVectorPotential.hpp b/src/fluid/constrainedTransport/evolveVectorPotential.hpp index 0887d2e1e..ebd0a32f9 100644 --- a/src/fluid/constrainedTransport/evolveVectorPotential.hpp +++ b/src/fluid/constrainedTransport/evolveVectorPotential.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/constrainedTransport/evolveVectorPotential.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/convertConsToPrim.hpp b/src/fluid/convertConsToPrim.hpp index 45607b86f..3a201b61e 100644 --- a/src/fluid/convertConsToPrim.hpp +++ b/src/fluid/convertConsToPrim.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/convertConsToPrim.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/drag.cpp b/src/fluid/drag.cpp index 4cf879cdd..79464cdf4 100644 --- a/src/fluid/drag.cpp +++ b/src/fluid/drag.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/drag.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #include "drag.hpp" diff --git a/src/fluid/drag.hpp b/src/fluid/drag.hpp index 63b5e1bdb..786d48d6d 100644 --- a/src/fluid/drag.hpp +++ b/src/fluid/drag.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/drag.hpp +// +// Last modified : 10/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** #ifndef FLUID_DRAG_HPP_ diff --git a/src/fluid/enroll.hpp b/src/fluid/enroll.hpp index 77e8876fb..68406d56e 100644 --- a/src/fluid/enroll.hpp +++ b/src/fluid/enroll.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/enroll.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/eos/CMakeLists.txt b/src/fluid/eos/CMakeLists.txt index f939d9d55..14a2c484d 100644 --- a/src/fluid/eos/CMakeLists.txt +++ b/src/fluid/eos/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/eos/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/eos_adiabatic.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/eos_isothermal.hpp diff --git a/src/fluid/eos/eos.hpp b/src/fluid/eos/eos.hpp index 7e0a490a3..bff87f378 100644 --- a/src/fluid/eos/eos.hpp +++ b/src/fluid/eos/eos.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/eos/eos.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/eos/eos_adiabatic.hpp b/src/fluid/eos/eos_adiabatic.hpp index 88d4f0f66..49b35a4e8 100644 --- a/src/fluid/eos/eos_adiabatic.hpp +++ b/src/fluid/eos/eos_adiabatic.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/eos/eos_adiabatic.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/eos/eos_isothermal.hpp b/src/fluid/eos/eos_isothermal.hpp index 04efc9b2d..72ca0604f 100644 --- a/src/fluid/eos/eos_isothermal.hpp +++ b/src/fluid/eos/eos_isothermal.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/eos/eos_isothermal.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/eos/eos_template.hpp b/src/fluid/eos/eos_template.hpp index 3d6150817..df5e1c064 100644 --- a/src/fluid/eos/eos_template.hpp +++ b/src/fluid/eos/eos_template.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/eos/eos_template.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/evolveStage.hpp b/src/fluid/evolveStage.hpp index b0a467ba4..44c61cf3e 100644 --- a/src/fluid/evolveStage.hpp +++ b/src/fluid/evolveStage.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/evolveStage.hpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/fluid.hpp b/src/fluid/fluid.hpp index 9e0615dee..d32b074fc 100644 --- a/src/fluid/fluid.hpp +++ b/src/fluid/fluid.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/fluid.hpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/fluid_defs.hpp b/src/fluid/fluid_defs.hpp index 3f68c9b49..9acf98fb2 100644 --- a/src/fluid/fluid_defs.hpp +++ b/src/fluid/fluid_defs.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/fluid_defs.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Victor Réville (IRAP - 2024 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/showConfig.hpp b/src/fluid/showConfig.hpp index 0f8b64ed9..069806553 100644 --- a/src/fluid/showConfig.hpp +++ b/src/fluid/showConfig.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/showConfig.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/thermalDiffusion.cpp b/src/fluid/thermalDiffusion.cpp index 344e0d168..b7abecb71 100644 --- a/src/fluid/thermalDiffusion.cpp +++ b/src/fluid/thermalDiffusion.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/thermalDiffusion.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/thermalDiffusion.hpp b/src/fluid/thermalDiffusion.hpp index cce827492..9f45221e7 100644 --- a/src/fluid/thermalDiffusion.hpp +++ b/src/fluid/thermalDiffusion.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/thermalDiffusion.hpp +// +// Last modified : 12/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/tracer/CMakeLists.txt b/src/fluid/tracer/CMakeLists.txt index cb8e35757..282ec7ddb 100644 --- a/src/fluid/tracer/CMakeLists.txt +++ b/src/fluid/tracer/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/fluid/tracer/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/tracer.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/tracer.hpp diff --git a/src/fluid/tracer/tracer.cpp b/src/fluid/tracer/tracer.cpp index 7ee95c6c7..7abd46999 100644 --- a/src/fluid/tracer/tracer.cpp +++ b/src/fluid/tracer/tracer.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/tracer/tracer.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/tracer/tracer.hpp b/src/fluid/tracer/tracer.hpp index 57889131e..9a460788e 100644 --- a/src/fluid/tracer/tracer.hpp +++ b/src/fluid/tracer/tracer.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/tracer/tracer.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/viscosity.cpp b/src/fluid/viscosity.cpp index 5d6d8a65a..90df416eb 100644 --- a/src/fluid/viscosity.cpp +++ b/src/fluid/viscosity.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/viscosity.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/fluid/viscosity.hpp b/src/fluid/viscosity.hpp index 3f004c272..aae353a5b 100644 --- a/src/fluid/viscosity.hpp +++ b/src/fluid/viscosity.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/fluid/viscosity.hpp +// +// Last modified : 12/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/global.cpp b/src/global.cpp index 1ed33ba11..f47c76a54 100644 --- a/src/global.cpp +++ b/src/global.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/global.cpp +// +// Last modified : 05/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2025) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/global.hpp b/src/global.hpp index c4de3926e..ae9439e12 100644 --- a/src/global.hpp +++ b/src/global.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/global.hpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2025) +// - Clément Robert (IPAG/UGA/CNRS - 2022 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gravity/CMakeLists.txt b/src/gravity/CMakeLists.txt index ad2585791..1a643fa23 100644 --- a/src/gravity/CMakeLists.txt +++ b/src/gravity/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/gravity/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/gravity.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/gravity.cpp diff --git a/src/gravity/gravity.cpp b/src/gravity/gravity.cpp index a39b00063..ae15dfaab 100644 --- a/src/gravity/gravity.cpp +++ b/src/gravity/gravity.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/gravity.cpp +// +// Last modified : 04/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Antonin Borderies (ENS Lyon - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gravity/gravity.hpp b/src/gravity/gravity.hpp index aa0184aa6..40c5732d4 100644 --- a/src/gravity/gravity.hpp +++ b/src/gravity/gravity.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/gravity.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gravity/laplacian.cpp b/src/gravity/laplacian.cpp index 127299548..2c7dafb72 100644 --- a/src/gravity/laplacian.cpp +++ b/src/gravity/laplacian.cpp @@ -1,12 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/laplacian.cpp +// +// Last modified : 06/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** - - #include #include #include "laplacian.hpp" diff --git a/src/gravity/laplacian.hpp b/src/gravity/laplacian.hpp index 285724399..f3cd6a827 100644 --- a/src/gravity/laplacian.hpp +++ b/src/gravity/laplacian.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/laplacian.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gravity/selfGravity.cpp b/src/gravity/selfGravity.cpp index 43f764713..c3407ec61 100644 --- a/src/gravity/selfGravity.cpp +++ b/src/gravity/selfGravity.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/selfGravity.cpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gravity/selfGravity.hpp b/src/gravity/selfGravity.hpp index badd729ce..25534b826 100644 --- a/src/gravity/selfGravity.hpp +++ b/src/gravity/selfGravity.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gravity/selfGravity.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/grid.cpp b/src/grid.cpp index ace5eb0ca..8d13f65a4 100644 --- a/src/grid.cpp +++ b/src/grid.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/grid.cpp +// +// Last modified : 12/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// - Nicolas Scepi (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/grid.hpp b/src/grid.hpp index 947d05d12..c989cb21b 100644 --- a/src/grid.hpp +++ b/src/grid.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/grid.hpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gridHost.cpp b/src/gridHost.cpp index 0c85d8e41..be36cfa6a 100644 --- a/src/gridHost.cpp +++ b/src/gridHost.cpp @@ -1,7 +1,18 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gridHost.cpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Jonah Mauxion (IPAG/UGA/CNRS - 2023) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/gridHost.hpp b/src/gridHost.hpp index 55283a5c9..7600d8bf5 100644 --- a/src/gridHost.hpp +++ b/src/gridHost.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/gridHost.hpp +// +// Last modified : 12/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/idefix.hpp b/src/idefix.hpp index 7485f95f0..77b20fa7b 100644 --- a/src/idefix.hpp +++ b/src/idefix.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/idefix.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/input.cpp b/src/input.cpp index 6be052f66..39fd44e9a 100644 --- a/src/input.cpp +++ b/src/input.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/input.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/input.hpp b/src/input.hpp index 18fcf2601..6f6c802cf 100644 --- a/src/input.hpp +++ b/src/input.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/input.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/loop.hpp b/src/loop.hpp index 319ad8553..655513bd9 100644 --- a/src/loop.hpp +++ b/src/loop.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/loop.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/macros.hpp b/src/macros.hpp index 0df5f9430..99d39c684 100644 --- a/src/macros.hpp +++ b/src/macros.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/macros.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/main.cpp b/src/main.cpp index a2dcd630a..9d0a7dfda 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/main.cpp +// +// Last modified : 04/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/CMakeLists.txt b/src/mpi/CMakeLists.txt index 6042da654..8a9eef4d9 100644 --- a/src/mpi/CMakeLists.txt +++ b/src/mpi/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/mpi/CMakeLists.txt +# +# Last modified : 12/2025 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/buffer.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/exchanger.hpp diff --git a/src/mpi/buffer.hpp b/src/mpi/buffer.hpp index f4f4f423a..d7607c536 100644 --- a/src/mpi/buffer.hpp +++ b/src/mpi/buffer.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/buffer.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/commArray.hpp b/src/mpi/commArray.hpp index 3856c7e8c..f6acc6c29 100644 --- a/src/mpi/commArray.hpp +++ b/src/mpi/commArray.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/commArray.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/exchanger.cpp b/src/mpi/exchanger.cpp index 7f377c2ac..136e06ca6 100644 --- a/src/mpi/exchanger.cpp +++ b/src/mpi/exchanger.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/exchanger.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/exchanger.hpp b/src/mpi/exchanger.hpp index d5b53e123..db370eda7 100644 --- a/src/mpi/exchanger.hpp +++ b/src/mpi/exchanger.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/exchanger.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/mpi.cpp b/src/mpi/mpi.cpp index 75c45c0f7..fae1b4680 100644 --- a/src/mpi/mpi.cpp +++ b/src/mpi/mpi.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/mpi.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/mpi.hpp b/src/mpi/mpi.hpp index 41f13be68..d366b69cc 100644 --- a/src/mpi/mpi.hpp +++ b/src/mpi/mpi.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/mpi.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/mpi/mpiWrapper.hpp b/src/mpi/mpiWrapper.hpp index 71cc5b265..0862aa415 100644 --- a/src/mpi/mpiWrapper.hpp +++ b/src/mpi/mpiWrapper.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/mpi/mpiWrapper.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/CMakeLists.txt b/src/output/CMakeLists.txt index 8c54eaebc..17d19b549 100644 --- a/src/output/CMakeLists.txt +++ b/src/output/CMakeLists.txt @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/output/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/slice.cpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/slice.hpp diff --git a/src/output/dump.cpp b/src/output/dump.cpp index d20eec265..4d0a63717 100644 --- a/src/output/dump.cpp +++ b/src/output/dump.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/dump.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Clément Robert (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/dump.hpp b/src/output/dump.hpp index 87cb7a3ba..16dafbe11 100644 --- a/src/output/dump.hpp +++ b/src/output/dump.hpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/dump.hpp +// +// Last modified : 01/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2020 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/output.cpp b/src/output/output.cpp index 9df188926..30e84b46f 100644 --- a/src/output/output.cpp +++ b/src/output/output.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/output.cpp +// +// Last modified : 04/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// - Alankar Dutta (MPA Garching - 2023) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/output.hpp b/src/output/output.hpp index 039ab1570..1f76aa940 100644 --- a/src/output/output.hpp +++ b/src/output/output.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/output.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2024) +// - Alankar Dutta (MPA Garching - 2023) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/scalarField.hpp b/src/output/scalarField.hpp index 6cbb9dd40..a11be598b 100644 --- a/src/output/scalarField.hpp +++ b/src/output/scalarField.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/scalarField.hpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/slice.cpp b/src/output/slice.cpp index b6e8709ec..eb83b650e 100644 --- a/src/output/slice.cpp +++ b/src/output/slice.cpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/slice.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2024) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/slice.hpp b/src/output/slice.hpp index ed19a3b21..2f72c7be2 100644 --- a/src/output/slice.hpp +++ b/src/output/slice.hpp @@ -1,11 +1,18 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/slice.hpp +// +// Last modified : 05/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** - #ifndef OUTPUT_SLICE_HPP_ #define OUTPUT_SLICE_HPP_ diff --git a/src/output/vtk.cpp b/src/output/vtk.cpp index 664e97b39..a80c94d57 100644 --- a/src/output/vtk.cpp +++ b/src/output/vtk.cpp @@ -1,7 +1,19 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/vtk.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Alankar Dutta (MPA Garching - 2023) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/vtk.hpp b/src/output/vtk.hpp index 1a55f67f5..bd9cc7149 100644 --- a/src/output/vtk.hpp +++ b/src/output/vtk.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/vtk.hpp +// +// Last modified : 11/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/xdmf.cpp b/src/output/xdmf.cpp index 7d559a6d6..aceda0379 100644 --- a/src/output/xdmf.cpp +++ b/src/output/xdmf.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/xdmf.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Alankar Dutta (MPA Garching - 2023 - 2026) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/output/xdmf.hpp b/src/output/xdmf.hpp index 6c6fc15cc..8af8348f4 100644 --- a/src/output/xdmf.hpp +++ b/src/output/xdmf.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/output/xdmf.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Alankar Dutta (MPA Garching - 2023) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/physics.hpp b/src/physics.hpp index e9b29c455..3cb51e7fe 100644 --- a/src/physics.hpp +++ b/src/physics.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/physics.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/profiler.cpp b/src/profiler.cpp index 04ff5f5cb..439d2c7e7 100644 --- a/src/profiler.cpp +++ b/src/profiler.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/profiler.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/profiler.hpp b/src/profiler.hpp index 49814dd3f..eba7f39bf 100644 --- a/src/profiler.hpp +++ b/src/profiler.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/profiler.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/pydefix.cpp b/src/pydefix.cpp index 457faa4eb..241797f5a 100644 --- a/src/pydefix.cpp +++ b/src/pydefix.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/pydefix.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/pydefix.hpp b/src/pydefix.hpp index a12086f82..ee292549b 100644 --- a/src/pydefix.hpp +++ b/src/pydefix.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/pydefix.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/real_types.hpp b/src/real_types.hpp index 988ca1675..bada79895 100644 --- a/src/real_types.hpp +++ b/src/real_types.hpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/real_types.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2022) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Alankar Dutta (MPA Garching - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/reduce.hpp b/src/reduce.hpp index 17ba6b04a..cc1e84db7 100644 --- a/src/reduce.hpp +++ b/src/reduce.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/reduce.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/rkl/CMakeLists.txt b/src/rkl/CMakeLists.txt index 245fe415e..865410265 100644 --- a/src/rkl/CMakeLists.txt +++ b/src/rkl/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/rkl/CMakeLists.txt +# +# Last modified : 09/2021 +# +# Copyright(C) by : +# - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/rkl.hpp ) diff --git a/src/rkl/rkl.hpp b/src/rkl/rkl.hpp index 8288cd0fa..61fa9047f 100644 --- a/src/rkl/rkl.hpp +++ b/src/rkl/rkl.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/rkl/rkl.hpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2021) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/setup.cpp b/src/setup.cpp index b82f118f8..6713749b1 100644 --- a/src/setup.cpp +++ b/src/setup.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/setup.cpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/setup.hpp b/src/setup.hpp index 8e1aa0eda..c25322605 100644 --- a/src/setup.hpp +++ b/src/setup.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/setup.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/timeIntegrator.cpp b/src/timeIntegrator.cpp index e3f6949ed..e5183df9f 100644 --- a/src/timeIntegrator.cpp +++ b/src/timeIntegrator.cpp @@ -1,7 +1,19 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/timeIntegrator.cpp +// +// Last modified : 09/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) +// - Nicolas Scepi (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/timeIntegrator.hpp b/src/timeIntegrator.hpp index f83593724..fc8288898 100644 --- a/src/timeIntegrator.hpp +++ b/src/timeIntegrator.hpp @@ -1,7 +1,17 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/timeIntegrator.hpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2024) +// - Soufiane Baghdadi (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/units.cpp b/src/units.cpp index 2baf97b1e..334ad5dca 100644 --- a/src/units.cpp +++ b/src/units.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/units.cpp +// +// Last modified : 04/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/units.hpp b/src/units.hpp index 525e44bc0..bb6f06d38 100644 --- a/src/units.hpp +++ b/src/units.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/units.hpp +// +// Last modified : 10/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/CMakeLists.txt b/src/utils/CMakeLists.txt index afb4f57d4..ef71c20c7 100644 --- a/src/utils/CMakeLists.txt +++ b/src/utils/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/utils/CMakeLists.txt +# +# Last modified : 01/2025 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2025) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + add_subdirectory(iterativesolver) target_sources(idefix diff --git a/src/utils/bigEndian.hpp b/src/utils/bigEndian.hpp index 08bd73c04..d0f9f6baf 100644 --- a/src/utils/bigEndian.hpp +++ b/src/utils/bigEndian.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/bigEndian.hpp +// +// Last modified : 07/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/column.cpp b/src/utils/column.cpp index dadac1976..dee61c652 100644 --- a/src/utils/column.cpp +++ b/src/utils/column.cpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/column.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/column.hpp b/src/utils/column.hpp index 8e2e619dd..665b6e78a 100644 --- a/src/utils/column.hpp +++ b/src/utils/column.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/column.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/dumpImage.cpp b/src/utils/dumpImage.cpp index 04f413a7c..fd4222010 100644 --- a/src/utils/dumpImage.cpp +++ b/src/utils/dumpImage.cpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/dumpImage.cpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/dumpImage.hpp b/src/utils/dumpImage.hpp index e13da5638..b37b29898 100644 --- a/src/utils/dumpImage.hpp +++ b/src/utils/dumpImage.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/dumpImage.hpp +// +// Last modified : 05/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/iterativesolver/CMakeLists.txt b/src/utils/iterativesolver/CMakeLists.txt index c8367b3f4..f9cd84c6e 100644 --- a/src/utils/iterativesolver/CMakeLists.txt +++ b/src/utils/iterativesolver/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file src/utils/iterativesolver/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + target_sources(idefix PUBLIC ${CMAKE_CURRENT_LIST_DIR}/cg.hpp PUBLIC ${CMAKE_CURRENT_LIST_DIR}/minres.hpp diff --git a/src/utils/iterativesolver/bicgstab.hpp b/src/utils/iterativesolver/bicgstab.hpp index 0b3dbb1ba..326e95c52 100644 --- a/src/utils/iterativesolver/bicgstab.hpp +++ b/src/utils/iterativesolver/bicgstab.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/iterativesolver/bicgstab.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/iterativesolver/cg.hpp b/src/utils/iterativesolver/cg.hpp index de75b7381..1bffed674 100644 --- a/src/utils/iterativesolver/cg.hpp +++ b/src/utils/iterativesolver/cg.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/iterativesolver/cg.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/iterativesolver/iterativesolver.hpp b/src/utils/iterativesolver/iterativesolver.hpp index e128f7fff..41b7f33d8 100644 --- a/src/utils/iterativesolver/iterativesolver.hpp +++ b/src/utils/iterativesolver/iterativesolver.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/iterativesolver/iterativesolver.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/iterativesolver/jacobi.hpp b/src/utils/iterativesolver/jacobi.hpp index 941415e48..15f5e55da 100644 --- a/src/utils/iterativesolver/jacobi.hpp +++ b/src/utils/iterativesolver/jacobi.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/iterativesolver/jacobi.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/iterativesolver/minres.hpp b/src/utils/iterativesolver/minres.hpp index 148457e51..b157a6d47 100644 --- a/src/utils/iterativesolver/minres.hpp +++ b/src/utils/iterativesolver/minres.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/iterativesolver/minres.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/lookupTable.hpp b/src/utils/lookupTable.hpp index b97c9a56e..b16d9649d 100644 --- a/src/utils/lookupTable.hpp +++ b/src/utils/lookupTable.hpp @@ -1,7 +1,16 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/lookupTable.hpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +// - Alankar Dutta (MPA Garching - 2026) +// - Sébastien Valat (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/npy.hpp b/src/utils/npy.hpp index edae82ee3..7c8867a15 100644 --- a/src/utils/npy.hpp +++ b/src/utils/npy.hpp @@ -1,7 +1,15 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/npy.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// - Clément Robert (IPAG/UGA/CNRS - 2024) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/utils/vector.hpp b/src/utils/vector.hpp index 68c49eea7..daf2a9b03 100644 --- a/src/utils/vector.hpp +++ b/src/utils/vector.hpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/utils/vector.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/src/version.h.in b/src/version.h.in index 5561658aa..ee4dbb0e7 100644 --- a/src/version.h.in +++ b/src/version.h.in @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file src/version.h.in +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/test.py b/test.py index a680be613..2e00981b0 100755 --- a/test.py +++ b/test.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test.py +# +# Last modified : 09/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### import os import sys diff --git a/test/Dust/DustEnergy/definitions.hpp b/test/Dust/DustEnergy/definitions.hpp index 498be97af..e64a63241 100644 --- a/test/Dust/DustEnergy/definitions.hpp +++ b/test/Dust/DustEnergy/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustEnergy/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/Dust/DustEnergy/python/testidefix.py b/test/Dust/DustEnergy/python/testidefix.py index 241121233..dc6a1e6da 100755 --- a/test/Dust/DustEnergy/python/testidefix.py +++ b/test/Dust/DustEnergy/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustEnergy/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Mon Mar 13 14:45:58 2023 diff --git a/test/Dust/DustEnergy/setup.cpp b/test/Dust/DustEnergy/setup.cpp index cba900a09..4463300d7 100644 --- a/test/Dust/DustEnergy/setup.cpp +++ b/test/Dust/DustEnergy/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustEnergy/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/Dust/DustEnergy/testme.py b/test/Dust/DustEnergy/testme.py index 473f39db0..33fbf1f9d 100755 --- a/test/Dust/DustEnergy/testme.py +++ b/test/Dust/DustEnergy/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustEnergy/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Dust/DustyShock/definitions.hpp b/test/Dust/DustyShock/definitions.hpp index cdbe23d6e..d15f31646 100644 --- a/test/Dust/DustyShock/definitions.hpp +++ b/test/Dust/DustyShock/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustyShock/definitions.hpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/Dust/DustyShock/python/testidefix.py b/test/Dust/DustyShock/python/testidefix.py index b87708be1..8e831a74e 100755 --- a/test/Dust/DustyShock/python/testidefix.py +++ b/test/Dust/DustyShock/python/testidefix.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustyShock/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/Dust/DustyShock/setup.cpp b/test/Dust/DustyShock/setup.cpp index f8632248a..7bf7d050e 100644 --- a/test/Dust/DustyShock/setup.cpp +++ b/test/Dust/DustyShock/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustyShock/setup.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/Dust/DustyShock/testme.py b/test/Dust/DustyShock/testme.py index 2aecf0253..47692d3a4 100755 --- a/test/Dust/DustyShock/testme.py +++ b/test/Dust/DustyShock/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustyShock/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Dust/DustyWave/definitions.hpp b/test/Dust/DustyWave/definitions.hpp index cdbe23d6e..5160a2c98 100644 --- a/test/Dust/DustyWave/definitions.hpp +++ b/test/Dust/DustyWave/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustyWave/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/Dust/DustyWave/python/testidefix.py b/test/Dust/DustyWave/python/testidefix.py index 9e05128b9..ce2af493a 100755 --- a/test/Dust/DustyWave/python/testidefix.py +++ b/test/Dust/DustyWave/python/testidefix.py @@ -1,5 +1,20 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustyWave/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- + """ Created on Mon Mar 13 14:45:58 2023 diff --git a/test/Dust/DustyWave/setup.cpp b/test/Dust/DustyWave/setup.cpp index 9cd5c66b9..ba4367058 100644 --- a/test/Dust/DustyWave/setup.cpp +++ b/test/Dust/DustyWave/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/DustyWave/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/Dust/DustyWave/testme.py b/test/Dust/DustyWave/testme.py index 2aecf0253..8ca235fb5 100755 --- a/test/Dust/DustyWave/testme.py +++ b/test/Dust/DustyWave/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Dust/DustyWave/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Dust/FargoPlanet/definitions.hpp b/test/Dust/FargoPlanet/definitions.hpp index deac509ae..c0de18420 100644 --- a/test/Dust/FargoPlanet/definitions.hpp +++ b/test/Dust/FargoPlanet/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/FargoPlanet/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/Dust/FargoPlanet/setup.cpp b/test/Dust/FargoPlanet/setup.cpp index 8447efe0b..e2c115de6 100644 --- a/test/Dust/FargoPlanet/setup.cpp +++ b/test/Dust/FargoPlanet/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/FargoPlanet/setup.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" #include "setup.hpp" diff --git a/test/Dust/StreamingInstability/definitions.hpp b/test/Dust/StreamingInstability/definitions.hpp index 486a4ea34..8bb8acd38 100644 --- a/test/Dust/StreamingInstability/definitions.hpp +++ b/test/Dust/StreamingInstability/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/StreamingInstability/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 #define ISOTHERMAL diff --git a/test/Dust/StreamingInstability/setup.cpp b/test/Dust/StreamingInstability/setup.cpp index 410ab1349..339413292 100644 --- a/test/Dust/StreamingInstability/setup.cpp +++ b/test/Dust/StreamingInstability/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Dust/StreamingInstability/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/FargoPlanet/definitions.hpp b/test/HD/FargoPlanet/definitions.hpp index deac509ae..0112c0d36 100644 --- a/test/HD/FargoPlanet/definitions.hpp +++ b/test/HD/FargoPlanet/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/FargoPlanet/definitions.hpp +// +// Last modified : 03/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/HD/FargoPlanet/setup.cpp b/test/HD/FargoPlanet/setup.cpp index 314858bae..1fafd1e6d 100644 --- a/test/HD/FargoPlanet/setup.cpp +++ b/test/HD/FargoPlanet/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/FargoPlanet/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/FargoPlanet/testme.py b/test/HD/FargoPlanet/testme.py index 7be82a4ba..74a13601c 100755 --- a/test/HD/FargoPlanet/testme.py +++ b/test/HD/FargoPlanet/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/FargoPlanet/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/KHI/definitions.hpp b/test/HD/KHI/definitions.hpp index 4c88d3387..631ec410d 100644 --- a/test/HD/KHI/definitions.hpp +++ b/test/HD/KHI/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/KHI/definitions.hpp +// +// Last modified : 02/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 #define ISOTHERMAL diff --git a/test/HD/KHI/setup.cpp b/test/HD/KHI/setup.cpp index fb6f35c28..0e797e44f 100644 --- a/test/HD/KHI/setup.cpp +++ b/test/HD/KHI/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/KHI/setup.cpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/MachReflection/definitions.hpp b/test/HD/MachReflection/definitions.hpp index 69f0c49e9..bfe306841 100644 --- a/test/HD/MachReflection/definitions.hpp +++ b/test/HD/MachReflection/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/MachReflection/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/HD/MachReflection/setup.cpp b/test/HD/MachReflection/setup.cpp index 7d7f2c55d..175ef4050 100644 --- a/test/HD/MachReflection/setup.cpp +++ b/test/HD/MachReflection/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/MachReflection/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/MachReflection/testme.py b/test/HD/MachReflection/testme.py index 7007c6e39..af210e660 100755 --- a/test/HD/MachReflection/testme.py +++ b/test/HD/MachReflection/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/MachReflection/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/RWI-cavity/definitions.hpp b/test/HD/RWI-cavity/definitions.hpp index e97456095..40995d0e4 100644 --- a/test/HD/RWI-cavity/definitions.hpp +++ b/test/HD/RWI-cavity/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/RWI-cavity/definitions.hpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/HD/RWI-cavity/setup.cpp b/test/HD/RWI-cavity/setup.cpp index 726690e68..8baf68eff 100644 --- a/test/HD/RWI-cavity/setup.cpp +++ b/test/HD/RWI-cavity/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/RWI-cavity/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/SedovBlastWave/definitions-spherical.hpp b/test/HD/SedovBlastWave/definitions-spherical.hpp index 53b4f38e3..f2b4f579a 100644 --- a/test/HD/SedovBlastWave/definitions-spherical.hpp +++ b/test/HD/SedovBlastWave/definitions-spherical.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/definitions-spherical.hpp +// +// Last modified : 10/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/HD/SedovBlastWave/definitions-unequal.hpp b/test/HD/SedovBlastWave/definitions-unequal.hpp index 3b581bd62..465d7f0c9 100644 --- a/test/HD/SedovBlastWave/definitions-unequal.hpp +++ b/test/HD/SedovBlastWave/definitions-unequal.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/definitions-unequal.hpp +// +// Last modified : 08/2023 +// +// Copyright(C) by : +// - Alankar Dutta (MPA Garching - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/HD/SedovBlastWave/definitions.hpp b/test/HD/SedovBlastWave/definitions.hpp index 3b581bd62..57b411d3b 100644 --- a/test/HD/SedovBlastWave/definitions.hpp +++ b/test/HD/SedovBlastWave/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/definitions.hpp +// +// Last modified : 10/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/HD/SedovBlastWave/python/1Dsolution/definitions.hpp b/test/HD/SedovBlastWave/python/1Dsolution/definitions.hpp index 3349b3ae7..9cb5b4604 100644 --- a/test/HD/SedovBlastWave/python/1Dsolution/definitions.hpp +++ b/test/HD/SedovBlastWave/python/1Dsolution/definitions.hpp @@ -1,3 +1,16 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/python/1Dsolution/definitions.hpp +// +// Last modified : 10/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/HD/SedovBlastWave/python/1Dsolution/setup.cpp b/test/HD/SedovBlastWave/python/1Dsolution/setup.cpp index 043fe5349..904525049 100644 --- a/test/HD/SedovBlastWave/python/1Dsolution/setup.cpp +++ b/test/HD/SedovBlastWave/python/1Dsolution/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/python/1Dsolution/setup.cpp +// +// Last modified : 10/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/SedovBlastWave/python/testidefix.py b/test/HD/SedovBlastWave/python/testidefix.py index e926a19dd..119fe9c15 100755 --- a/test/HD/SedovBlastWave/python/testidefix.py +++ b/test/HD/SedovBlastWave/python/testidefix.py @@ -1,5 +1,20 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/SedovBlastWave/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- + """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/HD/SedovBlastWave/setup.cpp b/test/HD/SedovBlastWave/setup.cpp index 7b17b6bae..63d74aa15 100644 --- a/test/HD/SedovBlastWave/setup.cpp +++ b/test/HD/SedovBlastWave/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/SedovBlastWave/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/SedovBlastWave/testme.py b/test/HD/SedovBlastWave/testme.py index 531debb54..4f7055850 100755 --- a/test/HD/SedovBlastWave/testme.py +++ b/test/HD/SedovBlastWave/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/SedovBlastWave/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/ShearingBox/CMakeLists.txt b/test/HD/ShearingBox/CMakeLists.txt index f4b25bfde..9b5f5c3d6 100644 --- a/test/HD/ShearingBox/CMakeLists.txt +++ b/test/HD/ShearingBox/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ShearingBox/CMakeLists.txt +# +# Last modified : 10/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # add specific source file to idefix build tree add_idefix_source(analysis.cpp) add_idefix_source(analysis.hpp) diff --git a/test/HD/ShearingBox/analysis.cpp b/test/HD/ShearingBox/analysis.cpp index dacf2a70c..d01c58a24 100644 --- a/test/HD/ShearingBox/analysis.cpp +++ b/test/HD/ShearingBox/analysis.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ShearingBox/analysis.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "analysis.hpp" #include "idefix.hpp" #include "fluid.hpp" diff --git a/test/HD/ShearingBox/analysis.hpp b/test/HD/ShearingBox/analysis.hpp index 8b65c4317..1634a6329 100644 --- a/test/HD/ShearingBox/analysis.hpp +++ b/test/HD/ShearingBox/analysis.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ShearingBox/analysis.hpp +// +// Last modified : 06/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #ifndef ANALYSIS_HPP_ #define ANALYSIS_HPP_ diff --git a/test/HD/ShearingBox/definitions.hpp b/test/HD/ShearingBox/definitions.hpp index 3b581bd62..592f215ec 100644 --- a/test/HD/ShearingBox/definitions.hpp +++ b/test/HD/ShearingBox/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ShearingBox/definitions.hpp +// +// Last modified : 06/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/HD/ShearingBox/python/testidefix.py b/test/HD/ShearingBox/python/testidefix.py index db04f443b..14da6db86 100755 --- a/test/HD/ShearingBox/python/testidefix.py +++ b/test/HD/ShearingBox/python/testidefix.py @@ -1,5 +1,20 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ShearingBox/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- + """ Created on Mon Jun 21 15:42:19 2021 diff --git a/test/HD/ShearingBox/setup.cpp b/test/HD/ShearingBox/setup.cpp index e82701d0c..0be990299 100644 --- a/test/HD/ShearingBox/setup.cpp +++ b/test/HD/ShearingBox/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ShearingBox/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "analysis.hpp" diff --git a/test/HD/ShearingBox/testme.py b/test/HD/ShearingBox/testme.py index 28d61fc06..445f28218 100755 --- a/test/HD/ShearingBox/testme.py +++ b/test/HD/ShearingBox/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ShearingBox/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/VSI/definitions.hpp b/test/HD/VSI/definitions.hpp index 016442642..2fb48ee23 100644 --- a/test/HD/VSI/definitions.hpp +++ b/test/HD/VSI/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/VSI/definitions.hpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/HD/VSI/setup.cpp b/test/HD/VSI/setup.cpp index 19800e67d..e048dfc10 100644 --- a/test/HD/VSI/setup.cpp +++ b/test/HD/VSI/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/VSI/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/ViscousDisk/definitions.hpp b/test/HD/ViscousDisk/definitions.hpp index 016442642..97bf72ccb 100644 --- a/test/HD/ViscousDisk/definitions.hpp +++ b/test/HD/ViscousDisk/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ViscousDisk/definitions.hpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/HD/ViscousDisk/python/testidefix.py b/test/HD/ViscousDisk/python/testidefix.py index 6e9ef66f0..d5309031a 100755 --- a/test/HD/ViscousDisk/python/testidefix.py +++ b/test/HD/ViscousDisk/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ViscousDisk/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/HD/ViscousDisk/setup.cpp b/test/HD/ViscousDisk/setup.cpp index 826b0dc9d..f03e6cb81 100644 --- a/test/HD/ViscousDisk/setup.cpp +++ b/test/HD/ViscousDisk/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ViscousDisk/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/ViscousDisk/testme.py b/test/HD/ViscousDisk/testme.py index 8dd6bab3c..8706b335a 100755 --- a/test/HD/ViscousDisk/testme.py +++ b/test/HD/ViscousDisk/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ViscousDisk/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/ViscousFlowPastCylinder/definitions.hpp b/test/HD/ViscousFlowPastCylinder/definitions.hpp index 381b71f77..5f296e097 100644 --- a/test/HD/ViscousFlowPastCylinder/definitions.hpp +++ b/test/HD/ViscousFlowPastCylinder/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ViscousFlowPastCylinder/definitions.hpp +// +// Last modified : 12/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 #define ISOTHERMAL diff --git a/test/HD/ViscousFlowPastCylinder/setup.cpp b/test/HD/ViscousFlowPastCylinder/setup.cpp index 1282ac0ce..0cddac102 100644 --- a/test/HD/ViscousFlowPastCylinder/setup.cpp +++ b/test/HD/ViscousFlowPastCylinder/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/ViscousFlowPastCylinder/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/ViscousFlowPastCylinder/testme.py b/test/HD/ViscousFlowPastCylinder/testme.py index fbee068fe..cd0b0c90e 100755 --- a/test/HD/ViscousFlowPastCylinder/testme.py +++ b/test/HD/ViscousFlowPastCylinder/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/ViscousFlowPastCylinder/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/sod-iso/definitions.hpp b/test/HD/sod-iso/definitions.hpp index cdbe23d6e..fb40286e0 100644 --- a/test/HD/sod-iso/definitions.hpp +++ b/test/HD/sod-iso/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/sod-iso/definitions.hpp +// +// Last modified : 10/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/HD/sod-iso/python/testidefix.py b/test/HD/sod-iso/python/testidefix.py index 46c0bfce0..d02f373c9 100755 --- a/test/HD/sod-iso/python/testidefix.py +++ b/test/HD/sod-iso/python/testidefix.py @@ -1,5 +1,20 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/sod-iso/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- + """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/HD/sod-iso/setup.cpp b/test/HD/sod-iso/setup.cpp index a32365569..b62089615 100644 --- a/test/HD/sod-iso/setup.cpp +++ b/test/HD/sod-iso/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/sod-iso/setup.cpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/sod-iso/testme.py b/test/HD/sod-iso/testme.py index aeb3f6e72..96a194b3c 100755 --- a/test/HD/sod-iso/testme.py +++ b/test/HD/sod-iso/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/sod-iso/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/sod/definitions.hpp b/test/HD/sod/definitions.hpp index 498be97af..ed56869e4 100644 --- a/test/HD/sod/definitions.hpp +++ b/test/HD/sod/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/sod/definitions.hpp +// +// Last modified : 03/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/HD/sod/pydefix_example.py b/test/HD/sod/pydefix_example.py index 39c240353..374c61521 100644 --- a/test/HD/sod/pydefix_example.py +++ b/test/HD/sod/pydefix_example.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/sod/pydefix_example.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import matplotlib.pyplot as plt import numpy as np import pydefix as pdfx diff --git a/test/HD/sod/python/testidefix.py b/test/HD/sod/python/testidefix.py index f0cbf425c..9256f916d 100755 --- a/test/HD/sod/python/testidefix.py +++ b/test/HD/sod/python/testidefix.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/sod/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/HD/sod/setup.cpp b/test/HD/sod/setup.cpp index 92668f096..8e14984bc 100644 --- a/test/HD/sod/setup.cpp +++ b/test/HD/sod/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/sod/setup.cpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/sod/testme.py b/test/HD/sod/testme.py index aeb3f6e72..55669c7a4 100755 --- a/test/HD/sod/testme.py +++ b/test/HD/sod/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/sod/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/HD/thermalDiffusion/definitions.hpp b/test/HD/thermalDiffusion/definitions.hpp index 3b581bd62..0f3db9bfc 100644 --- a/test/HD/thermalDiffusion/definitions.hpp +++ b/test/HD/thermalDiffusion/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/thermalDiffusion/definitions.hpp +// +// Last modified : 02/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/HD/thermalDiffusion/python/testidefix.py b/test/HD/thermalDiffusion/python/testidefix.py index b24777a9c..3562a5b37 100755 --- a/test/HD/thermalDiffusion/python/testidefix.py +++ b/test/HD/thermalDiffusion/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/thermalDiffusion/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- import argparse diff --git a/test/HD/thermalDiffusion/setup.cpp b/test/HD/thermalDiffusion/setup.cpp index dab61a16f..508fb113c 100644 --- a/test/HD/thermalDiffusion/setup.cpp +++ b/test/HD/thermalDiffusion/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/HD/thermalDiffusion/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/HD/thermalDiffusion/testme.py b/test/HD/thermalDiffusion/testme.py index 14c438ae3..9243703e8 100755 --- a/test/HD/thermalDiffusion/testme.py +++ b/test/HD/thermalDiffusion/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/HD/thermalDiffusion/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/IO/dump/CMakeLists.txt b/test/IO/dump/CMakeLists.txt index 629aed2d1..aba9c2789 100644 --- a/test/IO/dump/CMakeLists.txt +++ b/test/IO/dump/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/dump/CMakeLists.txt +# +# Last modified : 03/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/IO/dump/definitions.hpp b/test/IO/dump/definitions.hpp index a854ad9e3..79d63eea8 100644 --- a/test/IO/dump/definitions.hpp +++ b/test/IO/dump/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/IO/dump/definitions.hpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 //#define DEBUG diff --git a/test/IO/dump/setup.cpp b/test/IO/dump/setup.cpp index 1db56f5b0..3b801a72c 100644 --- a/test/IO/dump/setup.cpp +++ b/test/IO/dump/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/IO/dump/setup.cpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/IO/dump/testme.py b/test/IO/dump/testme.py index 74eb7f8f2..622b89295 100755 --- a/test/IO/dump/testme.py +++ b/test/IO/dump/testme.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/dump/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + """ @author: glesur diff --git a/test/IO/pydefix/CMakeLists.txt b/test/IO/pydefix/CMakeLists.txt index 83d16a526..a9d4c1509 100644 --- a/test/IO/pydefix/CMakeLists.txt +++ b/test/IO/pydefix/CMakeLists.txt @@ -1,2 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/pydefix/CMakeLists.txt +# +# Last modified : 10/2024 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) enable_idefix_property(Idefix_PYTHON) diff --git a/test/IO/pydefix/definitions.hpp b/test/IO/pydefix/definitions.hpp index 69f0c49e9..d3f5578d8 100644 --- a/test/IO/pydefix/definitions.hpp +++ b/test/IO/pydefix/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/IO/pydefix/definitions.hpp +// +// Last modified : 10/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/IO/pydefix/pydefix_example.py b/test/IO/pydefix/pydefix_example.py index ffb1430ef..d5a90d13c 100644 --- a/test/IO/pydefix/pydefix_example.py +++ b/test/IO/pydefix/pydefix_example.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/pydefix/pydefix_example.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import matplotlib.pyplot as plt import numpy as np from pydefix import * diff --git a/test/IO/pydefix/testme.py b/test/IO/pydefix/testme.py index 7facac19c..bb033a225 100755 --- a/test/IO/pydefix/testme.py +++ b/test/IO/pydefix/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/pydefix/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/IO/xdmf/CMakeLists.txt b/test/IO/xdmf/CMakeLists.txt index 8ce9e0f4d..57298314e 100644 --- a/test/IO/xdmf/CMakeLists.txt +++ b/test/IO/xdmf/CMakeLists.txt @@ -1,2 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/xdmf/CMakeLists.txt +# +# Last modified : 03/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) enable_idefix_property(Idefix_HDF5) diff --git a/test/IO/xdmf/definitions.hpp b/test/IO/xdmf/definitions.hpp index a854ad9e3..26084767a 100644 --- a/test/IO/xdmf/definitions.hpp +++ b/test/IO/xdmf/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/IO/xdmf/definitions.hpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 //#define DEBUG diff --git a/test/IO/xdmf/setup.cpp b/test/IO/xdmf/setup.cpp index 8cc40857f..c46bdaa09 100644 --- a/test/IO/xdmf/setup.cpp +++ b/test/IO/xdmf/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/IO/xdmf/setup.cpp +// +// Last modified : 03/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/IO/xdmf/testme.py b/test/IO/xdmf/testme.py index ec7340d72..41c709930 100755 --- a/test/IO/xdmf/testme.py +++ b/test/IO/xdmf/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/IO/xdmf/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2026) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/AmbipolarCshock/CMakeLists.txt b/test/MHD/AmbipolarCshock/CMakeLists.txt index 629aed2d1..b42e6deac 100644 --- a/test/MHD/AmbipolarCshock/CMakeLists.txt +++ b/test/MHD/AmbipolarCshock/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/AmbipolarCshock/definitions.hpp b/test/MHD/AmbipolarCshock/definitions.hpp index 3008864ea..31051165f 100644 --- a/test/MHD/AmbipolarCshock/definitions.hpp +++ b/test/MHD/AmbipolarCshock/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarCshock/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/MHD/AmbipolarCshock/python/testidefix.py b/test/MHD/AmbipolarCshock/python/testidefix.py index 3544426ec..c75a1b63d 100755 --- a/test/MHD/AmbipolarCshock/python/testidefix.py +++ b/test/MHD/AmbipolarCshock/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Sep 8 09:10:06 2020 diff --git a/test/MHD/AmbipolarCshock/setup.cpp b/test/MHD/AmbipolarCshock/setup.cpp index 65f42ffdb..b3a11d876 100644 --- a/test/MHD/AmbipolarCshock/setup.cpp +++ b/test/MHD/AmbipolarCshock/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarCshock/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/AmbipolarCshock/testme.py b/test/MHD/AmbipolarCshock/testme.py index 1b3f843f7..e89e27f24 100755 --- a/test/MHD/AmbipolarCshock/testme.py +++ b/test/MHD/AmbipolarCshock/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/AmbipolarCshock3D/CMakeLists.txt b/test/MHD/AmbipolarCshock3D/CMakeLists.txt index 629aed2d1..bbc860a76 100644 --- a/test/MHD/AmbipolarCshock3D/CMakeLists.txt +++ b/test/MHD/AmbipolarCshock3D/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock3D/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/AmbipolarCshock3D/definitions.hpp b/test/MHD/AmbipolarCshock3D/definitions.hpp index f023918fa..1c517331f 100644 --- a/test/MHD/AmbipolarCshock3D/definitions.hpp +++ b/test/MHD/AmbipolarCshock3D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarCshock3D/definitions.hpp +// +// Last modified : 05/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 #define ISOTHERMAL diff --git a/test/MHD/AmbipolarCshock3D/python/testidefix.py b/test/MHD/AmbipolarCshock3D/python/testidefix.py index 2e62c09d6..08361ab6a 100755 --- a/test/MHD/AmbipolarCshock3D/python/testidefix.py +++ b/test/MHD/AmbipolarCshock3D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock3D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Sep 8 09:10:06 2020 diff --git a/test/MHD/AmbipolarCshock3D/setup.cpp b/test/MHD/AmbipolarCshock3D/setup.cpp index abf8a0f24..5defddcf2 100644 --- a/test/MHD/AmbipolarCshock3D/setup.cpp +++ b/test/MHD/AmbipolarCshock3D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarCshock3D/setup.cpp +// +// Last modified : 12/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/AmbipolarCshock3D/testme.py b/test/MHD/AmbipolarCshock3D/testme.py index 37363d5bc..42a3eb46e 100755 --- a/test/MHD/AmbipolarCshock3D/testme.py +++ b/test/MHD/AmbipolarCshock3D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarCshock3D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/AmbipolarShearingBox/CMakeLists.txt b/test/MHD/AmbipolarShearingBox/CMakeLists.txt index 629aed2d1..59e586822 100644 --- a/test/MHD/AmbipolarShearingBox/CMakeLists.txt +++ b/test/MHD/AmbipolarShearingBox/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarShearingBox/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/AmbipolarShearingBox/definitions.hpp b/test/MHD/AmbipolarShearingBox/definitions.hpp index 3b581bd62..e1127b289 100644 --- a/test/MHD/AmbipolarShearingBox/definitions.hpp +++ b/test/MHD/AmbipolarShearingBox/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarShearingBox/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/AmbipolarShearingBox/python/testidefix.py b/test/MHD/AmbipolarShearingBox/python/testidefix.py index 779ecfae2..c00531950 100755 --- a/test/MHD/AmbipolarShearingBox/python/testidefix.py +++ b/test/MHD/AmbipolarShearingBox/python/testidefix.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarShearingBox/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Wed Sep 9 15:31:57 2020 diff --git a/test/MHD/AmbipolarShearingBox/setup.cpp b/test/MHD/AmbipolarShearingBox/setup.cpp index 8c9092fd5..e5bf314b1 100644 --- a/test/MHD/AmbipolarShearingBox/setup.cpp +++ b/test/MHD/AmbipolarShearingBox/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarShearingBox/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/AmbipolarWind/CMakeLists.txt b/test/MHD/AmbipolarWind/CMakeLists.txt index 629aed2d1..ff27f6c18 100644 --- a/test/MHD/AmbipolarWind/CMakeLists.txt +++ b/test/MHD/AmbipolarWind/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AmbipolarWind/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/AmbipolarWind/definitions.hpp b/test/MHD/AmbipolarWind/definitions.hpp index fbf0a7c45..71c25745f 100644 --- a/test/MHD/AmbipolarWind/definitions.hpp +++ b/test/MHD/AmbipolarWind/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarWind/definitions.hpp +// +// Last modified : 12/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/MHD/AmbipolarWind/setup.cpp b/test/MHD/AmbipolarWind/setup.cpp index 99b45ba8f..6bc801347 100644 --- a/test/MHD/AmbipolarWind/setup.cpp +++ b/test/MHD/AmbipolarWind/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AmbipolarWind/setup.cpp +// +// Last modified : 06/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/AxisFluxTube/CMakeLists.txt b/test/MHD/AxisFluxTube/CMakeLists.txt index 629aed2d1..e3c70540e 100644 --- a/test/MHD/AxisFluxTube/CMakeLists.txt +++ b/test/MHD/AxisFluxTube/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AxisFluxTube/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/AxisFluxTube/definitions.hpp b/test/MHD/AxisFluxTube/definitions.hpp index 53b4f38e3..696a44229 100644 --- a/test/MHD/AxisFluxTube/definitions.hpp +++ b/test/MHD/AxisFluxTube/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AxisFluxTube/definitions.hpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/AxisFluxTube/python/checkAxisBounds.py b/test/MHD/AxisFluxTube/python/checkAxisBounds.py index cb313a44e..a63f26e49 100755 --- a/test/MHD/AxisFluxTube/python/checkAxisBounds.py +++ b/test/MHD/AxisFluxTube/python/checkAxisBounds.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AxisFluxTube/python/checkAxisBounds.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Jan 26 15:52:44 2021 diff --git a/test/MHD/AxisFluxTube/setup.cpp b/test/MHD/AxisFluxTube/setup.cpp index 4c30506d3..7819bc4e1 100644 --- a/test/MHD/AxisFluxTube/setup.cpp +++ b/test/MHD/AxisFluxTube/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/AxisFluxTube/setup.cpp +// +// Last modified : 03/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/AxisFluxTube/testme.py b/test/MHD/AxisFluxTube/testme.py index f027b24b4..f3bc4c1c8 100755 --- a/test/MHD/AxisFluxTube/testme.py +++ b/test/MHD/AxisFluxTube/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/AxisFluxTube/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/Coarsening/CMakeLists.txt b/test/MHD/Coarsening/CMakeLists.txt index 629aed2d1..129d1914a 100644 --- a/test/MHD/Coarsening/CMakeLists.txt +++ b/test/MHD/Coarsening/CMakeLists.txt @@ -1 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/Coarsening/CMakeLists.txt +# +# Last modified : 03/2024 +# +# Copyright(C) by : +# - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/Coarsening/definitions.hpp b/test/MHD/Coarsening/definitions.hpp index 10b5f5f10..bac087ffb 100644 --- a/test/MHD/Coarsening/definitions.hpp +++ b/test/MHD/Coarsening/definitions.hpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/Coarsening/definitions.hpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/Coarsening/python/testidefix.py b/test/MHD/Coarsening/python/testidefix.py index 32b60711b..12158561c 100755 --- a/test/MHD/Coarsening/python/testidefix.py +++ b/test/MHD/Coarsening/python/testidefix.py @@ -1,4 +1,20 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/Coarsening/python/testidefix.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/MHD/Coarsening/setup.cpp b/test/MHD/Coarsening/setup.cpp index a7683eee6..8e10b7fb7 100644 --- a/test/MHD/Coarsening/setup.cpp +++ b/test/MHD/Coarsening/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/Coarsening/setup.cpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/Coarsening/testme.py b/test/MHD/Coarsening/testme.py index c1e63ac80..993f53127 100755 --- a/test/MHD/Coarsening/testme.py +++ b/test/MHD/Coarsening/testme.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/Coarsening/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2024) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/FargoMHDSpherical/CMakeLists.txt b/test/MHD/FargoMHDSpherical/CMakeLists.txt index 629aed2d1..f2b64435d 100644 --- a/test/MHD/FargoMHDSpherical/CMakeLists.txt +++ b/test/MHD/FargoMHDSpherical/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/FargoMHDSpherical/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/FargoMHDSpherical/definitions.hpp b/test/MHD/FargoMHDSpherical/definitions.hpp index b2aa4ab59..8e01162a5 100644 --- a/test/MHD/FargoMHDSpherical/definitions.hpp +++ b/test/MHD/FargoMHDSpherical/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/FargoMHDSpherical/definitions.hpp +// +// Last modified : 04/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 #define ISOTHERMAL diff --git a/test/MHD/FargoMHDSpherical/setup.cpp b/test/MHD/FargoMHDSpherical/setup.cpp index 0ff536997..45cce8f51 100644 --- a/test/MHD/FargoMHDSpherical/setup.cpp +++ b/test/MHD/FargoMHDSpherical/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/FargoMHDSpherical/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/FargoMHDSpherical/testme.py b/test/MHD/FargoMHDSpherical/testme.py index 5f003ed52..c8a286aa3 100755 --- a/test/MHD/FargoMHDSpherical/testme.py +++ b/test/MHD/FargoMHDSpherical/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/FargoMHDSpherical/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/FieldLoop/CMakeLists.txt b/test/MHD/FieldLoop/CMakeLists.txt index 629aed2d1..08ba5edb3 100644 --- a/test/MHD/FieldLoop/CMakeLists.txt +++ b/test/MHD/FieldLoop/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/FieldLoop/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/FieldLoop/definitions.hpp b/test/MHD/FieldLoop/definitions.hpp index 3b581bd62..e05bf33d5 100644 --- a/test/MHD/FieldLoop/definitions.hpp +++ b/test/MHD/FieldLoop/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/FieldLoop/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/FieldLoop/setup.cpp b/test/MHD/FieldLoop/setup.cpp index d1ea953ec..537506e31 100644 --- a/test/MHD/FieldLoop/setup.cpp +++ b/test/MHD/FieldLoop/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/FieldLoop/setup.cpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/HallDisk/CMakeLists.txt b/test/MHD/HallDisk/CMakeLists.txt index 629aed2d1..ed644dd4b 100644 --- a/test/MHD/HallDisk/CMakeLists.txt +++ b/test/MHD/HallDisk/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/HallDisk/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/HallDisk/definitions.hpp b/test/MHD/HallDisk/definitions.hpp index 993757b1d..4ba9f6cee 100644 --- a/test/MHD/HallDisk/definitions.hpp +++ b/test/MHD/HallDisk/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/HallDisk/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/HallDisk/setup.cpp b/test/MHD/HallDisk/setup.cpp index 641126aba..4c6c1ba01 100644 --- a/test/MHD/HallDisk/setup.cpp +++ b/test/MHD/HallDisk/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/HallDisk/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/HallWhistler/CMakeLists.txt b/test/MHD/HallWhistler/CMakeLists.txt index 629aed2d1..51ba83ef4 100644 --- a/test/MHD/HallWhistler/CMakeLists.txt +++ b/test/MHD/HallWhistler/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/HallWhistler/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/HallWhistler/definitions.hpp b/test/MHD/HallWhistler/definitions.hpp index 3b581bd62..a5ab09e2b 100644 --- a/test/MHD/HallWhistler/definitions.hpp +++ b/test/MHD/HallWhistler/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/HallWhistler/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/HallWhistler/python/testidefix.py b/test/MHD/HallWhistler/python/testidefix.py index 2e08f387c..6ed8e1f29 100755 --- a/test/MHD/HallWhistler/python/testidefix.py +++ b/test/MHD/HallWhistler/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/HallWhistler/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2021 - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Sep 10 15:33:28 2020 diff --git a/test/MHD/HallWhistler/setup.cpp b/test/MHD/HallWhistler/setup.cpp index df281f8d4..a83b32186 100644 --- a/test/MHD/HallWhistler/setup.cpp +++ b/test/MHD/HallWhistler/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/HallWhistler/setup.cpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include diff --git a/test/MHD/HallWhistler/testme.py b/test/MHD/HallWhistler/testme.py index 2e0b0abc0..94d1fbd1f 100755 --- a/test/MHD/HallWhistler/testme.py +++ b/test/MHD/HallWhistler/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/HallWhistler/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/LinearWaveTest/CMakeLists.txt b/test/MHD/LinearWaveTest/CMakeLists.txt index 629aed2d1..9de2eff6b 100644 --- a/test/MHD/LinearWaveTest/CMakeLists.txt +++ b/test/MHD/LinearWaveTest/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/LinearWaveTest/CMakeLists.txt +# +# Last modified : 07/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/LinearWaveTest/definitions.hpp b/test/MHD/LinearWaveTest/definitions.hpp index 10b5f5f10..05f2b16dc 100644 --- a/test/MHD/LinearWaveTest/definitions.hpp +++ b/test/MHD/LinearWaveTest/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/LinearWaveTest/definitions.hpp +// +// Last modified : 07/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/LinearWaveTest/python/testidefix.py b/test/MHD/LinearWaveTest/python/testidefix.py index f15559915..b609da3c1 100755 --- a/test/MHD/LinearWaveTest/python/testidefix.py +++ b/test/MHD/LinearWaveTest/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/LinearWaveTest/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- import math diff --git a/test/MHD/LinearWaveTest/setup.cpp b/test/MHD/LinearWaveTest/setup.cpp index 06f8a7002..5fe1e42dd 100644 --- a/test/MHD/LinearWaveTest/setup.cpp +++ b/test/MHD/LinearWaveTest/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/LinearWaveTest/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/LinearWaveTest/testme.py b/test/MHD/LinearWaveTest/testme.py index 4e6ae7498..a3e2256c7 100755 --- a/test/MHD/LinearWaveTest/testme.py +++ b/test/MHD/LinearWaveTest/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/LinearWaveTest/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/MTI/CMakeLists.txt b/test/MHD/MTI/CMakeLists.txt index 7fcdaa863..62d9a282c 100644 --- a/test/MHD/MTI/CMakeLists.txt +++ b/test/MHD/MTI/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/MTI/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + set_idefix_property(Idefix_RECONSTRUCTION LimO3) enable_idefix_property(Idefix_MHD) add_idefix_source(analysis.hpp) diff --git a/test/MHD/MTI/analysis.cpp b/test/MHD/MTI/analysis.cpp index d0065cf9f..e7cd714fe 100644 --- a/test/MHD/MTI/analysis.cpp +++ b/test/MHD/MTI/analysis.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/MTI/analysis.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include diff --git a/test/MHD/MTI/analysis.hpp b/test/MHD/MTI/analysis.hpp index 9f8b9707a..3887e711d 100644 --- a/test/MHD/MTI/analysis.hpp +++ b/test/MHD/MTI/analysis.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/MTI/analysis.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #ifndef ANALYSIS_HPP_ #define ANALYSIS_HPP_ diff --git a/test/MHD/MTI/definitions.hpp b/test/MHD/MTI/definitions.hpp index 69f0c49e9..c6cce9495 100644 --- a/test/MHD/MTI/definitions.hpp +++ b/test/MHD/MTI/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/MTI/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/MHD/MTI/python/testidefix.py b/test/MHD/MTI/python/testidefix.py index 278366eb9..770c5681e 100644 --- a/test/MHD/MTI/python/testidefix.py +++ b/test/MHD/MTI/python/testidefix.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/MTI/python/testidefix.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + """ Created in July 2021 diff --git a/test/MHD/MTI/setup.cpp b/test/MHD/MTI/setup.cpp index 552f76465..0149d996b 100644 --- a/test/MHD/MTI/setup.cpp +++ b/test/MHD/MTI/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/MTI/setup.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// - Victor Réville (IRAP - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "analysis.hpp" diff --git a/test/MHD/MTI/testme.py b/test/MHD/MTI/testme.py index cb145f3a6..afc50362a 100755 --- a/test/MHD/MTI/testme.py +++ b/test/MHD/MTI/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/MTI/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/OrszagTang/CMakeLists.txt b/test/MHD/OrszagTang/CMakeLists.txt index 629aed2d1..74e1a3df5 100644 --- a/test/MHD/OrszagTang/CMakeLists.txt +++ b/test/MHD/OrszagTang/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/OrszagTang/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/OrszagTang/definitions.hpp b/test/MHD/OrszagTang/definitions.hpp index 69f0c49e9..581c79b3e 100644 --- a/test/MHD/OrszagTang/definitions.hpp +++ b/test/MHD/OrszagTang/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/OrszagTang/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/MHD/OrszagTang/setup.cpp b/test/MHD/OrszagTang/setup.cpp index b337ff6bf..21114ce88 100644 --- a/test/MHD/OrszagTang/setup.cpp +++ b/test/MHD/OrszagTang/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/OrszagTang/setup.cpp +// +// Last modified : 09/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/OrszagTang/testme.py b/test/MHD/OrszagTang/testme.py index 3c0e56bc2..e7d8c005e 100755 --- a/test/MHD/OrszagTang/testme.py +++ b/test/MHD/OrszagTang/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/OrszagTang/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/OrszagTang3D/CMakeLists.txt b/test/MHD/OrszagTang3D/CMakeLists.txt index 629aed2d1..4a457930c 100644 --- a/test/MHD/OrszagTang3D/CMakeLists.txt +++ b/test/MHD/OrszagTang3D/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/OrszagTang3D/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/OrszagTang3D/definitions.hpp b/test/MHD/OrszagTang3D/definitions.hpp index a854ad9e3..92e7ff34a 100644 --- a/test/MHD/OrszagTang3D/definitions.hpp +++ b/test/MHD/OrszagTang3D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/OrszagTang3D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 //#define DEBUG diff --git a/test/MHD/OrszagTang3D/setup.cpp b/test/MHD/OrszagTang3D/setup.cpp index abbc78534..2f20958a1 100644 --- a/test/MHD/OrszagTang3D/setup.cpp +++ b/test/MHD/OrszagTang3D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/OrszagTang3D/setup.cpp +// +// Last modified : 09/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/OrszagTang3D/testme.py b/test/MHD/OrszagTang3D/testme.py index 885da1dea..20caf4501 100755 --- a/test/MHD/OrszagTang3D/testme.py +++ b/test/MHD/OrszagTang3D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/OrszagTang3D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ @author: glesur diff --git a/test/MHD/ResistiveAlfvenWave/CMakeLists.txt b/test/MHD/ResistiveAlfvenWave/CMakeLists.txt index 629aed2d1..cfb97d069 100644 --- a/test/MHD/ResistiveAlfvenWave/CMakeLists.txt +++ b/test/MHD/ResistiveAlfvenWave/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ResistiveAlfvenWave/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/ResistiveAlfvenWave/definitions.hpp b/test/MHD/ResistiveAlfvenWave/definitions.hpp index 536d96048..664f3d0aa 100644 --- a/test/MHD/ResistiveAlfvenWave/definitions.hpp +++ b/test/MHD/ResistiveAlfvenWave/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ResistiveAlfvenWave/definitions.hpp +// +// Last modified : 09/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 1 diff --git a/test/MHD/ResistiveAlfvenWave/python/testidefix.py b/test/MHD/ResistiveAlfvenWave/python/testidefix.py index c221544dc..9e70fba53 100644 --- a/test/MHD/ResistiveAlfvenWave/python/testidefix.py +++ b/test/MHD/ResistiveAlfvenWave/python/testidefix.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ResistiveAlfvenWave/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import argparse import sys diff --git a/test/MHD/ResistiveAlfvenWave/setup.cpp b/test/MHD/ResistiveAlfvenWave/setup.cpp index d03f583eb..9bfa7f48a 100644 --- a/test/MHD/ResistiveAlfvenWave/setup.cpp +++ b/test/MHD/ResistiveAlfvenWave/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ResistiveAlfvenWave/setup.cpp +// +// Last modified : 11/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/ResistiveAlfvenWave/testme.py b/test/MHD/ResistiveAlfvenWave/testme.py index b7ce4a73c..c9579d6f5 100755 --- a/test/MHD/ResistiveAlfvenWave/testme.py +++ b/test/MHD/ResistiveAlfvenWave/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ResistiveAlfvenWave/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/RotorCartesian/CMakeLists.txt b/test/MHD/RotorCartesian/CMakeLists.txt index 629aed2d1..c52e9b969 100644 --- a/test/MHD/RotorCartesian/CMakeLists.txt +++ b/test/MHD/RotorCartesian/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/RotorCartesian/CMakeLists.txt +# +# Last modified : 08/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/RotorCartesian/definitions.hpp b/test/MHD/RotorCartesian/definitions.hpp index 69f0c49e9..b2f7f3895 100644 --- a/test/MHD/RotorCartesian/definitions.hpp +++ b/test/MHD/RotorCartesian/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/RotorCartesian/definitions.hpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/MHD/RotorCartesian/setup.cpp b/test/MHD/RotorCartesian/setup.cpp index c2e668b9a..4f85c6d22 100644 --- a/test/MHD/RotorCartesian/setup.cpp +++ b/test/MHD/RotorCartesian/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/RotorCartesian/setup.cpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/RotorPolar/CMakeLists.txt b/test/MHD/RotorPolar/CMakeLists.txt index 629aed2d1..da8966d2c 100644 --- a/test/MHD/RotorPolar/CMakeLists.txt +++ b/test/MHD/RotorPolar/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/RotorPolar/CMakeLists.txt +# +# Last modified : 08/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/RotorPolar/definitions.hpp b/test/MHD/RotorPolar/definitions.hpp index fe0999f1c..c86114d84 100644 --- a/test/MHD/RotorPolar/definitions.hpp +++ b/test/MHD/RotorPolar/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/RotorPolar/definitions.hpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/MHD/RotorPolar/setup.cpp b/test/MHD/RotorPolar/setup.cpp index 7e0d910a8..981e0783d 100644 --- a/test/MHD/RotorPolar/setup.cpp +++ b/test/MHD/RotorPolar/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/RotorPolar/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/ShearingBox/CMakeLists.txt b/test/MHD/ShearingBox/CMakeLists.txt index 2ea4f2e12..51322c308 100644 --- a/test/MHD/ShearingBox/CMakeLists.txt +++ b/test/MHD/ShearingBox/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ShearingBox/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # add specific source file to idefix build tree add_idefix_source(analysis.cpp) add_idefix_source(analysis.hpp) diff --git a/test/MHD/ShearingBox/analysis.cpp b/test/MHD/ShearingBox/analysis.cpp index c227c3fa8..cf9a3e704 100644 --- a/test/MHD/ShearingBox/analysis.cpp +++ b/test/MHD/ShearingBox/analysis.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ShearingBox/analysis.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "analysis.hpp" #include "idefix.hpp" #include "fluid.hpp" diff --git a/test/MHD/ShearingBox/analysis.hpp b/test/MHD/ShearingBox/analysis.hpp index 3a0633f37..602a4610f 100644 --- a/test/MHD/ShearingBox/analysis.hpp +++ b/test/MHD/ShearingBox/analysis.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ShearingBox/analysis.hpp +// +// Last modified : 08/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #ifndef ANALYSIS_HPP_ #define ANALYSIS_HPP_ diff --git a/test/MHD/ShearingBox/definitions.hpp b/test/MHD/ShearingBox/definitions.hpp index 3b581bd62..314c63853 100644 --- a/test/MHD/ShearingBox/definitions.hpp +++ b/test/MHD/ShearingBox/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ShearingBox/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/ShearingBox/python/testidefix.py b/test/MHD/ShearingBox/python/testidefix.py index 559c6c6ff..f9056c99f 100755 --- a/test/MHD/ShearingBox/python/testidefix.py +++ b/test/MHD/ShearingBox/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ShearingBox/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Mon Jun 21 15:42:19 2021 diff --git a/test/MHD/ShearingBox/setup.cpp b/test/MHD/ShearingBox/setup.cpp index fb25092a6..c1219f6e1 100644 --- a/test/MHD/ShearingBox/setup.cpp +++ b/test/MHD/ShearingBox/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/ShearingBox/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "analysis.hpp" diff --git a/test/MHD/ShearingBox/testme.py b/test/MHD/ShearingBox/testme.py index 0d782c1c5..be3a43703 100755 --- a/test/MHD/ShearingBox/testme.py +++ b/test/MHD/ShearingBox/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/ShearingBox/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/advectionOBlique/CMakeLists.txt b/test/MHD/advectionOBlique/CMakeLists.txt index 629aed2d1..e5aa0071f 100644 --- a/test/MHD/advectionOBlique/CMakeLists.txt +++ b/test/MHD/advectionOBlique/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/advectionOBlique/CMakeLists.txt +# +# Last modified : 08/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/advectionOBlique/definitions.hpp b/test/MHD/advectionOBlique/definitions.hpp index 3b581bd62..67014485d 100644 --- a/test/MHD/advectionOBlique/definitions.hpp +++ b/test/MHD/advectionOBlique/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/advectionOBlique/definitions.hpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/advectionOBlique/setup.cpp b/test/MHD/advectionOBlique/setup.cpp index 594a38e39..ddc1dd208 100644 --- a/test/MHD/advectionOBlique/setup.cpp +++ b/test/MHD/advectionOBlique/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/advectionOBlique/setup.cpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/clessTDiffusion/CMakeLists.txt b/test/MHD/clessTDiffusion/CMakeLists.txt index 629aed2d1..98215b8d3 100644 --- a/test/MHD/clessTDiffusion/CMakeLists.txt +++ b/test/MHD/clessTDiffusion/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/clessTDiffusion/CMakeLists.txt +# +# Last modified : 01/2025 +# +# Copyright(C) by : +# - Victor Réville (IRAP - 2025) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/clessTDiffusion/definitions.hpp b/test/MHD/clessTDiffusion/definitions.hpp index 21b1f8733..ee11160cf 100644 --- a/test/MHD/clessTDiffusion/definitions.hpp +++ b/test/MHD/clessTDiffusion/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/clessTDiffusion/definitions.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Victor Réville (IRAP - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 1 #define GEOMETRY SPHERICAL diff --git a/test/MHD/clessTDiffusion/python/testidefix.py b/test/MHD/clessTDiffusion/python/testidefix.py index fac2d084f..091745f13 100644 --- a/test/MHD/clessTDiffusion/python/testidefix.py +++ b/test/MHD/clessTDiffusion/python/testidefix.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/clessTDiffusion/python/testidefix.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Victor Réville (IRAP - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import os import sys diff --git a/test/MHD/clessTDiffusion/setup.cpp b/test/MHD/clessTDiffusion/setup.cpp index c540c0def..4c16d3b0e 100644 --- a/test/MHD/clessTDiffusion/setup.cpp +++ b/test/MHD/clessTDiffusion/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/clessTDiffusion/setup.cpp +// +// Last modified : 02/2025 +// +// Copyright(C) by : +// - Victor Réville (IRAP - 2025) +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/clessTDiffusion/testme.py b/test/MHD/clessTDiffusion/testme.py index 0d1ca73c9..e7efc14f0 100755 --- a/test/MHD/clessTDiffusion/testme.py +++ b/test/MHD/clessTDiffusion/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/clessTDiffusion/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Victor Réville (IRAP - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/disk/CMakeLists.txt b/test/MHD/disk/CMakeLists.txt index 629aed2d1..74f85b679 100644 --- a/test/MHD/disk/CMakeLists.txt +++ b/test/MHD/disk/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/disk/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/disk/definitions.hpp b/test/MHD/disk/definitions.hpp index 993757b1d..11b3864e0 100644 --- a/test/MHD/disk/definitions.hpp +++ b/test/MHD/disk/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/disk/definitions.hpp +// +// Last modified : 08/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/disk/setup.cpp b/test/MHD/disk/setup.cpp index c59332077..4175fab42 100644 --- a/test/MHD/disk/setup.cpp +++ b/test/MHD/disk/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/disk/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/diskSpherical/CMakeLists.txt b/test/MHD/diskSpherical/CMakeLists.txt index 629aed2d1..a0ea4404e 100644 --- a/test/MHD/diskSpherical/CMakeLists.txt +++ b/test/MHD/diskSpherical/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/diskSpherical/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/diskSpherical/definitions.hpp b/test/MHD/diskSpherical/definitions.hpp index 0f44bb5b6..1c6a03830 100644 --- a/test/MHD/diskSpherical/definitions.hpp +++ b/test/MHD/diskSpherical/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/diskSpherical/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/diskSpherical/setup.cpp b/test/MHD/diskSpherical/setup.cpp index d18b6b7e9..8a811f505 100644 --- a/test/MHD/diskSpherical/setup.cpp +++ b/test/MHD/diskSpherical/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/diskSpherical/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2023) +// - Clément Robert (IPAG/UGA/CNRS - 2021 - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/sod-iso/CMakeLists.txt b/test/MHD/sod-iso/CMakeLists.txt index 629aed2d1..f0c9a00bf 100644 --- a/test/MHD/sod-iso/CMakeLists.txt +++ b/test/MHD/sod-iso/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sod-iso/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/sod-iso/definitions.hpp b/test/MHD/sod-iso/definitions.hpp index 3048637d7..1283eff1f 100644 --- a/test/MHD/sod-iso/definitions.hpp +++ b/test/MHD/sod-iso/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sod-iso/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/MHD/sod-iso/setup.cpp b/test/MHD/sod-iso/setup.cpp index d47c764e1..3473d9f32 100644 --- a/test/MHD/sod-iso/setup.cpp +++ b/test/MHD/sod-iso/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sod-iso/setup.cpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/sod-iso/testme.py b/test/MHD/sod-iso/testme.py index f559eeb17..a9cde01b9 100755 --- a/test/MHD/sod-iso/testme.py +++ b/test/MHD/sod-iso/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sod-iso/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/sod/CMakeLists.txt b/test/MHD/sod/CMakeLists.txt index 629aed2d1..1daac5ddb 100644 --- a/test/MHD/sod/CMakeLists.txt +++ b/test/MHD/sod/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sod/CMakeLists.txt +# +# Last modified : 12/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/sod/definitions.hpp b/test/MHD/sod/definitions.hpp index b19c2df81..51cfd1c46 100644 --- a/test/MHD/sod/definitions.hpp +++ b/test/MHD/sod/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sod/definitions.hpp +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 1 diff --git a/test/MHD/sod/setup.cpp b/test/MHD/sod/setup.cpp index 6a6d68ae8..062b06940 100644 --- a/test/MHD/sod/setup.cpp +++ b/test/MHD/sod/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sod/setup.cpp +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020 - 2021) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/sod/testme.py b/test/MHD/sod/testme.py index f559eeb17..167853581 100755 --- a/test/MHD/sod/testme.py +++ b/test/MHD/sod/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sod/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/sphBragTDiffusion/CMakeLists.txt b/test/MHD/sphBragTDiffusion/CMakeLists.txt index 629aed2d1..05093e1e3 100644 --- a/test/MHD/sphBragTDiffusion/CMakeLists.txt +++ b/test/MHD/sphBragTDiffusion/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragTDiffusion/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/MHD/sphBragTDiffusion/definitions.hpp b/test/MHD/sphBragTDiffusion/definitions.hpp index 53b4f38e3..57c73aee5 100644 --- a/test/MHD/sphBragTDiffusion/definitions.hpp +++ b/test/MHD/sphBragTDiffusion/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sphBragTDiffusion/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/sphBragTDiffusion/python/testidefix.py b/test/MHD/sphBragTDiffusion/python/testidefix.py index 2cd3655dd..481d2f2c8 100644 --- a/test/MHD/sphBragTDiffusion/python/testidefix.py +++ b/test/MHD/sphBragTDiffusion/python/testidefix.py @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragTDiffusion/python/testidefix.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### import os import sys diff --git a/test/MHD/sphBragTDiffusion/setup.cpp b/test/MHD/sphBragTDiffusion/setup.cpp index 41a45f010..2f1767d8b 100644 --- a/test/MHD/sphBragTDiffusion/setup.cpp +++ b/test/MHD/sphBragTDiffusion/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sphBragTDiffusion/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/sphBragTDiffusion/testme.py b/test/MHD/sphBragTDiffusion/testme.py index 0d1ca73c9..6fc21e43e 100755 --- a/test/MHD/sphBragTDiffusion/testme.py +++ b/test/MHD/sphBragTDiffusion/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragTDiffusion/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/MHD/sphBragViscosity/CMakeLists.txt b/test/MHD/sphBragViscosity/CMakeLists.txt index ba8dc8b1c..9659bd1f5 100644 --- a/test/MHD/sphBragViscosity/CMakeLists.txt +++ b/test/MHD/sphBragViscosity/CMakeLists.txt @@ -1,3 +1,17 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragViscosity/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) ## The current test is not physics, but merely a non-regression check ## The physical test needs to have the divergence of the velocity field artifiacially set to zero diff --git a/test/MHD/sphBragViscosity/definitions.hpp b/test/MHD/sphBragViscosity/definitions.hpp index efd699f11..bc825a20c 100644 --- a/test/MHD/sphBragViscosity/definitions.hpp +++ b/test/MHD/sphBragViscosity/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sphBragViscosity/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/MHD/sphBragViscosity/noDivBragViscosity.cpp b/test/MHD/sphBragViscosity/noDivBragViscosity.cpp index befb93d0c..b1af5886a 100644 --- a/test/MHD/sphBragViscosity/noDivBragViscosity.cpp +++ b/test/MHD/sphBragViscosity/noDivBragViscosity.cpp @@ -1,7 +1,14 @@ // *********************************************************************************** // Idefix MHD astrophysical code -// Copyright(C) Geoffroy R. J. Lesur +// +// Source file test/MHD/sphBragViscosity/noDivBragViscosity.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) // and other code contributors +// // Licensed under CeCILL 2.1 License, see COPYING for more information // *********************************************************************************** diff --git a/test/MHD/sphBragViscosity/python/testidefix.py b/test/MHD/sphBragViscosity/python/testidefix.py index 05ae619c0..c73cdfb9d 100644 --- a/test/MHD/sphBragViscosity/python/testidefix.py +++ b/test/MHD/sphBragViscosity/python/testidefix.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragViscosity/python/testidefix.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import os import sys diff --git a/test/MHD/sphBragViscosity/setup.cpp b/test/MHD/sphBragViscosity/setup.cpp index fa20e1684..f2f7df03e 100644 --- a/test/MHD/sphBragViscosity/setup.cpp +++ b/test/MHD/sphBragViscosity/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/MHD/sphBragViscosity/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" diff --git a/test/MHD/sphBragViscosity/testme.py b/test/MHD/sphBragViscosity/testme.py index 47c90c0ef..c63bdbd67 100755 --- a/test/MHD/sphBragViscosity/testme.py +++ b/test/MHD/sphBragViscosity/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/MHD/sphBragViscosity/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/Planet3Body/definitions.hpp b/test/Planet/Planet3Body/definitions.hpp index e2c9ceee3..e0b023a38 100644 --- a/test/Planet/Planet3Body/definitions.hpp +++ b/test/Planet/Planet3Body/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/Planet3Body/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 2 #define DIMENSIONS 2 diff --git a/test/Planet/Planet3Body/python/testidefix.py b/test/Planet/Planet3Body/python/testidefix.py index c66176f48..203b81962 100755 --- a/test/Planet/Planet3Body/python/testidefix.py +++ b/test/Planet/Planet3Body/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/Planet3Body/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Dec 21 12:04:41 2021 diff --git a/test/Planet/Planet3Body/setup.cpp b/test/Planet/Planet3Body/setup.cpp index 01bae094e..68d349aa4 100644 --- a/test/Planet/Planet3Body/setup.cpp +++ b/test/Planet/Planet3Body/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/Planet3Body/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/Planet3Body/testme.py b/test/Planet/Planet3Body/testme.py index 4a54d197c..c9c6056cf 100755 --- a/test/Planet/Planet3Body/testme.py +++ b/test/Planet/Planet3Body/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/Planet3Body/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/PlanetMigration2D/definitions.hpp b/test/Planet/PlanetMigration2D/definitions.hpp index 9ea3b16e5..36708e428 100644 --- a/test/Planet/PlanetMigration2D/definitions.hpp +++ b/test/Planet/PlanetMigration2D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetMigration2D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/Planet/PlanetMigration2D/python/testidefix.py b/test/Planet/PlanetMigration2D/python/testidefix.py index 3414df983..3c954fe6c 100755 --- a/test/Planet/PlanetMigration2D/python/testidefix.py +++ b/test/Planet/PlanetMigration2D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetMigration2D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Dec 21 12:04:41 2021 diff --git a/test/Planet/PlanetMigration2D/setup.cpp b/test/Planet/PlanetMigration2D/setup.cpp index c6ec4cb64..1c8b03ab6 100644 --- a/test/Planet/PlanetMigration2D/setup.cpp +++ b/test/Planet/PlanetMigration2D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetMigration2D/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/PlanetMigration2D/testme.py b/test/Planet/PlanetMigration2D/testme.py index 94c277343..90797e808 100755 --- a/test/Planet/PlanetMigration2D/testme.py +++ b/test/Planet/PlanetMigration2D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetMigration2D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/PlanetPlanetRK42D/definitions.hpp b/test/Planet/PlanetPlanetRK42D/definitions.hpp index bdda00a5d..4d1f27120 100644 --- a/test/Planet/PlanetPlanetRK42D/definitions.hpp +++ b/test/Planet/PlanetPlanetRK42D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetPlanetRK42D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/Planet/PlanetPlanetRK42D/python/testidefix.py b/test/Planet/PlanetPlanetRK42D/python/testidefix.py index fdb4aa2a0..49e618734 100755 --- a/test/Planet/PlanetPlanetRK42D/python/testidefix.py +++ b/test/Planet/PlanetPlanetRK42D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetPlanetRK42D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Dec 21 12:04:41 2021 diff --git a/test/Planet/PlanetPlanetRK42D/setup.cpp b/test/Planet/PlanetPlanetRK42D/setup.cpp index 912b77644..417bc2726 100644 --- a/test/Planet/PlanetPlanetRK42D/setup.cpp +++ b/test/Planet/PlanetPlanetRK42D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetPlanetRK42D/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/PlanetPlanetRK42D/testme.py b/test/Planet/PlanetPlanetRK42D/testme.py index 002ca263e..aea485b9f 100755 --- a/test/Planet/PlanetPlanetRK42D/testme.py +++ b/test/Planet/PlanetPlanetRK42D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetPlanetRK42D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/PlanetSpiral2D/definitions.hpp b/test/Planet/PlanetSpiral2D/definitions.hpp index 9ea3b16e5..f8a35e36e 100644 --- a/test/Planet/PlanetSpiral2D/definitions.hpp +++ b/test/Planet/PlanetSpiral2D/definitions.hpp @@ -1,3 +1,16 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetSpiral2D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/Planet/PlanetSpiral2D/python/testidefix.py b/test/Planet/PlanetSpiral2D/python/testidefix.py index e1dccb554..facbca2ee 100755 --- a/test/Planet/PlanetSpiral2D/python/testidefix.py +++ b/test/Planet/PlanetSpiral2D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetSpiral2D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # coding: utf-8 import os diff --git a/test/Planet/PlanetSpiral2D/setup.cpp b/test/Planet/PlanetSpiral2D/setup.cpp index 064d6c75b..94d4b7544 100644 --- a/test/Planet/PlanetSpiral2D/setup.cpp +++ b/test/Planet/PlanetSpiral2D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetSpiral2D/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/PlanetSpiral2D/testme.py b/test/Planet/PlanetSpiral2D/testme.py index 94c277343..35c7b0cef 100755 --- a/test/Planet/PlanetSpiral2D/testme.py +++ b/test/Planet/PlanetSpiral2D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetSpiral2D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/PlanetTorque3D/definitions.hpp b/test/Planet/PlanetTorque3D/definitions.hpp index a81d32864..a96f5f62e 100644 --- a/test/Planet/PlanetTorque3D/definitions.hpp +++ b/test/Planet/PlanetTorque3D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetTorque3D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/Planet/PlanetTorque3D/python/testidefix.py b/test/Planet/PlanetTorque3D/python/testidefix.py index ce8d911d5..a940d711a 100755 --- a/test/Planet/PlanetTorque3D/python/testidefix.py +++ b/test/Planet/PlanetTorque3D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetTorque3D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Dec 21 12:04:41 2021 diff --git a/test/Planet/PlanetTorque3D/setup.cpp b/test/Planet/PlanetTorque3D/setup.cpp index 367f49c8b..0b07e0a80 100644 --- a/test/Planet/PlanetTorque3D/setup.cpp +++ b/test/Planet/PlanetTorque3D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetTorque3D/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/PlanetTorque3D/testme.py b/test/Planet/PlanetTorque3D/testme.py index ab5e88603..634cf4745 100755 --- a/test/Planet/PlanetTorque3D/testme.py +++ b/test/Planet/PlanetTorque3D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetTorque3D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Planet/PlanetsIsActiveRK52D/definitions.hpp b/test/Planet/PlanetsIsActiveRK52D/definitions.hpp index bdda00a5d..0ab1b2d4c 100644 --- a/test/Planet/PlanetsIsActiveRK52D/definitions.hpp +++ b/test/Planet/PlanetsIsActiveRK52D/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetsIsActiveRK52D/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 2 diff --git a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py index 0baa46a21..0b6f254ec 100755 --- a/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py +++ b/test/Planet/PlanetsIsActiveRK52D/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetsIsActiveRK52D/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Tue Dec 21 12:04:41 2021 diff --git a/test/Planet/PlanetsIsActiveRK52D/setup.cpp b/test/Planet/PlanetsIsActiveRK52D/setup.cpp index a1d16c590..810e41134 100644 --- a/test/Planet/PlanetsIsActiveRK52D/setup.cpp +++ b/test/Planet/PlanetsIsActiveRK52D/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Planet/PlanetsIsActiveRK52D/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include "idefix.hpp" diff --git a/test/Planet/PlanetsIsActiveRK52D/testme.py b/test/Planet/PlanetsIsActiveRK52D/testme.py index 769be8fbf..a491b6960 100755 --- a/test/Planet/PlanetsIsActiveRK52D/testme.py +++ b/test/Planet/PlanetsIsActiveRK52D/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Planet/PlanetsIsActiveRK52D/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/Pluto/HD/FargoPlanet/definitions.h b/test/Pluto/HD/FargoPlanet/definitions.h index 255f8c034..2ad5d3ed0 100644 --- a/test/Pluto/HD/FargoPlanet/definitions.h +++ b/test/Pluto/HD/FargoPlanet/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/FargoPlanet/definitions.h +// +// Last modified : 03/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 2 #define COMPONENTS 2 diff --git a/test/Pluto/HD/FargoPlanet/eos.c b/test/Pluto/HD/FargoPlanet/eos.c index 61845c172..dfa3d46cc 100644 --- a/test/Pluto/HD/FargoPlanet/eos.c +++ b/test/Pluto/HD/FargoPlanet/eos.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/FargoPlanet/eos.c +// +// Last modified : 03/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" /* **************************************************************** */ diff --git a/test/Pluto/HD/FargoPlanet/init.c b/test/Pluto/HD/FargoPlanet/init.c index 5504b18d9..84617d9ba 100644 --- a/test/Pluto/HD/FargoPlanet/init.c +++ b/test/Pluto/HD/FargoPlanet/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/FargoPlanet/init.c +// +// Last modified : 03/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/MachReflection/definitions.h b/test/Pluto/HD/MachReflection/definitions.h index f35626906..b6b70e77f 100644 --- a/test/Pluto/HD/MachReflection/definitions.h +++ b/test/Pluto/HD/MachReflection/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/MachReflection/definitions.h +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 2 #define COMPONENTS 2 diff --git a/test/Pluto/HD/MachReflection/init.c b/test/Pluto/HD/MachReflection/init.c index c556f91a7..827244ba0 100644 --- a/test/Pluto/HD/MachReflection/init.c +++ b/test/Pluto/HD/MachReflection/init.c @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/MachReflection/init.c +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/PlanetDisk/definitions.h b/test/Pluto/HD/PlanetDisk/definitions.h index 255f8c034..1b3fdb259 100644 --- a/test/Pluto/HD/PlanetDisk/definitions.h +++ b/test/Pluto/HD/PlanetDisk/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk/definitions.h +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 2 #define COMPONENTS 2 diff --git a/test/Pluto/HD/PlanetDisk/eos.c b/test/Pluto/HD/PlanetDisk/eos.c index 61845c172..99638be92 100644 --- a/test/Pluto/HD/PlanetDisk/eos.c +++ b/test/Pluto/HD/PlanetDisk/eos.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk/eos.c +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" /* **************************************************************** */ diff --git a/test/Pluto/HD/PlanetDisk/init.c b/test/Pluto/HD/PlanetDisk/init.c index bd35a262f..bfd688d1e 100644 --- a/test/Pluto/HD/PlanetDisk/init.c +++ b/test/Pluto/HD/PlanetDisk/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk/init.c +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/PlanetDisk3D/definitions.h b/test/Pluto/HD/PlanetDisk3D/definitions.h index 5ad7a3154..158d745d8 100644 --- a/test/Pluto/HD/PlanetDisk3D/definitions.h +++ b/test/Pluto/HD/PlanetDisk3D/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk3D/definitions.h +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 3 #define COMPONENTS 3 diff --git a/test/Pluto/HD/PlanetDisk3D/eos.c b/test/Pluto/HD/PlanetDisk3D/eos.c index 61845c172..4dd7543ee 100644 --- a/test/Pluto/HD/PlanetDisk3D/eos.c +++ b/test/Pluto/HD/PlanetDisk3D/eos.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk3D/eos.c +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" /* **************************************************************** */ diff --git a/test/Pluto/HD/PlanetDisk3D/init.c b/test/Pluto/HD/PlanetDisk3D/init.c index 39577c773..4f58ac906 100644 --- a/test/Pluto/HD/PlanetDisk3D/init.c +++ b/test/Pluto/HD/PlanetDisk3D/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/PlanetDisk3D/init.c +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/ViscousFlowPastCylinder/definitions.h b/test/Pluto/HD/ViscousFlowPastCylinder/definitions.h index bf502011c..87318e709 100644 --- a/test/Pluto/HD/ViscousFlowPastCylinder/definitions.h +++ b/test/Pluto/HD/ViscousFlowPastCylinder/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/ViscousFlowPastCylinder/definitions.h +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 2 #define COMPONENTS 2 diff --git a/test/Pluto/HD/ViscousFlowPastCylinder/init.c b/test/Pluto/HD/ViscousFlowPastCylinder/init.c index 508503db9..e6b8636db 100644 --- a/test/Pluto/HD/ViscousFlowPastCylinder/init.c +++ b/test/Pluto/HD/ViscousFlowPastCylinder/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/ViscousFlowPastCylinder/init.c +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/ViscousFlowPastCylinder/userdef_output.c b/test/Pluto/HD/ViscousFlowPastCylinder/userdef_output.c index b93b41710..abff72fe0 100644 --- a/test/Pluto/HD/ViscousFlowPastCylinder/userdef_output.c +++ b/test/Pluto/HD/ViscousFlowPastCylinder/userdef_output.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/ViscousFlowPastCylinder/userdef_output.c +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" /* *************************************************************** */ diff --git a/test/Pluto/HD/ViscousFlowPastCylinder/visc_nu.c b/test/Pluto/HD/ViscousFlowPastCylinder/visc_nu.c index 19579a520..7f21a9478 100644 --- a/test/Pluto/HD/ViscousFlowPastCylinder/visc_nu.c +++ b/test/Pluto/HD/ViscousFlowPastCylinder/visc_nu.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/ViscousFlowPastCylinder/visc_nu.c +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* /////////////////////////////////////////////////////////////////// */ /*! \file * \brief Specification of explicit first and second viscosity coefficients*/ diff --git a/test/Pluto/HD/sod/definitions.h b/test/Pluto/HD/sod/definitions.h index 5c7fb3253..5e7810097 100644 --- a/test/Pluto/HD/sod/definitions.h +++ b/test/Pluto/HD/sod/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/sod/definitions.h +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS HD #define DIMENSIONS 1 #define COMPONENTS 1 diff --git a/test/Pluto/HD/sod/init.c b/test/Pluto/HD/sod/init.c index 39971778e..b94887a48 100644 --- a/test/Pluto/HD/sod/init.c +++ b/test/Pluto/HD/sod/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/HD/sod/init.c +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/HD/sod/python/idefixTools.py b/test/Pluto/HD/sod/python/idefixTools.py index 5dd73f7bf..90d9ac685 100644 --- a/test/Pluto/HD/sod/python/idefixTools.py +++ b/test/Pluto/HD/sod/python/idefixTools.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Pluto/HD/sod/python/idefixTools.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Mon Nov 3 15:23:00 2014 diff --git a/test/Pluto/HD/sod/python/sod.py b/test/Pluto/HD/sod/python/sod.py index 99e55b7c4..14236465b 100755 --- a/test/Pluto/HD/sod/python/sod.py +++ b/test/Pluto/HD/sod/python/sod.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Pluto/HD/sod/python/sod.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:27:16 2020 diff --git a/test/Pluto/HD/sod/python/testidefix.py b/test/Pluto/HD/sod/python/testidefix.py index bdd6daf15..525d865bb 100755 --- a/test/Pluto/HD/sod/python/testidefix.py +++ b/test/Pluto/HD/sod/python/testidefix.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/Pluto/HD/sod/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/Pluto/MHD/OrszagTang/definitions.h b/test/Pluto/MHD/OrszagTang/definitions.h index a9d6a3aef..6b8d7ce67 100644 --- a/test/Pluto/MHD/OrszagTang/definitions.h +++ b/test/Pluto/MHD/OrszagTang/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/OrszagTang/definitions.h +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS MHD #define DIMENSIONS 2 #define COMPONENTS 2 diff --git a/test/Pluto/MHD/OrszagTang/init.c b/test/Pluto/MHD/OrszagTang/init.c index c96ab1c14..f21df9469 100644 --- a/test/Pluto/MHD/OrszagTang/init.c +++ b/test/Pluto/MHD/OrszagTang/init.c @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/OrszagTang/init.c +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + /* ///////////////////////////////////////////////////////////////////// */ /*! \file diff --git a/test/Pluto/MHD/sod-iso/definitions.h b/test/Pluto/MHD/sod-iso/definitions.h index 3204bb5f7..b30eeac1f 100644 --- a/test/Pluto/MHD/sod-iso/definitions.h +++ b/test/Pluto/MHD/sod-iso/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/sod-iso/definitions.h +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS MHD #define DIMENSIONS 1 #define COMPONENTS 3 diff --git a/test/Pluto/MHD/sod-iso/init.c b/test/Pluto/MHD/sod-iso/init.c index f03c3114b..94def23fd 100644 --- a/test/Pluto/MHD/sod-iso/init.c +++ b/test/Pluto/MHD/sod-iso/init.c @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/sod-iso/init.c +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" #define LEFTGOING YES diff --git a/test/Pluto/MHD/sod/definitions.h b/test/Pluto/MHD/sod/definitions.h index 5517b826e..c8e729867 100644 --- a/test/Pluto/MHD/sod/definitions.h +++ b/test/Pluto/MHD/sod/definitions.h @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/sod/definitions.h +// +// Last modified : 11/2020 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define PHYSICS MHD #define DIMENSIONS 1 #define COMPONENTS 3 diff --git a/test/Pluto/MHD/sod/init.c b/test/Pluto/MHD/sod/init.c index 7d1248f12..476fd8859 100644 --- a/test/Pluto/MHD/sod/init.c +++ b/test/Pluto/MHD/sod/init.c @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/Pluto/MHD/sod/init.c +// +// Last modified : 01/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2020) +// - Clément Robert (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "pluto.h" #define LEFTGOING YES diff --git a/test/SelfGravity/DustyCollapse/definitions.hpp b/test/SelfGravity/DustyCollapse/definitions.hpp index 77affc7ef..7ffedc491 100644 --- a/test/SelfGravity/DustyCollapse/definitions.hpp +++ b/test/SelfGravity/DustyCollapse/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/DustyCollapse/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/SelfGravity/DustyCollapse/python/testidefix.py b/test/SelfGravity/DustyCollapse/python/testidefix.py index 1ace55c5b..a10a87f8b 100644 --- a/test/SelfGravity/DustyCollapse/python/testidefix.py +++ b/test/SelfGravity/DustyCollapse/python/testidefix.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/DustyCollapse/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import os import sys diff --git a/test/SelfGravity/DustyCollapse/setup.cpp b/test/SelfGravity/DustyCollapse/setup.cpp index 2399de914..ea7169a9d 100644 --- a/test/SelfGravity/DustyCollapse/setup.cpp +++ b/test/SelfGravity/DustyCollapse/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/DustyCollapse/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "npy.hpp" diff --git a/test/SelfGravity/DustyCollapse/testme.py b/test/SelfGravity/DustyCollapse/testme.py index 12b5c21a9..7d3da1fac 100755 --- a/test/SelfGravity/DustyCollapse/testme.py +++ b/test/SelfGravity/DustyCollapse/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/DustyCollapse/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/SelfGravity/JeansInstability/definitions.hpp b/test/SelfGravity/JeansInstability/definitions.hpp index f64d67e95..518c5bb1a 100644 --- a/test/SelfGravity/JeansInstability/definitions.hpp +++ b/test/SelfGravity/JeansInstability/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/JeansInstability/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/SelfGravity/JeansInstability/python/testidefix.py b/test/SelfGravity/JeansInstability/python/testidefix.py index a3ad8ce2b..43f248d37 100755 --- a/test/SelfGravity/JeansInstability/python/testidefix.py +++ b/test/SelfGravity/JeansInstability/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/JeansInstability/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/SelfGravity/JeansInstability/setup.cpp b/test/SelfGravity/JeansInstability/setup.cpp index 78ee7a154..794b03575 100644 --- a/test/SelfGravity/JeansInstability/setup.cpp +++ b/test/SelfGravity/JeansInstability/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/JeansInstability/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" diff --git a/test/SelfGravity/JeansInstability/testme.py b/test/SelfGravity/JeansInstability/testme.py index 7d915a266..bed603c9b 100755 --- a/test/SelfGravity/JeansInstability/testme.py +++ b/test/SelfGravity/JeansInstability/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/JeansInstability/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/SelfGravity/RandomSphere/definitions.hpp b/test/SelfGravity/RandomSphere/definitions.hpp index 1abadf739..612bfcf02 100644 --- a/test/SelfGravity/RandomSphere/definitions.hpp +++ b/test/SelfGravity/RandomSphere/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/RandomSphere/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/SelfGravity/RandomSphere/python/testidefix.py b/test/SelfGravity/RandomSphere/python/testidefix.py index 197472ffe..cff04f926 100755 --- a/test/SelfGravity/RandomSphere/python/testidefix.py +++ b/test/SelfGravity/RandomSphere/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/RandomSphere/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/SelfGravity/RandomSphere/setup.cpp b/test/SelfGravity/RandomSphere/setup.cpp index ce545b0a5..098ed02aa 100644 --- a/test/SelfGravity/RandomSphere/setup.cpp +++ b/test/SelfGravity/RandomSphere/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/RandomSphere/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" diff --git a/test/SelfGravity/RandomSphere/testme.py b/test/SelfGravity/RandomSphere/testme.py index ff8decdc5..ea242d153 100755 --- a/test/SelfGravity/RandomSphere/testme.py +++ b/test/SelfGravity/RandomSphere/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/RandomSphere/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/SelfGravity/RandomSphereCartesian/definitions.hpp b/test/SelfGravity/RandomSphereCartesian/definitions.hpp index 0eebd2c1f..7cba4803d 100644 --- a/test/SelfGravity/RandomSphereCartesian/definitions.hpp +++ b/test/SelfGravity/RandomSphereCartesian/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/RandomSphereCartesian/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/SelfGravity/RandomSphereCartesian/python/testidefix.py b/test/SelfGravity/RandomSphereCartesian/python/testidefix.py index 46de01379..37f5d0cd1 100755 --- a/test/SelfGravity/RandomSphereCartesian/python/testidefix.py +++ b/test/SelfGravity/RandomSphereCartesian/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/RandomSphereCartesian/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/SelfGravity/RandomSphereCartesian/setup.cpp b/test/SelfGravity/RandomSphereCartesian/setup.cpp index 7eaf4411f..e13430863 100644 --- a/test/SelfGravity/RandomSphereCartesian/setup.cpp +++ b/test/SelfGravity/RandomSphereCartesian/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/RandomSphereCartesian/setup.cpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" diff --git a/test/SelfGravity/RandomSphereCartesian/testme.py b/test/SelfGravity/RandomSphereCartesian/testme.py index 3923ee028..4e19f9447 100755 --- a/test/SelfGravity/RandomSphereCartesian/testme.py +++ b/test/SelfGravity/RandomSphereCartesian/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/RandomSphereCartesian/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/SelfGravity/UniformCollapse/CMakeLists.txt b/test/SelfGravity/UniformCollapse/CMakeLists.txt index fe9547125..63e8260af 100644 --- a/test/SelfGravity/UniformCollapse/CMakeLists.txt +++ b/test/SelfGravity/UniformCollapse/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/UniformCollapse/CMakeLists.txt +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + #replace_idefix_source(main.cpp main.cpp) diff --git a/test/SelfGravity/UniformCollapse/definitions.hpp b/test/SelfGravity/UniformCollapse/definitions.hpp index 923795c2a..95a4c2dd9 100644 --- a/test/SelfGravity/UniformCollapse/definitions.hpp +++ b/test/SelfGravity/UniformCollapse/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/UniformCollapse/definitions.hpp +// +// Last modified : 10/2023 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 #define ISOTHERMAL diff --git a/test/SelfGravity/UniformCollapse/python/testidefix.py b/test/SelfGravity/UniformCollapse/python/testidefix.py index 547b47710..0832e6492 100755 --- a/test/SelfGravity/UniformCollapse/python/testidefix.py +++ b/test/SelfGravity/UniformCollapse/python/testidefix.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/UniformCollapse/python/testidefix.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # -*- coding: utf-8 -*- """ Created on Thu Mar 5 11:29:41 2020 diff --git a/test/SelfGravity/UniformCollapse/setup.cpp b/test/SelfGravity/UniformCollapse/setup.cpp index 22f4a34d6..ba213f8f6 100644 --- a/test/SelfGravity/UniformCollapse/setup.cpp +++ b/test/SelfGravity/UniformCollapse/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/SelfGravity/UniformCollapse/setup.cpp +// +// Last modified : 03/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include "idefix.hpp" diff --git a/test/SelfGravity/UniformCollapse/testme.py b/test/SelfGravity/UniformCollapse/testme.py index 123f417d6..a1f4b85f1 100755 --- a/test/SelfGravity/UniformCollapse/testme.py +++ b/test/SelfGravity/UniformCollapse/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/SelfGravity/UniformCollapse/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/checks_examples.sh b/test/checks_examples.sh index 4cca16217..8d32f9e8e 100755 --- a/test/checks_examples.sh +++ b/test/checks_examples.sh @@ -1,4 +1,17 @@ #!/bin/bash +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/checks_examples.sh +# +# Last modified : 10/2023 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2023) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### # check that the provided examples (which do not have a reference case) compile and run for a few loops diff --git a/test/skeleton/CMakeLists.txt b/test/skeleton/CMakeLists.txt index 55ea7b2ca..602e996ae 100644 --- a/test/skeleton/CMakeLists.txt +++ b/test/skeleton/CMakeLists.txt @@ -1,2 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/skeleton/CMakeLists.txt +# +# Last modified : 10/2021 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # replace the normal idefix main by our skeleton replace_idefix_source(main.cpp main.cpp) diff --git a/test/skeleton/definitions.hpp b/test/skeleton/definitions.hpp index 498be97af..59d595250 100644 --- a/test/skeleton/definitions.hpp +++ b/test/skeleton/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/skeleton/definitions.hpp +// +// Last modified : 10/2021 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/skeleton/main.cpp b/test/skeleton/main.cpp index aecadc962..76b4d4f25 100644 --- a/test/skeleton/main.cpp +++ b/test/skeleton/main.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/skeleton/main.cpp +// +// Last modified : 06/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2021 - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include diff --git a/test/utils/columnDensity/definitions.hpp b/test/utils/columnDensity/definitions.hpp index 3b581bd62..34e5c59b7 100644 --- a/test/utils/columnDensity/definitions.hpp +++ b/test/utils/columnDensity/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/columnDensity/definitions.hpp +// +// Last modified : 01/2025 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/utils/columnDensity/setup.cpp b/test/utils/columnDensity/setup.cpp index 090024abc..1158e0cde 100644 --- a/test/utils/columnDensity/setup.cpp +++ b/test/utils/columnDensity/setup.cpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/columnDensity/setup.cpp +// +// Last modified : 06/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2025 - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "column.hpp" diff --git a/test/utils/columnDensity/testme.py b/test/utils/columnDensity/testme.py index b0a6b5737..75a326310 100755 --- a/test/utils/columnDensity/testme.py +++ b/test/utils/columnDensity/testme.py @@ -1,4 +1,18 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/columnDensity/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2025) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/utils/dumpImage/CMakeLists.txt b/test/utils/dumpImage/CMakeLists.txt index 629aed2d1..4fa3e1fbc 100644 --- a/test/utils/dumpImage/CMakeLists.txt +++ b/test/utils/dumpImage/CMakeLists.txt @@ -1 +1,15 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/dumpImage/CMakeLists.txt +# +# Last modified : 08/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + enable_idefix_property(Idefix_MHD) diff --git a/test/utils/dumpImage/definitions.hpp b/test/utils/dumpImage/definitions.hpp index 3b581bd62..b2c20e75f 100644 --- a/test/utils/dumpImage/definitions.hpp +++ b/test/utils/dumpImage/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/dumpImage/definitions.hpp +// +// Last modified : 08/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 3 #define DIMENSIONS 3 diff --git a/test/utils/dumpImage/setup.cpp b/test/utils/dumpImage/setup.cpp index 5e080e1b0..d44afacf4 100644 --- a/test/utils/dumpImage/setup.cpp +++ b/test/utils/dumpImage/setup.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/dumpImage/setup.cpp +// +// Last modified : 05/2024 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2024) +// - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include "idefix.hpp" #include "setup.hpp" #include "dumpImage.hpp" diff --git a/test/utils/dumpImage/testme.py b/test/utils/dumpImage/testme.py index b0a6b5737..3a50dfb8b 100755 --- a/test/utils/dumpImage/testme.py +++ b/test/utils/dumpImage/testme.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/dumpImage/testme.py +# +# Last modified : 07/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023 - 2024) +# - Gaylor Wafflard (IPAG/UGA/CNRS - 2024) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/utils/lookupTable/CMakeLists.txt b/test/utils/lookupTable/CMakeLists.txt index 55ea7b2ca..6bf9e8b0d 100644 --- a/test/utils/lookupTable/CMakeLists.txt +++ b/test/utils/lookupTable/CMakeLists.txt @@ -1,2 +1,16 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/lookupTable/CMakeLists.txt +# +# Last modified : 06/2022 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + # replace the normal idefix main by our skeleton replace_idefix_source(main.cpp main.cpp) diff --git a/test/utils/lookupTable/definitions.hpp b/test/utils/lookupTable/definitions.hpp index 498be97af..b33de1670 100644 --- a/test/utils/lookupTable/definitions.hpp +++ b/test/utils/lookupTable/definitions.hpp @@ -1,3 +1,17 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/lookupTable/definitions.hpp +// +// Last modified : 06/2022 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #define COMPONENTS 1 #define DIMENSIONS 1 diff --git a/test/utils/lookupTable/main.cpp b/test/utils/lookupTable/main.cpp index d13c47e02..263178a0b 100644 --- a/test/utils/lookupTable/main.cpp +++ b/test/utils/lookupTable/main.cpp @@ -1,3 +1,18 @@ +// *********************************************************************************** +// Idefix MHD astrophysical code +// +// Source file test/utils/lookupTable/main.cpp +// +// Last modified : 08/2026 +// +// Copyright(C) by : +// - Geoffroy Lesur (IPAG/UGA/CNRS - 2022 - 2026) +// - Alankar Dutta (MPA Garching - 2026) +// and other code contributors +// +// Licensed under CeCILL 2.1 License, see COPYING for more information +// *********************************************************************************** + #include #include #include diff --git a/test/utils/lookupTable/testme.py b/test/utils/lookupTable/testme.py index 133ea61b4..c724b6eb1 100755 --- a/test/utils/lookupTable/testme.py +++ b/test/utils/lookupTable/testme.py @@ -1,4 +1,19 @@ #!/usr/bin/env python3 +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/lookupTable/testme.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Geoffroy Lesur (IPAG/UGA/CNRS - 2023) +# - Clément Robert (IPAG/UGA/CNRS - 2026) +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### """ diff --git a/test/utils/lookupTable/testmelib.py b/test/utils/lookupTable/testmelib.py index 5a5b942af..52fb36434 100644 --- a/test/utils/lookupTable/testmelib.py +++ b/test/utils/lookupTable/testmelib.py @@ -1,3 +1,18 @@ +###################################################################################### +# Idefix MHD astrophysical code +# +# Source file test/utils/lookupTable/testmelib.py +# +# Last modified : 08/2026 +# +# Copyright(C) by : +# - Sébastien Valat (IPAG/UGA/CNRS - 2026) +# - Alankar Dutta (MPA Garching - 2026) +# and other code contributors +# +# Licensed under CeCILL 2.1 License, see COPYING for more information +###################################################################################### + import numpy as np from scipy.interpolate import RegularGridInterpolator From 2ff6c505afc3678654631f7f99aabbab7813c0f0 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:14:39 +0200 Subject: [PATCH 136/144] update changelog --- CHANGELOG.md | 30 ++++++++++++++++++++++++++++++ src/kokkos-fft | 1 + 2 files changed, 31 insertions(+) create mode 160000 src/kokkos-fft diff --git a/CHANGELOG.md b/CHANGELOG.md index 6bb7f979e..0a0baa307 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -4,6 +4,36 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). +## [2.4.0] 2026-09-23 +### Changed + +- bump up Kokkos to 5.1. As a result, Idefix now requires a C++20-compatible compiler (#384) +- improve Kokkos 5 performances on AMD targets (#402) +- make MPI gpu-direct optional with a device-host fallback transfer path (#389) +- refactor communication packing/unpacking in Axis and ConstrainedTransport using Buffer and BoundingBox (#385) +- move CheckNan to the end of loop stages in TimeIntegrator (#403) +- keep inter-cell flux in every direction for analysis (#337) +- update CI/tooling and dependencies (#371,#372,#377,#383,#390,#392,#393,#400) +- update copyright headers across the project (#410) + +### Fixed + +- fix div(B) check robustness (#369) +- fix segfault when using UCT_HLL with DIMENSIONS < 3 (#386) +- fix coarsening + viscosity CFL condition violation (#397) +- fix issues when linking parallel HDF5 with CMake (#391) +- restore Ctrl-C handling when pydefix is active (#388) +- ensure shearing-box tests also analyse magnetic field B (#412) +- fix security settings in CI jobs (#373) + +### Added + +- enable parsing of 1D column data and interpolation in functional space using `LookupTable` (#401) +- add conservation tests to OT and OT3D (#407) +- add/improve `testme.json` validation in tests (#378, #394, #405) +- add documentation for pydefix usage in virtual environments (#365) + + ## [2.3.0] 2026-04-21 ### Changed diff --git a/src/kokkos-fft b/src/kokkos-fft new file mode 160000 index 000000000..ee53f8c68 --- /dev/null +++ b/src/kokkos-fft @@ -0,0 +1 @@ +Subproject commit ee53f8c68af9f4febe51c406312d4497368b0ba8 From 448131a489d204f5d76e96fe17285f408d102d9f Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:17:32 +0200 Subject: [PATCH 137/144] add a changelog message --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 0a0baa307..6008ba50b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -32,6 +32,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 - add conservation tests to OT and OT3D (#407) - add/improve `testme.json` validation in tests (#378, #394, #405) - add documentation for pydefix usage in virtual environments (#365) +- add compiler informations in the logs and in stdout (#402) ## [2.3.0] 2026-04-21 From 494de1e0bdb0bd7e6548ad68e0845e26e280d32d Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:46:50 +0200 Subject: [PATCH 138/144] update version # --- CMakeLists.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index a54905501..e0206f4d7 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -23,10 +23,10 @@ endif() set (CMAKE_CXX_STANDARD 20) set(Idefix_VERSION_MAJOR 2) -set(Idefix_VERSION_MINOR 3) +set(Idefix_VERSION_MINOR 4) set(Idefix_VERSION_PATCH 0) -project (idefix VERSION 2.3.0) +project (idefix VERSION 2.4.0) option(Idefix_MHD "enable MHD" OFF) option(Idefix_MPI "enable Message Passing Interface parallelisation" OFF) option(Idefix_HIGH_ORDER_FARGO "Force Fargo to use a PPM reconstruction scheme" OFF) From 3c11c78543d123a0a54aac61bb42358475893b2b Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:47:34 +0200 Subject: [PATCH 139/144] update copyright and version number --- doc/source/conf.py | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/doc/source/conf.py b/doc/source/conf.py index b6806b800..e0598f65f 100644 --- a/doc/source/conf.py +++ b/doc/source/conf.py @@ -34,11 +34,11 @@ # -- Project information ----------------------------------------------------- project = "Idefix" -copyright = "Geoffroy Lesur et al." +copyright = "The Idefix Code contributors" author = "Geoffroy Lesur" # The full version, including alpha/beta/rc tags -release = "2.3.0" +release = "2.4.0" # -- General configuration --------------------------------------------------- @@ -114,6 +114,7 @@ def setup(app): "exhaleDoxygenStdin": textwrap.dedent(""" INPUT = ../../src EXCLUDE = ../../src/kokkos + EXCLUDE += ../../src/kokkos-fft """), } From 80baf8161815b5dc75ccb34ee674e627f92a8a8e Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:47:47 +0200 Subject: [PATCH 140/144] update mpi requirements --- doc/source/index.rst | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/doc/source/index.rst b/doc/source/index.rst index b3be783b1..527689cfb 100644 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -30,8 +30,8 @@ Kokkos library *Idefix* relies internally on the `Kokkos `_ library, which is bundled with *Idefix* as a git submodule and compiled on the fly, hence no external installation is required. MPI library - When using MPI parallelisation, *Idefix* relies on an external MPI library. *Idefix* has been tested successfully with OpenMPI and IntelMPI libraries. When used on GPU architectures, *Idefix* assumes that - the MPI library is GPU-Aware. If unsure, check this last point with your system administrator. + When using MPI parallelisation, *Idefix* relies on an external MPI library. *Idefix* has been tested successfully with OpenMPI, Mpich and IntelMPI libraries. When used on GPU architectures, *Idefix* assumes that + the MPI library is GPU-Aware by default. It is possible to fallback to a non-GPU-Aware mode if needed (check :ref:`configurationOptions`), at the cost of lower performances. If unsure, check this with your system administrator. Python When using *Idefix* with its python interface through the module `Pydefix`, *Idefix* relies on an external python>=3.10 interpreter with the module `pybind11 `_ @@ -91,7 +91,7 @@ Marc Coiffier Continuous integration, automatic benchmarking Sébastien Valat - Continuous integration + Continuous integration, MPI fallback ======================== About this documentation From 25390be6a5165e62932aa3393db93b263a465715 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:48:03 +0200 Subject: [PATCH 141/144] typo in GPU direct MPI doc --- doc/source/reference/makefile.rst | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/source/reference/makefile.rst b/doc/source/reference/makefile.rst index fa83b4935..5f86c66fe 100644 --- a/doc/source/reference/makefile.rst +++ b/doc/source/reference/makefile.rst @@ -36,7 +36,7 @@ Several options can be enabled from the command line (or are accessible with ``c Enable MPI parallelisation. Requires an MPI library. When used in conjonction with CUDA (Nvidia GPUs), a CUDA-aware MPI library is required by *Idefix*. ``-D Idefix_MPI_GPU_DIRECT=OFF`` - Disable the usage of MPI GPU direct for inter-process communication. In this case it uses a copy between GPU and GPU before and after making communications. + Disable the usage of MPI GPU direct for inter-process communication. In this case it uses a copy between GPU and CPU before and after making communications. It is usefull if your MPI is not GPU-aware. Note that this option decreases performances. ``-D Idefix_DEFS=foo.hpp`` From a53e75142bc2cb558f553e657dd683a8e3e7eeea Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 17:50:34 +0200 Subject: [PATCH 142/144] update version number --- src/main.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main.cpp b/src/main.cpp index 9d0a7dfda..b46c8a434 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -19,7 +19,7 @@ //@HEADER // ************************************************************************ // -// IDEFIX v 2.3.0 +// IDEFIX v 2.4.0 // // ************************************************************************ //@HEADER From 7ff23fc8c9e294564dd12a3bf46b9a4851302718 Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 18:01:35 +0200 Subject: [PATCH 143/144] remove kokkos fft from dependendences --- src/kokkos-fft | 1 - 1 file changed, 1 deletion(-) delete mode 160000 src/kokkos-fft diff --git a/src/kokkos-fft b/src/kokkos-fft deleted file mode 160000 index ee53f8c68..000000000 --- a/src/kokkos-fft +++ /dev/null @@ -1 +0,0 @@ -Subproject commit ee53f8c68af9f4febe51c406312d4497368b0ba8 From 7a7db96443197f1e616341a30d23d9afc2f11bda Mon Sep 17 00:00:00 2001 From: Geoffroy Lesur Date: Wed, 23 Sep 2026 18:04:43 +0200 Subject: [PATCH 144/144] update readme --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 92e3e79da..b0857abdc 100644 --- a/README.md +++ b/README.md @@ -21,7 +21,7 @@ What is Idefix? --------------- -Idefix is a computational fluid dynamics code based on a finite-volume high-order Godunov method, originally designed for astrophysical fluid dynamics applications. Idefix is designed to be performance-portable, and uses the [Kokkos](https://github.com/kokkos/kokkos) framework to achieve this goal. This means that it can run both on your laptop's cpu and on the largest GPU Exascale clusters. More technically, Idefix can run in serial, use OpenMP and/or MPI (message passing interface) for parallelization, and use GPU acceleration when available (based on Nvidia Cuda, AMD HIP, etc...). All these capabilities are embedded within one single code, so the code relies on relatively abstracted classes and objects available in C++17, which are not necessarily +Idefix is a computational fluid dynamics code based on a finite-volume high-order Godunov method, originally designed for astrophysical fluid dynamics applications. Idefix is designed to be performance-portable, and uses the [Kokkos](https://github.com/kokkos/kokkos) framework to achieve this goal. This means that it can run both on your laptop's cpu and on the largest GPU Exascale clusters. More technically, Idefix can run in serial, use OpenMP and/or MPI (message passing interface) for parallelization, and use GPU acceleration when available (based on Nvidia Cuda, AMD HIP, etc...). All these capabilities are embedded within one single code, so the code relies on relatively abstracted classes and objects available in C++20, which are not necessarily familiar to astrophysicists. A large effort has been devoted to simplify this level of abstraction so that the code can be modified by researchers and students familiar with C and who are aware of basic object-oriented concepts.