Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
115 commits
Select commit Hold shift + click to select a range
c5efb59
Add CMake build artifacts and vim swap files to .gitignore
Eleven7825 Oct 13, 2025
b324b1f
Add Integrator class to encapsulate Newton iteration logic
Eleven7825 Oct 13, 2025
c4609d5
Refactor main.cpp to use Integrator class
Eleven7825 Oct 13, 2025
7eec430
Fix: Add missing iEqOld variable for output calls
Eleven7825 Oct 13, 2025
d095026
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Oct 17, 2025
1d7c5cf
change license header
mrp089 Oct 17, 2025
fbe9c34
Rename integrator files to Integrator to follow class naming convention
Eleven7825 Oct 23, 2025
d3d942f
Convert Integrator class documentation to Doxygen format
Eleven7825 Oct 23, 2025
0113997
Refactor istr to be a class member variable
Eleven7825 Oct 23, 2025
9955e3d
De-clutter step() method by moving debug writes to individual functions
Eleven7825 Oct 23, 2025
8dbde2f
Standardize terminology to use 'Newton iteration' instead of 'inner l…
Eleven7825 Oct 23, 2025
7065339
Move dmsg debug statements into respective Integrator helper functions
Eleven7825 Oct 24, 2025
f2ee520
Remove pic namespace and integrate functions into Integrator class
Eleven7825 Nov 6, 2025
98d09f0
Extract An, Dn, and Yn from ComMod to Integrator class
Eleven7825 Nov 7, 2025
8e2f9d6
Extract Ao, Do, Yo from ComMod to Integrator class
Eleven7825 Nov 7, 2025
bbb88d6
Merge remote changes with Ao, Do, Yo extraction work
Eleven7825 Nov 7, 2025
9b52ad5
Thread Do/Dn displacement parameters through all boundary condition a…
Eleven7825 Nov 12, 2025
316d6da
Fix Do/Dn displacement parameter threading for moving mesh simulations
Eleven7825 Nov 13, 2025
63e5753
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Nov 13, 2025
4407dc1
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Dec 11, 2025
65d3eec
address mrp089's comments on renaming methods and remove redundant va…
Jan 6, 2026
22459d8
remove Do checks and some comments of Ao, Yo, Do
Jan 8, 2026
39f0b94
Merge branch 'main' into feature/issue-442-integrator-class
Eleven7825 Jan 9, 2026
e4f88d3
Lump An, Dn, Yn, Ao, Do, Yo into solu_state_vars
Eleven7825 Jan 9, 2026
ccf7ecd
Change `solutions` struct to be nested, for example `solution.old.A` …
Eleven7825 Jan 14, 2026
ec07838
Change the argument positions at `all_fun.h`. Now Dn and Do no longer…
Jan 19, 2026
ca653bb
Fix the function signature gnnb at nn.cpp to make Dn and Do not take …
Jan 20, 2026
1f4acb8
Add Solution getters to ComMod.h and update Integrator to use them
Jan 23, 2026
695f9d6
Update boundary condition functions to use SolutionStates
Jan 25, 2026
75db517
Refactor ris functions to use SolutionStates and remove temp_solution…
Jan 25, 2026
f0eacd7
Update eq_assem functions to use SolutionStates
Jan 25, 2026
5917389
Update txt functions to use SolutionStates
Jan 25, 2026
c49aff3
Update output functions to use SolutionStates
Jan 25, 2026
7309075
Update initialization functions to use SolutionStates
Jan 25, 2026
a73c528
Update all_fun integ functions and uris functions to use SolutionStates
Jan 25, 2026
7bd5223
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Jan 28, 2026
d6919af
Update txt functions and uris functions to use SolutionStates
Jan 28, 2026
3b23497
Fix missed integ call in uris_meanp
Jan 28, 2026
7716ab5
Merge branch 'feature/issue-442-integrator-class' of github.com:Eleve…
Jan 28, 2026
93a60f6
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Feb 2, 2026
eb75141
Merge branch 'main' into feature/issue-442-integrator-class
Eleven7825 Feb 11, 2026
b5ca973
Add const to read-only SolutionStates& params and pass SolutionStates…
Feb 13, 2026
a662804
Merge branch 'main' into feature/issue-442-integrator-class
mrp089 Apr 1, 2026
0ddd574
use solutions object in function calls
mrp089 Apr 1, 2026
770ade1
const solutions
mrp089 Apr 1, 2026
dbe71cc
WE NEED AUTOMATED CODE FORMATTING, THIS IS A WASTE OF TIME: revert wh…
mrp089 Apr 1, 2026
6b15c85
move Solution and SolutionStates objects to new file
mrp089 Apr 1, 2026
c0442e0
small fixes in Integrator
mrp089 Apr 1, 2026
0d3a664
make solution components private and exclusively use getter functions
mrp089 Apr 1, 2026
c740b98
small fixes
mrp089 Apr 1, 2026
c45225f
Add step_equation() for single-equation Newton solve (#431)
mrp089 Apr 2, 2026
13c452d
Add FSI interface data exchange functions (#431)
mrp089 Apr 2, 2026
1276447
Merge branch 'feature/issue-431-fsi-interface-exchange' into feature/…
mrp089 Apr 2, 2026
3a33c69
Implement partitioned FSI coupling with Aitken relaxation (#431)
mrp089 Apr 2, 2026
1a33822
Fix partitioned FSI: enforce interface Dirichlet BC and add no-slip wall
mrp089 Apr 2, 2026
6a78870
Add partitioned FSI test meshes and 50-step results
mrp089 Apr 2, 2026
8ed9348
Add ALE mesh motion for partitioned fluid solve
mrp089 Apr 2, 2026
f967ce0
Fix partitioned FSI: proper linear solver setup and velocity coupling
mrp089 Apr 2, 2026
7dbc639
Update partitioned FSI results with velocity coupling
mrp089 Apr 2, 2026
1057b2d
Rewrite partitioned FSI v2: 3 independent sub-Simulation instances
mrp089 Apr 3, 2026
808b3ff
Fix partitioned FSI coupling: no-slip in mesh frame, not lab frame
mrp089 Apr 3, 2026
4f31b40
Add ALE mesh velocity coupling: fluid+mesh in same sub-sim
mrp089 Apr 3, 2026
4ce07ee
Improve partitioned FSI output: match solver format, add coupling log
mrp089 Apr 3, 2026
d773e1c
Clean up coupling output: remove CONVERGED lines, align coupling.dat
mrp089 Apr 3, 2026
f148872
Fix partitioned FSI: use FSI equation type, Newmark mesh velocity, no…
mrp089 Apr 3, 2026
1df0adf
Implement IQN-ILS coupling acceleration (Degroote 2013, Algorithm 10)
mrp089 Apr 3, 2026
9bc4767
Add Robin-Neumann coupling: stable convergence with wall velocity
mrp089 Apr 4, 2026
8c6d95e
Fix traction sign: R -= traction (not +=), solid now moves outward
mrp089 Apr 4, 2026
f4dcf49
Use fluid formulation with manual mesh deformation
mrp089 Apr 4, 2026
dd312fa
Restructure to 3 separate sub-sims, velocity coupling, mesh at end
mrp089 Apr 4, 2026
a2a5da8
Fix convergence check and velocity computation in coupling loop
mrp089 Apr 4, 2026
6939090
Add Aitken relaxation for velocity-coupled partitioned FSI
mrp089 Apr 4, 2026
6859f63
Use solid velocity directly, fix time stepping concerns
mrp089 Apr 4, 2026
12d4a1a
Add unit tests for partitioned FSI sanity checks
mrp089 Apr 4, 2026
06fa5b6
Quantitative traction verification in unit tests
mrp089 Apr 4, 2026
fd17bf6
Add diagnostic test cases for partitioned FSI
mrp089 Apr 4, 2026
92bf528
Stiff structure test: partitioned matches monolithic to 0.2%
mrp089 Apr 4, 2026
c12d2e7
Ramping pressure test: partitioned matches monolithic at 98% by step 7
mrp089 Apr 4, 2026
9233ceb
Add wall velocity mass conservation test
mrp089 Apr 4, 2026
72063dc
Wall velocity test: mass conservation verified at 92.5%
mrp089 Apr 4, 2026
d79fc23
Revert to Aitken relaxation, IQN-ILS attempt unsuccessful
mrp089 Apr 5, 2026
72c7f76
Refactor: extract relax_interface for swappable coupling methods
mrp089 Apr 5, 2026
7d5eaf2
Partitioned FSI converges to monolithic at tight tolerance
mrp089 Apr 5, 2026
2f0be30
Fix Aitken relaxation: allow negative omega (Küttler & Wall 2008)
mrp089 Apr 5, 2026
b747671
Fix compare_fsi.py: extract outermost ring for radial displacement
mrp089 Apr 5, 2026
fb643c7
Add Omega_max as XML input parameter for Aitken relaxation
mrp089 Apr 5, 2026
6ee9f85
Add ALE mesh velocity correction and improve post-processing
mrp089 Apr 5, 2026
9e035e5
Add selectable coupling methods (constant/aitken/iqn-ils) and NaN det…
mrp089 Apr 5, 2026
1cac5ae
Rewrite IQN-ILS to match svFSGe reference implementation
mrp089 Apr 5, 2026
047d7fe
Add IQN-ILS parameters and fix NaN detection
mrp089 Apr 5, 2026
5bd2b80
current 50 step comparison resutls
mrp089 Apr 6, 2026
7db9ff8
Print coupling.dat format to screen, save old screen format to histor…
mrp089 Apr 6, 2026
deeaa08
Fix fluid mesh deformation accumulating total displacement across tim…
mrp089 Apr 6, 2026
09fa221
Remove interface sanity check output
mrp089 Apr 6, 2026
611d0e4
Suppress sub-field and initialization screen output in partitioned FSI
mrp089 Apr 6, 2026
d78da16
Format coupling output like standard physics types (CP cTS-iter[s])
mrp089 Apr 6, 2026
1ca09fc
Fix IQN-ILS correction and compute velocity from Newmark
mrp089 Apr 6, 2026
b08717c
Rewrite IQN-ILS QR filtering to match svFSGe
mrp089 Apr 6, 2026
0311766
Clean up partitioned FSI code for PR
mrp089 Apr 6, 2026
778853f
Move FSI coupling functions to their proper modules
mrp089 Apr 6, 2026
8a110c0
Remove IQN-ILS coupling method
mrp089 Apr 6, 2026
6ec04f5
Break up PartitionedFSI::step into smaller methods
mrp089 Apr 6, 2026
bf5ebcc
updated results with 50 steps
mrp089 Apr 6, 2026
21fcabb
Move ALE mesh velocity ownership from ComMod to Integrator
mrp089 Apr 6, 2026
49735ef
Merge branch 'main' into feature/issue-431-partitioned-fsi
mrp089 Apr 13, 2026
899f0b5
Fix merge conflict resolution errors
mrp089 Apr 14, 2026
c09500d
fix fluid mesh movement by changing order to mesh, fluid, solid, (relax)
mrp089 Apr 15, 2026
9f15007
Add MPI multi-core support to partitioned FSI coupling
May 22, 2026
c750449
Move add_eq_linear_algebra out of main.cpp to fix unit test link error
May 22, 2026
9d94c76
Remove duplicate add_eq_linear_algebra from test_step_equation.cpp
May 22, 2026
f55bb14
Fix const cmType& build error on macOS/clang
May 22, 2026
318aed0
Merge branch 'main' into feature/issue-431-partitioned-fsi
Eleven7825 May 22, 2026
e1d5b10
Merge sub-XMLs into main XML via equation role attributes (Option B)
May 23, 2026
f9a0a01
Add partitioned FSI CI tests and reference solutions
May 23, 2026
07a7b50
Fix array out-of-bounds crash in mesh sub-sim initialization
May 23, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion Code/Source/solver/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,8 @@ set(CSRCS
eq_assem.h eq_assem.cpp
fluid.h fluid.cpp
fsi.h fsi.cpp
fsi_coupling.h fsi_coupling.cpp
PartitionedFSI.h PartitionedFSI.cpp
fs.h fs.cpp
fft.h fft.cpp
heatf.h heatf.cpp
Expand Down Expand Up @@ -357,7 +359,13 @@ if(ENABLE_UNIT_TEST)

# include source files (same as what svMultiPhysics does except for main.cpp)
add_executable(run_all_unit_tests ${CSRCS})


# Define test data directory for integration tests
# CMAKE_SOURCE_DIR points to Code/, so go up one level to reach the repo root
target_compile_definitions(run_all_unit_tests PRIVATE
TEST_DATA_DIR="${CMAKE_SOURCE_DIR}/../tests/cases"
)

if(USE_TRILINOS)
target_link_libraries(run_all_unit_tests ${Trilinos_LIBRARIES} ${Trilinos_TPL_LIBRARIES})
endif()
Expand Down
7 changes: 6 additions & 1 deletion Code/Source/solver/ComMod.h
Original file line number Diff line number Diff line change
Expand Up @@ -1553,9 +1553,14 @@ class ComMod {
/// @brief Whether there is a requirement to update mesh and Dn-Do variables
bool dFlag = false;

/// @brief Whether mesh is moving
/// @brief Whether mesh is moving (monolithic FSI: mesh velocity in DOFs nsd+1..2*nsd)
bool mvMsh = false;

/// @brief ALE mesh velocity for partitioned FSI (nsd, tnNo).
/// When non-empty, the fluid assembly subtracts this from the convective
/// velocity, providing the ALE correction without expanding tDof.
Array<double> ale_mesh_velocity;

/// @brief Whether to averaged results
bool saveAve = false;

Expand Down
144 changes: 133 additions & 11 deletions Code/Source/solver/Integrator.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
#include "utils.h"

#include <algorithm>
#include <cmath>
#include <iostream>
#include <set>

Expand Down Expand Up @@ -171,6 +172,94 @@ bool Integrator::step() {
} // End of Newton iteration loop
}

//------------------------
// step_equation
//------------------------
/// @brief Solve a single equation to convergence without cycling to other equations
bool Integrator::step_equation(int iEq, std::function<void()> post_assembly) {
using namespace consts;

auto& com_mod = simulation_->com_mod;
auto& cm_mod = simulation_->cm_mod;

int& cTS = com_mod.cTS;

// Set up for this equation
com_mod.cEq = iEq;
auto& eq = com_mod.eq[iEq];
eq.itr = 0;
eq.ok = false;
eq.iNorm = 0.0;

newton_count_ = 1;

while (true) {
istr_ = "_" + std::to_string(cTS) + "_" + std::to_string(newton_count_);
auto& eq = com_mod.eq[iEq];

// Coupled BC handling (same as step())
if (com_mod.cplBC.coupled && iEq == 0) {
set_bc::set_bc_cpl(com_mod, cm_mod, solutions_);
set_bc::set_bc_dir(com_mod, solutions_);
}

// Initiator step for Generalized α-Method
initiator_step();

if (com_mod.Rd.size() != 0) {
com_mod.Rd = 0.0;
com_mod.Kd = 0.0;
}

// Allocate, assemble, apply BCs
allocate_linear_system(eq);
set_body_forces();
assemble_equations();
apply_boundary_conditions();

// Optional post-assembly callback (e.g., for injecting interface traction)
if (post_assembly) {
post_assembly();
}

// Synchronize R across processes
if (!eq.assmTLS) {
all_fun::commu(com_mod, com_mod.R);
}

// Update residual in displacement equation for USTRUCT phys
if (com_mod.sstEq) {
ustruct::ustruct_r(com_mod, solutions_);
}

// Set the residual of the continuity equation to 0 on edge nodes
if (std::set<EquationType>{Equation_stokes, Equation_fluid, Equation_ustruct, Equation_FSI}.count(eq.phys) != 0) {
fs::thood_val_rc(com_mod);
}

set_bc::set_bc_undef_neu(com_mod);
update_residual_arrays(eq);

// Solve linear system
solve_linear_system();

// Update solution and check convergence (no equation cycling)
update_solution();

if (eq.ok) {
return true;
}

// Abort on NaN in residual norm (indicates divergence).
if (newton_count_ > 1 && std::isnan(eq.FSILS.RI.iNorm)) {
return false;
}

output::output_result(simulation_, com_mod.timeP, 2, iEq);
newton_count_ += 1;
}
}

//------------------------
// initiator_step
//------------------------
Expand Down Expand Up @@ -374,8 +463,8 @@ void Integrator::update_residual_arrays(eqType& eq) {
// 1. Bazilevs, et al. "Isogeometric fluid-structure interaction:
// theory, algorithms, and computations.", Computational Mechanics,
// 43 (2008): 3-37. doi: 10.1007/s00466-008-0315-x
// 2. Bazilevs, et al. "Variational multiscale residual-based
// turbulence modeling for large eddy simulation of incompressible
// 2. Bazilevs, et al. "Variational multiscale residual-based
// turbulence modeling for large eddy simulation of incompressible
// flows.", CMAME (2007)
//------------------------
// predictor (picp)
Expand Down Expand Up @@ -621,11 +710,13 @@ void Integrator::initiator(SolutionStates& solutions)
}
}
//------------------------
// corrector
// update_solution
//------------------------
/// @brief Corrector with convergence check
/// @brief Update solution from linear solve result and check convergence
///
/// Decision for next eqn is also made here (modifies cEq global).
/// Performs the corrector update of An, Yn, Dn from the Newton solve result
/// and checks convergence norms. Sets eq.ok if converged.
/// Does NOT handle equation cycling (that is done by corrector()).
///
/// Modifies:
/// \code {.cpp}
Expand All @@ -637,13 +728,12 @@ void Integrator::initiator(SolutionStates& solutions)
/// com_mod.pS0
/// com_mod.pSa
/// com_mod.pSn
///
/// com_mod.cEq
/// eq.FSILS.RI.iNorm
/// eq.pNorm
/// eq.ok
/// \endcode
//
void Integrator::corrector()
void Integrator::update_solution()
{
using namespace consts;

Expand Down Expand Up @@ -853,10 +943,42 @@ void Integrator::corrector()
dmsg << "com_mod.eq[1].ok: " << com_mod.eq[1].ok;
#endif
}
}

//------------------------
// corrector
//------------------------
/// @brief Corrector with convergence check and equation cycling
///
/// Calls update_solution() to update the solution and check convergence,
/// then handles equation switching for coupled problems (modifies cEq global).
//
void Integrator::corrector()
{
using namespace consts;

auto& com_mod = simulation_->com_mod;
const int tnNo = com_mod.tnNo;
auto& cEq = com_mod.cEq;
auto& eq = com_mod.eq[cEq];

auto& An = solutions_.current.get_acceleration();
auto& Dn = solutions_.current.get_displacement();
auto& Yn = solutions_.current.get_velocity();

#define n_debug_corrector_cycling
#ifdef debug_corrector_cycling
DebugMsg dmsg(__func__, com_mod.cm.idcm());
dmsg.banner();
#endif

// Update solution and check convergence
update_solution();

// Check if all equations converged - if so, skip equation cycling
auto& eqs = com_mod.eq;
if (std::count_if(eqs.begin(),eqs.end(),[](eqType& eq){return eq.ok;}) == eqs.size()) {
#ifdef debug_corrector
#ifdef debug_corrector_cycling
dmsg << "all ok";
#endif
return;
Expand All @@ -868,7 +990,7 @@ void Integrator::corrector()
// For coupled equations, if explicit geometric coupling is not used,
// increment the equation counter after each linear solve
cEq = cEq + 1;
#ifdef debug_corrector
#ifdef debug_corrector_cycling
dmsg << "eq " << " coupled ";
dmsg << "1st update cEq: " << cEq;
#endif
Expand Down Expand Up @@ -929,7 +1051,7 @@ void Integrator::corrector()
cEq = cEq + 1;
}
}
#ifdef debug_corrector
#ifdef debug_corrector_cycling
dmsg << "eq " << " coupled ";
dmsg << "2nd update cEq: " << cEq;
#endif
Expand Down
60 changes: 58 additions & 2 deletions Code/Source/solver/Integrator.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,38 @@
#include "Vector.h"
#include "Simulation.h"

#include <functional>

/// @brief Newmark time integration utilities.
///
/// Compute consistent state variables from a prescribed displacement or
/// velocity using the Newmark-beta / generalized-alpha relationships:
/// Dn = Do + dt*Yo + dt^2*((0.5-beta)*Ao + beta*An)
/// Yn = Yo + dt*((1-gamma)*Ao + gamma*An)
namespace newmark {

/// Compute acceleration and velocity from prescribed displacement.
inline void state_from_displacement(
double d_new, double d_old, double v_old, double a_old,
double dt, double beta, double gam,
double& a_new, double& v_new)
{
a_new = (d_new - d_old - dt * v_old) / (beta * dt * dt)
- (0.5 - beta) / beta * a_old;
v_new = v_old + dt * ((1.0 - gam) * a_old + gam * a_new);
}

/// Compute acceleration from prescribed velocity.
inline void state_from_velocity(
double v_new, double v_old, double a_old,
double dt, double gam,
double& a_new)
{
a_new = (v_new - v_old) / (gam * dt) - (1.0 - gam) / gam * a_old;
}

} // namespace newmark

/**
* @brief Integrator class encapsulates the Newton iteration loop for time integration
*
Expand Down Expand Up @@ -42,6 +74,21 @@ class Integrator {
*/
bool step();

/**
* @brief Solve a single equation to convergence (for partitioned coupling)
*
* Runs Newton iterations for only the specified equation, without cycling
* to other equations. Used by partitioned FSI to solve fluid, solid, and
* mesh equations independently.
*
* @param iEq Index of the equation to solve
* @param post_assembly Optional callback invoked after boundary condition
* application but before the linear solve. Used by partitioned FSI
* to inject interface traction into the residual.
* @return True if the equation converged, false if max iterations reached
*/
bool step_equation(int iEq, std::function<void()> post_assembly = nullptr);

/**
* @brief Perform predictor step for next time step
*
Expand Down Expand Up @@ -173,11 +220,20 @@ class Integrator {
*/
void initiator(SolutionStates& solutions);

/**
* @brief Update solution and check convergence of current equation
*
* Performs the corrector step: updates An, Yn, Dn from the linear solve
* result and checks convergence norms. Sets eq.ok if converged.
* Does NOT handle equation cycling -- that is done separately in corrector().
*/
void update_solution();

/**
* @brief Corrector function with convergence check (corrector)
*
* Updates solution at n+1 time level and checks convergence of Newton
* iterations. Also handles equation switching for coupled problems.
* Calls update_solution(), then handles equation switching for coupled
* problems (modifies cEq global).
*/
void corrector();

Expand Down
Loading
Loading