Skip to content

Implement under-relaxation for the tight-coupling iterative solver#3300

Open
luwang00 wants to merge 36 commits intoOpenFAST:devfrom
luwang00:f/underrelaxation
Open

Implement under-relaxation for the tight-coupling iterative solver#3300
luwang00 wants to merge 36 commits intoOpenFAST:devfrom
luwang00:f/underrelaxation

Conversation

@luwang00
Copy link
Copy Markdown
Contributor

@luwang00 luwang00 commented Apr 8, 2026

This PR is ready to be merged.

Feature or improvement description
This PR adds under-relaxation for the tight-coupling iterative solver to address occasional solution divergence. Using an under-relaxation factor less than 1 can potentially improve the stability of numerically challenging models. It can also improve simulation time by avoiding oscillatory convergence and reducing the number of times the Jacobian needs to be updated. The under-relaxation is only applied to the input corrections and not the state corrections. This appears to be adequate.

The user can either provide a constant under-relaxation factor or enable adaptive adjustment of the relaxation factor. With the latter, the user still needs to provide an initial under-relaxation factor to be used during the first iteration of each predictor or corrector step if enabled.

Using a constant under-relaxation factor of 1 removes the under-relaxation and recovers the previous behavior. However, based on limited testing, setting an under-relaxation factor above 0.8 is usually detrimental to convergence and performance and is not recommended. (Note that to avoid changes to r-test results, the r-test input files will be updated to use a constant factor of 1, even though that is likely not optimal.)

The adaptive under-relaxation uses a simple delayed correction approach to avoid having to save duplicated states and inputs for backtracking. With this approach, the first iteration of each predictor step (or corrector step if enabled) uses the initial under-relaxation factor provided by the user. From the second iteration onward, the under-relaxation factor is

  • increased by a factor of 1.2 if the residual decreases (converging solution) or
  • halved if the residual increases (diverging solution), and
  • bounded between a minimum of 0.01 and a maximum of 0.8.

To minimize the chance of solution diverging from the first iteration, a smaller initial under-relaxation factor is suggested with this approach. Based on limited testing, the adaptive under-relaxation method does not provide significant performance improvement over a reasonable constant under-relaxation factor for a typical convergence tolerance of 1e-4. However, it does reduce the number of iterations in each step significantly for smaller tolerances such as 1e-5. In practice, any improvement is likely sensitive to the characteristics of the model and the tolerance requested.

To support the added functionality, two new inputs are inserted in the main fst input file on line 14 and line 15:

true   AutoRelax    - Adaptive under-relaxation for the tight-coupling iterative solver (flag) [default=true]
 0.3   RelaxFactor  - Constant or initial (if AutoRelax) under-relaxation factor for the tight-coupling iterative solver (-) [>0 and <=1; default=0.7 if AutoRelax=false; default=0.3 if AutoRelax=true]

The default keyword can be used with both as indicated in the input descriptions above.

Example results
The following example results are based on a very challenging model of a floating twin-rotor MHK turbine system with flexible blades (with added mass) and support structures and OLAF FVW model.

Without under-relaxation, the simulation diverges after about 22 s. In contrast, the simulation proceeds without issue with a constant under-relaxation factor of 0.3 (higher value not tested). Before the simulation diverges without under-relaxation, the two simulations give consistent results. See example output channels below:
imageimage

The numbers of iterations at each time step are compared below. Interestingly, simulating with under-relaxation requires comparable or fewer iterations, suggesting very poor convergence without. This is also obvious from the fact that when simulating without under-relaxation, OpenFAST needs to recompute the Jacobian frequently, as indicated by the spikes in the number of iterations in the figure below. In contrast, the simulation with under-relaxation does not require any Jacobian update after initialization.
image

Impacted areas of the software
Glue-code, docs, r-test

Test results, if applicable
r-test input files needed to be updated with the new under-relaxation input. Results should not change if the under-relaxation factor is set to 1 with adaptive relaxation turned off.

To-Dos

  • Updated api changes and glue-code inputs in docs
  • Updated r-test input files (all tests passed)
  • r-test branch merging required

andrew-platt and others added 30 commits March 12, 2026 17:53
Update docs for 5.0.0 release, including missing api changes
MD: standardize input file header text to match docs
 * Previously, olaf wake propagation did not consider wave velocity.
 * A similar bug was found in the SetSectAvgInflow subroutine.
 * The optional BoxExceedAllow flag for IfW_FlowField_GetVelAcc was not passed correctly through the SeaState WaveField subroutine for AD.
Various bug fixes for AeroDyn when modeling MHK turbines
Temporary fix for HydroDyn rectangular member visualization
Previously, the self-weight of the reaction node(s) is missing. This is now added back along with any cable loads on the reaction node(s) just in case.
FVW: Fix notification about wake extent
andrew-platt and others added 2 commits April 7, 2026 13:03
OLAF FVW stability issue when simulating multiple rotors
@jjonkman
Copy link
Copy Markdown
Collaborator

jjonkman commented Apr 9, 2026

Dear @luwang00,

Thanks for this addition. Should it be that the relaxation factor reduces with each iteration of the nonlinear solve, and after convergence, the factor gets reset back to unity for the next time step? This is what we did within the nonlinear solve for the old quasi-static mooring module of FAST; I believe MAP++ does something similar. Perhaps with this method, the additional user input is not needed.

Best regards,

@andrew-platt
Copy link
Copy Markdown
Collaborator

Changing this to a dynamic relaxation factor could be really useful. Perhaps later.

if (Failed()) return

! Relax - Under-relaxation factor for the iterative solver (-) [>0 and <=1]
CALL ReadVar( UnIn, InputFile, p%Relax, "Relax", "Under-relaxation factor for the iterative solver (-) [>0 and <=1]", ErrStat2, ErrMsg2, UnEc)
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

could we change this to a ReadVarWDefault and use a default value of 1.0?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think a constant default should be around 0.8. Alternatively, we can make the default the adaptive option.

@andrew-platt andrew-platt changed the base branch from rc-5.0.1 to dev April 9, 2026 17:15
@luwang00
Copy link
Copy Markdown
Contributor Author

luwang00 commented Apr 9, 2026

Hi @jjonkman, thanks for the comment.

I think typically the relaxation factors should be smaller, i.e., take smaller steps, for the first few iterations when the solution is far from convergence and the correction step is large. This is where there is the greatest danger of overshooting and divergence. As we approach a converged solution, the corrections are smaller, and we can gradually increase the underrelaxation factor safely to some maximum value.

I want to see if I can implement a simple adaptive underrelaxation based on the change in residual, but even then, I think it would be nice to give the user some control over this (with default settings), like a fixed underrelaxation factor or a max and a min value for adaptive underrelaxation. Different models can have very different characteristics. For some models, proper under-relaxation can be critical, and it is hard to have some thing that is one size fit all.

I also added some example results in the PR message above.

@jjonkman
Copy link
Copy Markdown
Collaborator

jjonkman commented Apr 9, 2026

Thanks for the addition insight and example results, @luwang00.

I see your point about wanting to increase the relaxation factor with successive iterations. If I recall from past quasi-static mooring work, we chose the opposite because our starting point was the converged solution from the previous time step and only small changes are expected between time steps. So, divergence was not really a concern and reducing the relaxation factor with iteration helped ensure that convergence was reached for the few cases where the solution did start to diverge. I suspect the same is true for tight coupling solver.

Regardless, a bit more testing with different models will probably help identify the best solution.

Copy link
Copy Markdown
Collaborator

@andrew-platt andrew-platt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll be curious how much of a difference the auto-relax makes.

@andrew-platt
Copy link
Copy Markdown
Collaborator

Merge this to dev after cross-merging of rc-5.0.1

@luwang00 luwang00 added this to the v5.1.0 milestone Apr 10, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants