From 2bbc96fd9a43530b05e346c7daef69ccc70fdb04 Mon Sep 17 00:00:00 2001 From: logan-nc Date: Thu, 22 Oct 2026 00:19:23 -0400 Subject: [PATCH 1/2] ForceFreeStates - BUGFIX! - Lower the default singfac_min to 1e-6 so the singular coupling converges At 1e-4 the coupling at the outermost rational surfaces is off by up to 20% and differs between working coordinates; at 1e-6 Hamada, PEST and Boozer agree to 0.5% at no measurable runtime cost. Example decks follow the new default; the test fixtures and Fortran benchmark namelists keep 1e-4. Documents the row and column normalization of the singular coupling matrices. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01VdRsGGg4YRG6E9fgLGbpdF --- examples/DIIID-like_SLAYER_example/gpec.toml | 2 +- examples/DIIID-like_error_field_example/gpec.toml | 2 +- examples/DIIID-like_gal_resistive_example/gpec.toml | 2 +- examples/DIIID-like_gal_resistive_pe_example/gpec.toml | 2 +- examples/DIIID-like_ideal_example/gpec.toml | 2 +- examples/DIIID-like_ideal_multi_n_example/gpec.toml | 2 +- examples/DIIID-like_riccati_deltaprime_example/gpec.toml | 2 +- examples/DIIID-like_truncation_example/gpec.toml | 2 +- examples/LAR_beta_scan/gpec.toml | 2 +- examples/LAR_epsilon_scan/gpec.toml | 2 +- examples/LAR_ideal_match_test/gpec.toml | 2 +- examples/LAR_resistive_match_test/gpec.toml | 2 +- examples/Solovev_ideal_example/gpec.toml | 2 +- examples/Solovev_ideal_example_3D/gpec.toml | 2 +- examples/Solovev_ideal_example_multi_n/gpec.toml | 2 +- .../Solovev_ideal_example_multi_n/single_n_1/gpec.toml | 2 +- .../Solovev_ideal_example_multi_n/single_n_2/gpec.toml | 2 +- examples/Solovev_kinetic_NTV_example/gpec.toml | 2 +- examples/Solovev_kinetic_calculated_example/gpec.toml | 2 +- examples/Solovev_kinetic_multiion_example/gpec.toml | 2 +- examples/a10_kinetic_example/gpec.toml | 2 +- src/Equilibrium/GridRefinement.jl | 4 ++-- src/ForceFreeStates/CoreTypes.jl | 2 +- src/PerturbedEquilibrium/SingularCoupling.jl | 9 +++++++++ src/Precompile.jl | 2 +- 25 files changed, 34 insertions(+), 25 deletions(-) diff --git a/examples/DIIID-like_SLAYER_example/gpec.toml b/examples/DIIID-like_SLAYER_example/gpec.toml index 61ce57700f..2de6f18a30 100644 --- a/examples/DIIID-like_SLAYER_example/gpec.toml +++ b/examples/DIIID-like_SLAYER_example/gpec.toml @@ -48,7 +48,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_error_field_example/gpec.toml b/examples/DIIID-like_error_field_example/gpec.toml index a4f303562c..6a71bf7ca2 100644 --- a/examples/DIIID-like_error_field_example/gpec.toml +++ b/examples/DIIID-like_error_field_example/gpec.toml @@ -51,7 +51,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_gal_resistive_example/gpec.toml b/examples/DIIID-like_gal_resistive_example/gpec.toml index dac772545c..e81e2794c8 100644 --- a/examples/DIIID-like_gal_resistive_example/gpec.toml +++ b/examples/DIIID-like_gal_resistive_example/gpec.toml @@ -47,7 +47,7 @@ kinetic_source = "fixed" # Kinetic matrix source ("fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_gal_resistive_pe_example/gpec.toml b/examples/DIIID-like_gal_resistive_pe_example/gpec.toml index a93549f3bd..348d002bc1 100644 --- a/examples/DIIID-like_gal_resistive_pe_example/gpec.toml +++ b/examples/DIIID-like_gal_resistive_pe_example/gpec.toml @@ -47,7 +47,7 @@ kinetic_source = "fixed" # Kinetic matrix source ("fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_ideal_example/gpec.toml b/examples/DIIID-like_ideal_example/gpec.toml index 448ac5d078..9da711a0fe 100644 --- a/examples/DIIID-like_ideal_example/gpec.toml +++ b/examples/DIIID-like_ideal_example/gpec.toml @@ -46,7 +46,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_ideal_multi_n_example/gpec.toml b/examples/DIIID-like_ideal_multi_n_example/gpec.toml index 325a248545..edcf0cd578 100644 --- a/examples/DIIID-like_ideal_multi_n_example/gpec.toml +++ b/examples/DIIID-like_ideal_multi_n_example/gpec.toml @@ -48,7 +48,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_riccati_deltaprime_example/gpec.toml b/examples/DIIID-like_riccati_deltaprime_example/gpec.toml index 2c369b2539..2f2ba5ebbf 100644 --- a/examples/DIIID-like_riccati_deltaprime_example/gpec.toml +++ b/examples/DIIID-like_riccati_deltaprime_example/gpec.toml @@ -48,7 +48,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_truncation_example/gpec.toml b/examples/DIIID-like_truncation_example/gpec.toml index eb2180e033..fd13a27c17 100644 --- a/examples/DIIID-like_truncation_example/gpec.toml +++ b/examples/DIIID-like_truncation_example/gpec.toml @@ -35,7 +35,7 @@ delta_mlow = 8 # Expands lower bound of Fourier harmonics delta_mhigh = 8 # Expands upper bound of Fourier harmonics eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) integrator = "forward" # Integration formalism: "forward" (dense ξ, needed for [PerturbedEquilibrium]/kinetic), "riccati" (chunked propagator BVP, unlocks the singular-surface Δ′ matrix), or "galerkin" (RDCON outer-region singular Galerkin Δ′, with the optional RPEC inner-layer match) diff --git a/examples/LAR_beta_scan/gpec.toml b/examples/LAR_beta_scan/gpec.toml index da0e40fe1b..551e24bb16 100644 --- a/examples/LAR_beta_scan/gpec.toml +++ b/examples/LAR_beta_scan/gpec.toml @@ -48,7 +48,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at the plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Order of the singular-surface (Frobenius) series expansion diff --git a/examples/LAR_epsilon_scan/gpec.toml b/examples/LAR_epsilon_scan/gpec.toml index ee6e3709ce..adb3a04371 100644 --- a/examples/LAR_epsilon_scan/gpec.toml +++ b/examples/LAR_epsilon_scan/gpec.toml @@ -49,7 +49,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at the plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Order of the singular-surface (Frobenius) series expansion diff --git a/examples/LAR_ideal_match_test/gpec.toml b/examples/LAR_ideal_match_test/gpec.toml index b24604a116..68224317f5 100644 --- a/examples/LAR_ideal_match_test/gpec.toml +++ b/examples/LAR_ideal_match_test/gpec.toml @@ -45,7 +45,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Power-series order for the singular-surface asymptotics save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/LAR_resistive_match_test/gpec.toml b/examples/LAR_resistive_match_test/gpec.toml index 98d9d56a2e..1b7c57004f 100644 --- a/examples/LAR_resistive_match_test/gpec.toml +++ b/examples/LAR_resistive_match_test/gpec.toml @@ -46,7 +46,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Power-series order for the singular-surface asymptotics save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_ideal_example/gpec.toml b/examples/Solovev_ideal_example/gpec.toml index a42fe4cb02..6f5315243d 100644 --- a/examples/Solovev_ideal_example/gpec.toml +++ b/examples/Solovev_ideal_example/gpec.toml @@ -67,7 +67,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_ideal_example_3D/gpec.toml b/examples/Solovev_ideal_example_3D/gpec.toml index ab1909e15d..9024bba219 100644 --- a/examples/Solovev_ideal_example_3D/gpec.toml +++ b/examples/Solovev_ideal_example_3D/gpec.toml @@ -33,7 +33,7 @@ nzeta_vacuum = 96 # Number of points used in splines over toroidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_ideal_example_multi_n/gpec.toml b/examples/Solovev_ideal_example_multi_n/gpec.toml index 0150e1b73f..e3eeff12bb 100644 --- a/examples/Solovev_ideal_example_multi_n/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/gpec.toml @@ -44,7 +44,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details). diff --git a/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml b/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml index 4725466346..baac506e36 100644 --- a/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml @@ -43,7 +43,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file HDF5_filename = "euler_n1.h5" # Output HDF5 filename diff --git a/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml b/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml index 97f108a5a5..f3b9570bd3 100644 --- a/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml @@ -43,7 +43,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file HDF5_filename = "euler_n2.h5" # Output HDF5 filename diff --git a/examples/Solovev_kinetic_NTV_example/gpec.toml b/examples/Solovev_kinetic_NTV_example/gpec.toml index cd02c559f5..12eabf5af4 100644 --- a/examples/Solovev_kinetic_NTV_example/gpec.toml +++ b/examples/Solovev_kinetic_NTV_example/gpec.toml @@ -64,7 +64,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_kinetic_calculated_example/gpec.toml b/examples/Solovev_kinetic_calculated_example/gpec.toml index a6bce31b95..5df17fb3dc 100644 --- a/examples/Solovev_kinetic_calculated_example/gpec.toml +++ b/examples/Solovev_kinetic_calculated_example/gpec.toml @@ -60,7 +60,7 @@ kinetic_source = "calculated" # Kinetic matrix source — exercises KineticForce kinetic_factor = 1.0 # Full-strength kinetic matrices (the "calculated" path is the real physics; no perturbation scaling) integrator = "forward" # Integration formalism: "forward" (dense ξ, needed for [PerturbedEquilibrium]/kinetic), "riccati" (chunked propagator BVP, unlocks the singular-surface Δ′ matrix), or "galerkin" (RDCON outer-region singular Galerkin Δ′, with the optional RPEC inner-layer match) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file verbose = false # Enable verbose logging diff --git a/examples/Solovev_kinetic_multiion_example/gpec.toml b/examples/Solovev_kinetic_multiion_example/gpec.toml index bee59220ed..561b53647e 100644 --- a/examples/Solovev_kinetic_multiion_example/gpec.toml +++ b/examples/Solovev_kinetic_multiion_example/gpec.toml @@ -65,7 +65,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/a10_kinetic_example/gpec.toml b/examples/a10_kinetic_example/gpec.toml index c7a32b36cc..38cb98d81a 100644 --- a/examples/a10_kinetic_example/gpec.toml +++ b/examples/a10_kinetic_example/gpec.toml @@ -41,7 +41,7 @@ kinetic_source = "calculated" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 1.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode; 1.0 = full strength) integrator = "forward" # Integration formalism: "forward" (dense ξ, needed for [PerturbedEquilibrium]/kinetic), "riccati" (chunked propagator BVP, unlocks the singular-surface Δ′ matrix), or "galerkin" (RDCON outer-region singular Galerkin Δ′, with the optional RPEC inner-layer match) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file force_termination = true # Stop after force-free states — the kinetic stability eigenvalues are the result of interest diff --git a/src/Equilibrium/GridRefinement.jl b/src/Equilibrium/GridRefinement.jl index cc80c9cebe..1290a49569 100644 --- a/src/Equilibrium/GridRefinement.jl +++ b/src/Equilibrium/GridRefinement.jl @@ -505,7 +505,7 @@ end """ refined_psi_grid(equil::PlasmaEquilibrium; tau, kin=nothing, mandatory=Float64[], - singfac_min=1e-4, n_min=1, bracket_coef=BRACKET_COEF, + singfac_min=1e-6, n_min=1, bracket_coef=BRACKET_COEF, min_spacing=MIN_KNOT_SPACING, N_cap=1024) -> Vector{Float64} Build the refined pass-2 ψ grid from a formed pass-1 equilibrium: measured-curvature knot @@ -524,7 +524,7 @@ function refined_psi_grid(equil::PlasmaEquilibrium; kin::Union{Nothing,KineticProfileSplines}=nothing, mandatory::Vector{Float64}=Float64[], pinned::Vector{Float64}=Float64[], - singfac_min::Float64=1e-4, + singfac_min::Float64=1e-6, n_min::Int=1, bracket_coef::Float64=BRACKET_COEF, min_spacing::Float64=MIN_KNOT_SPACING, diff --git a/src/ForceFreeStates/CoreTypes.jl b/src/ForceFreeStates/CoreTypes.jl index c321fa98f5..1065f1572b 100644 --- a/src/ForceFreeStates/CoreTypes.jl +++ b/src/ForceFreeStates/CoreTypes.jl @@ -166,7 +166,7 @@ gpec.toml. renorm_threshold::Float64 = 1e3 numsteps_init::Int = 4000 numunorms_init::Int = 100 - singfac_min::Float64 = 1e-4 # Matches Fortran STRIDE; required nonzero for the Riccati path. + singfac_min::Float64 = 1e-6 # Converges the singular coupling (Fortran STRIDE uses 1e-4); required nonzero for the Riccati path. truncate_at_rational_offset::Bool = true # Safe default for diverted equilibria (most production use); set false for limited/analytical (LAR, Solovev). Auto-skipped for multi-n. See docstring. psilim_from_layer_overlap::Bool = false # Cap psilim where adjacent resistive layers overlap. Opt-in; the scan is recorded either way. See docstring. rational_offset_fraction::Float64 = 0.2 diff --git a/src/PerturbedEquilibrium/SingularCoupling.jl b/src/PerturbedEquilibrium/SingularCoupling.jl index e8c5c9e09c..208858f2a6 100644 --- a/src/PerturbedEquilibrium/SingularCoupling.jl +++ b/src/PerturbedEquilibrium/SingularCoupling.jl @@ -249,6 +249,15 @@ Applied resonant vectors `[n_rational]` = C · amp_vec: Diagnostics `[n_rational]`: `island_half_width`, `chirikov_parameter` Metadata `[n_rational]`: `rational_psi`, `rational_q`, `rational_m_res`, `rational_n`, `rational_surface_idx` + +## Normalization + + - Rows: the resonant and penetrated rows are a resonant flux divided by that surface's own area + `rational_area[row]`, so both are fields in T. `C_resonant_current`, `C_island_width_sq` and + `C_delta_prime` carry their own normalizations. + - Columns: every stored matrix is right-multiplied by the control-surface `flux_conform`, so it + acts on the root-area-weighted field b̃ in T and its singular values do not depend on `jac_type`. + The applied vectors are evaluated before that, on the run's own forcing flux. """ function compute_singular_coupling_metrics!( state::PerturbedEquilibriumState, diff --git a/src/Precompile.jl b/src/Precompile.jl index 3dfd8912fd..fb426d7183 100644 --- a/src/Precompile.jl +++ b/src/Precompile.jl @@ -14,7 +14,7 @@ import Logging "Wall" => Dict{String,Any}("shape" => "conformal", "standoff_fraction" => 0.2415, "equal_arc_wall" => true), "ForceFreeStates" => Dict{String,Any}( "vac_flag" => true, "dW_edge_scan_start" => 0.99, "qlow" => 1.02, "qhigh" => 1e3, "nn_low" => 1, "nn_high" => 1, - "mtheta_vacuum" => 64, "singfac_min" => 1e-4, "renorm_threshold" => 1e3, "eulerlagrange_tolerance" => 1e-7, + "mtheta_vacuum" => 64, "singfac_min" => 1e-6, "renorm_threshold" => 1e3, "eulerlagrange_tolerance" => 1e-7, "write_outputs_to_HDF5" => false, "verbose" => false ), "SOL_INPUT" => Dict{String,Any}("mr" => 128, "mz" => 128, "ma" => 128, "elongation" => 1.6, "a" => 0.33, "r0" => 1.0, "q0" => 1.9) From e3da4cf7fdade72d7204504245c5eaf8620fb3ff Mon Sep 17 00:00:00 2001 From: logan-nc Date: Thu, 22 Oct 2026 03:40:20 -0400 Subject: [PATCH 2/2] PerturbedEquilibrium - BUGFIX! - Converge the singular coupling with singfac_min = 1e-6 in the forward-integrator decks MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The Riccati Δ' gains a spurious imaginary part as singfac_min shrinks (on the DIII-D-like deck, surface 4 goes from -2275-9i at 1e-4 to -2278-421i at 1e-5 and -2449-19369i at 1e-6), so the code default and the Riccati, Galerkin and SLAYER decks stay at 1e-4. Only the forward-integrator decks, which feed PerturbedEquilibrium, move to 1e-6, and the singfac_min docstring states the trade-off. Co-Authored-By: Claude Opus 5.5 Claude-Session: https://claude.ai/code/session_01VdRsGGg4YRG6E9fgLGbpdF --- examples/DIIID-like_SLAYER_example/gpec.toml | 2 +- examples/DIIID-like_gal_resistive_example/gpec.toml | 2 +- examples/DIIID-like_gal_resistive_pe_example/gpec.toml | 2 +- examples/DIIID-like_riccati_deltaprime_example/gpec.toml | 2 +- examples/LAR_beta_scan/gpec.toml | 2 +- examples/LAR_epsilon_scan/gpec.toml | 2 +- examples/LAR_ideal_match_test/gpec.toml | 2 +- examples/LAR_resistive_match_test/gpec.toml | 2 +- examples/Solovev_ideal_example_3D/gpec.toml | 2 +- examples/Solovev_ideal_example_multi_n/gpec.toml | 2 +- examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml | 2 +- examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml | 2 +- src/Equilibrium/GridRefinement.jl | 4 ++-- src/ForceFreeStates/CoreTypes.jl | 4 ++-- src/Precompile.jl | 2 +- 15 files changed, 17 insertions(+), 17 deletions(-) diff --git a/examples/DIIID-like_SLAYER_example/gpec.toml b/examples/DIIID-like_SLAYER_example/gpec.toml index 2de6f18a30..61ce57700f 100644 --- a/examples/DIIID-like_SLAYER_example/gpec.toml +++ b/examples/DIIID-like_SLAYER_example/gpec.toml @@ -48,7 +48,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_gal_resistive_example/gpec.toml b/examples/DIIID-like_gal_resistive_example/gpec.toml index e81e2794c8..dac772545c 100644 --- a/examples/DIIID-like_gal_resistive_example/gpec.toml +++ b/examples/DIIID-like_gal_resistive_example/gpec.toml @@ -47,7 +47,7 @@ kinetic_source = "fixed" # Kinetic matrix source ("fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_gal_resistive_pe_example/gpec.toml b/examples/DIIID-like_gal_resistive_pe_example/gpec.toml index 348d002bc1..a93549f3bd 100644 --- a/examples/DIIID-like_gal_resistive_pe_example/gpec.toml +++ b/examples/DIIID-like_gal_resistive_pe_example/gpec.toml @@ -47,7 +47,7 @@ kinetic_source = "fixed" # Kinetic matrix source ("fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10# Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/DIIID-like_riccati_deltaprime_example/gpec.toml b/examples/DIIID-like_riccati_deltaprime_example/gpec.toml index 2f2ba5ebbf..2c369b2539 100644 --- a/examples/DIIID-like_riccati_deltaprime_example/gpec.toml +++ b/examples/DIIID-like_riccati_deltaprime_example/gpec.toml @@ -48,7 +48,7 @@ kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, o kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-10 # Relative tolerance for ODE integration of Euler-Lagrange equations save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details) diff --git a/examples/LAR_beta_scan/gpec.toml b/examples/LAR_beta_scan/gpec.toml index 551e24bb16..da0e40fe1b 100644 --- a/examples/LAR_beta_scan/gpec.toml +++ b/examples/LAR_beta_scan/gpec.toml @@ -48,7 +48,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at the plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Order of the singular-surface (Frobenius) series expansion diff --git a/examples/LAR_epsilon_scan/gpec.toml b/examples/LAR_epsilon_scan/gpec.toml index adb3a04371..ee6e3709ce 100644 --- a/examples/LAR_epsilon_scan/gpec.toml +++ b/examples/LAR_epsilon_scan/gpec.toml @@ -49,7 +49,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at the plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Order of the singular-surface (Frobenius) series expansion diff --git a/examples/LAR_ideal_match_test/gpec.toml b/examples/LAR_ideal_match_test/gpec.toml index 68224317f5..b24604a116 100644 --- a/examples/LAR_ideal_match_test/gpec.toml +++ b/examples/LAR_ideal_match_test/gpec.toml @@ -45,7 +45,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Power-series order for the singular-surface asymptotics save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/LAR_resistive_match_test/gpec.toml b/examples/LAR_resistive_match_test/gpec.toml index 1b7c57004f..98d9d56a2e 100644 --- a/examples/LAR_resistive_match_test/gpec.toml +++ b/examples/LAR_resistive_match_test/gpec.toml @@ -46,7 +46,7 @@ delta_mhigh = 8 # Expands upper bound of Fourier harmonics mtheta_vacuum = 960 # Number of points used in splines over poloidal angle at plasma-vacuum interface eulerlagrange_tolerance = 1e-12 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization frobenius_order = 6 # Power-series order for the singular-surface asymptotics save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_ideal_example_3D/gpec.toml b/examples/Solovev_ideal_example_3D/gpec.toml index 9024bba219..ab1909e15d 100644 --- a/examples/Solovev_ideal_example_3D/gpec.toml +++ b/examples/Solovev_ideal_example_3D/gpec.toml @@ -33,7 +33,7 @@ nzeta_vacuum = 96 # Number of points used in splines over toroidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization save_interval = 1 # Save every Nth ODE step (1=all). Always saves near rational surfaces. diff --git a/examples/Solovev_ideal_example_multi_n/gpec.toml b/examples/Solovev_ideal_example_multi_n/gpec.toml index e3eeff12bb..0150e1b73f 100644 --- a/examples/Solovev_ideal_example_multi_n/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/gpec.toml @@ -44,7 +44,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization # Integrator selection and domain truncation (see ForceFreeStatesControl docstring for details). diff --git a/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml b/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml index baac506e36..4725466346 100644 --- a/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/single_n_1/gpec.toml @@ -43,7 +43,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file HDF5_filename = "euler_n1.h5" # Output HDF5 filename diff --git a/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml b/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml index f3b9570bd3..97f108a5a5 100644 --- a/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml +++ b/examples/Solovev_ideal_example_multi_n/single_n_2/gpec.toml @@ -43,7 +43,7 @@ mtheta_vacuum = 960 # Number of points used in splines over poloidal a kinetic_source = "fixed" # Kinetic matrix source: "fixed" test matrices, or "calculated" from the kinetic NTV model kinetic_factor = 0.0 # Scaling of kinetic matrices (0 = ideal path; >0 enables kinetic mode) eulerlagrange_tolerance = 1e-7 # Relative tolerance for ODE integration of Euler-Lagrange equations -singfac_min = 1e-6 # Fractional distance from rational q at which ideal jump enforced +singfac_min = 1e-4 # Fractional distance from rational q at which ideal jump enforced renorm_threshold = 1e3 # Column-norm threshold that triggers solution renormalization write_outputs_to_HDF5 = true # Write outputs to the HDF5 file HDF5_filename = "euler_n2.h5" # Output HDF5 filename diff --git a/src/Equilibrium/GridRefinement.jl b/src/Equilibrium/GridRefinement.jl index 1290a49569..cc80c9cebe 100644 --- a/src/Equilibrium/GridRefinement.jl +++ b/src/Equilibrium/GridRefinement.jl @@ -505,7 +505,7 @@ end """ refined_psi_grid(equil::PlasmaEquilibrium; tau, kin=nothing, mandatory=Float64[], - singfac_min=1e-6, n_min=1, bracket_coef=BRACKET_COEF, + singfac_min=1e-4, n_min=1, bracket_coef=BRACKET_COEF, min_spacing=MIN_KNOT_SPACING, N_cap=1024) -> Vector{Float64} Build the refined pass-2 ψ grid from a formed pass-1 equilibrium: measured-curvature knot @@ -524,7 +524,7 @@ function refined_psi_grid(equil::PlasmaEquilibrium; kin::Union{Nothing,KineticProfileSplines}=nothing, mandatory::Vector{Float64}=Float64[], pinned::Vector{Float64}=Float64[], - singfac_min::Float64=1e-6, + singfac_min::Float64=1e-4, n_min::Int=1, bracket_coef::Float64=BRACKET_COEF, min_spacing::Float64=MIN_KNOT_SPACING, diff --git a/src/ForceFreeStates/CoreTypes.jl b/src/ForceFreeStates/CoreTypes.jl index 1065f1572b..dfc3225346 100644 --- a/src/ForceFreeStates/CoreTypes.jl +++ b/src/ForceFreeStates/CoreTypes.jl @@ -132,7 +132,7 @@ gpec.toml. - `renorm_threshold::Float64` - Critical value of unorm ratio to trigger solution normalization. In the standard path it triggers Gaussian reduction; in the Riccati path it triggers `renormalize_riccati_inplace!`. Default `1e3`. The trigger compares column-norm growth, not conditioning, so near-parallel columns can leave an error in the free-boundary energies that does not shrink with `eulerlagrange_tolerance`. - `numsteps_init::Int` - Initial array size for ODE data storage - `numunorms_init::Int` - Initial array size for solution normalization data - - `singfac_min::Float64` - Fractional distance from rational q at which ideal jump condition is enforced + - `singfac_min::Float64` - Fractional distance from rational q at which ideal jump condition is enforced. The default 1e-4 suits the Riccati Δ′, whose asymptotic matching gains a spurious imaginary part as it shrinks; `"forward"` runs feeding PerturbedEquilibrium need about 1e-6 for the singular coupling to converge at the outer rational surfaces. - `truncate_at_rational_offset::Bool` - Truncate the integration domain at `(last_rational_q + rational_offset_fraction) / n` rather than at `qhigh` / `psihigh`. Fortran STRIDE found that truncating ~20 % above the outermost rational (`rational_offset_fraction = 0.2`) avoids a numerical kink instability in δW that appears when the integration ends too close to or just below a rational surface. **For diverted equilibria where q → ∞ at the separatrix** (e.g. DIII-D geqdsks, the bulk of production use) this costs negligible physical domain because rationals get arbitrarily dense near the LCFS — `truncate_at_rational_offset = true` is the safe and recommended default. **For limited circular / analytical equilibria with finite q at the edge** (Solovev, LAR scans), rationals are sparse and 20 % above the last rational chops off too much edge, so set `truncate_at_rational_offset = false` and let `qhigh` / `psihigh` control the truncation. Multi-`n` runs are not supported by this truncation (the "outermost rational + rational_offset_fraction / n" depends on which `n`); when `truncate_at_rational_offset = true` with `nn_low != nn_high`, `sing_lim!` warns and falls back to `qhigh` / `psihigh`. Default `true`. - `psilim_from_layer_overlap::Bool` - Cap the integration domain where adjacent rational surfaces' resistive layers overlap, after Fitzpatrick, Nucl. Fusion 2025 Sect. 5.9: past that point no surface retains a well-separated inner region. Applied as an upper bound on `qlim` at the top of `sing_lim!`, so `rational_offset_fraction` / `qhigh` still select the final surface from inside it. The scan runs whenever the run's `[SLAYER]` section names a readable `profile_file` — the same profiles and χ⊥(ψ) the SLAYER analysis uses — and is recorded under `ForceFreeStates/LayerOverlap/` either way; this flag only decides whether it constrains the domain. It resolves that file from the run's TOML, so the programmatic `solve(prob, alg)` entry point cannot run it and the flag is inert there (with a warning). Off on every shipped deck; with the shipped DIII-D-like profiles the overlap point (ψ ≈ 0.9985) lies outside the 0.995 decks' domain but inside the SLAYER deck's 0.9995. See the integration-domain truncation section of the stability documentation. Default `false`. - `rational_offset_fraction::Float64` - Distance beyond last rational surface (normalised ∈ [0,1) in units of 1/n). Only used when `truncate_at_rational_offset` is true. Fortran STRIDE convention is 0.2 (truncate 20 % of one rational-surface spacing above the last surface), retained here. @@ -166,7 +166,7 @@ gpec.toml. renorm_threshold::Float64 = 1e3 numsteps_init::Int = 4000 numunorms_init::Int = 100 - singfac_min::Float64 = 1e-6 # Converges the singular coupling (Fortran STRIDE uses 1e-4); required nonzero for the Riccati path. + singfac_min::Float64 = 1e-4 # Matches Fortran STRIDE; required nonzero for the Riccati path. truncate_at_rational_offset::Bool = true # Safe default for diverted equilibria (most production use); set false for limited/analytical (LAR, Solovev). Auto-skipped for multi-n. See docstring. psilim_from_layer_overlap::Bool = false # Cap psilim where adjacent resistive layers overlap. Opt-in; the scan is recorded either way. See docstring. rational_offset_fraction::Float64 = 0.2 diff --git a/src/Precompile.jl b/src/Precompile.jl index fb426d7183..3dfd8912fd 100644 --- a/src/Precompile.jl +++ b/src/Precompile.jl @@ -14,7 +14,7 @@ import Logging "Wall" => Dict{String,Any}("shape" => "conformal", "standoff_fraction" => 0.2415, "equal_arc_wall" => true), "ForceFreeStates" => Dict{String,Any}( "vac_flag" => true, "dW_edge_scan_start" => 0.99, "qlow" => 1.02, "qhigh" => 1e3, "nn_low" => 1, "nn_high" => 1, - "mtheta_vacuum" => 64, "singfac_min" => 1e-6, "renorm_threshold" => 1e3, "eulerlagrange_tolerance" => 1e-7, + "mtheta_vacuum" => 64, "singfac_min" => 1e-4, "renorm_threshold" => 1e3, "eulerlagrange_tolerance" => 1e-7, "write_outputs_to_HDF5" => false, "verbose" => false ), "SOL_INPUT" => Dict{String,Any}("mr" => 128, "mz" => 128, "ma" => 128, "elongation" => 1.6, "a" => 0.33, "r0" => 1.0, "q0" => 1.9)