diff --git a/moment_kinetics/src/input_structs.jl b/moment_kinetics/src/input_structs.jl index edcdb9a8a..2bf4cf57c 100644 --- a/moment_kinetics/src/input_structs.jl +++ b/moment_kinetics/src/input_structs.jl @@ -33,7 +33,7 @@ using TOML an option but known at compile time when a `time_info` struct is passed as a function argument. """ -struct time_info{Terrorsum <: Real, T_debug_output, T_electron, Trkimp, Timpzero} +struct time_info{Terrorsum <: Real, T_debug_output, T_electron, Trkimp, Timpzero, Telectronprecon} n_variables::mk_int nstep::mk_int end_time::mk_float @@ -81,6 +81,7 @@ struct time_info{Terrorsum <: Real, T_debug_output, T_electron, Trkimp, Timpzero implicit_ion_advance::Bool implicit_vpa_advection::Bool implicit_electron_ppar::Bool + electron_preconditioner_type::Telectronprecon constraint_forcing_rate::mk_float decrease_dt_iteration_threshold::mk_int increase_dt_iteration_threshold::mk_int diff --git a/moment_kinetics/src/time_advance.jl b/moment_kinetics/src/time_advance.jl index 219fd0ef9..b9b0981e4 100644 --- a/moment_kinetics/src/time_advance.jl +++ b/moment_kinetics/src/time_advance.jl @@ -409,6 +409,32 @@ function setup_time_info(t_input, n_variables, code_time, dt_reload, else error_sum_zero = 0.0 end + + implicit_electron_ppar = (t_input["implicit_electron_ppar"] !== false) + if implicit_electron_ppar + if t_input["implicit_electron_ppar"] === true + if block_size[] == 1 + # No need to parallelise, so un-split LU solver should be most efficient. + electron_preconditioner_type = Val(:electron_lu) + else + # Want to parallelise preconditioner, so use ADI method. + electron_preconditioner_type = Val(:electron_adi) + end + else + electron_precon_types = Dict("lu" => :electron_lu, "adi" => :electron_adi) + if t_input["implicit_electron_ppar"] ∈ keys(electron_precon_types) + electron_preconditioner_type = Val(electron_precon_types[t_input["implicit_electron_ppar"]]) + else + precon_keys = collect(keys(electron_precon_types)) + error("Unrecognised option implicit_electron_ppar=" + * "\"$(t_input["implicit_electron_ppar"])\" which should be " + * "either false/true or a string giving the type of " + * "preconditioner to use - one of $precon_keys.") + end + end + else + electron_preconditioner_type = Val(:none) + end if electron === nothing # Setting up time_info for electrons. # Store io_input as the debug_io variable so we can use it to open the debug @@ -458,7 +484,8 @@ function setup_time_info(t_input, n_variables, code_time, dt_reload, electron !== nothing && t_input["implicit_electron_advance"], electron !== nothing && t_input["implicit_ion_advance"], electron !== nothing && t_input["implicit_vpa_advection"], - electron !== nothing && t_input["implicit_electron_ppar"], + electron !== nothing && implicit_electron_ppar, + electron_preconditioner_type, mk_float(t_input["constraint_forcing_rate"]), decrease_dt_iteration_threshold, increase_dt_iteration_threshold, mk_float(cap_factor_ion_dt), t_input["write_after_fixed_step_count"], @@ -667,13 +694,6 @@ function setup_time_advance!(pdf, fields, vz, vr, vzeta, vpa, vperp, z, r, gyrop input_dict, (z=z,); default_rtol=t_params.rtol / 10.0, default_atol=t_params.atol / 10.0) - if block_size[] == 1 - # No need to parallelise, so un-split LU solver should be most efficient. - electron_preconditioner_type = Val(:electron_lu) - else - # Want to parallelise preconditioner, so use ADI method. - electron_preconditioner_type = Val(:electron_adi) - end nl_solver_electron_advance_params = setup_nonlinear_solve(t_params.implicit_electron_advance || composition.electron_physics ∈ (kinetic_electrons, kinetic_electrons_with_temperature_equation), input_dict, @@ -682,7 +702,7 @@ function setup_time_advance!(pdf, fields, vz, vr, vzeta, vpa, vperp, z, r, gyrop default_rtol=t_params.rtol / 10.0, default_atol=t_params.atol / 10.0, electron_ppar_pdf_solve=true, - preconditioner_type=electron_preconditioner_type) + preconditioner_type=t_params.electron_preconditioner_type) nl_solver_ion_advance_params = setup_nonlinear_solve(t_params.implicit_ion_advance, input_dict, (s=composition.n_ion_species, r=r, z=z, vperp=vperp,