22 double precision,
public ::
mhd_eta = 0.0d0
45 double precision,
public,
protected ::
h_ion_fr=1d0
48 double precision,
public,
protected ::
he_ion_fr=1d0
55 double precision,
public,
protected ::
rr=1d0
57 double precision :: gamma_1, inv_gamma_1
59 double precision :: inv_squared_c0, inv_squared_c
66 integer,
public,
protected ::
rho_
68 integer,
allocatable,
public,
protected ::
mom(:)
70 integer,
public,
protected :: ^
c&m^C_
72 integer,
public,
protected ::
e_
74 integer,
public,
protected :: ^
c&b^C_
76 integer,
public,
protected ::
p_
78 integer,
public,
protected ::
qpar_
82 integer,
public,
protected ::
psi_
84 integer,
public,
protected ::
r_e
86 integer,
public,
protected ::
te_
88 integer,
public,
protected ::
fip_ = -1
90 logical,
public,
protected ::
mhd_fip = .false.
95 integer,
allocatable,
public,
protected ::
tracer(:)
103 integer,
parameter :: divb_none = 0
104 integer,
parameter :: divb_multigrid = -1
105 integer,
parameter :: divb_glm = 1
106 integer,
parameter :: divb_powel = 2
107 integer,
parameter :: divb_janhunen = 3
108 integer,
parameter :: divb_linde = 4
109 integer,
parameter :: divb_lindejanhunen = 5
110 integer,
parameter :: divb_lindepowel = 6
111 integer,
parameter :: divb_lindeglm = 7
112 integer,
parameter :: divb_ct = 8
153 logical,
public,
protected ::
mhd_glm = .false.
196 logical :: total_energy = .true.
200 logical :: gravity_energy
202 character(len=std_len),
public,
protected ::
typedivbfix =
'linde'
204 character(len=std_len),
public,
protected ::
type_ct =
'uct_contact'
206 character(len=std_len) :: typedivbdiff =
'all'
217 subroutine mask_subroutine(ixI^L,ixO^L,w,x,res)
219 integer,
intent(in) :: ixi^
l, ixo^
l
220 double precision,
intent(in) :: x(ixi^s,1:
ndim)
221 double precision,
intent(in) :: w(ixi^s,1:nw)
222 double precision,
intent(inout) :: res(ixi^s)
223 end subroutine mask_subroutine
278 subroutine mhd_read_params(files)
281 character(len=*),
intent(in) :: files(:)
300 do n = 1,
size(files)
301 open(
unitpar, file=trim(files(n)), status=
"old")
302 read(
unitpar, mhd_list,
end=111)
306 end subroutine mhd_read_params
309 subroutine mhd_write_info(fh)
311 integer,
intent(in) :: fh
314 integer,
parameter :: n_par = 1
315 double precision :: values(n_par)
316 integer,
dimension(MPI_STATUS_SIZE) :: st
317 character(len=name_len) :: names(n_par)
319 call mpi_file_write(fh, n_par, 1, mpi_integer, st, er)
323 call mpi_file_write(fh, values, n_par, mpi_double_precision, st, er)
324 call mpi_file_write(fh, names, n_par * name_len, mpi_character, st, er)
325 end subroutine mhd_write_info
353 if(
mype==0)
write(*,*)
'WARNING: set mhd_hydrodynamic_e=F when mhd_internal_e=T'
357 if(
mype==0)
write(*,*)
'WARNING: set has_equi_rho_and_p=F when mhd_internal_e=T'
364 if(
mype==0)
write(*,*)
'WARNING: set mhd_internal_e=F when mhd_hydrodynamic_e=T'
368 if(
mype==0)
write(*,*)
'WARNING: set B0field=F when mhd_hydrodynamic_e=T'
372 if(
mype==0)
write(*,*)
'WARNING: set has_equi_rho_and_p=F when mhd_hydrodynamic_e=T'
379 if(
mype==0)
write(*,*)
'WARNING: set B0field=F when mhd_semirelativistic=T'
383 if(
mype==0)
write(*,*)
'WARNING: set has_equi_rho_and_p=F when mhd_semirelativistic=T'
387 if(
mype==0)
write(*,*)
'WARNING: set mhd_hydrodynamic_e=F when mhd_semirelativistic=T'
394 if(
mype==0)
write(*,*)
'WARNING: set mhd_internal_e=F when mhd_energy=F'
398 if(
mype==0)
write(*,*)
'WARNING: set mhd_hydrodynamic_e=F when mhd_energy=F'
402 if(
mype==0)
write(*,*)
'WARNING: set mhd_thermal_conduction=F when mhd_energy=F'
406 if(
mype==0)
write(*,*)
'WARNING: set mhd_hyperbolic_tc=F when mhd_energy=F'
410 if(
mype==0)
write(*,*)
'WARNING: set mhd_radiative_cooling=F when mhd_energy=F'
414 if(
mype==0)
write(*,*)
'WARNING: set mhd_trac=F when mhd_energy=F'
418 if(
mype==0)
write(*,*)
'WARNING: set mhd_partial_ionization=F when mhd_energy=F'
422 if(
mype==0)
write(*,*)
'WARNING: set B0field=F when mhd_energy=F'
426 if(
mype==0)
write(*,*)
'WARNING: set has_equi_rho_and_p=F when mhd_energy=F'
432 if(
mype==0)
write(*,*)
'WARNING: set mhd_partial_ionization=F when eq_state_units=F'
438 if(
mype==0)
write(*,*)
'WARNING: set either parabolic TC or hyperbolic TC to F'
439 if(
mype==0)
write(*,*)
'WARNING: defaulting to only mhd_hyperbolic_tc=T'
443 call mpistop(
"mhd_hyperbolic_tc_use_perp is not supported in 1D")
467 phys_total_energy=total_energy
470 gravity_energy=.false.
472 gravity_energy=.true.
475 gravity_energy=.false.
481 if(
mype==0)
write(*,*)
'WARNING: reset mhd_trac_type=1 for 1D simulation'
486 if(
mype==0)
write(*,*)
'WARNING: set mhd_trac_mask==bigdouble for global TRAC method'
494 type_divb = divb_none
497 if(
mhd_radiation_fld)
call mpistop(
'To verify whether mg usage for FLD versus divB can be combined')
498 type_divb = divb_multigrid
500 mg%operator_type = mg_laplacian
507 case (
'powel',
'powell')
508 type_divb = divb_powel
510 type_divb = divb_janhunen
512 type_divb = divb_linde
513 case (
'lindejanhunen')
514 type_divb = divb_lindejanhunen
516 type_divb = divb_lindepowel
520 type_divb = divb_lindeglm
525 call mpistop(
'Unknown divB fix')
530 allocate(start_indices(number_species),stop_indices(number_species))
537 mom(:) = var_set_momentum(
ndir)
543 e_ = var_set_energy()
552 mag(:) = var_set_bfield(
ndir)
556 psi_ = var_set_fluxvar(
'psi',
'psi', need_bc=.false.)
562 qpar_ = var_set_fluxvar(
'q',
'q', need_bc=.false.)
564 qperp_ = var_set_fluxvar(
'qperp',
'qperp', need_bc=.false.)
575 fip_ = var_set_fluxvar(
'rho_fip',
'fip', need_bc=.false.)
583 tracer(itr) = var_set_fluxvar(
"trc",
"trp", itr, need_bc=.false.)
589 write(*,*)
'Warning: CAK force addition together with FLD radiation'
594 write(*,*)
'Warning: Optically thin cooling together with FLD radiation'
598 call mpistop(
'using FLD implies the use of an energy equation, set mhd_energy=T')
601 call mpistop(
'using FLD not yet with semirelativistic energy formalism')
604 call mpistop(
'using FLD not yet with hydrodynamic or internal energy formalism')
607 call mpistop(
'using FLD not yet with split off rho and p')
611 r_e = var_set_radiation_energy()
623 te_ = var_set_auxvar(
'Te',
'Te')
632 stop_indices(1)=nwflux
660 allocate(iw_vector(nvector))
661 iw_vector(1) =
mom(1) - 1
662 iw_vector(2) = mag(1) - 1
665 if (.not.
allocated(flux_type))
then
666 allocate(flux_type(
ndir, nwflux))
667 flux_type = flux_default
668 else if (any(shape(flux_type) /= [
ndir, nwflux]))
then
669 call mpistop(
"phys_check error: flux_type has wrong shape")
672 if(nwflux>mag(
ndir))
then
674 flux_type(:,mag(
ndir)+1:nwflux)=flux_hll
679 flux_type(:,
psi_)=flux_special
681 flux_type(idir,mag(idir))=flux_special
685 flux_type(idir,mag(idir))=flux_tvdlf
691 phys_get_dt => mhd_get_dt
694 phys_get_cmax => mhd_get_cmax_semirelati
696 phys_get_cmax => mhd_get_cmax_semirelati_noe
700 phys_get_cmax => mhd_get_cmax_origin
702 phys_get_cmax => mhd_get_cmax_origin_noe
705 phys_get_tcutoff => mhd_get_tcutoff
706 phys_get_h_speed => mhd_get_h_speed
708 phys_get_cbounds => mhd_get_cbounds_split_rho
710 phys_get_cbounds => mhd_get_cbounds_semirelati
712 phys_get_cbounds => mhd_get_cbounds
715 phys_to_primitive => mhd_to_primitive_hde
717 phys_to_conserved => mhd_to_conserved_hde
721 phys_to_primitive => mhd_to_primitive_semirelati
723 phys_to_conserved => mhd_to_conserved_semirelati
726 phys_to_primitive => mhd_to_primitive_semirelati_noe
728 phys_to_conserved => mhd_to_conserved_semirelati_noe
733 phys_to_primitive => mhd_to_primitive_split_rho
735 phys_to_conserved => mhd_to_conserved_split_rho
738 phys_to_primitive => mhd_to_primitive_inte
740 phys_to_conserved => mhd_to_conserved_inte
743 phys_to_primitive => mhd_to_primitive_origin
745 phys_to_conserved => mhd_to_conserved_origin
748 phys_to_primitive => mhd_to_primitive_origin_noe
750 phys_to_conserved => mhd_to_conserved_origin_noe
755 phys_get_flux => mhd_get_flux_hde
758 phys_get_flux => mhd_get_flux_semirelati
760 phys_get_flux => mhd_get_flux_semirelati_noe
764 phys_get_flux => mhd_get_flux_split
766 phys_get_flux => mhd_get_flux
768 phys_get_flux => mhd_get_flux_noe
773 phys_add_source_geom => mhd_add_source_geom_semirelati
775 phys_add_source_geom => mhd_add_source_geom_split
777 phys_add_source_geom => mhd_add_source_geom
779 phys_add_source => mhd_add_source
780 phys_check_params => mhd_check_params
781 phys_write_info => mhd_write_info
784 phys_handle_small_values => mhd_handle_small_values_inte
785 mhd_handle_small_values => mhd_handle_small_values_inte
786 phys_check_w => mhd_check_w_inte
788 phys_handle_small_values => mhd_handle_small_values_hde
789 mhd_handle_small_values => mhd_handle_small_values_hde
790 phys_check_w => mhd_check_w_hde
792 phys_handle_small_values => mhd_handle_small_values_semirelati
793 mhd_handle_small_values => mhd_handle_small_values_semirelati
794 phys_check_w => mhd_check_w_semirelati
796 phys_handle_small_values => mhd_handle_small_values_split
797 mhd_handle_small_values => mhd_handle_small_values_split
798 phys_check_w => mhd_check_w_split
800 phys_handle_small_values => mhd_handle_small_values_origin
801 mhd_handle_small_values => mhd_handle_small_values_origin
802 phys_check_w => mhd_check_w_origin
804 phys_handle_small_values => mhd_handle_small_values_noe
805 mhd_handle_small_values => mhd_handle_small_values_noe
806 phys_check_w => mhd_check_w_noe
810 phys_get_pthermal => mhd_get_pthermal_inte
813 phys_get_pthermal => mhd_get_pthermal_hde
816 phys_get_pthermal => mhd_get_pthermal_semirelati
819 phys_get_pthermal => mhd_get_pthermal_origin
822 phys_get_pthermal => mhd_get_pthermal_noe
827 phys_set_equi_vars => set_equi_vars_grid
830 if(type_divb==divb_glm)
then
831 phys_modify_wlr => mhd_modify_wlr
837 phys_update_temperature => mhd_update_temperature
864 transverse_ghost_cells = 1
865 phys_get_ct_velocity => mhd_get_ct_velocity_average
866 phys_update_faces => mhd_update_faces_average
868 transverse_ghost_cells = 1
869 phys_get_ct_velocity => mhd_get_ct_velocity_contact
870 phys_update_faces => mhd_update_faces_contact
872 transverse_ghost_cells = 2
873 phys_get_ct_velocity => mhd_get_ct_velocity_hll
874 phys_update_faces => mhd_update_faces_hll
876 call mpistop(
'choose average, uct_contact,or uct_hll for type_ct!')
879 phys_modify_wlr => mhd_modify_wlr
881 phys_boundary_adjust => mhd_boundary_adjust
887 call mpistop(
'To verify whether mg usage for FLD versus divB can be combined')
892 call mhd_physical_units()
925 call mpistop(
"thermal conduction needs mhd_energy=T")
928 call mpistop(
"hyperbolic thermal conduction needs mhd_energy=T")
931 call mpistop(
"radiative cooling needs mhd_energy=T")
937 if(
mype==0)
write(*,*)
'WARNING: turning mhd_equi_thermal=F as no splitting or total e in use'
940 if(
mype==0)
write(*,*)
'Will subtract thermal balance in TC or RC with mhd_equi_thermal=T'
943 if(
mype==0)
write(*,*)
'WARNING: turning mhd_equi_thermal=F as no TC or RC in use'
962 tc_fl%get_temperature_from_conserved => mhd_get_temperature_from_eint_with_equi
964 tc_fl%get_temperature_from_conserved => mhd_get_temperature_from_eint
970 tc_fl%get_temperature_from_eint => mhd_get_temperature_from_eint_with_equi
972 tc_fl%subtract_equi = .true.
973 tc_fl%get_temperature_equi => mhd_get_temperature_equi
974 tc_fl%get_rho_equi => mhd_get_rho_equi
976 tc_fl%subtract_equi = .false.
979 tc_fl%get_temperature_from_eint => mhd_get_temperature_from_eint
1009 rc_fl%subtract_equi = .true.
1010 rc_fl%get_rho_equi => mhd_get_rho_equi
1011 rc_fl%get_pthermal_equi => mhd_get_pe_equi
1012 rc_fl%get_temperature_equi => mhd_get_temperature_equi
1014 rc_fl%subtract_equi = .false.
1024 phys_te_images => mhd_te_images
1030 write(*,*)
'*****Using hyperresistivity: with mhd_eta_hyper :',
mhd_eta_hyper
1034 call mpistop(
"Must have B0field=F when using hyperresistivity")
1038 call mpistop(
"Must have mhd_eta_hyper positive when using hyperresistivity")
1055 call mpistop(
"Must have has_equi_rho_and_p=F when mhd_rotating_frame=T")
1069 call mpistop(
"Must have mhd_hall=F when mhd_semirelativistic=T")
1073 call mpistop(
"Must have Cartesian coordinates for Hall")
1077 phys_wider_stencil = 1
1084 call add_sts_method(get_ambipolar_dt,sts_set_source_ambipolar,mag(1),&
1095 phys_wider_stencil = 1
1105 call mpistop(
"CAK implementation not available in internal or semirelativistic variants")
1108 call mpistop(
"CAK force implementation not available for split off pressure and density")
1116 subroutine mhd_te_images
1121 case(
'EIvtiCCmpi',
'EIvtuCCmpi')
1123 case(
'ESvtiCCmpi',
'ESvtuCCmpi')
1125 case(
'SIvtiCCmpi',
'SIvtuCCmpi')
1127 case(
'WIvtiCCmpi',
'WIvtuCCmpi')
1130 call mpistop(
"Error in synthesize emission: Unknown convert_type")
1132 end subroutine mhd_te_images
1138 subroutine mhd_sts_set_source_tc_mhd(ixI^L,ixO^L,w,x,wres,fix_conserve_at_step,my_dt,igrid,nflux)
1142 integer,
intent(in) :: ixi^
l, ixo^
l, igrid, nflux
1143 double precision,
intent(in) :: x(ixi^s,1:
ndim)
1144 double precision,
intent(inout) :: wres(ixi^s,1:nw), w(ixi^s,1:nw)
1145 double precision,
intent(in) :: my_dt
1146 logical,
intent(in) :: fix_conserve_at_step
1148 end subroutine mhd_sts_set_source_tc_mhd
1150 subroutine mhd_sts_set_source_tc_hd(ixI^L,ixO^L,w,x,wres,fix_conserve_at_step,my_dt,igrid,nflux)
1154 integer,
intent(in) :: ixi^
l, ixo^
l, igrid, nflux
1155 double precision,
intent(in) :: x(ixi^s,1:
ndim)
1156 double precision,
intent(inout) :: wres(ixi^s,1:nw), w(ixi^s,1:nw)
1157 double precision,
intent(in) :: my_dt
1158 logical,
intent(in) :: fix_conserve_at_step
1160 end subroutine mhd_sts_set_source_tc_hd
1162 function mhd_get_tc_dt_mhd(w,ixI^L,ixO^L,dx^D,x)
result(dtnew)
1169 integer,
intent(in) :: ixi^
l, ixo^
l
1170 double precision,
intent(in) ::
dx^
d, x(ixi^s,1:
ndim)
1171 double precision,
intent(in) :: w(ixi^s,1:nw)
1172 double precision :: dtnew
1175 end function mhd_get_tc_dt_mhd
1177 function mhd_get_tc_dt_hd(w,ixI^L,ixO^L,dx^D,x)
result(dtnew)
1184 integer,
intent(in) :: ixi^
l, ixo^
l
1185 double precision,
intent(in) ::
dx^
d, x(ixi^s,1:
ndim)
1186 double precision,
intent(in) :: w(ixi^s,1:nw)
1187 double precision :: dtnew
1190 end function mhd_get_tc_dt_hd
1192 subroutine mhd_tc_handle_small_e(w, x, ixI^L, ixO^L, step)
1195 integer,
intent(in) :: ixi^
l,ixo^
l
1196 double precision,
intent(inout) :: w(ixi^s,1:nw)
1197 double precision,
intent(in) :: x(ixi^s,1:
ndim)
1198 integer,
intent(in) :: step
1199 character(len=140) :: error_msg
1201 write(error_msg,
"(a,i3)")
"Thermal conduction step ", step
1202 call mhd_handle_small_ei(w,x,ixi^
l,ixo^
l,
e_,error_msg)
1203 end subroutine mhd_tc_handle_small_e
1206 subroutine tc_params_read_mhd(fl)
1208 type(tc_fluid),
intent(inout) :: fl
1210 double precision :: tc_k_para=0d0
1211 double precision :: tc_k_perp=0d0
1214 logical :: tc_perpendicular=.false.
1215 logical :: tc_saturate=.false.
1216 character(len=std_len) :: tc_slope_limiter=
"MC"
1218 namelist /tc_list/ tc_perpendicular, tc_saturate, tc_slope_limiter, tc_k_para, tc_k_perp
1222 read(
unitpar, tc_list,
end=111)
1226 fl%tc_perpendicular = tc_perpendicular
1227 fl%tc_saturate = tc_saturate
1228 fl%tc_k_para = tc_k_para
1229 fl%tc_k_perp = tc_k_perp
1230 select case(tc_slope_limiter)
1232 fl%tc_slope_limiter = 0
1235 fl%tc_slope_limiter = 1
1238 fl%tc_slope_limiter = 2
1241 fl%tc_slope_limiter = 3
1244 fl%tc_slope_limiter = 4
1247 fl%tc_slope_limiter = 5
1249 call mpistop(
"Unknown tc_slope_limiter, choose MC, minmod, superbee, koren, vanleer")
1251 end subroutine tc_params_read_mhd
1255 subroutine rc_params_read(fl)
1258 type(rc_fluid),
intent(inout) :: fl
1262 double precision :: rad_damp_height=0.5d0
1263 double precision :: rad_damp_scale=0.15d0
1266 integer :: ncool = 4000
1268 logical :: tfix=.false.
1270 logical :: rc_split=.false.
1271 logical :: rad_damp=.false.
1273 character(len=std_len) :: coolcurve=
'JCcorona'
1274 logical :: rad_newton = .false.
1275 double precision :: rad_newton_trad = 0.006d0
1276 double precision :: rad_newton_rhosurf = 1.d4
1277 double precision :: rad_newton_pthick = 25.d0
1279 namelist /rc_list/ coolcurve, ncool, tlow, tfix, rc_split, &
1280 rad_newton, rad_newton_trad, rad_newton_rhosurf, &
1281 rad_newton_pthick, rad_damp, rad_damp_height, rad_damp_scale
1285 read(
unitpar, rc_list,
end=111)
1290 fl%coolcurve=coolcurve
1293 fl%rc_split=rc_split
1294 fl%rad_damp=rad_damp
1295 fl%rad_damp_height=rad_damp_height
1296 fl%rad_damp_scale=rad_damp_scale
1297 fl%rad_newton=rad_newton
1298 fl%rad_newton_trad=rad_newton_trad
1299 fl%rad_newton_rhosurf=rad_newton_rhosurf
1300 fl%rad_newton_pthick=rad_newton_pthick
1301 end subroutine rc_params_read
1304 subroutine set_equi_vars_grid_faces(igrid,x,ixI^L,ixO^L)
1307 integer,
intent(in) :: igrid, ixi^
l, ixo^
l
1308 double precision,
intent(in) :: x(ixi^s,1:
ndim)
1310 double precision :: delx(ixi^s,1:
ndim)
1311 double precision :: xc(ixi^s,1:
ndim),xshift^
d
1312 integer :: idims, ixc^
l, hxo^
l, ix, idims2
1318 delx(ixi^s,1:
ndim)=ps(igrid)%dx(ixi^s,1:
ndim)
1322 hxo^
l=ixo^
l-
kr(idims,^
d);
1328 ixcmax^
d=ixomax^
d; ixcmin^
d=hxomin^
d;
1331 xshift^
d=half*(one-
kr(^
d,idims));
1338 xc(ix^
d%ixC^s,^
d)=x(ix^
d%ixC^s,^
d)+(half-xshift^
d)*delx(ix^
d%ixC^s,^
d)
1342 call usr_set_equi_vars(ixi^l,ixc^l,xc,ps(igrid)%equi_vars(ixi^s,1:number_equi_vars,idims))
1344 end subroutine set_equi_vars_grid_faces
1347 subroutine set_equi_vars_grid(igrid)
1351 integer,
intent(in) :: igrid
1357 call set_equi_vars_grid_faces(igrid,ps(igrid)%x,ixg^
ll,
ixm^
ll)
1359 end subroutine set_equi_vars_grid
1362 function convert_vars_splitting(ixI^L,ixO^L, w, x, nwc)
result(wnew)
1364 integer,
intent(in) :: ixi^
l,ixo^
l, nwc
1365 double precision,
intent(in) :: w(ixi^s, 1:nw)
1366 double precision,
intent(in) :: x(ixi^s,1:
ndim)
1367 double precision :: wnew(ixo^s, 1:nwc)
1374 wnew(ixo^s,
mom(:))=w(ixo^s,
mom(:))
1380 wnew(ixo^s,mag(1:
ndir))=w(ixo^s,mag(1:
ndir))
1384 wnew(ixo^s,
e_)=w(ixo^s,
e_)
1388 if(
b0field .and. total_energy)
then
1389 wnew(ixo^s,
e_)=wnew(ixo^s,
e_)+0.5d0*sum(
block%B0(ixo^s,:,0)**2,dim=
ndim+1) &
1390 + sum(w(ixo^s,mag(:))*
block%B0(ixo^s,:,0),dim=
ndim+1)
1394 end function convert_vars_splitting
1396 subroutine mhd_check_params
1403 ngridvars,num_particles,physics_type_particles
1406 double precision :: a,
b,xfrac,yfrac
1411 if (particles_eta < zero) particles_eta =
mhd_eta
1412 if (particles_etah < zero) particles_eta =
mhd_etah
1418 if (
mhd_gamma <= 0.0d0)
call mpistop (
"Error: mhd_gamma <= 0")
1419 if (
mhd_adiab < 0.0d0)
call mpistop (
"Error: mhd_adiab < 0")
1423 call mpistop (
"Error: mhd_gamma <= 0 or mhd_gamma == 1")
1424 inv_gamma_1=1.d0/gamma_1
1430 call mpistop(
"usr_set_equi_vars has to be implemented in the user file")
1435 if(
mype .eq. 0) print*,
" add conversion method: split -> full "
1443 call mpistop(
'select IMEX scheme for FLD radiation use')
1446 call phys_set_mg_bounds()
1448 if(.not.
fld_no_mg)
call mpistop(
'multigrid must have BCs for IMEX and FLD radiation use')
1451 write(*,*)
'==FLD SETUP======================'
1452 write(*,*)
'Using FLD with settings:'
1457 write(*,*)
'Using FLD with settings: fld_kappa0=',
fld_kappa0
1458 write(*,*)
'Using FLD with settings: fld_opal_table=',
fld_opal_table
1460 write(*,*)
'Using FLD with settings: fld_bisect_tol=',
fld_bisect_tol
1461 write(*,*)
'Using FLD with settings: fld_diff_tol=',
fld_diff_tol
1465 print *,
'NORMALIZED arad_norm=',
arad_norm
1466 print *,
'NORMALIZED c_norm=',
c_norm
1473 print *,
'physical fld_kappa (in cgs or SI) =',
fld_kappa0
1477 write(*,*)
'===FLD SETUP====================='
1482 write(*,*)
'====MHD run with settings===================='
1483 write(*,*)
'Using mod_mhd_phys with settings:'
1485 write(*,*)
'Dimensionality :',
ndim
1486 write(*,*)
'vector components:',
ndir
1488 write(*,*)
'number of variables nw=',nw
1489 write(*,*)
' start index iwstart=',iwstart
1490 write(*,*)
'number of vector variables=',nvector
1491 write(*,*)
'number of stagger variables nws=',nws
1492 write(*,*)
'number of variables with BCs=',nwgc
1493 write(*,*)
'number of vars with fluxes=',nwflux
1494 write(*,*)
'number of vars with flux + BC=',nwfluxbc
1495 write(*,*)
'number of auxiliary variables=',nwaux
1496 write(*,*)
'number of extra vars without flux=',nwextra
1497 write(*,*)
'number of extra vars for wextra=',nw_extra
1498 write(*,*)
'number of auxiliary I/O variables=',
nwauxio
1500 write(*,*)
' mhd_energy=',
mhd_energy,
' with total_energy=',total_energy
1505 write(*,*)
' mhd_eta=',
mhd_eta,
' nonzero implies resistivity'
1519 write(*,*)
'*****Using particles: with mhd_eta, mhd_etah :',
mhd_eta,
mhd_etah
1520 write(*,*)
'*****Using particles: particles_eta, particles_etah :', particles_eta, particles_etah
1521 write(*,*)
'*****Using particles: npayload,ngridvars :', npayload,ngridvars
1522 write(*,*)
'*****Using particles: nusrpayload :', nusrpayload
1523 write(*,*)
'*****Using particles: num_particles :', num_particles
1524 write(*,*)
'*****Using particles: physics_type_particles=',physics_type_particles
1527 write(*,*)
'number due to phys_wider_stencil=',phys_wider_stencil
1528 write(*,*)
'==========================================='
1529 print *,
'========EOS and UNITS==========='
1535 print *,
'========EOS and UNITS==========='
1557 print *,
' compare this to ',mp_si*(1.d0+4.d0*
he_abundance)
1559 print *,
' compare this to ',mp_cgs*(1.d0+4.d0*
he_abundance)
1563 print *,
' compare this to ',kb_si*(2.d0+3.d0*
he_abundance)
1567 print *,
' compare this to ',kb_cgs*(2.d0+3.d0*
he_abundance)
1575 print *,
'mass fraction hydrogen X is =',1/a,
' and this equals ', 1.d0/(1.d0+4.d0*
he_abundance)
1576 print *,
'mass fraction helium Y is =',yfrac
1577 print *,
' check that 1/mu',
b/a,
' is equal to 2X+3Y/4=',2.d0*xfrac+3.d0*yfrac/4.d0
1580 print *,
'========UNITS==========='
1583 end subroutine mhd_check_params
1585 subroutine mhd_physical_units()
1587 double precision :: mp,kb,miu0,c_lightspeed,xfrac,sigma_telectron
1588 double precision :: a,
b
1596 sigma_telectron=sigma_te_si
1602 c_lightspeed=const_c
1603 sigma_telectron=sigma_te_cgs
1762 end subroutine mhd_physical_units
1764 subroutine mhd_check_w_semirelati(primitive,ixI^L,ixO^L,w,flag)
1767 logical,
intent(in) :: primitive
1768 logical,
intent(inout) :: flag(ixi^s,1:nw)
1769 integer,
intent(in) :: ixi^
l, ixo^
l
1770 double precision,
intent(in) :: w(ixi^s,nw)
1772 double precision :: tmp,
b(1:
ndir),v(1:
ndir),factor
1783 {
do ix^db=ixomin^db,ixomax^db \}
1787 {
do ix^db=ixomin^db,ixomax^db \}
1789 tmp=(^
c&w(ix^d,
b^
c_)*w(ix^d,
m^
c_)+)*inv_squared_c
1790 factor=1.0d0/(w(ix^d,
rho_)*(w(ix^d,
rho_)+(^
c&w(ix^d,
b^
c_)**2+)*inv_squared_c))
1791 ^
c&v(^
c)=factor*(w(ix^d,
m^
c_)*w(ix^d,
rho_)+w(ix^d,
b^
c_)*tmp)\
1794 b(1)=w(ix^d,b2_)*v(3)-w(ix^d,b3_)*v(2)
1795 b(2)=w(ix^d,b3_)*v(1)-w(ix^d,b1_)*v(3)
1796 b(3)=w(ix^d,b1_)*v(2)-w(ix^d,b2_)*v(1)
1801 b(2)=w(ix^d,b1_)*v(2)-w(ix^d,b2_)*v(1)
1807 tmp=w(ix^d,
e_)-half*((^
c&v(^
c)**2+)*w(ix^d,
rho_)&
1808 +(^
c&w(ix^d,
b^
c_)**2+)+(^
c&
b(^
c)**2+)*inv_squared_c)
1809 if(tmp<small_e) flag(ix^d,
e_)=.true.
1815 end subroutine mhd_check_w_semirelati
1817 subroutine mhd_check_w_origin(primitive,ixI^L,ixO^L,w,flag)
1820 logical,
intent(in) :: primitive
1821 integer,
intent(in) :: ixi^
l, ixo^
l
1822 double precision,
intent(in) :: w(ixi^s,nw)
1823 logical,
intent(inout) :: flag(ixi^s,1:nw)
1828 {
do ix^db=ixomin^db,ixomax^db\}
1841 end subroutine mhd_check_w_origin
1843 subroutine mhd_check_w_split(primitive,ixI^L,ixO^L,w,flag)
1846 logical,
intent(in) :: primitive
1847 integer,
intent(in) :: ixi^
l, ixo^
l
1848 double precision,
intent(in) :: w(ixi^s,nw)
1849 logical,
intent(inout) :: flag(ixi^s,1:nw)
1851 double precision :: tmp
1855 {
do ix^db=ixomin^db,ixomax^db\}
1861 tmp=w(ix^
d,
e_)-half*((^
c&w(ix^
d,
m^
c_)**2+)/tmp+(^
c&w(ix^
d,
b^
c_)**2+))
1866 end subroutine mhd_check_w_split
1868 subroutine mhd_check_w_noe(primitive,ixI^L,ixO^L,w,flag)
1871 logical,
intent(in) :: primitive
1872 integer,
intent(in) :: ixi^
l, ixo^
l
1873 double precision,
intent(in) :: w(ixi^s,nw)
1874 logical,
intent(inout) :: flag(ixi^s,1:nw)
1879 {
do ix^db=ixomin^db,ixomax^db\}
1883 end subroutine mhd_check_w_noe
1885 subroutine mhd_check_w_inte(primitive,ixI^L,ixO^L,w,flag)
1888 logical,
intent(in) :: primitive
1889 integer,
intent(in) :: ixi^
l, ixo^
l
1890 double precision,
intent(in) :: w(ixi^s,nw)
1891 logical,
intent(inout) :: flag(ixi^s,1:nw)
1896 {
do ix^db=ixomin^db,ixomax^db\}
1905 end subroutine mhd_check_w_inte
1907 subroutine mhd_check_w_hde(primitive,ixI^L,ixO^L,w,flag)
1910 logical,
intent(in) :: primitive
1911 integer,
intent(in) :: ixi^
l, ixo^
l
1912 double precision,
intent(in) :: w(ixi^s,nw)
1913 logical,
intent(inout) :: flag(ixi^s,1:nw)
1918 {
do ix^db=ixomin^db,ixomax^db\}
1927 end subroutine mhd_check_w_hde
1929 subroutine mhd_bound_fip(primitive, ixI^L, ixO^L, w)
1931 logical,
intent(in) :: primitive
1932 integer,
intent(in) :: ixi^
l, ixo^
l
1933 double precision,
intent(inout) :: w(ixi^s,1:nw)
1935 double precision :: rho_safe(ixi^s), fip_prim(ixi^s)
1947 fip_prim(ixo^s) = w(ixo^s,
fip_) / rho_safe(ixo^s)
1948 fip_prim(ixo^s) = min(
maxfip, max(
minfip, fip_prim(ixo^s)))
1949 w(ixo^s,
fip_) = rho_safe(ixo^s) * fip_prim(ixo^s)
1951 end subroutine mhd_bound_fip
1954 subroutine mhd_to_conserved_origin(ixI^L,ixO^L,w,x)
1956 integer,
intent(in) :: ixi^
l, ixo^
l
1957 double precision,
intent(inout) :: w(ixi^s, nw)
1958 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
1962 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
1963 {
do ix^db=ixomin^db,ixomax^db\}
1965 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1&
1967 +(^
c&w(ix^
d,
b^
c_)**2+))
1973 end subroutine mhd_to_conserved_origin
1976 subroutine mhd_to_conserved_origin_noe(ixI^L,ixO^L,w,x)
1978 integer,
intent(in) :: ixi^
l, ixo^
l
1979 double precision,
intent(inout) :: w(ixi^s, nw)
1980 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
1984 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
1985 {
do ix^db=ixomin^db,ixomax^db\}
1991 end subroutine mhd_to_conserved_origin_noe
1994 subroutine mhd_to_conserved_hde(ixI^L,ixO^L,w,x)
1996 integer,
intent(in) :: ixi^
l, ixo^
l
1997 double precision,
intent(inout) :: w(ixi^s, nw)
1998 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2002 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
2003 {
do ix^db=ixomin^db,ixomax^db\}
2005 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1&
2012 end subroutine mhd_to_conserved_hde
2015 subroutine mhd_to_conserved_inte(ixI^L,ixO^L,w,x)
2017 integer,
intent(in) :: ixi^
l, ixo^
l
2018 double precision,
intent(inout) :: w(ixi^s, nw)
2019 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2023 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
2024 {
do ix^db=ixomin^db,ixomax^db\}
2026 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1
2032 end subroutine mhd_to_conserved_inte
2035 subroutine mhd_to_conserved_split_rho(ixI^L,ixO^L,w,x)
2037 integer,
intent(in) :: ixi^
l, ixo^
l
2038 double precision,
intent(inout) :: w(ixi^s, nw)
2039 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2041 double precision :: rho
2044 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
2045 {
do ix^db=ixomin^db,ixomax^db\}
2048 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1&
2049 +half*((^
c&w(ix^
d,
m^
c_)**2+)*rho&
2050 +(^
c&w(ix^
d,
b^
c_)**2+))
2056 end subroutine mhd_to_conserved_split_rho
2059 subroutine mhd_to_conserved_semirelati(ixI^L,ixO^L,w,x)
2061 integer,
intent(in) :: ixi^
l, ixo^
l
2062 double precision,
intent(inout) :: w(ixi^s, nw)
2063 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2066 double precision :: ef(ixo^s,1:
ndir), s(ixo^s,1:
ndir)
2069 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
2070 {
do ix^db=ixomin^db,ixomax^db\}
2072 ef(ix^
d,1)=w(ix^
d,b2_)*w(ix^
d,m3_)-w(ix^
d,b3_)*w(ix^
d,m2_)
2073 ef(ix^
d,2)=w(ix^
d,b3_)*w(ix^
d,m1_)-w(ix^
d,b1_)*w(ix^
d,m3_)
2074 ef(ix^
d,3)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2075 s(ix^
d,1)=ef(ix^
d,2)*w(ix^
d,b3_)-ef(ix^
d,3)*w(ix^
d,b2_)
2076 s(ix^
d,2)=ef(ix^
d,3)*w(ix^
d,b1_)-ef(ix^
d,1)*w(ix^
d,b3_)
2077 s(ix^
d,3)=ef(ix^
d,1)*w(ix^
d,b2_)-ef(ix^
d,2)*w(ix^
d,b1_)
2082 ef(ix^
d,2)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2083 s(ix^
d,1)=-ef(ix^
d,2)*w(ix^
d,b2_)
2084 s(ix^
d,2)=ef(ix^
d,2)*w(ix^
d,b1_)
2092 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1
2096 w(ix^
d,
e_)=w(ix^
d,
p_)*inv_gamma_1&
2098 +(^
c&w(ix^
d,
b^
c_)**2+)&
2099 +(^
c&ef(ix^
d,^
c)**2+)*inv_squared_c)
2108 end subroutine mhd_to_conserved_semirelati
2110 subroutine mhd_to_conserved_semirelati_noe(ixI^L,ixO^L,w,x)
2112 integer,
intent(in) :: ixi^
l, ixo^
l
2113 double precision,
intent(inout) :: w(ixi^s, nw)
2114 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2116 double precision :: e(ixo^s,1:
ndir), s(ixo^s,1:
ndir)
2119 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^
l, ixo^
l, w)
2120 {
do ix^db=ixomin^db,ixomax^db\}
2122 e(ix^
d,1)=w(ix^
d,b2_)*w(ix^
d,m3_)-w(ix^
d,b3_)*w(ix^
d,m2_)
2123 e(ix^
d,2)=w(ix^
d,b3_)*w(ix^
d,m1_)-w(ix^
d,b1_)*w(ix^
d,m3_)
2124 e(ix^
d,3)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2125 s(ix^
d,1)=e(ix^
d,2)*w(ix^
d,b3_)-e(ix^
d,3)*w(ix^
d,b2_)
2126 s(ix^
d,2)=e(ix^
d,3)*w(ix^
d,b1_)-e(ix^
d,1)*w(ix^
d,b3_)
2127 s(ix^
d,3)=e(ix^
d,1)*w(ix^
d,b2_)-e(ix^
d,2)*w(ix^
d,b1_)
2132 e(ix^
d,2)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2133 s(ix^
d,1)=-e(ix^
d,2)*w(ix^
d,b2_)
2134 s(ix^
d,2)=e(ix^
d,2)*w(ix^
d,b1_)
2143 end subroutine mhd_to_conserved_semirelati_noe
2146 subroutine mhd_to_primitive_origin(ixI^L,ixO^L,w,x)
2148 integer,
intent(in) :: ixi^
l, ixo^
l
2149 double precision,
intent(inout) :: w(ixi^s, nw)
2150 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2152 double precision :: inv_rho
2157 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_origin')
2160 {
do ix^db=ixomin^db,ixomax^db\}
2161 inv_rho = 1.d0/w(ix^
d,
rho_)
2166 w(ix^
d,
p_)=gamma_1*(w(ix^
d,
e_)&
2168 +(^
c&w(ix^
d,
b^
c_)**2+)))
2170 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2171 end subroutine mhd_to_primitive_origin
2174 subroutine mhd_to_primitive_origin_noe(ixI^L,ixO^L,w,x)
2176 integer,
intent(in) :: ixi^
l, ixo^
l
2177 double precision,
intent(inout) :: w(ixi^s, nw)
2178 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2180 double precision :: inv_rho
2185 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_origin_noe')
2188 {
do ix^db=ixomin^db,ixomax^db\}
2189 inv_rho = 1.d0/w(ix^
d,
rho_)
2194 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2195 end subroutine mhd_to_primitive_origin_noe
2198 subroutine mhd_to_primitive_hde(ixI^L,ixO^L,w,x)
2200 integer,
intent(in) :: ixi^
l, ixo^
l
2201 double precision,
intent(inout) :: w(ixi^s, nw)
2202 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2204 double precision :: inv_rho
2209 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_hde')
2212 {
do ix^db=ixomin^db,ixomax^db\}
2213 inv_rho = 1d0/w(ix^
d,
rho_)
2220 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2221 end subroutine mhd_to_primitive_hde
2224 subroutine mhd_to_primitive_inte(ixI^L,ixO^L,w,x)
2226 integer,
intent(in) :: ixi^
l, ixo^
l
2227 double precision,
intent(inout) :: w(ixi^s, nw)
2228 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2230 double precision :: inv_rho
2235 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_inte')
2238 {
do ix^db=ixomin^db,ixomax^db\}
2240 w(ix^
d,
p_)=w(ix^
d,
e_)*gamma_1
2242 inv_rho = 1.d0/w(ix^
d,
rho_)
2246 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2247 end subroutine mhd_to_primitive_inte
2250 subroutine mhd_to_primitive_split_rho(ixI^L,ixO^L,w,x)
2252 integer,
intent(in) :: ixi^
l, ixo^
l
2253 double precision,
intent(inout) :: w(ixi^s, nw)
2254 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2256 double precision :: inv_rho
2261 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_split_rho')
2264 {
do ix^db=ixomin^db,ixomax^db\}
2270 w(ix^
d,
p_)=gamma_1*(w(ix^
d,
e_)&
2272 (^
c&w(ix^
d,
m^
c_)**2+)+(^
c&w(ix^
d,
b^
c_)**2+)))
2274 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2275 end subroutine mhd_to_primitive_split_rho
2278 subroutine mhd_to_primitive_semirelati(ixI^L,ixO^L,w,x)
2280 integer,
intent(in) :: ixi^
l, ixo^
l
2281 double precision,
intent(inout) :: w(ixi^s, nw)
2282 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2284 double precision :: e(1:
ndir), tmp, factor
2289 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_semirelati')
2292 {
do ix^db=ixomin^db,ixomax^db\}
2294 tmp=(^
c&w(ix^
d,
b^
c_)*w(ix^
d,
m^
c_)+)*inv_squared_c
2295 factor=1.0d0/(w(ix^
d,
rho_)*(w(ix^
d,
rho_)+(^
c&w(ix^
d,
b^
c_)**2+)*inv_squared_c))
2301 w(ix^
d,
p_)=gamma_1*w(ix^
d,
e_)
2305 e(1)=w(ix^
d,b2_)*w(ix^
d,m3_)-w(ix^
d,b3_)*w(ix^
d,m2_)
2306 e(2)=w(ix^
d,b3_)*w(ix^
d,m1_)-w(ix^
d,b1_)*w(ix^
d,m3_)
2307 e(3)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2311 e(2)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
2317 w(ix^
d,
p_)=gamma_1*(w(ix^
d,
e_)&
2319 +(^
c&w(ix^
d,
b^
c_)**2+)&
2320 +(^
c&e(^
c)**2+)*inv_squared_c))
2323 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2324 end subroutine mhd_to_primitive_semirelati
2327 subroutine mhd_to_primitive_semirelati_noe(ixI^L,ixO^L,w,x)
2329 integer,
intent(in) :: ixi^
l, ixo^
l
2330 double precision,
intent(inout) :: w(ixi^s, nw)
2331 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2333 double precision :: tmp, factor
2338 call mhd_handle_small_values(.false., w, x, ixi^
l, ixo^
l,
'mhd_to_primitive_semirelati_noe')
2341 {
do ix^db=ixomin^db,ixomax^db\}
2344 tmp=(^
c&w(ix^
d,
b^
c_)*w(ix^
d,
m^
c_)+)*inv_squared_c
2345 factor=1.0d0/(w(ix^
d,
rho_)*(w(ix^
d,
rho_)+(^
c&w(ix^
d,
b^
c_)**2+)*inv_squared_c))
2348 if (
mhd_fip)
call mhd_bound_fip(.true., ixi^l, ixo^l, w)
2349 end subroutine mhd_to_primitive_semirelati_noe
2354 integer,
intent(in) :: ixi^
l, ixo^
l
2355 double precision,
intent(inout) :: w(ixi^s, nw)
2356 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2361 {
do ix^db=ixomin^db,ixomax^db\}
2364 +half*((^
c&w(ix^
d,
m^
c_)**2+)/&
2366 +(^
c&w(ix^
d,
b^
c_)**2+))
2369 {
do ix^db=ixomin^db,ixomax^db\}
2371 w(ix^d,
e_)=w(ix^d,
e_)&
2372 +half*((^
c&w(ix^d,
m^
c_)**2+)/w(ix^d,
rho_)&
2373 +(^
c&w(ix^d,
b^
c_)**2+))
2379 subroutine mhd_ei_to_e_hde(ixI^L,ixO^L,w,x)
2381 integer,
intent(in) :: ixi^
l, ixo^
l
2382 double precision,
intent(inout) :: w(ixi^s, nw)
2383 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2387 {
do ix^db=ixomin^db,ixomax^db\}
2393 end subroutine mhd_ei_to_e_hde
2396 subroutine mhd_ei_to_e_semirelati(ixI^L,ixO^L,w,x)
2398 integer,
intent(in) :: ixi^
l, ixo^
l
2399 double precision,
intent(inout) :: w(ixi^s, nw)
2400 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2402 w(ixo^s,
p_)=w(ixo^s,
e_)*gamma_1
2403 call mhd_to_conserved_semirelati(ixi^
l,ixo^
l,w,x)
2405 end subroutine mhd_ei_to_e_semirelati
2410 integer,
intent(in) :: ixi^
l, ixo^
l
2411 double precision,
intent(inout) :: w(ixi^s, nw)
2412 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2417 {
do ix^db=ixomin^db,ixomax^db\}
2420 -half*((^
c&w(ix^
d,
m^
c_)**2+)/&
2422 +(^
c&w(ix^
d,
b^
c_)**2+))
2425 {
do ix^db=ixomin^db,ixomax^db\}
2427 w(ix^d,
e_)=w(ix^d,
e_)&
2428 -half*((^
c&w(ix^d,
m^
c_)**2+)/w(ix^d,
rho_)&
2429 +(^
c&w(ix^d,
b^
c_)**2+))
2433 if(fix_small_values)
then
2434 call mhd_handle_small_ei(w,x,ixi^l,ixi^l,
e_,
'mhd_e_to_ei')
2440 subroutine mhd_e_to_ei_hde(ixI^L,ixO^L,w,x)
2442 integer,
intent(in) :: ixi^
l, ixo^
l
2443 double precision,
intent(inout) :: w(ixi^s, nw)
2444 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2448 {
do ix^db=ixomin^db,ixomax^db\}
2454 if(fix_small_values)
then
2455 call mhd_handle_small_ei(w,x,ixi^l,ixi^l,
e_,
'mhd_e_to_ei_hde')
2458 end subroutine mhd_e_to_ei_hde
2461 subroutine mhd_e_to_ei_semirelati(ixI^L,ixO^L,w,x)
2463 integer,
intent(in) :: ixi^
l, ixo^
l
2464 double precision,
intent(inout) :: w(ixi^s, nw)
2465 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
2467 call mhd_to_primitive_semirelati(ixi^
l,ixo^
l,w,x)
2468 w(ixo^s,
e_)=w(ixo^s,
p_)*inv_gamma_1
2470 end subroutine mhd_e_to_ei_semirelati
2472 subroutine mhd_handle_small_values_semirelati(primitive, w, x, ixI^L, ixO^L, subname)
2475 logical,
intent(in) :: primitive
2476 integer,
intent(in) :: ixi^
l,ixo^
l
2477 double precision,
intent(inout) :: w(ixi^s,1:nw)
2478 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2479 character(len=*),
intent(in) :: subname
2481 double precision :: e(ixi^s,1:
ndir), pressure(ixi^s), v(ixi^s,1:
ndir)
2482 double precision :: tmp, factor
2484 logical :: flag(ixi^s,1:nw)
2493 {
do ix^db=ixomin^db,ixomax^db\}
2495 tmp=(^
c&w(ix^
d,
b^
c_)*w(ix^
d,
m^
c_)+)*inv_squared_c
2496 factor=1.0d0/(w(ix^
d,
rho_)*(w(ix^
d,
rho_)+(^
c&w(ix^
d,
b^
c_)**2+)*inv_squared_c))
2500 e(ix^
d,1)=w(ix^
d,b2_)*v(ix^
d,3)-w(ix^
d,b3_)*v(ix^
d,2)
2501 e(ix^
d,2)=w(ix^
d,b3_)*v(ix^
d,1)-w(ix^
d,b1_)*v(ix^
d,3)
2502 e(ix^
d,3)=w(ix^
d,b1_)*v(ix^
d,2)-w(ix^
d,b2_)*v(ix^
d,1)
2506 e(ix^
d,2)=w(ix^
d,b1_)*v(ix^
d,2)-w(ix^
d,b2_)*v(ix^
d,1)
2512 pressure(ix^
d)=gamma_1*(w(ix^
d,
e_)&
2513 -half*((^
c&v(ix^
d,^
c)**2+)*w(ix^
d,
rho_)&
2514 +(^
c&w(ix^
d,
b^
c_)**2+)+(^
c&e(ix^
d,^
c)**2+)*inv_squared_c))
2521 select case (small_values_method)
2523 {
do ix^db=ixomin^db,ixomax^db\}
2524 if(flag(ix^d,
rho_))
then
2525 w(ix^d,
rho_) = small_density
2526 ^
c&w(ix^d,
m^
c_)=0.d0\
2530 if(flag(ix^d,
e_)) w(ix^d,
p_) = small_pressure
2532 if(flag(ix^d,
e_))
then
2533 w(ix^d,
e_)=small_pressure*inv_gamma_1+half*((^
c&v(ix^d,^
c)**2+)*w(ix^d,
rho_)&
2534 +(^
c&w(ix^d,
b^
c_)**2+)+(^
c&e(ix^d,^
c)**2+)*inv_squared_c)
2541 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2544 call small_values_average(ixi^l, ixo^l, w, x, flag,
p_)
2546 w(ixo^s,
e_)=pressure(ixo^s)
2547 call small_values_average(ixi^l, ixo^l, w, x, flag,
p_)
2548 {
do ix^db=ixomin^db,ixomax^db\}
2549 w(ix^d,
e_)=w(ix^d,
p_)*inv_gamma_1+half*((^
c&v(ix^d,^
c)**2+)*w(ix^d,
rho_)&
2550 +(^
c&w(ix^d,
b^
c_)**2+)+(^
c&e(ix^d,^
c)**2+)*inv_squared_c)
2555 if(.not.primitive)
then
2557 w(ixo^s,
mom(1:ndir))=v(ixo^s,1:ndir)
2560 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2563 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2564 end subroutine mhd_handle_small_values_semirelati
2566 subroutine mhd_handle_small_values_origin(primitive, w, x, ixI^L, ixO^L, subname)
2569 logical,
intent(in) :: primitive
2570 integer,
intent(in) :: ixi^
l,ixo^
l
2571 double precision,
intent(inout) :: w(ixi^s,1:nw)
2572 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2573 character(len=*),
intent(in) :: subname
2576 logical :: flag(ixi^s,1:nw)
2578 call phys_check_w(primitive, ixi^
l, ixo^
l, w, flag)
2583 {
do ix^db=ixomin^db,ixomax^db\}
2587 if(flag({ix^
d},
rho_)) w({ix^
d},
m^
c_)=0.0d0
2604 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2606 call small_values_average(ixi^l, ixo^l, w, x, flag,
p_)
2609 {
do ix^db=iximin^db,iximax^db\}
2610 w(ix^d,
e_)=w(ix^d,
e_)&
2611 -half*((^
c&w(ix^d,
m^
c_)**2+)/w(ix^d,
rho_)+(^
c&w(ix^d,
b^
c_)**2+))
2613 call small_values_average(ixi^l, ixo^l, w, x, flag,
e_)
2615 {
do ix^db=iximin^db,iximax^db\}
2616 w(ix^d,
e_)=w(ix^d,
e_)&
2617 +half*((^
c&w(ix^d,
m^
c_)**2+)/w(ix^d,
rho_)+(^
c&w(ix^d,
b^
c_)**2+))
2621 call small_values_average(ixi^l, ixo^l, w, x, flag,
r_e)
2624 if(.not.primitive)
then
2626 {
do ix^db=ixomin^db,ixomax^db\}
2628 w(ix^d,
p_)=gamma_1*(w(ix^d,
e_)&
2629 -half*((^
c&w(ix^d,
m^
c_)**2+)*w(ix^d,
rho_)+(^
c&w(ix^d,
b^
c_)**2+)))
2632 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2635 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2636 end subroutine mhd_handle_small_values_origin
2638 subroutine mhd_handle_small_values_split(primitive, w, x, ixI^L, ixO^L, subname)
2641 logical,
intent(in) :: primitive
2642 integer,
intent(in) :: ixi^
l,ixo^
l
2643 double precision,
intent(inout) :: w(ixi^s,1:nw)
2644 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2645 character(len=*),
intent(in) :: subname
2647 double precision :: rho
2649 logical :: flag(ixi^s,1:nw)
2651 call phys_check_w(primitive, ixi^
l, ixo^
l, w, flag)
2656 {
do ix^db=ixomin^db,ixomax^db\}
2661 if(flag({ix^
d},
rho_)) w({ix^
d},
m^
c_)=0.0d0
2674 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2676 call small_values_average(ixi^l, ixo^l, w, x, flag,
p_)
2679 {
do ix^db=iximin^db,iximax^db\}
2681 w(ix^d,
e_)=w(ix^d,
e_)&
2682 -half*((^
c&w(ix^d,
m^
c_)**2+)/rho+(^
c&w(ix^d,
b^
c_)**2+))
2684 call small_values_average(ixi^l, ixo^l, w, x, flag,
e_)
2686 {
do ix^db=iximin^db,iximax^db\}
2688 w(ix^d,
e_)=w(ix^d,
e_)&
2689 +half*((^
c&w(ix^d,
m^
c_)**2+)/rho+(^
c&w(ix^d,
b^
c_)**2+))
2693 if(.not.primitive)
then
2695 {
do ix^db=ixomin^db,ixomax^db\}
2697 ^
c&w(ix^d,
m^
c_)=w(ix^d,
m^
c_)/rho\
2698 w(ix^d,
p_)=gamma_1*(w(ix^d,
e_)&
2699 -half*((^
c&w(ix^d,
m^
c_)**2+)*rho+(^
c&w(ix^d,
b^
c_)**2+)))
2702 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2705 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2706 end subroutine mhd_handle_small_values_split
2708 subroutine mhd_handle_small_values_inte(primitive, w, x, ixI^L, ixO^L, subname)
2711 logical,
intent(in) :: primitive
2712 integer,
intent(in) :: ixi^
l,ixo^
l
2713 double precision,
intent(inout) :: w(ixi^s,1:nw)
2714 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2715 character(len=*),
intent(in) :: subname
2718 logical :: flag(ixi^s,1:nw)
2720 call phys_check_w(primitive, ixi^
l, ixo^
l, w, flag)
2725 {
do ix^db=ixomin^db,ixomax^db\}
2726 if(flag(ix^
d,
rho_))
then
2728 ^
c&w(ix^
d,
m^
c_)=0.d0\
2738 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2740 call small_values_average(ixi^l, ixo^l, w, x, flag,
p_)
2742 if(.not.primitive)
then
2744 {
do ix^db=ixomin^db,ixomax^db\}
2746 w(ix^d,
p_)=gamma_1*w(ix^d,
e_)
2749 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2752 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2753 end subroutine mhd_handle_small_values_inte
2755 subroutine mhd_handle_small_values_noe(primitive, w, x, ixI^L, ixO^L, subname)
2758 logical,
intent(in) :: primitive
2759 integer,
intent(in) :: ixi^
l,ixo^
l
2760 double precision,
intent(inout) :: w(ixi^s,1:nw)
2761 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2762 character(len=*),
intent(in) :: subname
2765 logical :: flag(ixi^s,1:nw)
2767 call phys_check_w(primitive, ixi^
l, ixo^
l, w, flag)
2772 {
do ix^db=ixomin^db,ixomax^db\}
2776 if(flag({ix^
d},
rho_)) w({ix^
d},
m^
c_)=0.0d0
2782 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2784 if(.not.primitive)
then
2786 {
do ix^db=ixomin^db,ixomax^db\}
2790 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2793 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2794 end subroutine mhd_handle_small_values_noe
2796 subroutine mhd_handle_small_values_hde(primitive, w, x, ixI^L, ixO^L, subname)
2799 logical,
intent(in) :: primitive
2800 integer,
intent(in) :: ixi^
l,ixo^
l
2801 double precision,
intent(inout) :: w(ixi^s,1:nw)
2802 double precision,
intent(in) :: x(ixi^s,1:
ndim)
2803 character(len=*),
intent(in) :: subname
2806 logical :: flag(ixi^s,1:nw)
2808 call phys_check_w(primitive, ixi^
l, ixo^
l, w, flag)
2813 {
do ix^db=ixomin^db,ixomax^db\}
2814 if(flag(ix^
d,
rho_))
then
2816 ^
c&w(ix^
d,
m^
c_)=0.d0\
2826 call small_values_average(ixi^l, ixo^l, w, x, flag,
rho_)
2828 call small_values_average(ixi^l, ixo^l, w, x, flag,
e_)
2830 if(.not.primitive)
then
2832 {
do ix^db=ixomin^db,ixomax^db\}
2834 w(ix^d,
p_)=gamma_1*(w(ix^d,
e_)-half*(^
c&w(ix^d,
m^
c_)**2+)*w(ix^d,
rho_))
2837 call small_values_error(w, x, ixi^l, ixo^l, flag, subname)
2840 if (
mhd_fip)
call mhd_bound_fip(primitive, ixi^l, ixo^l, w)
2841 end subroutine mhd_handle_small_values_hde
2847 integer,
intent(in) :: ixi^
l, ixo^
l
2848 double precision,
intent(in) :: w(ixi^s,nw), x(ixi^s,1:
ndim)
2849 double precision,
intent(out) :: v(ixi^s,
ndir)
2851 double precision :: rho(ixi^s)
2856 rho(ixo^s)=1.d0/rho(ixo^s)
2859 v(ixo^s, idir) = w(ixo^s,
mom(idir))*rho(ixo^s)
2865 subroutine mhd_get_csound2(w,x,ixI^L,ixO^L,cs2)
2868 integer,
intent(in) :: ixi^
l, ixo^
l
2869 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
2870 double precision,
intent(inout) :: cs2(ixi^s)
2872 double precision :: rho, inv_rho, ploc
2875 {
do ix^db=ixomin^db,ixomax^db \}
2887 end subroutine mhd_get_csound2
2890 subroutine mhd_get_cmax_origin(w,x,ixI^L,ixO^L,idim,cmax)
2893 integer,
intent(in) :: ixi^
l, ixo^
l, idim
2894 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
2895 double precision,
intent(inout) :: cmax(ixi^s)
2897 double precision :: rho, inv_rho, ploc, cfast2, avmincs2, b2, kmax
2903 {
do ix^db=ixomin^db,ixomax^db \}
2916 cfast2=b2*inv_rho+cmax(ix^
d)
2917 avmincs2=cfast2**2-4.0d0*cmax(ix^
d)*(w(ix^
d,mag(idim))+
block%B0(ix^
d,idim,
b0i))**2*inv_rho
2918 if(avmincs2<zero) avmincs2=zero
2919 cmax(ix^
d)=sqrt(half*(cfast2+sqrt(avmincs2)))
2923 cmax(ix^
d)=max(cmax(ix^
d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
2925 cmax(ix^
d)=abs(w(ix^
d,
mom(idim)))+cmax(ix^
d)
2928 {
do ix^db=ixomin^db,ixomax^db \}
2931 ploc=(w(ix^d,
p_)+block%equi_vars(ix^d,
equi_pe0_,b0i))
2940 b2=(^
c&w(ix^d,
b^
c_)**2+)
2941 cfast2=b2*inv_rho+cmax(ix^d)
2942 avmincs2=cfast2**2-4.0d0*cmax(ix^d)*w(ix^d,mag(idim))**2*inv_rho
2943 if(avmincs2<zero) avmincs2=zero
2944 cmax(ix^d)=sqrt(half*(cfast2+sqrt(avmincs2)))
2948 cmax(ix^d)=max(cmax(ix^d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
2950 cmax(ix^d)=abs(w(ix^d,
mom(idim)))+cmax(ix^d)
2954 end subroutine mhd_get_cmax_origin
2957 subroutine mhd_get_cmax_origin_noe(w,x,ixI^L,ixO^L,idim,cmax)
2961 integer,
intent(in) :: ixi^
l, ixo^
l, idim
2962 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
2963 double precision,
intent(inout) :: cmax(ixi^s)
2965 double precision :: rho, inv_rho, cfast2, avmincs2, b2, kmax
2966 double precision :: adiabs(ixi^s), gammas(ixi^s)
2981 {
do ix^db=ixomin^db,ixomax^db \}
2985 cmax(ix^
d)=gammas(ix^
d)*adiabs(ix^
d)*rho**(gammas(ix^
d)-1.d0)
2987 b2=(^
c&w(ix^
d,
b^
c_)**2+)
2988 cfast2=b2*inv_rho+cmax(ix^
d)
2989 avmincs2=cfast2**2-4.0d0*cmax(ix^
d)*w(ix^
d,mag(idim))**2*inv_rho
2990 if(avmincs2<zero) avmincs2=zero
2991 cmax(ix^
d)=sqrt(half*(cfast2+sqrt(avmincs2)))
2995 cmax(ix^
d)=max(cmax(ix^
d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
2997 cmax(ix^
d)=abs(w(ix^
d,
mom(idim)))+cmax(ix^
d)
3000 end subroutine mhd_get_cmax_origin_noe
3003 subroutine mhd_get_cmax_semirelati(w,x,ixI^L,ixO^L,idim,cmax)
3006 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3007 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3008 double precision,
intent(inout):: cmax(ixi^s)
3010 double precision :: csound, avmincs2, idim_alfven_speed2
3011 double precision :: inv_rho, alfven_speed2, gamma2
3014 {
do ix^db=ixomin^db,ixomax^db \}
3015 inv_rho=1.d0/w(ix^
d,
rho_)
3016 alfven_speed2=(^
c&w(ix^
d,
b^
c_)**2+)*inv_rho
3017 gamma2=1.0d0/(1.d0+alfven_speed2*inv_squared_c)
3018 cmax(ix^
d)=1.d0-gamma2*w(ix^
d,
mom(idim))**2*inv_squared_c
3021 idim_alfven_speed2=w(ix^
d,mag(idim))**2*inv_rho
3024 alfven_speed2=alfven_speed2*cmax(ix^
d)+csound*(1.d0+idim_alfven_speed2*inv_squared_c)
3025 avmincs2=(gamma2*alfven_speed2)**2-4.0d0*gamma2*csound*idim_alfven_speed2*cmax(ix^
d)
3026 if(avmincs2<zero) avmincs2=zero
3028 csound = sqrt(half*(gamma2*alfven_speed2+sqrt(avmincs2)))
3029 cmax(ix^
d)=gamma2*abs(w(ix^
d,
mom(idim)))+csound
3032 end subroutine mhd_get_cmax_semirelati
3035 subroutine mhd_get_cmax_semirelati_noe(w,x,ixI^L,ixO^L,idim,cmax)
3039 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3040 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3041 double precision,
intent(inout):: cmax(ixi^s)
3043 double precision :: adiabs(ixi^s), gammas(ixi^s)
3044 double precision :: csound, avmincs2, idim_alfven_speed2
3045 double precision :: inv_rho, alfven_speed2, gamma2
3059 {
do ix^db=ixomin^db,ixomax^db \}
3060 inv_rho=1.d0/w(ix^
d,
rho_)
3061 alfven_speed2=(^
c&w(ix^
d,
b^
c_)**2+)*inv_rho
3062 gamma2=1.0d0/(1.d0+alfven_speed2*inv_squared_c)
3063 cmax(ix^
d)=1.d0-gamma2*w(ix^
d,
mom(idim))**2*inv_squared_c
3064 csound=gammas(ix^
d)*adiabs(ix^
d)*w(ix^
d,
rho_)**(gammas(ix^
d)-1.d0)
3065 idim_alfven_speed2=w(ix^
d,mag(idim))**2*inv_rho
3068 alfven_speed2=alfven_speed2*cmax(ix^
d)+csound*(1.d0+idim_alfven_speed2*inv_squared_c)
3069 avmincs2=(gamma2*alfven_speed2)**2-4.0d0*gamma2*csound*idim_alfven_speed2*cmax(ix^
d)
3070 if(avmincs2<zero) avmincs2=zero
3072 csound = sqrt(half*(gamma2*alfven_speed2+sqrt(avmincs2)))
3073 cmax(ix^
d)=gamma2*abs(w(ix^
d,
mom(idim)))+csound
3076 end subroutine mhd_get_cmax_semirelati_noe
3079 subroutine mhd_get_tcutoff(ixI^L,ixO^L,w,x,Tco_local,Tmax_local)
3082 integer,
intent(in) :: ixi^
l,ixo^
l
3083 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3085 double precision,
intent(inout) :: w(ixi^s,1:nw)
3086 double precision,
intent(out) :: tco_local,tmax_local
3088 double precision,
parameter :: trac_delta=0.25d0
3089 double precision :: te(ixi^s),lts(ixi^s)
3090 double precision,
dimension(1:ndim) :: bdir, bunitvec
3091 double precision,
dimension(ixI^S,1:ndim) :: gradt
3092 double precision :: ltrc,ltrp,altr
3093 integer :: idims,ix^
d,jxo^
l,hxo^
l,ixa^
d,ixb^
d
3094 integer :: jxp^
l,hxp^
l,ixp^
l,ixq^
l
3097 call mhd_get_temperature_from_te(w,x,ixi^
l,ixi^
l,te)
3100 te(ixi^s)=w(ixi^s,
p_)/(te(ixi^s)*w(ixi^s,
rho_))
3103 tmax_local=maxval(te(ixo^s))
3111 do ix1=ixomin1,ixomax1
3112 lts(ix1)=0.5d0*abs(te(ix1+1)-te(ix1-1))/te(ix1)
3113 if(lts(ix1)>trac_delta)
then
3114 tco_local=max(tco_local,te(ix1))
3126 lts(ixp^s)=0.5d0*abs(te(jxp^s)-te(hxp^s))/te(ixp^s)
3127 lts(ixp^s)=max(one, (exp(lts(ixp^s))/ltrc)**ltrp)
3128 lts(ixo^s)=0.25d0*(lts(jxo^s)+two*lts(ixo^s)+lts(hxo^s))
3129 block%wextra(ixo^s,
tcoff_)=te(ixo^s)*lts(ixo^s)**0.4d0
3131 call mpistop(
"mhd_trac_type not allowed for 1D simulation")
3142 call gradient(te,ixi^
l,ixo^
l,idims,gradt(ixi^s,idims))
3149 ixb^
d=(ixomin^
d+ixomax^
d-1)/2+ixa^
d;
3154 ixb^d=(ixomin^d+ixomax^d-1)/2+ixa^d;
3155 bdir(1:ndim)=bdir(1:ndim)+w(ixb^d,iw_mag(1:ndim))
3159 if(bdir(1)/=0.d0)
then
3160 block%special_values(3)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2)
3162 block%special_values(3)=0.d0
3164 if(bdir(2)/=0.d0)
then
3165 block%special_values(4)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2)
3167 block%special_values(4)=0.d0
3171 if(bdir(1)/=0.d0)
then
3172 block%special_values(3)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2+&
3173 (bdir(3)/bdir(1))**2)
3175 block%special_values(3)=0.d0
3177 if(bdir(2)/=0.d0)
then
3178 block%special_values(4)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2+&
3179 (bdir(3)/bdir(2))**2)
3181 block%special_values(4)=0.d0
3183 if(bdir(3)/=0.d0)
then
3184 block%special_values(5)=sign(1.d0,bdir(3))/dsqrt(1.d0+(bdir(1)/bdir(3))**2+&
3185 (bdir(2)/bdir(3))**2)
3187 block%special_values(5)=0.d0
3192 block%special_values(1)=zero
3193 {
do ix^db=ixomin^db,ixomax^db\}
3195 ^d&bdir(^d)=w({ix^d},iw_mag(^d))+block%B0({ix^d},^d,0)\
3197 ^d&bdir(^d)=w({ix^d},iw_mag(^d))\
3200 if(bdir(1)/=0.d0)
then
3201 bunitvec(1)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2)
3205 if(bdir(2)/=0.d0)
then
3206 bunitvec(2)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2)
3211 lts(ix^d)=min(block%ds(ix^d,1),block%ds(ix^d,2))*&
3212 abs(^d&gradt({ix^d},^d)*bunitvec(^d)+)/te(ix^d)
3215 if(bdir(1)/=0.d0)
then
3216 bunitvec(1)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2+(bdir(3)/bdir(1))**2)
3220 if(bdir(2)/=0.d0)
then
3221 bunitvec(2)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2+(bdir(3)/bdir(2))**2)
3225 if(bdir(3)/=0.d0)
then
3226 bunitvec(3)=sign(1.d0,bdir(3))/dsqrt(1.d0+(bdir(1)/bdir(3))**2+(bdir(2)/bdir(3))**2)
3231 lts(ix^d)=min(block%ds(ix^d,1),block%ds(ix^d,2),block%ds(ix^d,3))*&
3232 abs(^d&gradt({ix^d},^d)*bunitvec(^d)+)/te(ix^d)
3234 if(lts(ix^d)>trac_delta)
then
3235 block%special_values(1)=max(block%special_values(1),te(ix^d))
3238 block%special_values(2)=tmax_local
3257 call gradient(te,ixi^l,ixq^l,idims,gradt(ixi^s,idims))
3258 call gradientf(te,x,ixi^l,hxp^l,idims,gradt(ixi^s,idims),nghostcells,.true.)
3259 call gradientf(te,x,ixi^l,jxp^l,idims,gradt(ixi^s,idims),nghostcells,.false.)
3263 {
do ix^db=ixpmin^db,ixpmax^db\}
3264 ^d&bdir(^d)=w({ix^d},iw_mag(^d))+block%B0({ix^d},^d,0)\
3266 if(bdir(1)/=0.d0)
then
3267 bunitvec(1)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2)
3271 if(bdir(2)/=0.d0)
then
3272 bunitvec(2)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2)
3278 if(bdir(1)/=0.d0)
then
3279 bunitvec(1)=sign(1.d0,bdir(1))/dsqrt(1.d0+(bdir(2)/bdir(1))**2+(bdir(3)/bdir(1))**2)
3283 if(bdir(2)/=0.d0)
then
3284 bunitvec(2)=sign(1.d0,bdir(2))/dsqrt(1.d0+(bdir(1)/bdir(2))**2+(bdir(3)/bdir(2))**2)
3288 if(bdir(3)/=0.d0)
then
3289 bunitvec(3)=sign(1.d0,bdir(3))/dsqrt(1.d0+(bdir(1)/bdir(3))**2+(bdir(2)/bdir(3))**2)
3295 lts(ix^d)=abs(^d&gradt({ix^d},^d)*bunitvec(^d)+)/te(ix^d)
3297 lts(ix^d)=min(^d&block%ds({ix^d},^d))*lts(ix^d)
3298 lts(ix^d)=max(one,(exp(lts(ix^d))/ltrc)**ltrp)
3301 {
do ix^db=ixpmin^db,ixpmax^db\}
3303 if(w(ix^d,iw_mag(1))/=0.d0)
then
3304 bunitvec(1)=sign(1.d0,w(ix^d,iw_mag(1)))/dsqrt(1.d0+(w(ix^d,iw_mag(2))/w(ix^d,iw_mag(1)))**2)
3308 if(w(ix^d,iw_mag(2))/=0.d0)
then
3309 bunitvec(2)=sign(1.d0,w(ix^d,iw_mag(2)))/dsqrt(1.d0+(w(ix^d,iw_mag(1))/w(ix^d,iw_mag(2)))**2)
3315 if(w(ix^d,iw_mag(1))/=0.d0)
then
3316 bunitvec(1)=sign(1.d0,w(ix^d,iw_mag(1)))/dsqrt(1.d0+(w(ix^d,iw_mag(2))/w(ix^d,iw_mag(1)))**2+&
3317 (w(ix^d,iw_mag(3))/w(ix^d,iw_mag(1)))**2)
3321 if(w(ix^d,iw_mag(2))/=0.d0)
then
3322 bunitvec(2)=sign(1.d0,w(ix^d,iw_mag(2)))/dsqrt(1.d0+(w(ix^d,iw_mag(1))/w(ix^d,iw_mag(2)))**2+&
3323 (w(ix^d,iw_mag(3))/w(ix^d,iw_mag(2)))**2)
3327 if(w(ix^d,iw_mag(3))/=0.d0)
then
3328 bunitvec(3)=sign(1.d0,w(ix^d,iw_mag(3)))/dsqrt(1.d0+(w(ix^d,iw_mag(1))/w(ix^d,iw_mag(3)))**2+&
3329 (w(ix^d,iw_mag(2))/w(ix^d,iw_mag(3)))**2)
3335 lts(ix^d)=abs(^d&gradt({ix^d},^d)*bunitvec(^d)+)/te(ix^d)
3337 lts(ix^d)=min(^d&block%ds({ix^d},^d))*lts(ix^d)
3338 lts(ix^d)=max(one,(exp(lts(ix^d))/ltrc)**ltrp)
3344 {
do ix^db=ixpmin^db,ixpmax^db\}
3346 altr=0.25d0*((lts(ix1-1,ix2)+two*lts(ix^d)+lts(ix1+1,ix2))*bunitvec(1)**2+&
3347 (lts(ix1,ix2-1)+two*lts(ix^d)+lts(ix1,ix2+1))*bunitvec(2)**2)
3348 block%wextra(ix^d,
tcoff_)=te(ix^d)*altr**0.4d0
3351 altr=0.25d0*((lts(ix1-1,ix2,ix3)+two*lts(ix^d)+lts(ix1+1,ix2,ix3))*bunitvec(1)**2+&
3352 (lts(ix1,ix2-1,ix3)+two*lts(ix^d)+lts(ix1,ix2+1,ix3))*bunitvec(2)**2+&
3353 (lts(ix1,ix2,ix3-1)+two*lts(ix^d)+lts(ix1,ix2,ix3+1))*bunitvec(3)**2)
3354 block%wextra(ix^d,
tcoff_)=te(ix^d)*altr**0.4d0
3360 call mpistop(
"unknown mhd_trac_type")
3363 end subroutine mhd_get_tcutoff
3366 subroutine mhd_get_h_speed(wprim,x,ixI^L,ixO^L,idim,Hspeed)
3369 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3370 double precision,
intent(in) :: wprim(ixi^s, nw)
3371 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3372 double precision,
intent(out) :: hspeed(ixi^s,1:number_species)
3374 double precision :: csound(ixi^s,
ndim)
3375 double precision,
allocatable :: tmp(:^
d&)
3376 integer :: jxc^
l, ixc^
l, ixa^
l, id, ix^
d
3380 allocate(tmp(ixa^s))
3383 call mhd_get_csound_prim_split(wprim,x,ixi^
l,ixa^
l,id,tmp)
3385 call mhd_get_csound_prim(wprim,x,ixi^
l,ixa^
l,id,tmp)
3387 csound(ixa^s,id)=tmp(ixa^s)
3390 ixcmin^
d=ixomin^
d+
kr(idim,^
d)-1;
3391 jxcmax^
d=ixcmax^
d+
kr(idim,^
d);
3392 jxcmin^
d=ixcmin^
d+
kr(idim,^
d);
3393 hspeed(ixc^s,1)=0.5d0*abs(wprim(jxc^s,
mom(idim))+csound(jxc^s,idim)-wprim(ixc^s,
mom(idim))+csound(ixc^s,idim))
3397 ixamax^
d=ixcmax^
d+
kr(id,^
d);
3398 ixamin^
d=ixcmin^
d+
kr(id,^
d);
3399 hspeed(ixc^s,1)=max(hspeed(ixc^s,1),0.5d0*abs(wprim(ixa^s,
mom(id))+csound(ixa^s,id)-wprim(ixc^s,
mom(id))+csound(ixc^s,id)))
3400 ixamax^
d=ixcmax^
d-
kr(id,^
d);
3401 ixamin^
d=ixcmin^
d-
kr(id,^
d);
3402 hspeed(ixc^s,1)=max(hspeed(ixc^s,1),0.5d0*abs(wprim(ixc^s,
mom(id))+csound(ixc^s,id)-wprim(ixa^s,
mom(id))+csound(ixa^s,id)))
3407 ixamax^
d=jxcmax^
d+
kr(id,^
d);
3408 ixamin^
d=jxcmin^
d+
kr(id,^
d);
3409 hspeed(ixc^s,1)=max(hspeed(ixc^s,1),0.5d0*abs(wprim(ixa^s,
mom(id))+csound(ixa^s,id)-wprim(jxc^s,
mom(id))+csound(jxc^s,id)))
3410 ixamax^
d=jxcmax^
d-
kr(id,^
d);
3411 ixamin^
d=jxcmin^
d-
kr(id,^
d);
3412 hspeed(ixc^s,1)=max(hspeed(ixc^s,1),0.5d0*abs(wprim(jxc^s,
mom(id))+csound(jxc^s,id)-wprim(ixa^s,
mom(id))+csound(ixa^s,id)))
3416 end subroutine mhd_get_h_speed
3419 subroutine mhd_get_cbounds(wLC,wRC,wLp,wRp,x,ixI^L,ixO^L,idim,Hspeed,cmax,cmin)
3422 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3423 double precision,
intent(in) :: wlc(ixi^s, nw), wrc(ixi^s, nw)
3424 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3425 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3426 double precision,
intent(inout) :: cmax(ixi^s,1:number_species)
3427 double precision,
intent(inout),
optional :: cmin(ixi^s,1:number_species)
3428 double precision,
intent(in) :: hspeed(ixi^s,1:number_species)
3430 double precision :: wmean(ixi^s,nw), csoundl(ixo^s), csoundr(ixo^s)
3431 double precision :: umean, dmean, tmp1, tmp2, tmp3
3438 call mhd_get_csound_prim(wlp,x,ixi^
l,ixo^
l,idim,csoundl)
3439 call mhd_get_csound_prim(wrp,x,ixi^
l,ixo^
l,idim,csoundr)
3440 if(
present(cmin))
then
3441 {
do ix^db=ixomin^db,ixomax^db\}
3442 tmp1=sqrt(wlp(ix^
d,
rho_))
3443 tmp2=sqrt(wrp(ix^
d,
rho_))
3444 tmp3=1.d0/(tmp1+tmp2)
3445 umean=(wlp(ix^
d,
mom(idim))*tmp1+wrp(ix^
d,
mom(idim))*tmp2)*tmp3
3446 dmean=sqrt((tmp1*csoundl(ix^
d)**2+tmp2*csoundr(ix^
d)**2)*tmp3+&
3447 half*tmp1*tmp2*tmp3**2*(wrp(ix^
d,
mom(idim))-wlp(ix^
d,
mom(idim)))**2)
3448 cmin(ix^
d,1)=umean-dmean
3449 cmax(ix^
d,1)=umean+dmean
3451 if(h_correction)
then
3452 {
do ix^db=ixomin^db,ixomax^db\}
3453 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3454 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3458 {
do ix^db=ixomin^db,ixomax^db\}
3459 tmp1=sqrt(wlp(ix^d,
rho_))
3460 tmp2=sqrt(wrp(ix^d,
rho_))
3461 tmp3=1.d0/(tmp1+tmp2)
3462 umean=(wlp(ix^d,
mom(idim))*tmp1+wrp(ix^d,
mom(idim))*tmp2)*tmp3
3463 dmean=sqrt((tmp1*csoundl(ix^d)**2+tmp2*csoundr(ix^d)**2)*tmp3+&
3464 half*tmp1*tmp2*tmp3**2*(wrp(ix^d,
mom(idim))-wlp(ix^d,
mom(idim)))**2)
3465 cmax(ix^d,1)=abs(umean)+dmean
3469 wmean(ixo^s,1:nwflux)=0.5d0*(wlp(ixo^s,1:nwflux)+wrp(ixo^s,1:nwflux))
3470 call mhd_get_csound_prim(wmean,x,ixi^l,ixo^l,idim,csoundr)
3471 if(
present(cmin))
then
3472 {
do ix^db=ixomin^db,ixomax^db\}
3473 cmax(ix^d,1)=max(wmean(ix^d,
mom(idim))+csoundr(ix^d),zero)
3474 cmin(ix^d,1)=min(wmean(ix^d,
mom(idim))-csoundr(ix^d),zero)
3476 if(h_correction)
then
3477 {
do ix^db=ixomin^db,ixomax^db\}
3478 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3479 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3483 cmax(ixo^s,1)=abs(wmean(ixo^s,
mom(idim)))+csoundr(ixo^s)
3487 call mhd_get_csound_prim(wlp,x,ixi^l,ixo^l,idim,csoundl)
3488 call mhd_get_csound_prim(wrp,x,ixi^l,ixo^l,idim,csoundr)
3489 if(
present(cmin))
then
3490 {
do ix^db=ixomin^db,ixomax^db\}
3491 csoundl(ix^d)=max(csoundl(ix^d),csoundr(ix^d))
3492 cmin(ix^d,1)=min(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))-csoundl(ix^d)
3493 cmax(ix^d,1)=max(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))+csoundl(ix^d)
3495 if(h_correction)
then
3496 {
do ix^db=ixomin^db,ixomax^db\}
3497 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3498 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3502 {
do ix^db=ixomin^db,ixomax^db\}
3503 csoundl(ix^d)=max(csoundl(ix^d),csoundr(ix^d))
3504 cmax(ix^d,1)=max(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))+csoundl(ix^d)
3509 end subroutine mhd_get_cbounds
3512 subroutine mhd_get_cbounds_semirelati(wLC,wRC,wLp,wRp,x,ixI^L,ixO^L,idim,Hspeed,cmax,cmin)
3515 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3516 double precision,
intent(in) :: wlc(ixi^s, nw), wrc(ixi^s, nw)
3517 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3518 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3519 double precision,
intent(inout) :: cmax(ixi^s,1:number_species)
3520 double precision,
intent(inout),
optional :: cmin(ixi^s,1:number_species)
3521 double precision,
intent(in) :: hspeed(ixi^s,1:number_species)
3523 double precision,
dimension(ixO^S) :: csoundl, csoundr, gamma2l, gamma2r
3528 call mhd_get_csound_semirelati(wlp,x,ixi^
l,ixo^
l,idim,csoundl,gamma2l)
3529 call mhd_get_csound_semirelati(wrp,x,ixi^
l,ixo^
l,idim,csoundr,gamma2r)
3531 call mhd_get_csound_semirelati_noe(wlp,x,ixi^
l,ixo^
l,idim,csoundl,gamma2l)
3532 call mhd_get_csound_semirelati_noe(wrp,x,ixi^
l,ixo^
l,idim,csoundr,gamma2r)
3534 if(
present(cmin))
then
3535 {
do ix^db=ixomin^db,ixomax^db\}
3536 csoundl(ix^
d)=max(csoundl(ix^
d),csoundr(ix^
d))
3537 cmin(ix^
d,1)=min(gamma2l(ix^
d)*wlp(ix^
d,
mom(idim)),gamma2r(ix^
d)*wrp(ix^
d,
mom(idim)))-csoundl(ix^
d)
3538 cmax(ix^
d,1)=max(gamma2l(ix^
d)*wlp(ix^
d,
mom(idim)),gamma2r(ix^
d)*wrp(ix^
d,
mom(idim)))+csoundl(ix^
d)
3541 {
do ix^db=ixomin^db,ixomax^db\}
3542 csoundl(ix^d)=max(csoundl(ix^d),csoundr(ix^d))
3543 cmax(ix^d,1)=max(gamma2l(ix^d)*wlp(ix^d,
mom(idim)),gamma2r(ix^d)*wrp(ix^d,
mom(idim)))+csoundl(ix^d)
3547 end subroutine mhd_get_cbounds_semirelati
3550 subroutine mhd_get_cbounds_split_rho(wLC,wRC,wLp,wRp,x,ixI^L,ixO^L,idim,Hspeed,cmax,cmin)
3553 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3554 double precision,
intent(in) :: wlc(ixi^s, nw), wrc(ixi^s, nw)
3555 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3556 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3557 double precision,
intent(inout) :: cmax(ixi^s,1:number_species)
3558 double precision,
intent(inout),
optional :: cmin(ixi^s,1:number_species)
3559 double precision,
intent(in) :: hspeed(ixi^s,1:number_species)
3561 double precision :: wmean(ixi^s,nw), csoundl(ixo^s), csoundr(ixo^s)
3562 double precision :: umean, dmean, tmp1, tmp2, tmp3
3569 call mhd_get_csound_prim_split(wlp,x,ixi^
l,ixo^
l,idim,csoundl)
3570 call mhd_get_csound_prim_split(wrp,x,ixi^
l,ixo^
l,idim,csoundr)
3571 if(
present(cmin))
then
3572 {
do ix^db=ixomin^db,ixomax^db\}
3575 tmp3=1.d0/(tmp1+tmp2)
3576 umean=(wlp(ix^
d,
mom(idim))*tmp1+wrp(ix^
d,
mom(idim))*tmp2)*tmp3
3577 dmean=sqrt((tmp1*csoundl(ix^
d)**2+tmp2*csoundr(ix^
d)**2)*tmp3+&
3578 half*tmp1*tmp2*tmp3**2*(wrp(ix^
d,
mom(idim))-wlp(ix^
d,
mom(idim)))**2)
3579 cmin(ix^
d,1)=umean-dmean
3580 cmax(ix^
d,1)=umean+dmean
3582 if(h_correction)
then
3583 {
do ix^db=ixomin^db,ixomax^db\}
3584 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3585 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3589 {
do ix^db=ixomin^db,ixomax^db\}
3592 tmp3=1.d0/(tmp1+tmp2)
3593 umean=(wlp(ix^d,
mom(idim))*tmp1+wrp(ix^d,
mom(idim))*tmp2)*tmp3
3594 dmean=sqrt((tmp1*csoundl(ix^d)**2+tmp2*csoundr(ix^d)**2)*tmp3+&
3595 half*tmp1*tmp2*tmp3**2*(wrp(ix^d,
mom(idim))-wlp(ix^d,
mom(idim)))**2)
3596 cmax(ix^d,1)=abs(umean)+dmean
3600 wmean(ixo^s,1:nwflux)=0.5d0*(wlp(ixo^s,1:nwflux)+wrp(ixo^s,1:nwflux))
3601 call mhd_get_csound_prim_split(wmean,x,ixi^l,ixo^l,idim,csoundr)
3602 if(
present(cmin))
then
3603 {
do ix^db=ixomin^db,ixomax^db\}
3604 cmax(ix^d,1)=max(wmean(ix^d,
mom(idim))+csoundr(ix^d),zero)
3605 cmin(ix^d,1)=min(wmean(ix^d,
mom(idim))-csoundr(ix^d),zero)
3607 if(h_correction)
then
3608 {
do ix^db=ixomin^db,ixomax^db\}
3609 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3610 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3614 cmax(ixo^s,1)=abs(wmean(ixo^s,
mom(idim)))+csoundr(ixo^s)
3618 call mhd_get_csound_prim_split(wlp,x,ixi^l,ixo^l,idim,csoundl)
3619 call mhd_get_csound_prim_split(wrp,x,ixi^l,ixo^l,idim,csoundr)
3620 if(
present(cmin))
then
3621 {
do ix^db=ixomin^db,ixomax^db\}
3622 csoundl(ix^d)=max(csoundl(ix^d),csoundr(ix^d))
3623 cmin(ix^d,1)=min(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))-csoundl(ix^d)
3624 cmax(ix^d,1)=max(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))+csoundl(ix^d)
3626 if(h_correction)
then
3627 {
do ix^db=ixomin^db,ixomax^db\}
3628 cmin(ix^d,1)=sign(one,cmin(ix^d,1))*max(abs(cmin(ix^d,1)),hspeed(ix^d,1))
3629 cmax(ix^d,1)=sign(one,cmax(ix^d,1))*max(abs(cmax(ix^d,1)),hspeed(ix^d,1))
3633 {
do ix^db=ixomin^db,ixomax^db\}
3634 csoundl(ix^d)=max(csoundl(ix^d),csoundr(ix^d))
3635 cmax(ix^d,1)=max(wlp(ix^d,
mom(idim)),wrp(ix^d,
mom(idim)))+csoundl(ix^d)
3640 end subroutine mhd_get_cbounds_split_rho
3643 subroutine mhd_get_ct_velocity_average(vcts,wLp,wRp,ixI^L,ixO^L,idim,cmax,cmin)
3646 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3647 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3648 double precision,
intent(in) :: cmax(ixi^s)
3649 double precision,
intent(in),
optional :: cmin(ixi^s)
3650 type(ct_velocity),
intent(inout):: vcts
3652 end subroutine mhd_get_ct_velocity_average
3654 subroutine mhd_get_ct_velocity_contact(vcts,wLp,wRp,ixI^L,ixO^L,idim,cmax,cmin)
3657 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3658 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3659 double precision,
intent(in) :: cmax(ixi^s)
3660 double precision,
intent(in),
optional :: cmin(ixi^s)
3661 type(ct_velocity),
intent(inout):: vcts
3663 if(.not.
allocated(vcts%vnorm))
allocate(vcts%vnorm(ixi^s,1:
ndim))
3665 vcts%vnorm(ixo^s,idim)=0.5d0*(wlp(ixo^s,
mom(idim))+wrp(ixo^s,
mom(idim)))
3667 end subroutine mhd_get_ct_velocity_contact
3669 subroutine mhd_get_ct_velocity_hll(vcts,wLp,wRp,ixI^L,ixO^L,idim,cmax,cmin)
3672 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3673 double precision,
intent(in) :: wlp(ixi^s, nw), wrp(ixi^s, nw)
3674 double precision,
intent(in) :: cmax(ixi^s)
3675 double precision,
intent(in),
optional :: cmin(ixi^s)
3676 type(ct_velocity),
intent(inout):: vcts
3678 integer :: idime,idimn
3680 if(.not.
allocated(vcts%vbarC))
then
3681 allocate(vcts%vbarC(ixi^s,1:
ndir,2),vcts%vbarLC(ixi^s,1:
ndir,2),vcts%vbarRC(ixi^s,1:
ndir,2))
3682 allocate(vcts%cbarmin(ixi^s,1:
ndim),vcts%cbarmax(ixi^s,1:
ndim))
3685 if(
present(cmin))
then
3686 vcts%cbarmin(ixo^s,idim)=max(-cmin(ixo^s),zero)
3687 vcts%cbarmax(ixo^s,idim)=max( cmax(ixo^s),zero)
3689 vcts%cbarmax(ixo^s,idim)=max( cmax(ixo^s),zero)
3690 vcts%cbarmin(ixo^s,idim)=vcts%cbarmax(ixo^s,idim)
3693 idimn=mod(idim,
ndir)+1
3694 idime=mod(idim+1,
ndir)+1
3696 vcts%vbarLC(ixo^s,idim,1)=wlp(ixo^s,
mom(idimn))
3697 vcts%vbarRC(ixo^s,idim,1)=wrp(ixo^s,
mom(idimn))
3698 vcts%vbarC(ixo^s,idim,1)=(vcts%cbarmax(ixo^s,idim)*vcts%vbarLC(ixo^s,idim,1) &
3699 +vcts%cbarmin(ixo^s,idim)*vcts%vbarRC(ixo^s,idim,1))&
3700 /(vcts%cbarmax(ixo^s,idim)+vcts%cbarmin(ixo^s,idim))
3702 vcts%vbarLC(ixo^s,idim,2)=wlp(ixo^s,
mom(idime))
3703 vcts%vbarRC(ixo^s,idim,2)=wrp(ixo^s,
mom(idime))
3704 vcts%vbarC(ixo^s,idim,2)=(vcts%cbarmax(ixo^s,idim)*vcts%vbarLC(ixo^s,idim,2) &
3705 +vcts%cbarmin(ixo^s,idim)*vcts%vbarRC(ixo^s,idim,1))&
3706 /(vcts%cbarmax(ixo^s,idim)+vcts%cbarmin(ixo^s,idim))
3708 end subroutine mhd_get_ct_velocity_hll
3715 integer,
intent(in) :: ixi^
l, ixo^
l
3716 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3717 double precision,
intent(out):: csound(ixi^s)
3719 double precision :: wprim(ixi^s, nw)
3721 wprim(ixi^s,1:nw)=w(ixi^s,1:nw)
3734 integer,
intent(in) :: ixi^
l, ixo^
l
3735 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3736 double precision,
intent(out):: csound(ixi^s)
3738 double precision :: inv_rho, b2
3739 double precision :: prad_tensor(ixi^s, 1:
ndim, 1:
ndim)
3740 double precision :: prad_max(ixi^s)
3746 {
do ix^db=ixomin^db,ixomax^db \}
3747 inv_rho=1.d0/w(ix^
d,
rho_)
3748 prad_max(ix^
d) = maxval(prad_tensor(ix^
d,:,:))
3753 {
do ix^db=ixomin^db,ixomax^db \}
3754 inv_rho=1.d0/w(ix^d,
rho_)
3755 prad_max(ix^d) = maxval(prad_tensor(ix^d,:,:))
3756 b2=(^
c&w(ix^d,
b^
c_)**2+)
3757 csound(ix^d)=(
mhd_gamma*w(ix^d,
p_)+b2+prad_max(ix^d))*inv_rho
3761 if(minval(csound(ixo^s))<smalldouble)
then
3762 print *,
'issue with squared speed and rad pressure'
3763 print *,minval(csound(ixo^s))
3764 print *,minval(prad_max(ixo^s))
3765 call mpistop(
"negative squared speed in get_csrad2 for dt")
3771 subroutine mhd_get_csound_prim(w,x,ixI^L,ixO^L,idim,csound)
3775 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3776 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3777 double precision,
intent(out):: csound(ixo^s)
3779 double precision :: adiabs(ixi^s), gammas(ixi^s)
3780 double precision :: inv_rho, cfast2, avmincs2, b2, kmax
3800 {
do ix^db=ixomin^db,ixomax^db \}
3801 inv_rho=1.d0/w(ix^
d,
rho_)
3805 csound(ix^
d)=gammas(ix^
d)*adiabs(ix^
d)*w(ix^
d,
rho_)**(gammas(ix^
d)-1.d0)
3808 cfast2=b2*inv_rho+csound(ix^
d)
3809 avmincs2=cfast2**2-4.0d0*csound(ix^
d)*(w(ix^
d,mag(idim))+&
3811 if(avmincs2<zero) avmincs2=zero
3812 csound(ix^
d)=sqrt(half*(cfast2+sqrt(avmincs2)))
3814 csound(ix^
d)=max(csound(ix^
d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
3818 {
do ix^db=ixomin^db,ixomax^db \}
3819 inv_rho=1.d0/w(ix^d,
rho_)
3823 csound(ix^d)=gammas(ix^d)*adiabs(ix^d)*w(ix^d,
rho_)**(gammas(ix^d)-1.d0)
3825 b2=(^
c&w(ix^d,
b^
c_)**2+)
3826 cfast2=b2*inv_rho+csound(ix^d)
3827 avmincs2=cfast2**2-4.0d0*csound(ix^d)*w(ix^d,mag(idim))**2*inv_rho
3828 if(avmincs2<zero) avmincs2=zero
3829 csound(ix^d)=sqrt(half*(cfast2+sqrt(avmincs2)))
3831 csound(ix^d)=max(csound(ix^d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
3836 end subroutine mhd_get_csound_prim
3840 subroutine mhd_get_csound_prim_split(w,x,ixI^L,ixO^L,idim,csound)
3843 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3844 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3845 double precision,
intent(out):: csound(ixo^s)
3847 double precision :: rho, inv_rho, cfast2, avmincs2, b2, kmax
3854 {
do ix^db=ixomin^db,ixomax^db \}
3859 cfast2=b2*inv_rho+csound(ix^
d)
3860 avmincs2=cfast2**2-4.0d0*csound(ix^
d)*(w(ix^
d,mag(idim))+&
3862 if(avmincs2<zero) avmincs2=zero
3863 csound(ix^
d)=sqrt(half*(cfast2+sqrt(avmincs2)))
3865 csound(ix^
d)=max(csound(ix^
d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
3869 {
do ix^db=ixomin^db,ixomax^db \}
3873 b2=(^
c&w(ix^d,
b^
c_)**2+)
3874 cfast2=b2*inv_rho+csound(ix^d)
3875 avmincs2=cfast2**2-4.0d0*csound(ix^d)*w(ix^d,mag(idim))**2*inv_rho
3876 if(avmincs2<zero) avmincs2=zero
3877 csound(ix^d)=sqrt(half*(cfast2+sqrt(avmincs2)))
3879 csound(ix^d)=max(csound(ix^d),
mhd_etah*sqrt(b2)*inv_rho*kmax)
3884 end subroutine mhd_get_csound_prim_split
3887 subroutine mhd_get_csound_semirelati(w,x,ixI^L,ixO^L,idim,csound,gamma2)
3890 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3892 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3893 double precision,
intent(out):: csound(ixo^s), gamma2(ixo^s)
3895 double precision :: avmincs2, inv_rho, alfven_speed2, idim_alfven_speed2
3898 {
do ix^db=ixomin^db,ixomax^db\}
3899 inv_rho = 1.d0/w(ix^
d,
rho_)
3902 alfven_speed2=(^
c&w(ix^
d,
b^
c_)**2+)*inv_rho
3903 gamma2(ix^
d) = 1.0d0/(1.d0+alfven_speed2*inv_squared_c)
3904 avmincs2=1.d0-gamma2(ix^
d)*w(ix^
d,
mom(idim))**2*inv_squared_c
3905 idim_alfven_speed2=w(ix^
d,mag(idim))**2*inv_rho
3908 alfven_speed2=alfven_speed2*avmincs2+csound(ix^
d)*(1.d0+idim_alfven_speed2*inv_squared_c)
3909 avmincs2=(gamma2(ix^
d)*alfven_speed2)**2-4.0d0*gamma2(ix^
d)*csound(ix^
d)*idim_alfven_speed2*avmincs2
3910 if(avmincs2<zero) avmincs2=zero
3912 csound(ix^
d) = sqrt(half*(gamma2(ix^
d)*alfven_speed2+sqrt(avmincs2)))
3915 end subroutine mhd_get_csound_semirelati
3918 subroutine mhd_get_csound_semirelati_noe(w,x,ixI^L,ixO^L,idim,csound,gamma2)
3922 integer,
intent(in) :: ixi^
l, ixo^
l, idim
3924 double precision,
intent(in) :: w(ixi^s, nw), x(ixi^s,1:
ndim)
3925 double precision,
intent(out):: csound(ixo^s), gamma2(ixo^s)
3927 double precision :: adiabs(ixi^s), gammas(ixi^s)
3928 double precision :: avmincs2, inv_rho, alfven_speed2, idim_alfven_speed2
3941 {
do ix^db=ixomin^db,ixomax^db\}
3942 inv_rho = 1.d0/w(ix^
d,
rho_)
3944 csound(ix^
d)=gammas(ix^
d)*adiabs(ix^
d)*w(ix^
d,
rho_)**(gammas(ix^
d)-1.d0)
3945 alfven_speed2=(^
c&w(ix^
d,
b^
c_)**2+)*inv_rho
3946 gamma2(ix^
d) = 1.0d0/(1.d0+alfven_speed2*inv_squared_c)
3947 avmincs2=1.d0-gamma2(ix^
d)*w(ix^
d,
mom(idim))**2*inv_squared_c
3948 idim_alfven_speed2=w(ix^
d,mag(idim))**2*inv_rho
3951 alfven_speed2=alfven_speed2*avmincs2+csound(ix^
d)*(1.d0+idim_alfven_speed2*inv_squared_c)
3952 avmincs2=(gamma2(ix^
d)*alfven_speed2)**2-4.0d0*gamma2(ix^
d)*csound(ix^
d)*idim_alfven_speed2*avmincs2
3953 if(avmincs2<zero) avmincs2=zero
3955 csound(ix^
d) = sqrt(half*(gamma2(ix^
d)*alfven_speed2+sqrt(avmincs2)))
3958 end subroutine mhd_get_csound_semirelati_noe
3961 subroutine mhd_get_pthermal_noe(w,x,ixI^L,ixO^L,pth)
3965 integer,
intent(in) :: ixi^
l, ixo^
l
3966 double precision,
intent(in) :: w(ixi^s,nw)
3967 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3968 double precision,
intent(out):: pth(ixi^s)
3970 double precision :: adiabs(ixi^s), gammas(ixi^s)
3983 {
do ix^db=ixomin^db,ixomax^db\}
3984 pth(ix^
d)=adiabs(ix^
d)*w(ix^
d,
rho_)**gammas(ix^
d)
3987 end subroutine mhd_get_pthermal_noe
3990 subroutine mhd_get_pthermal_inte(w,x,ixI^L,ixO^L,pth)
3994 integer,
intent(in) :: ixi^
l, ixo^
l
3995 double precision,
intent(in) :: w(ixi^s,nw)
3996 double precision,
intent(in) :: x(ixi^s,1:
ndim)
3997 double precision,
intent(out):: pth(ixi^s)
4001 {
do ix^db= ixomin^db,ixomax^db\}
4002 pth(ix^
d)=gamma_1*w(ix^
d,
e_)
4006 if(check_small_values.and..not.fix_small_values)
then
4007 {
do ix^db= ixomin^db,ixomax^db\}
4008 if(pth(ix^d)<small_pressure)
then
4009 write(*,*)
"Error: small value of gas pressure",pth(ix^d),&
4010 " encountered when call mhd_get_pthermal_inte"
4011 write(*,*)
"Iteration: ", it,
" Time: ", global_time
4012 write(*,*)
"Location: ", x(ix^d,:)
4013 write(*,*)
"Cell number: ", ix^d
4015 write(*,*) trim(cons_wnames(iw)),
": ",w(ix^d,iw)
4018 if(trace_small_values)
write(*,*) sqrt(pth(ix^d)-bigdouble)
4019 write(*,*)
"Saving status at the previous time step"
4025 end subroutine mhd_get_pthermal_inte
4028 subroutine mhd_get_pthermal_origin(w,x,ixI^L,ixO^L,pth)
4032 integer,
intent(in) :: ixi^
l, ixo^
l
4033 double precision,
intent(in) :: w(ixi^s,nw)
4034 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4035 double precision,
intent(out):: pth(ixi^s)
4039 {
do ix^db=ixomin^db,ixomax^db\}
4044 pth(ix^
d)=gamma_1*(w(ix^
d,
e_)-half*((^
c&w(ix^
d,
m^
c_)**2+)/w(ix^
d,
rho_)&
4045 +(^
c&w(ix^
d,
b^
c_)**2+)))
4050 if(check_small_values.and..not.fix_small_values)
then
4051 {
do ix^db=ixomin^db,ixomax^db\}
4052 if(pth(ix^d)<small_pressure)
then
4053 write(*,*)
"Error: small value of gas pressure",pth(ix^d),&
4054 " encountered when call mhd_get_pthermal"
4055 write(*,*)
"Iteration: ", it,
" Time: ", global_time
4056 write(*,*)
"Location: ", x(ix^d,:)
4057 write(*,*)
"Cell number: ", ix^d
4059 write(*,*) trim(cons_wnames(iw)),
": ",w(ix^d,iw)
4062 if(trace_small_values)
write(*,*) sqrt(pth(ix^d)-bigdouble)
4063 write(*,*)
"Saving status at the previous time step"
4069 end subroutine mhd_get_pthermal_origin
4072 subroutine mhd_get_pthermal_semirelati(w,x,ixI^L,ixO^L,pth)
4076 integer,
intent(in) :: ixi^
l, ixo^
l
4077 double precision,
intent(in) :: w(ixi^s,nw)
4078 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4079 double precision,
intent(out):: pth(ixi^s)
4081 double precision :: e(1:
ndir), v(1:
ndir), tmp, factor
4084 {
do ix^db=ixomin^db,ixomax^db\}
4086 tmp=(^
c&w(ix^
d,
b^
c_)*w(ix^
d,
m^
c_)+)*inv_squared_c
4087 factor=1.0d0/(w(ix^
d,
rho_)*(w(ix^
d,
rho_)+(^
c&w(ix^
d,
b^
c_)**2+)*inv_squared_c))
4092 e(1)=w(ix^
d,b2_)*v(3)-w(ix^
d,b3_)*v(2)
4093 e(2)=w(ix^
d,b3_)*v(1)-w(ix^
d,b1_)*v(3)
4094 e(3)=w(ix^
d,b1_)*v(2)-w(ix^
d,b2_)*v(1)
4098 e(2)=w(ix^
d,b1_)*v(2)-w(ix^
d,b2_)*v(1)
4104 pth(ix^
d)=gamma_1*(w(ix^
d,
e_)&
4105 -half*((^
c&v(^
c)**2+)*w(ix^
d,
rho_)&
4106 +(^
c&w(ix^
d,
b^
c_)**2+)+(^
c&e(^
c)**2+)*inv_squared_c))
4110 if(check_small_values.and..not.fix_small_values)
then
4111 {
do ix^db=ixomin^db,ixomax^db\}
4112 if(pth(ix^d)<small_pressure)
then
4113 write(*,*)
"Error: small value of gas pressure",pth(ix^d),&
4114 " encountered when call mhd_get_pthermal_semirelati"
4115 write(*,*)
"Iteration: ", it,
" Time: ", global_time
4116 write(*,*)
"Location: ", x(ix^d,:)
4117 write(*,*)
"Cell number: ", ix^d
4119 write(*,*) trim(cons_wnames(iw)),
": ",w(ix^d,iw)
4122 if(trace_small_values)
write(*,*) sqrt(pth(ix^d)-bigdouble)
4123 write(*,*)
"Saving status at the previous time step"
4129 end subroutine mhd_get_pthermal_semirelati
4132 subroutine mhd_get_pthermal_hde(w,x,ixI^L,ixO^L,pth)
4136 integer,
intent(in) :: ixi^
l, ixo^
l
4137 double precision,
intent(in) :: w(ixi^s,nw)
4138 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4139 double precision,
intent(out):: pth(ixi^s)
4143 {
do ix^db= ixomin^db,ixomax^db\}
4144 pth(ix^
d)=gamma_1*(w(ix^
d,
e_)-half*((^
c&w(ix^
d,
m^
c_)**2+)/w(ix^
d,
rho_)))
4147 if(check_small_values.and..not.fix_small_values)
then
4148 {
do ix^db= ixomin^db,ixomax^db\}
4149 if(pth(ix^d)<small_pressure)
then
4150 write(*,*)
"Error: small value of gas pressure",pth(ix^d),&
4151 " encountered when call mhd_get_pthermal_hde"
4152 write(*,*)
"Iteration: ", it,
" Time: ", global_time
4153 write(*,*)
"Location: ", x(ix^d,:)
4154 write(*,*)
"Cell number: ", ix^d
4156 write(*,*) trim(cons_wnames(iw)),
": ",w(ix^d,iw)
4159 if(trace_small_values)
write(*,*) sqrt(pth(ix^d)-bigdouble)
4160 write(*,*)
"Saving status at the previous time step"
4166 end subroutine mhd_get_pthermal_hde
4169 subroutine mhd_get_temperature_from_te(w, x, ixI^L, ixO^L, res)
4171 integer,
intent(in) :: ixi^
l, ixo^
l
4172 double precision,
intent(in) :: w(ixi^s, 1:nw)
4173 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4174 double precision,
intent(out):: res(ixi^s)
4175 res(ixo^s) = w(ixo^s,
te_)
4176 end subroutine mhd_get_temperature_from_te
4179 subroutine mhd_get_temperature_from_eint(w, x, ixI^L, ixO^L, res)
4181 integer,
intent(in) :: ixi^
l, ixo^
l
4182 double precision,
intent(in) :: w(ixi^s, 1:nw)
4183 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4184 double precision,
intent(out):: res(ixi^s)
4186 double precision :: r(ixi^s)
4189 res(ixo^s) = gamma_1 * w(ixo^s,
e_)/(w(ixo^s,
rho_)*r(ixo^s))
4190 end subroutine mhd_get_temperature_from_eint
4195 integer,
intent(in) :: ixi^
l, ixo^
l
4196 double precision,
intent(in) :: w(ixi^s, 1:nw)
4197 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4198 double precision,
intent(out):: res(ixi^s)
4200 double precision :: r(ixi^s)
4203 res(ixo^s) = w(ixo^s,
p_)/(w(ixo^s,
rho_)*r(ixo^s))
4209 integer,
intent(in) :: ixi^
l, ixo^
l
4210 double precision,
intent(in) :: w(ixi^s, 1:nw)
4211 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4212 double precision,
intent(out):: res(ixi^s)
4214 double precision :: r(ixi^s),rho(ixi^s),pth(ixi^s)
4219 res(ixo^s)=pth(ixo^s)/(r(ixo^s)*rho(ixo^s))
4223 subroutine mhd_get_temperature_from_eint_with_equi(w, x, ixI^L, ixO^L, res)
4225 integer,
intent(in) :: ixi^
l, ixo^
l
4226 double precision,
intent(in) :: w(ixi^s, 1:nw)
4227 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4228 double precision,
intent(out):: res(ixi^s)
4230 double precision :: r(ixi^s)
4236 end subroutine mhd_get_temperature_from_eint_with_equi
4238 subroutine mhd_get_temperature_equi(w,x, ixI^L, ixO^L, res)
4240 integer,
intent(in) :: ixi^
l, ixo^
l
4241 double precision,
intent(in) :: w(ixi^s, 1:nw)
4242 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4243 double precision,
intent(out):: res(ixi^s)
4245 double precision :: r(ixi^s)
4251 end subroutine mhd_get_temperature_equi
4253 subroutine mhd_get_rho_equi(w, x, ixI^L, ixO^L, res)
4255 integer,
intent(in) :: ixi^
l, ixo^
l
4256 double precision,
intent(in) :: w(ixi^s, 1:nw)
4257 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4258 double precision,
intent(out):: res(ixi^s)
4260 end subroutine mhd_get_rho_equi
4262 subroutine mhd_get_pe_equi(w,x, ixI^L, ixO^L, res)
4264 integer,
intent(in) :: ixi^
l, ixo^
l
4265 double precision,
intent(in) :: w(ixi^s, 1:nw)
4266 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4267 double precision,
intent(out):: res(ixi^s)
4269 end subroutine mhd_get_pe_equi
4275 integer,
intent(in) :: ixi^
l, ixo^
l
4276 double precision,
intent(in) :: w(ixi^s, 1:nw)
4277 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4278 double precision,
intent(out):: prad(ixi^s, 1:
ndim, 1:
ndim)
4287 integer,
intent(in) :: ixi^
l, ixo^
l
4288 double precision,
intent(in) :: w(ixi^s, 1:nw)
4289 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4290 double precision,
intent(out) :: pth_plus_prad(ixi^s)
4292 double precision :: wprim(ixi^s, 1:nw)
4293 double precision :: prad_tensor(ixi^s, 1:
ndim, 1:
ndim)
4294 double precision :: prad_max(ixi^s)
4297 wprim(ixi^s,1:nw)=w(ixi^s,1:nw)
4300 {
do ix^
d = ixomin^
d,ixomax^
d\}
4301 prad_max(ix^
d) = maxval(prad_tensor(ix^
d,:,:))
4303 pth_plus_prad(ixo^s) = wprim(ixo^s,
p_) + prad_max(ixo^s)
4311 integer,
intent(in) :: ixi^
l, ixo^
l
4312 double precision,
intent(in) :: w(ixi^s, 1:nw)
4313 double precision,
intent(in) :: x(ixi^s, 1:
ndim)
4314 double precision,
intent(out):: trad(ixi^s)
4321 subroutine mhd_get_flux(wC,w,x,ixI^L,ixO^L,idim,f)
4325 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4327 double precision,
intent(in) :: wc(ixi^s,nw)
4329 double precision,
intent(in) :: w(ixi^s,nw)
4330 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4331 double precision,
intent(out) :: f(ixi^s,nwflux)
4333 double precision :: vhall(ixi^s,1:
ndir)
4334 double precision :: ptotal
4335 double precision :: r(ixi^s), te(ixi^s), rho_loc(ixi^s)
4336 double precision :: bvec(ixi^s,1:
ndir)
4337 double precision :: bgradt(ixi^s), gradtperp_mag(ixi^s)
4338 double precision :: nperp(ixi^s,1:
ndir)
4339 logical :: use_perp_flux
4340 integer :: iw, ix^
d, idir
4343 {
do ix^db=ixomin^db,ixomax^db\}
4356 {
do ix^db=ixomin^db,ixomax^db\}
4360 ^
c&f(ix^d,
m^
c_)=wc(ix^d,
mom(idim))*w(ix^d,
m^
c_)-w(ix^d,mag(idim))*w(ix^d,
b^
c_)\
4361 ptotal=w(ix^d,
p_)+half*(^
c&w(ix^d,
b^
c_)**2+)
4363 f(ix^d,
mom(idim))=f(ix^d,
mom(idim))+ptotal
4366 f(ix^d,
e_)=w(ix^d,
mom(idim))*(wc(ix^d,
e_)+ptotal)&
4367 -w(ix^d,mag(idim))*(^
c&w(ix^d,
b^
c_)*w(ix^d,
m^
c_)+)
4369 ^
c&f(ix^d,
b^
c_)=w(ix^d,
mom(idim))*w(ix^d,
b^
c_)-w(ix^d,mag(idim))*w(ix^d,
m^
c_)\
4373 call mhd_getv_hall(w,x,ixi^l,ixo^l,vhall)
4374 {
do ix^db=ixomin^db,ixomax^db\}
4375 if(total_energy)
then
4377 f(ix^d,
e_)=f(ix^d,
e_)+vhall(ix^d,idim)*(^
c&w(ix^d,
b^
c_)**2+)&
4378 -w(ix^d,mag(idim))*(^
c&vhall(ix^d,^
c)*w(ix^d,
b^
c_)+)
4381 ^
c&f(ix^d,
b^
c_)=f(ix^d,
b^
c_)+vhall(ix^d,idim)*w(ix^d,
b^
c_)-vhall(ix^d,^
c)*w(ix^d,mag(idim))\
4386 {
do ix^db=ixomin^db,ixomax^db\}
4387 f(ix^d,mag(idim))=w(ix^d,
psi_)
4389 f(ix^d,
psi_) = cmax_global**2*w(ix^d,mag(idim))
4394 {
do ix^db=ixomin^db,ixomax^db\}
4395 f(ix^d,
r_e)=w(ix^d,
mom(idim))*wc(ix^d,
r_e)
4400 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4404 {
do ix^db=ixomin^db,ixomax^db\}
4410 if(use_perp_flux)
then
4413 te(ixi^s)=w(ixi^s,
p_)/(r(ixi^s)*rho_loc(ixi^s))
4414 {
do ix^db=ixomin^db,ixomax^db\}
4416 bvec(ix^d,idir)=w(ix^d,mag(idir))
4419 call mhd_get_hyperbolic_tc_geometry(ixi^l,ixo^l,te,bvec,bgradt,gradtperp_mag,nperp)
4423 {
do ix^db=ixomin^db,ixomax^db\}
4424 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qpar_)*w(ix^d,mag(idim))/(dsqrt(^
c&w(ix^d,
b^
c_)**2+)+smalldouble)
4426 if(use_perp_flux)
then
4427 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qperp_)*nperp(ix^d,idim)
4432 end subroutine mhd_get_flux
4436 subroutine mhd_get_flux_noe(wC,w,x,ixI^L,ixO^L,idim,f)
4441 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4443 double precision,
intent(in) :: wc(ixi^s,nw)
4445 double precision,
intent(in) :: w(ixi^s,nw)
4446 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4447 double precision,
intent(out) :: f(ixi^s,nwflux)
4449 double precision :: vhall(ixi^s,1:
ndir)
4450 double precision :: adiabs(ixi^s), gammas(ixi^s)
4463 {
do ix^db=ixomin^db,ixomax^db\}
4469 f(ix^
d,
mom(idim))=f(ix^
d,
mom(idim))+adiabs(ix^
d)*w(ix^
d,
rho_)**gammas(ix^
d)+half*(^
c&w(ix^
d,
b^
c_)**2+)
4474 call mhd_getv_hall(w,x,ixi^l,ixo^l,vhall)
4475 {
do ix^db=ixomin^db,ixomax^db\}
4477 ^
c&f(ix^d,
b^
c_)=f(ix^d,
b^
c_)+vhall(ix^d,idim)*w(ix^d,
b^
c_)-vhall(ix^d,^
c)*w(ix^d,mag(idim))\
4481 {
do ix^db=ixomin^db,ixomax^db\}
4482 f(ix^d,mag(idim))=w(ix^d,
psi_)
4484 f(ix^d,
psi_) = cmax_global**2*w(ix^d,mag(idim))
4488 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4492 {
do ix^db=ixomin^db,ixomax^db\}
4496 end subroutine mhd_get_flux_noe
4499 subroutine mhd_get_flux_hde(wC,w,x,ixI^L,ixO^L,idim,f)
4503 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4505 double precision,
intent(in) :: wc(ixi^s,nw)
4507 double precision,
intent(in) :: w(ixi^s,nw)
4508 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4509 double precision,
intent(out) :: f(ixi^s,nwflux)
4511 double precision :: vhall(ixi^s,1:
ndir)
4512 double precision :: r(ixi^s), te(ixi^s), rho_loc(ixi^s)
4513 double precision :: bvec(ixi^s,1:
ndir)
4514 double precision :: bgradt(ixi^s), gradtperp_mag(ixi^s)
4515 double precision :: nperp(ixi^s,1:
ndir)
4516 logical :: use_perp_flux
4517 integer :: iw, ix^
d, idir
4519 {
do ix^db=ixomin^db,ixomax^db\}
4532 call mhd_getv_hall(w,x,ixi^l,ixo^l,vhall)
4533 {
do ix^db=ixomin^db,ixomax^db\}
4535 ^
c&f(ix^d,
b^
c_)=f(ix^d,
b^
c_)+vhall(ix^d,idim)*w(ix^d,
b^
c_)-vhall(ix^d,^
c)*w(ix^d,mag(idim))\
4539 {
do ix^db=ixomin^db,ixomax^db\}
4540 f(ix^d,mag(idim))=w(ix^d,
psi_)
4542 f(ix^d,
psi_) = cmax_global**2*w(ix^d,mag(idim))
4546 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4550 {
do ix^db=ixomin^db,ixomax^db\}
4555 if(use_perp_flux)
then
4558 te(ixi^s)=w(ixi^s,
p_)/(r(ixi^s)*rho_loc(ixi^s))
4559 {
do ix^db=ixomin^db,ixomax^db\}
4561 bvec(ix^d,idir)=w(ix^d,mag(idir))
4564 call mhd_get_hyperbolic_tc_geometry(ixi^l,ixo^l,te,bvec,bgradt,gradtperp_mag,nperp)
4567 {
do ix^db=ixomin^db,ixomax^db\}
4568 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qpar_)*w(ix^d,mag(idim))/(dsqrt(^
c&w(ix^d,
b^
c_)**2+)+smalldouble)
4570 if(use_perp_flux)
then
4571 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qperp_)*nperp(ix^d,idim)
4576 end subroutine mhd_get_flux_hde
4583 subroutine mhd_get_flux_split(wC,w,x,ixI^L,ixO^L,idim,f)
4587 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4589 double precision,
intent(in) :: wc(ixi^s,nw)
4591 double precision,
intent(in) :: w(ixi^s,nw)
4592 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4593 double precision,
intent(out) :: f(ixi^s,nwflux)
4595 double precision :: vhall(ixi^s,1:
ndir)
4596 double precision :: ptotal, btotal(ixo^s,1:
ndir)
4597 double precision :: r(ixi^s), te(ixi^s), rho_loc(ixi^s)
4598 double precision :: bvec(ixi^s,1:
ndir)
4599 double precision :: bgradt(ixi^s), gradtperp_mag(ixi^s)
4600 double precision :: nperp(ixi^s,1:
ndir)
4601 logical :: use_perp_flux
4602 integer :: iw, ix^
d, idir
4604 {
do ix^db=ixomin^db,ixomax^db\}
4612 ptotal=w(ix^
d,
p_)+half*(^
c&w(ix^
d,
b^
c_)**2+)
4616 ptotal=ptotal+(^
c&w(ix^
d,
b^
c_)*
block%B0(ix^
d,^
c,idim)+)
4620 btotal(ix^
d,idim)*w(ix^
d,
b^
c_)-w(ix^
d,mag(idim))*
block%B0(ix^
d,^
c,idim)\
4621 f(ix^
d,
mom(idim))=f(ix^
d,
mom(idim))+ptotal
4623 ^
c&btotal(ix^
d,^
c)=w(ix^
d,
b^
c_)\
4627 f(ix^
d,
mom(idim))=f(ix^
d,
mom(idim))+ptotal
4630 ^
c&f(ix^
d,
b^
c_)=w(ix^
d,
mom(idim))*btotal(ix^
d,^
c)-btotal(ix^
d,idim)*w(ix^
d,
m^
c_)\
4637 f(ix^
d,
e_)=w(ix^
d,
mom(idim))*(wc(ix^
d,
e_)+ptotal)&
4638 -btotal(ix^
d,idim)*(^
c&w(ix^
d,
b^
c_)*w(ix^
d,
m^
c_)+)
4643 {
do ix^db=ixomin^db,ixomax^db\}
4644 f(ix^d,mag(idim))=w(ix^d,
psi_)
4646 f(ix^d,
psi_) = cmax_global**2*w(ix^d,mag(idim))
4651 {
do ix^db=ixomin^db,ixomax^db\}
4652 f(ix^d,
r_e)=w(ix^d,
mom(idim))*wc(ix^d,
r_e)
4657 call mhd_getv_hall(w,x,ixi^l,ixo^l,vhall)
4658 {
do ix^db=ixomin^db,ixomax^db\}
4660 ^
c&f(ix^d,
b^
c_)=f(ix^d,
b^
c_)+vhall(ix^d,idim)*btotal(ix^d,^
c)-btotal(ix^d,idim)*vhall(ix^d,^
c)\
4661 if(total_energy)
then
4663 f(ix^d,
e_)=f(ix^d,
e_)+vhall(ix^d,idim)*(^
c&w(ix^d,
b^
c_)*btotal(ix^d,^
c)+)&
4664 -btotal(ix^d,idim)*(^
c&vhall(ix^d,^
c)*w(ix^d,
b^
c_)+)
4669 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4673 {
do ix^db=ixomin^db,ixomax^db\}
4678 if(use_perp_flux)
then
4681 te(ixi^s)=w(ixi^s,
p_)/(r(ixi^s)*rho_loc(ixi^s))
4682 {
do ix^db=ixomin^db,ixomax^db\}
4684 bvec(ix^d,idir)=btotal(ix^d,idir)
4687 call mhd_get_hyperbolic_tc_geometry(ixi^l,ixo^l,te,bvec,bgradt,gradtperp_mag,nperp)
4690 {
do ix^db=ixomin^db,ixomax^db\}
4691 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qpar_)*btotal(ix^d,idim)/(dsqrt(^
c&btotal(ix^d,^
c)**2+)+smalldouble)
4693 if(use_perp_flux)
then
4694 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qperp_)*nperp(ix^d,idim)
4699 end subroutine mhd_get_flux_split
4702 subroutine mhd_get_flux_semirelati(wC,w,x,ixI^L,ixO^L,idim,f)
4706 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4708 double precision,
intent(in) :: wc(ixi^s,nw)
4710 double precision,
intent(in) :: w(ixi^s,nw)
4711 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4712 double precision,
intent(out) :: f(ixi^s,nwflux)
4713 double precision :: sa(ixo^s,1:
ndir),e(ixo^s,1:
ndir),e2
4714 double precision :: r(ixi^s), te(ixi^s), rho_loc(ixi^s)
4715 double precision :: bvec(ixi^s,1:
ndir)
4716 double precision :: bgradt(ixi^s), gradtperp_mag(ixi^s)
4717 double precision :: nperp(ixi^s,1:
ndir)
4718 logical :: use_perp_flux
4719 integer :: iw, ix^
d, idir
4721 {
do ix^db=ixomin^db,ixomax^db\}
4726 e(ix^
d,1)=w(ix^
d,b2_)*w(ix^
d,m3_)-w(ix^
d,b3_)*w(ix^
d,m2_)
4727 e(ix^
d,2)=w(ix^
d,b3_)*w(ix^
d,m1_)-w(ix^
d,b1_)*w(ix^
d,m3_)
4728 e(ix^
d,3)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
4733 e(ix^
d,2)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
4738 e2=(^
c&e(ix^
d,^
c)**2+)
4745 sa(ix^
d,1)=e(ix^
d,2)*w(ix^
d,b3_)-e(ix^
d,3)*w(ix^
d,b2_)
4746 sa(ix^
d,2)=e(ix^
d,3)*w(ix^
d,b1_)-e(ix^
d,1)*w(ix^
d,b3_)
4747 sa(ix^
d,3)=e(ix^
d,1)*w(ix^
d,b2_)-e(ix^
d,2)*w(ix^
d,b1_)
4750 sa(ix^
d,1)=-e(ix^
d,2)*w(ix^
d,b2_)
4751 sa(ix^
d,2)=e(ix^
d,2)*w(ix^
d,b1_)
4764 -w(ix^
d,mag(idim))*w(ix^
d,
b^
c_)-e(ix^
d,idim)*e(ix^
d,^
c)*inv_squared_c\
4766 f(ix^
d,
mom(idim))=f(ix^
d,
mom(idim))+w(ix^
d,
p_)+half*((^
c&w(ix^
d,
b^
c_)**2+)+e2*inv_squared_c)
4773 {
do ix^db=ixomin^db,ixomax^db\}
4774 f(ix^d,mag(idim))=w(ix^d,
psi_)
4776 f(ix^d,
psi_)=cmax_global**2*w(ix^d,mag(idim))
4780 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4784 {
do ix^db=ixomin^db,ixomax^db\}
4789 if(use_perp_flux)
then
4792 te(ixi^s)=w(ixi^s,
p_)/(r(ixi^s)*rho_loc(ixi^s))
4793 {
do ix^db=ixomin^db,ixomax^db\}
4795 bvec(ix^d,idir)=w(ix^d,mag(idir))
4798 call mhd_get_hyperbolic_tc_geometry(ixi^l,ixo^l,te,bvec,bgradt,gradtperp_mag,nperp)
4801 {
do ix^db=ixomin^db,ixomax^db\}
4802 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qpar_)*w(ix^d,mag(idim))/(dsqrt(^
c&w(ix^d,
b^
c_)**2+)+smalldouble)
4804 if(use_perp_flux)
then
4805 f(ix^d,
e_)=f(ix^d,
e_)+w(ix^d,
qperp_)*nperp(ix^d,idim)
4810 end subroutine mhd_get_flux_semirelati
4812 subroutine mhd_get_flux_semirelati_noe(wC,w,x,ixI^L,ixO^L,idim,f)
4817 integer,
intent(in) :: ixi^
l, ixo^
l, idim
4819 double precision,
intent(in) :: wc(ixi^s,nw)
4821 double precision,
intent(in) :: w(ixi^s,nw)
4822 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4823 double precision,
intent(out) :: f(ixi^s,nwflux)
4825 double precision :: adiabs(ixi^s), gammas(ixi^s)
4826 double precision :: e(ixo^s,1:
ndir),e2
4839 {
do ix^db=ixomin^db,ixomax^db\}
4844 e(ix^
d,1)=w(ix^
d,b2_)*w(ix^
d,m3_)-w(ix^
d,b3_)*w(ix^
d,m2_)
4845 e(ix^
d,2)=w(ix^
d,b3_)*w(ix^
d,m1_)-w(ix^
d,b1_)*w(ix^
d,m3_)
4846 e(ix^
d,3)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
4847 e2=(^
c&e(ix^
d,^
c)**2+)
4852 e(ix^
d,2)=w(ix^
d,b1_)*w(ix^
d,m2_)-w(ix^
d,b2_)*w(ix^
d,m1_)
4862 -w(ix^
d,mag(idim))*w(ix^
d,
b^
c_)-e(ix^
d,idim)*e(ix^
d,^
c)*inv_squared_c\
4864 f(ix^
d,
mom(idim))=f(ix^
d,
mom(idim))+adiabs(ix^
d)*w(ix^
d,
rho_)**gammas(ix^
d)+half*((^
c&w(ix^
d,
b^
c_)**2+)+e2*inv_squared_c)
4871 {
do ix^db=ixomin^db,ixomax^db\}
4872 f(ix^d,mag(idim))=w(ix^d,
psi_)
4874 f(ix^d,
psi_)=cmax_global**2*w(ix^d,mag(idim))
4878 f(ixo^s,
fip_) = w(ixo^s,
mom(idim)) * wc(ixo^s,
fip_)
4882 {
do ix^db=ixomin^db,ixomax^db\}
4886 end subroutine mhd_get_flux_semirelati_noe
4894 subroutine add_source_ambipolar_internal_energy(qdt,ixI^L,ixO^L,wCT,w,x)
4896 integer,
intent(in) :: ixi^
l, ixo^
l
4897 double precision,
intent(in) :: qdt
4898 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
4899 double precision,
intent(inout) :: w(ixi^s,1:nw)
4901 double precision :: tmp(ixi^s),btot2(ixi^s)
4902 double precision :: jxbxb(ixi^s,1:3)
4904 call mhd_get_jxbxb(wct,x,ixi^
l,ixo^
l,jxbxb)
4907 where (btot2(ixo^s)>smalldouble )
4908 tmp(ixo^s) = sum(jxbxb(ixo^s,1:3)**2,dim=
ndim+1) / btot2(ixo^s)
4915 w(ixo^s,
e_)=w(ixo^s,
e_)- qdt*tmp(ixo^s)
4917 end subroutine add_source_ambipolar_internal_energy
4920 subroutine mhd_get_jxbxb(w,x,ixI^L,ixO^L,res)
4923 integer,
intent(in) :: ixi^
l, ixo^
l
4924 double precision,
intent(in) :: w(ixi^s,nw)
4925 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4926 double precision,
intent(out) :: res(ixi^s,1:3)
4928 double precision :: btot(ixi^s,1:3)
4929 double precision :: current(ixi^s,7-2*
ndir:3)
4930 double precision :: tmp(ixi^s),b2(ixi^s)
4931 integer :: idir, idirmin
4941 btot(ixo^s, idir) = w(ixo^s,mag(idir)) +
block%B0(ixo^s,idir,
b0i)
4945 btot(ixo^s, idir) = w(ixo^s,mag(idir))
4949 tmp(ixo^s)= sum(current(ixo^s,idirmin:3)*btot(ixo^s,idirmin:3),dim=
ndim+1)
4950 b2(ixo^s) = sum(btot(ixo^s,1:3)**2,dim=
ndim+1)
4952 res(ixo^s,idir) = btot(ixo^s,idir) * tmp(ixo^s)
4955 res(ixo^s,idir) = btot(ixo^s,idir) * tmp(ixo^s) - current(ixo^s,idir) * b2(ixo^s)
4960 where (b2(ixo^s)<smalldouble )
4961 res(ixo^s,idir) = zero
4964 end subroutine mhd_get_jxbxb
4970 subroutine sts_set_source_ambipolar(ixI^L,ixO^L,w,x,wres,fix_conserve_at_step,my_dt,igrid,nflux)
4974 integer,
intent(in) :: ixi^
l,ixo^
l,igrid,nflux
4975 double precision,
intent(in) :: x(ixi^s,1:
ndim)
4976 double precision,
intent(inout) :: wres(ixi^s,1:nw), w(ixi^s,1:nw)
4977 double precision,
intent(in) :: my_dt
4978 logical,
intent(in) :: fix_conserve_at_step
4980 double precision,
dimension(ixI^S,1:3) :: tmp,ff
4981 double precision :: fluxall(ixi^s,1:nflux,1:
ndim)
4982 double precision :: fe(ixi^s,
sdim:3)
4983 double precision :: btot(ixi^s,1:3),tmp2(ixi^s)
4984 integer :: i, ixa^
l, ie_
4991 call mhd_get_jxbxb(w,x,ixi^
l,ixa^
l,tmp)
5008 btot(ixa^s,1:3) = 0.d0
5010 btot(ixa^s,1:
ndir) = w(ixa^s,mag(1:
ndir))
5014 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5015 if(fix_conserve_at_step) fluxall(ixi^s,1,1:
ndim)=ff(ixi^s,1:
ndim)
5017 wres(ixo^s,
e_)=-tmp2(ixo^s)
5024 ff(ixa^s,1) = tmp(ixa^s,2)
5025 ff(ixa^s,2) = -tmp(ixa^s,1)
5027 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5028 if(fix_conserve_at_step) fluxall(ixi^s,1+
ndir,1:
ndim)=ff(ixi^s,1:
ndim)
5029 wres(ixo^s,mag(
ndir))=-tmp2(ixo^s)
5032 call update_faces_ambipolar(ixi^
l,ixo^
l,w,x,tmp,fe,btot)
5034 ixamin^
d=ixomin^
d-1;
5035 wres(ixa^s,mag(1:
ndim))=-btot(ixa^s,1:
ndim)
5045 ff(ixa^s,2) = tmp(ixa^s,3)
5046 ff(ixa^s,3) = -tmp(ixa^s,2)
5047 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5048 if(fix_conserve_at_step) fluxall(ixi^s,2,1:
ndim)=ff(ixi^s,1:
ndim)
5050 wres(ixo^s,mag(1))=-tmp2(ixo^s)
5053 ff(ixa^s,1) = -tmp(ixa^s,3)
5055 ff(ixa^s,3) = tmp(ixa^s,1)
5056 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5057 if(fix_conserve_at_step) fluxall(ixi^s,3,1:
ndim)=ff(ixi^s,1:
ndim)
5058 wres(ixo^s,mag(2))=-tmp2(ixo^s)
5064 ff(ixa^s,2) = tmp(ixa^s,3)
5065 ff(ixa^s,3) = -tmp(ixa^s,2)
5066 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5067 if(fix_conserve_at_step) fluxall(ixi^s,2,1:
ndim)=ff(ixi^s,1:
ndim)
5069 wres(ixo^s,mag(1))=-tmp2(ixo^s)
5071 ff(ixa^s,1) = -tmp(ixa^s,3)
5073 ff(ixa^s,3) = tmp(ixa^s,1)
5074 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5075 if(fix_conserve_at_step) fluxall(ixi^s,3,1:
ndim)=ff(ixi^s,1:
ndim)
5076 wres(ixo^s,mag(2))=-tmp2(ixo^s)
5081 ff(ixa^s,1) = tmp(ixa^s,2)
5082 ff(ixa^s,2) = -tmp(ixa^s,1)
5084 call get_flux_on_cell_face(ixi^
l,ixo^
l,ff,tmp2)
5085 if(fix_conserve_at_step) fluxall(ixi^s,1+
ndir,1:
ndim)=ff(ixi^s,1:
ndim)
5086 wres(ixo^s,mag(
ndir))=-tmp2(ixo^s)
5091 if(fix_conserve_at_step)
then
5092 fluxall=my_dt*fluxall
5099 end subroutine sts_set_source_ambipolar
5102 subroutine update_faces_ambipolar(ixI^L,ixO^L,w,x,ECC,fE,circ)
5105 integer,
intent(in) :: ixi^
l, ixo^
l
5106 double precision,
intent(in) :: w(ixi^s,1:nw)
5107 double precision,
intent(in) :: x(ixi^s,1:
ndim)
5109 double precision,
intent(in) :: ecc(ixi^s,1:3)
5110 double precision,
intent(out) :: fe(ixi^s,
sdim:3)
5111 double precision,
intent(out) :: circ(ixi^s,1:
ndim)
5113 integer :: hxc^
l,ixc^
l,ixa^
l
5114 integer :: idim1,idim2,idir,ix^
d
5120 ixcmin^
d=ixomin^
d+
kr(idir,^
d)-1;
5122 if({ ix^
d==1 .and. ^
d==idir | .or.}) cycle
5123 ixamin^
d=ixcmin^
d+ix^
d;
5124 ixamax^
d=ixcmax^
d+ix^
d;
5125 fe(ixc^s,idir)=fe(ixc^s,idir)+ecc(ixa^s,idir)
5127 fe(ixc^s,idir)=fe(ixc^s,idir)*0.25d0*block%dsC(ixc^s,idir)
5133 ixcmin^d=ixomin^d-1;
5140 hxc^l=ixc^l-kr(idim2,^d);
5142 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
5143 +lvc(idim1,idim2,idir)&
5148 circ(ixc^s,idim1)=circ(ixc^s,idim1)/block%surfaceC(ixc^s,idim1)
5151 end subroutine update_faces_ambipolar
5157 subroutine get_flux_on_cell_face(ixI^L,ixO^L,ff,src)
5160 integer,
intent(in) :: ixi^
l, ixo^
l
5161 double precision,
dimension(ixI^S,1:3),
intent(inout) :: ff
5162 double precision,
intent(out) :: src(ixi^s)
5164 double precision :: ffc(ixi^s,1:
ndim)
5165 double precision :: dxinv(
ndim)
5166 integer :: idims, ix^
d, ixa^
l, ixb^
l, ixc^
l
5174 ixcmax^
d=ixomax^
d; ixcmin^
d=ixomin^
d-1;
5176 ixbmin^
d=ixcmin^
d+ix^
d;
5177 ixbmax^
d=ixcmax^
d+ix^
d;
5180 ffc(ixc^s,1:ndim)=0.5d0**ndim*ffc(ixc^s,1:ndim)
5182 call mpistop(
"to generalize using volume averaging")
5185 ff(ixi^s,1:ndim)=0.d0
5187 ixb^l=ixo^l-kr(idims,^d);
5188 ixcmax^d=ixomax^d; ixcmin^d=ixbmin^d;
5190 if({ ix^d==0 .and. ^d==idims | .or.})
then
5191 ixbmin^d=ixcmin^d-ix^d;
5192 ixbmax^d=ixcmax^d-ix^d;
5193 ff(ixc^s,idims)=ff(ixc^s,idims)+ffc(ixb^s,idims)
5196 ff(ixc^s,idims)=ff(ixc^s,idims)*0.5d0**(ndim-1)
5199 if(slab_uniform)
then
5201 ff(ixa^s,idims)=dxinv(idims)*ff(ixa^s,idims)
5202 ixb^l=ixo^l-kr(idims,^d);
5203 src(ixo^s)=src(ixo^s)+ff(ixo^s,idims)-ff(ixb^s,idims)
5207 ff(ixa^s,idims)=ff(ixa^s,idims)*block%surfaceC(ixa^s,idims)
5208 ixb^l=ixo^l-kr(idims,^d);
5209 src(ixo^s)=src(ixo^s)+ff(ixo^s,idims)-ff(ixb^s,idims)
5211 src(ixo^s)=src(ixo^s)/block%dvolume(ixo^s)
5213 end subroutine get_flux_on_cell_face
5217 function get_ambipolar_dt(w,ixI^L,ixO^L,dx^D,x)
result(dtnew)
5220 integer,
intent(in) :: ixi^
l, ixo^
l
5221 double precision,
intent(in) ::
dx^
d, x(ixi^s,1:
ndim)
5222 double precision,
intent(in) :: w(ixi^s,1:nw)
5223 double precision :: dtnew
5225 double precision :: coef
5226 double precision :: dxarr(
ndim)
5227 double precision :: tmp(ixi^s)
5233 coef = maxval(dabs(tmp(ixo^s)))
5240 dtnew=minval(dxarr(1:
ndim))**2.0d0*coef
5242 dtnew=minval(
block%ds(ixo^s,1:
ndim))**2.0d0*coef
5245 end function get_ambipolar_dt
5253 integer,
intent(in) :: ixi^
l, ixo^
l
5254 double precision,
intent(in) :: w(ixi^s,1:nw), x(ixi^s,1:
ndim)
5255 double precision,
intent(inout) :: res(ixi^s)
5256 double precision :: tmp(ixi^s)
5257 double precision :: rho(ixi^s)
5264 res(ixo^s) = tmp(ixo^s) * res(ixo^s)
5269 subroutine mhd_add_source(qdt,dtfactor,ixI^L,ixO^L,wCT,wCTprim,w,x,qsourcesplit,active)
5276 integer,
intent(in) :: ixi^
l, ixo^
l
5277 double precision,
intent(in) :: qdt,dtfactor
5278 double precision,
intent(in) :: wct(ixi^s,1:nw),wctprim(ixi^s,1:nw), x(ixi^s,1:
ndim)
5279 double precision,
intent(inout) :: w(ixi^s,1:nw)
5280 logical,
intent(in) :: qsourcesplit
5281 logical,
intent(inout) :: active
5288 if (.not. qsourcesplit)
then
5292 call add_source_internal_e(qdt,ixi^
l,ixo^
l,wct,w,x,wctprim)
5296 call add_equi_terms(qdt,dtfactor,ixi^
l,ixo^
l,wct,w,x,wctprim)
5302 call add_hyperbolic_tc_source(qdt,ixi^
l,ixo^
l,wct,w,x,wctprim)
5311 call add_source_b0split(qdt,dtfactor,ixi^
l,ixo^
l,wct,w,x,wctprim)
5315 if (abs(
mhd_eta)>smalldouble)
then
5317 call add_source_res_exp(qdt,ixi^
l,ixo^
l,wct,w,x)
5322 call add_source_ambi_exp(qdt,ixi^
l,ixo^
l,wct,w,x)
5327 call add_source_hyperres(qdt,ixi^
l,ixo^
l,wct,w,x)
5333 call add_source_hydrodynamic_e(qdt,ixi^
l,ixo^
l,wct,w,x,wctprim)
5337 call add_source_semirelativistic(qdt,ixi^
l,ixo^
l,wct,w,x,wctprim)
5344 select case (type_divb)
5349 call add_source_linde(qdt,ixi^
l,ixo^
l,wct,w,x)
5352 call add_source_glm(qdt,ixi^
l,ixo^
l,wct,w,x)
5355 call add_source_powel(qdt,ixi^
l,ixo^
l,wctprim,w,x)
5356 case (divb_janhunen)
5358 call add_source_janhunen(qdt,ixi^
l,ixo^
l,wctprim,w,x)
5359 case (divb_lindejanhunen)
5361 call add_source_linde(qdt,ixi^
l,ixo^
l,wct,w,x)
5362 call add_source_janhunen(qdt,ixi^
l,ixo^
l,wctprim,w,x)
5363 case (divb_lindepowel)
5365 call add_source_linde(qdt,ixi^
l,ixo^
l,wct,w,x)
5366 call add_source_powel(qdt,ixi^
l,ixo^
l,wctprim,w,x)
5367 case (divb_lindeglm)
5369 call add_source_linde(qdt,ixi^
l,ixo^
l,wct,w,x)
5370 call add_source_glm(qdt,ixi^
l,ixo^
l,wct,w,x)
5371 case (divb_multigrid)
5376 call mpistop(
'Unknown divB fix')
5383 w,x,qsourcesplit,active,
rc_fl)
5393 w,x,gravity_energy,qsourcesplit,active)
5402 call mhd_add_radiation_source(qdt,ixi^
l,ixo^
l,wct,wctprim,w,x,qsourcesplit,active)
5407 if(.not.qsourcesplit)
then
5409 call mhd_update_temperature(ixi^
l,ixo^
l,wct,w,x)
5413 end subroutine mhd_add_source
5415 subroutine mhd_add_radiation_source(qdt,ixI^L,ixO^L,wCT,wCTprim,w,x,qsourcesplit,active)
5421 integer,
intent(in) :: ixi^
l, ixo^
l
5422 double precision,
intent(in) :: qdt, x(ixi^s,1:
ndim)
5423 double precision,
intent(in) :: wct(ixi^s,1:nw),wctprim(ixi^s,1:nw)
5424 double precision,
intent(inout) :: w(ixi^s,1:nw)
5425 logical,
intent(in) :: qsourcesplit
5426 logical,
intent(inout) :: active
5432 end subroutine mhd_add_radiation_source
5435 subroutine add_equi_terms(qdt,dtfactor,ixI^L,ixO^L,wCT,w,x,wCTprim)
5440 integer,
intent(in) :: ixi^
l, ixo^
l
5441 double precision,
intent(in) :: qdt,dtfactor
5442 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
5443 double precision,
intent(in) :: wctprim(ixi^s,1:nw)
5444 double precision,
intent(inout) :: w(ixi^s,1:nw)
5446 double precision :: divv(ixi^s)
5447 double precision :: a(ixi^s,3),
b(ixi^s,3), axb(ixi^s,3)
5448 double precision :: gravity_field(ixi^s,1:
ndim)
5460 divv(ixo^s)=divv(ixo^s)*
mhd_gamma*inv_gamma_1
5471 w(ixo^s,
e_)=w(ixo^s,
e_)-qdt*wctprim(ixo^s,
mom(idir))*
block%equi_vars(ixo^s,
equi_rho0_,0)*gravity_field(ixo^s,idir)*inv_gamma_1
5480 a(ixo^s,idir)=
block%J0(ixo^s,idir)
5485 w(ixo^s,
e_)=w(ixo^s,
e_)-qdt*wctprim(ixo^s,
mom(idir))*axb(ixo^s,idir)*inv_gamma_1
5491 w(ixo^s,
e_)=w(ixo^s,
e_)-qdt*wctprim(ixo^s,
mom(idir))*
block%equi_vars(ixo^s,
equi_rho0_,0)*gravity_field(ixo^s,idir)*inv_gamma_1
5500 w(ixo^s,
e_)=w(ixo^s,
e_)-qdt*wctprim(ixo^s,
mom(idir))*
block%equi_vars(ixo^s,
equi_rho0_,0)*gravity_field(ixo^s,idir)*inv_gamma_1
5504 end subroutine add_equi_terms
5506 subroutine mhd_get_hyperbolic_tc_geometry(ixI^L,ixO^L,Te,Bvec,bgradT,gradTperp_mag,nperp)
5509 integer,
intent(in) :: ixi^
l,ixo^
l
5510 double precision,
intent(in) :: te(ixi^s)
5511 double precision,
intent(in) :: bvec(ixi^s,1:
ndir)
5512 double precision,
intent(out) :: bgradt(ixi^s), gradtperp_mag(ixi^s)
5513 double precision,
intent(out) :: nperp(ixi^s,1:
ndir)
5515 double precision :: bmag, bunitvec(
ndir), gradt(
ndir), gradt_perp(
ndir)
5516 double precision :: gradt_cell(ixi^s,1:
ndir)
5517 integer :: ix^
d, idir
5522 call gradient(te,ixi^
l,ixo^
l,idir,gradt_cell(ixi^s,idir))
5527 do ix2=ixomin2,ixomax2
5528 do ix1=ixomin1,ixomax1
5531 bmag=bmag+bvec(ix^
d,idir)**2
5535 if(bmag>smalldouble)
then
5537 bunitvec(idir)=bvec(ix^
d,idir)/bmag
5545 gradt(1)=((8.d0*(te(ix1+1,ix2)-te(ix1-1,ix2))-te(ix1+2,ix2)+te(ix1-2,ix2))/12.d0)/
block%ds(ix^
d,1)
5546 gradt(2)=((8.d0*(te(ix1,ix2+1)-te(ix1,ix2-1))-te(ix1,ix2+2)+te(ix1,ix2-2))/12.d0)/
block%ds(ix^
d,2)
5547 if(
ndir>2) gradt(3)=zero
5550 gradt(idir)=gradt_cell(ix^
d,idir)
5556 bgradt(ix^
d)=bgradt(ix^
d)+bunitvec(idir)*gradt(idir)
5560 gradt_perp(idir)=gradt(idir)-bgradt(ix^
d)*bunitvec(idir)
5563 gradtperp_mag(ix^
d)=zero
5565 gradtperp_mag(ix^
d)=gradtperp_mag(ix^
d)+gradt_perp(idir)**2
5567 gradtperp_mag(ix^
d)=dsqrt(gradtperp_mag(ix^
d))
5569 if(gradtperp_mag(ix^
d)>smalldouble)
then
5571 nperp(ix^
d,idir)=gradt_perp(idir)/gradtperp_mag(ix^
d)
5574 gradtperp_mag(ix^
d)=zero
5576 nperp(ix^
d,idir)=zero
5583 do ix3=ixomin3,ixomax3
5584 do ix2=ixomin2,ixomax2
5585 do ix1=ixomin1,ixomax1
5586 bmag=dsqrt(bvec(ix^
d,1)**2+bvec(ix^
d,2)**2+bvec(ix^
d,3)**2)
5587 if(bmag>smalldouble)
then
5588 bunitvec(1)=bvec(ix^
d,1)/bmag
5589 bunitvec(2)=bvec(ix^
d,2)/bmag
5590 bunitvec(3)=bvec(ix^
d,3)/bmag
5598 gradt(1)=((8.d0*(te(ix1+1,ix2,ix3)-te(ix1-1,ix2,ix3))-te(ix1+2,ix2,ix3)+te(ix1-2,ix2,ix3))/12.d0)/
block%ds(ix^
d,1)
5599 gradt(2)=((8.d0*(te(ix1,ix2+1,ix3)-te(ix1,ix2-1,ix3))-te(ix1,ix2+2,ix3)+te(ix1,ix2-2,ix3))/12.d0)/
block%ds(ix^
d,2)
5600 gradt(3)=((8.d0*(te(ix1,ix2,ix3+1)-te(ix1,ix2,ix3-1))-te(ix1,ix2,ix3+2)+te(ix1,ix2,ix3-2))/12.d0)/
block%ds(ix^
d,3)
5603 gradt(idir)=gradt_cell(ix^
d,idir)
5609 bgradt(ix^
d)=bgradt(ix^
d)+bunitvec(idir)*gradt(idir)
5613 gradt_perp(idir)=gradt(idir)-bgradt(ix^
d)*bunitvec(idir)
5616 gradtperp_mag(ix^
d)=dsqrt(gradt_perp(1)**2+gradt_perp(2)**2+gradt_perp(3)**2)
5617 if(gradtperp_mag(ix^
d)>smalldouble)
then
5619 nperp(ix^
d,idir)=gradt_perp(idir)/gradtperp_mag(ix^
d)
5622 gradtperp_mag(ix^
d)=zero
5624 nperp(ix^
d,idir)=zero
5631 end subroutine mhd_get_hyperbolic_tc_geometry
5633 subroutine add_hyperbolic_tc_source(qdt,ixI^L,ixO^L,wCT,w,x,wCTprim)
5636 integer,
intent(in) :: ixi^
l,ixo^
l
5637 double precision,
intent(in) :: qdt
5638 double precision,
dimension(ixI^S,1:ndim),
intent(in) :: x
5639 double precision,
dimension(ixI^S,1:nw),
intent(in) :: wct,wctprim
5640 double precision,
dimension(ixI^S,1:nw),
intent(inout) :: w
5642 double precision,
dimension(ixI^S) :: r,te,rho_loc,pth_loc
5643 double precision,
dimension(ixI^S,1:ndir) :: bvec
5644 double precision,
dimension(ixI^S) :: bgradt, gradtperp_mag
5645 double precision,
dimension(ixI^S,1:ndir) :: nperp
5646 double precision,
dimension(ixI^S) :: gradt_geom
5647 double precision,
parameter :: lnlambda_perp = 20.d0
5648 double precision,
parameter :: xe_prefac_cgs = 4.753567596681522d6
5649 double precision :: kappa_t5,kappa_t5_perp,kappa_t5_perp_eff
5650 double precision :: kappa_t7,f_sat,kappat5_bgradt,kappat5_gradtperp,tau,b2,fb,gradt1
5651 double precision :: bmag_loc,tloc,tcond,nloc_code,cchi,chi
5652 double precision :: cmax(
ndim),c2,cfast2,avmincs2(
ndim),inv_rho
5653 logical :: use_perp_source
5654 integer :: ix^
d,idir
5656 cchi = 0.823d0*(xe_prefac_cgs/lnlambda_perp) * &
5659 {
do ix^db=iximin^db,iximax^db\}
5664 rho_loc(ix^
d)=wctprim(ix^
d,
rho_)
5665 pth_loc(ix^
d)=wctprim(ix^
d,
p_)
5667 te(ix^
d)=pth_loc(ix^
d)/(r(ix^
d)*rho_loc(ix^
d))
5671 {
do ix^db=ixomin^db,ixomax^db\}
5673 bvec(ix^d,idir)=wct(ix^d,mag(idir))+block%B0(ix^d,idir,0)
5677 {
do ix^db=ixomin^db,ixomax^db\}
5679 bvec(ix^d,idir)=wct(ix^d,mag(idir))
5684 call mhd_get_hyperbolic_tc_geometry(ixi^l,ixo^l,te,bvec,bgradt,gradtperp_mag,nperp)
5688 if(.not.slab_uniform)
then
5689 call gradient(te,ixi^l,ixo^l,1,gradt_geom)
5691 do ix1=ixomin1,ixomax1
5694 kappa_t7=kappa_t5*te(ix1)
5698 tcond = max(tcond, block%wextra(ix1,
tcoff_))
5701 kappa_t7=kappa_t5*tcond
5703 if(slab_uniform)
then
5704 gradt1=((8.d0*(te(ix1+1)-te(ix1-1))-te(ix1+2)+te(ix1-2))/12.d0)/block%ds(ix1,1)
5706 gradt1=gradt_geom(ix1)
5710 b2=b2+bvec(ix1,idir)**2
5712 if(b2>smalldouble**2)
then
5713 bgradt(ix1)=bvec(ix1,1)*gradt1/dsqrt(b2)
5717 kappat5_bgradt=kappa_t5*bgradt(ix1)
5718 inv_rho=1.d0/rho_loc(ix1)
5720 cfast2 = b2*inv_rho + c2
5721 avmincs2(1) = cfast2**2 - 4.0d0*c2*bvec(ix1,1)**2*inv_rho
5722 cmax(1) = sqrt(half*(cfast2 + sqrt(dabs(avmincs2(1)))))
5724 f_sat=one/(one+dabs(kappat5_bgradt)/(1.5d0*rho_loc(ix^d)*(pth_loc(ix^d)/rho_loc(ix^d))**1.5d0))
5725 tau=max(4.d0*dt, f_sat*kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*cmax(1)**2))
5726 w(ix^d,
qpar_)=w(ix^d,
qpar_)-qdt*(f_sat*kappat5_bgradt+wct(ix^d,
qpar_))/tau
5729 max(4.d0*dt, kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*cmax(1)**2))
5734 do ix2=ixomin2,ixomax2
5735 do ix1=ixomin1,ixomax1
5738 kappa_t7=kappa_t5*te(ix^d)
5742 tcond=max(tcond, block%wextra(ix^d,
tcoff_))
5745 kappa_t7 = kappa_t5*tcond
5747 kappat5_bgradt=kappa_t5*bgradt(ix^d)
5750 b2 = b2 + bvec(ix^d,idir)**2
5752 if(use_perp_source)
then
5762 kappa_t5_perp_eff=(one-fb)*kappa_t5
5763 kappa_t5_perp=kappa_t5_perp_eff
5765 bmag_loc = dsqrt(b2)
5766 tloc = max(te(ix^d), smalldouble)
5767 nloc_code = max(rho_loc(ix^d), smalldouble)
5768 chi = cchi*bmag_loc*tloc**1.5d0/nloc_code
5769 kappa_t5_perp_eff = kappa_t5/(one+chi**2)
5770 kappa_t5_perp = kappa_t5_perp_eff
5774 kappat5_gradtperp=kappa_t5_perp*gradtperp_mag(ix^d)
5776 inv_rho=1.d0/rho_loc(ix^d)
5778 cfast2 = b2*inv_rho + c2
5780 avmincs2(idir)=cfast2**2-4.0d0*c2*bvec(ix^d,idir)**2*inv_rho
5781 cmax(idir)=sqrt(half*(cfast2+sqrt(dabs(avmincs2(idir)))))\
5784 f_sat=one/(one+dabs(kappat5_bgradt)/(1.5d0*rho_loc(ix^d)*(pth_loc(ix^d)/rho_loc(ix^d))**1.5d0))
5785 tau=max(4.d0*dt, f_sat*kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*maxval(cmax(:))**2))
5786 w(ix^d,
qpar_)=w(ix^d,
qpar_)-qdt*(f_sat*kappat5_bgradt+wct(ix^d,
qpar_))/tau
5787 if(use_perp_source)
then
5791 tau=max(4.d0*dt, kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*maxval(cmax(:))**2))
5793 if(use_perp_source)
then
5801 do ix3=ixomin3,ixomax3
5802 do ix2=ixomin2,ixomax2
5803 do ix1=ixomin1,ixomax1
5806 kappa_t7=kappa_t5*te(ix^d)
5810 tcond=max(tcond, block%wextra(ix^d,
tcoff_))
5813 kappa_t7 = kappa_t5*tcond
5815 kappat5_bgradt=kappa_t5*bgradt(ix^d)
5818 b2 = b2 + bvec(ix^d,idir)**2
5820 if(use_perp_source)
then
5830 kappa_t5_perp_eff=(one-fb)*kappa_t5
5831 kappa_t5_perp=kappa_t5_perp_eff
5833 bmag_loc = dsqrt(b2)
5834 tloc = max(te(ix^d), smalldouble)
5835 nloc_code = max(rho_loc(ix^d), smalldouble)
5836 chi = cchi*bmag_loc*tloc**1.5d0/nloc_code
5837 kappa_t5_perp_eff = kappa_t5/(one+chi**2)
5838 kappa_t5_perp = kappa_t5_perp_eff
5842 kappat5_gradtperp=kappa_t5_perp*gradtperp_mag(ix^d)
5844 inv_rho=1.d0/rho_loc(ix^d)
5846 cfast2 = b2*inv_rho + c2
5848 avmincs2(idir)=cfast2**2-4.0d0*c2*bvec(ix^d,idir)**2*inv_rho
5849 cmax(idir)=sqrt(half*(cfast2+sqrt(dabs(avmincs2(idir)))))\
5852 f_sat=one/(one+dabs(kappat5_bgradt)/(1.5d0*rho_loc(ix^d)*(pth_loc(ix^d)/rho_loc(ix^d))**1.5d0))
5853 tau=max(4.d0*dt, f_sat*kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*maxval(cmax(:))**2))
5854 w(ix^d,
qpar_)=w(ix^d,
qpar_)-qdt*(f_sat*kappat5_bgradt+wct(ix^d,
qpar_))/tau
5855 if(use_perp_source)
then
5859 tau=max(4.d0*dt, kappa_t7*courantpar**2/(pth_loc(ix^d)*inv_gamma_1*maxval(cmax(:))**2))
5861 if(use_perp_source)
then
5869 end subroutine add_hyperbolic_tc_source
5873 subroutine get_lorentz_force(ixI^L,ixO^L,w,JxB)
5875 integer,
intent(in) :: ixi^
l, ixo^
l
5876 double precision,
intent(in) :: w(ixi^s,1:nw)
5877 double precision,
intent(inout) :: jxb(ixi^s,3)
5878 double precision :: a(ixi^s,3),
b(ixi^s,3)
5880 double precision :: current(ixi^s,7-2*
ndir:3)
5881 integer :: idir, idirmin
5886 b(ixo^s, idir) = w(ixo^s,mag(idir))+
block%B0(ixo^s,idir,0)
5890 b(ixo^s, idir) = w(ixo^s,mag(idir))
5899 a(ixo^s,idir)=current(ixo^s,idir)
5903 end subroutine get_lorentz_force
5907 integer,
intent(in) :: ixi^
l, ixo^
l
5908 double precision,
intent(in) :: w(ixi^s,1:nw),x(ixi^s,1:
ndim)
5909 double precision,
intent(out) :: rho(ixi^s)
5914 rho(ixo^s) = w(ixo^s,
rho_)
5920 subroutine mhd_handle_small_ei(w, x, ixI^L, ixO^L, ie, subname)
5923 integer,
intent(in) :: ixi^
l,ixo^
l, ie
5924 double precision,
intent(inout) :: w(ixi^s,1:nw)
5925 double precision,
intent(in) :: x(ixi^s,1:
ndim)
5926 character(len=*),
intent(in) :: subname
5928 double precision :: rho(ixi^s)
5930 logical :: flag(ixi^s,1:nw)
5935 flag(ixo^s,ie)=.true.
5937 where(w(ixo^s,ie)<
small_e) flag(ixo^s,ie)=.true.
5939 if(any(flag(ixo^s,ie)))
then
5943 where(flag(ixo^s,ie)) w(ixo^s,ie)=
small_e - &
5946 where(flag(ixo^s,ie)) w(ixo^s,ie)=
small_e
5952 w(ixo^s,
e_)=w(ixo^s,
e_)*gamma_1
5955 w(ixo^s,
mom(idir)) = w(ixo^s,
mom(idir))/rho(ixo^s)
5961 end subroutine mhd_handle_small_ei
5963 subroutine mhd_update_temperature(ixI^L,ixO^L,wCT,w,x)
5967 integer,
intent(in) :: ixi^
l, ixo^
l
5968 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
5969 double precision,
intent(inout) :: w(ixi^s,1:nw)
5971 double precision :: iz_h(ixo^s),iz_he(ixo^s), pth(ixi^s)
5980 end subroutine mhd_update_temperature
5983 subroutine add_source_b0split(qdt,dtfactor,ixI^L,ixO^L,wCT,w,x,wCTprim)
5986 integer,
intent(in) :: ixi^
l, ixo^
l
5987 double precision,
intent(in) :: qdt, dtfactor,wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
5988 double precision,
intent(in) :: wctprim(ixi^s,1:nw)
5989 double precision,
intent(inout) :: w(ixi^s,1:nw)
5991 double precision :: a(ixi^s,3),
b(ixi^s,3), axb(ixi^s,3)
6003 a(ixo^s,idir)=
block%J0(ixo^s,idir)
6008 axb(ixo^s,idir)=axb(ixo^s,idir)*
block%dt(ixo^s)*dtfactor
6011 axb(ixo^s,:)=axb(ixo^s,:)*qdt
6017 if(total_energy)
then
6020 b(ixo^s,:)=wctprim(ixo^s,mag(:))
6029 axb(ixo^s,idir)=axb(ixo^s,idir)*
block%dt(ixo^s)*dtfactor
6032 axb(ixo^s,:)=axb(ixo^s,:)*qdt
6037 w(ixo^s,
e_)=w(ixo^s,
e_)-axb(ixo^s,idir)*
block%J0(ixo^s,idir)
6041 call mhd_getv_hall(wct,x,ixi^
l,ixo^
l,a,.true.)
6046 axb(ixo^s,idir)=axb(ixo^s,idir)*
block%dt(ixo^s)*dtfactor
6049 axb(ixo^s,:)=axb(ixo^s,:)*qdt
6053 w(ixo^s,
e_)=w(ixo^s,
e_)-axb(ixo^s,idir)*
block%J0(ixo^s,idir)
6061 call mhd_get_jxbxb(wct,x,ixi^
l,ixo^
l,axb)
6066 w(ixo^s,
e_)=w(ixo^s,
e_)+qdt*axb(ixo^s,idir)*
block%J0(ixo^s,idir)
6072 if (
fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^
l,ixo^
l,
'add_source_B0')
6074 end subroutine add_source_b0split
6077 subroutine add_source_semirelativistic(qdt,ixI^L,ixO^L,wCT,w,x,wCTprim)
6081 integer,
intent(in) :: ixi^
l, ixo^
l
6082 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6083 double precision,
intent(inout) :: w(ixi^s,1:nw)
6084 double precision,
intent(in),
optional :: wctprim(ixi^s,1:nw)
6086 double precision :: e(ixi^s,1:3),curle(ixi^s,1:3),dive(ixi^s)
6087 integer :: idir, idirmin, ix^
d
6091 {
do ix^db=iximin^db,iximax^db\}
6093 e(ix^
d,1)=w(ix^
d,b2_)*wctprim(ix^
d,m3_)-w(ix^
d,b3_)*wctprim(ix^
d,m2_)
6094 e(ix^
d,2)=w(ix^
d,b3_)*wctprim(ix^
d,m1_)-w(ix^
d,b1_)*wctprim(ix^
d,m3_)
6095 e(ix^
d,3)=w(ix^
d,b1_)*wctprim(ix^
d,m2_)-w(ix^
d,b2_)*wctprim(ix^
d,m1_)
6097 call divvector(e,ixi^l,ixo^l,dive)
6099 call curlvector(e,ixi^l,ixo^l,curle,idirmin,1,3)
6102 {
do ix^db=ixomin^db,ixomax^db\}
6103 w(ix^d,m1_)=w(ix^d,m1_)+qdt*(inv_squared_c0-inv_squared_c)*&
6104 (e(ix^d,1)*dive(ix^d)-e(ix^d,2)*curle(ix^d,3)+e(ix^d,3)*curle(ix^d,2))
6105 w(ix^d,m2_)=w(ix^d,m2_)+qdt*(inv_squared_c0-inv_squared_c)*&
6106 (e(ix^d,2)*dive(ix^d)-e(ix^d,3)*curle(ix^d,1)+e(ix^d,1)*curle(ix^d,3))
6107 w(ix^d,m3_)=w(ix^d,m3_)+qdt*(inv_squared_c0-inv_squared_c)*&
6108 (e(ix^d,3)*dive(ix^d)-e(ix^d,1)*curle(ix^d,2)+e(ix^d,2)*curle(ix^d,1) )
6112 end subroutine add_source_semirelativistic
6115 subroutine add_source_internal_e(qdt,ixI^L,ixO^L,wCT,w,x,wCTprim)
6119 integer,
intent(in) :: ixi^
l, ixo^
l
6120 double precision,
intent(in) :: qdt
6121 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6122 double precision,
intent(inout) :: w(ixi^s,1:nw)
6123 double precision,
intent(in) :: wctprim(ixi^s,1:nw)
6125 double precision :: divv(ixi^s), tmp
6137 {
do ix^db=ixomin^db,ixomax^db\}
6139 w(ix^
d,
e_)=w(ix^
d,
e_)-qdt*wctprim(ix^
d,
p_)*divv(ix^
d)
6145 call add_source_ambipolar_internal_energy(qdt,ixi^l,ixo^l,wct,w,x)
6148 if(fix_small_values)
then
6149 call mhd_handle_small_ei(w,x,ixi^l,ixo^l,
e_,
'add_source_internal_e')
6151 end subroutine add_source_internal_e
6154 subroutine add_source_hydrodynamic_e(qdt,ixI^L,ixO^L,wCT,w,x,wCTprim)
6159 integer,
intent(in) :: ixi^
l, ixo^
l
6160 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6161 double precision,
intent(inout) :: w(ixi^s,1:nw)
6162 double precision,
intent(in),
optional :: wctprim(ixi^s,1:nw)
6164 double precision ::
b(ixi^s,3), j(ixi^s,3), jxb(ixi^s,3)
6165 double precision :: current(ixi^s,7-2*
ndir:3)
6166 double precision :: bu(ixo^s,1:
ndir), tmp(ixo^s), b2(ixo^s)
6167 double precision :: gravity_field(ixi^s,1:
ndir), vaoc
6168 integer :: idir, idirmin, idims, ix^
d
6173 b(ixo^s, idir) = wct(ixo^s,mag(idir))
6185 j(ixo^s,idir)=current(ixo^s,idir)
6264 call add_source_ambipolar_internal_energy(qdt,ixi^
l,ixo^
l,wct,w,x)
6267 if (
fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^
l,ixo^
l,
'add_source_hydrodynamic_e')
6269 end subroutine add_source_hydrodynamic_e
6275 subroutine add_source_res1(qdt,ixI^L,ixO^L,wCT,w,x)
6280 integer,
intent(in) :: ixi^
l, ixo^
l
6281 double precision,
intent(in) :: qdt
6282 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6283 double precision,
intent(inout) :: w(ixi^s,1:nw)
6285 integer :: ixa^
l,idir,jdir,kdir,idirmin,idim
6286 double precision :: tmp(ixi^s),tmp2(ixi^s)
6289 double precision :: current(ixi^s,7-2*
ndir:3),eta(ixi^s)
6290 double precision :: gradeta(ixi^s,1:
ndim), bf(ixi^s,1:
ndir)
6291 double precision :: lapl_vec(ixi^s,1:
ndir)
6297 if (iximin^
d>ixamin^
d.or.iximax^
d<ixamax^
d|.or.) &
6298 call mpistop(
"Error in add_source_res1: Non-conforming input limits")
6305 gradeta(ixo^s,1:
ndim)=zero
6310 gradeta(ixo^s,idim)=tmp(ixo^s)
6317 bf(ixi^s,1:
ndir)=wct(ixi^s,mag(1:
ndir))
6324 tmp(ixo^s)=lapl_vec(ixo^s,idir)*eta(ixo^s)
6328 do jdir=1,
ndim;
do kdir=idirmin,3
6329 if (
lvc(idir,jdir,kdir)/=0)
then
6330 if (
lvc(idir,jdir,kdir)==1)
then
6331 tmp(ixo^s)=tmp(ixo^s)-gradeta(ixo^s,jdir)*current(ixo^s,kdir)
6333 tmp(ixo^s)=tmp(ixo^s)+gradeta(ixo^s,jdir)*current(ixo^s,kdir)
6340 w(ixo^s,mag(idir))=w(ixo^s,mag(idir))+qdt*tmp(ixo^s)
6341 if(total_energy)
then
6342 w(ixo^s,
e_)=w(ixo^s,
e_)+qdt*tmp(ixo^s)*bf(ixo^s,idir)
6348 w(ixo^s,
e_)=w(ixo^s,
e_)+qdt*eta(ixo^s)*sum(current(ixo^s,:)**2,dim=ndim+1)
6351 if (fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^l,ixo^l,
'add_source_res1')
6353 end subroutine add_source_res1
6357 subroutine add_source_res_exp(qdt,ixI^L,ixO^L,wCT,w,x)
6362 integer,
intent(in) :: ixi^
l, ixo^
l
6363 double precision,
intent(in) :: qdt
6364 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6365 double precision,
intent(inout) :: w(ixi^s,1:nw)
6368 double precision :: current(ixi^s,7-2*
ndir:3),eta(ixi^s),curlj(ixi^s,1:3)
6369 double precision :: tmpvec(ixi^s,1:3),tmp(ixo^s)
6370 integer :: ixa^
l,idir,idirmin,idirmin1
6374 if (iximin^
d>ixamin^
d.or.iximax^
d<ixamax^
d|.or.) &
6375 call mpistop(
"Error in add_source_res_exp: Non-conforming input limits")
6385 tmpvec(ixa^s,idir)=current(ixa^s,idir)*
mhd_eta
6390 tmpvec(ixa^s,idir)=current(ixa^s,idir)*eta(ixa^s)
6399 w(ixo^s,mag(
ndir)) = w(ixo^s,mag(
ndir))-qdt*curlj(ixo^s,
ndir)
6402 w(ixo^s,mag(1:
ndir)) = w(ixo^s,mag(1:
ndir))-qdt*curlj(ixo^s,1:
ndir)
6407 tmp(ixo^s)=qdt*
mhd_eta*sum(current(ixo^s,:)**2,dim=
ndim+1)
6409 tmp(ixo^s)=qdt*eta(ixo^s)*sum(current(ixo^s,:)**2,dim=
ndim+1)
6411 if(total_energy)
then
6414 w(ixo^s,
e_)=w(ixo^s,
e_)+tmp(ixo^s)-&
6415 qdt*sum(wct(ixo^s,mag(1:
ndir))*curlj(ixo^s,1:
ndir),dim=
ndim+1)
6418 w(ixo^s,
e_)=w(ixo^s,
e_)+tmp(ixo^s)
6422 if (
fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^
l,ixo^
l,
'add_source_res_exp')
6423 end subroutine add_source_res_exp
6428 subroutine add_source_ambi_exp(qdt,ixI^L,ixO^L,wCT,w,x)
6433 integer,
intent(in) :: ixi^
l, ixo^
l
6434 double precision,
intent(in) :: qdt
6435 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6436 double precision,
intent(inout) :: w(ixi^s,1:nw)
6438 double precision :: current(ixi^s,1:3),curlj(ixi^s,1:3)
6439 double precision :: tmpvec(ixi^s,1:3),tmp(ixi^s),btot2(ixi^s)
6440 integer :: ixa^
l,idir,idirmin1
6444 if (iximin^
d>ixamin^
d.or.iximax^
d<ixamax^
d|.or.) &
6445 call mpistop(
"Error in add_source_ambi_exp: Non-conforming input limits")
6449 call mhd_get_jxbxb(wct,x,ixi^
l,ixa^
l,current)
6463 w(ixo^s,mag(
ndir)) = w(ixo^s,mag(
ndir))-qdt*curlj(ixo^s,
ndir)
6466 w(ixo^s,mag(1:
ndir)) = w(ixo^s,mag(1:
ndir))-qdt*curlj(ixo^s,1:
ndir)
6473 where (btot2(ixa^s)>smalldouble )
6474 tmp(ixa^s) = sum(current(ixa^s,1:3)**2,dim=
ndim+1) / btot2(ixa^s)
6481 tmp(ixo^s)=-qdt*tmp(ixo^s)
6482 if(total_energy)
then
6485 w(ixo^s,
e_)=w(ixo^s,
e_)+tmp(ixo^s)-&
6486 qdt*sum(wct(ixo^s,mag(1:
ndir))*curlj(ixo^s,1:
ndir),dim=
ndim+1)
6489 w(ixo^s,
e_)=w(ixo^s,
e_)+tmp(ixo^s)
6493 if (
fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^
l,ixo^
l,
'add_source_ambi_exp')
6494 end subroutine add_source_ambi_exp
6498 subroutine add_source_hyperres(qdt,ixI^L,ixO^L,wCT,w,x)
6502 integer,
intent(in) :: ixi^
l, ixo^
l
6503 double precision,
intent(in) :: qdt
6504 double precision,
intent(in) :: wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6505 double precision,
intent(inout) :: w(ixi^s,1:nw)
6507 double precision :: current(ixi^s,7-2*
ndir:3)
6508 double precision :: tmpvec(ixi^s,1:3),tmpvec2(ixi^s,1:3),tmp(ixi^s),ehyper(ixi^s,1:3)
6509 integer :: ixa^
l,idir,jdir,kdir,idirmin,idirmin1
6512 if (iximin^
d>ixamin^
d.or.iximax^
d<ixamax^
d|.or.) &
6513 call mpistop(
"Error in add_source_hyperres: Non-conforming input limits")
6516 tmpvec(ixa^s,1:
ndir)=zero
6518 tmpvec(ixa^s,jdir)=current(ixa^s,jdir)
6522 call curlvector(tmpvec,ixi^
l,ixa^
l,tmpvec2,idirmin1,1,3)
6525 tmpvec(ixa^s,1:
ndir)=zero
6526 call curlvector(tmpvec2,ixi^
l,ixa^
l,tmpvec,idirmin1,1,3)
6530 tmpvec2(ixa^s,1:
ndir)=zero
6531 call curlvector(ehyper,ixi^
l,ixa^
l,tmpvec2,idirmin1,1,3)
6534 w(ixo^s,mag(idir)) = w(ixo^s,mag(idir))-tmpvec2(ixo^s,idir)*qdt
6537 if(total_energy)
then
6540 tmpvec2(ixa^s,1:
ndir)=zero
6541 do idir=1,
ndir;
do jdir=1,
ndir;
do kdir=idirmin,3
6542 tmpvec2(ixa^s,idir) = tmpvec(ixa^s,idir)&
6543 +
lvc(idir,jdir,kdir)*wct(ixa^s,mag(jdir))*ehyper(ixa^s,kdir)
6544 end do;
end do;
end do
6546 call divvector(tmpvec2,ixi^l,ixo^l,tmp)
6547 w(ixo^s,
e_)=w(ixo^s,
e_)+tmp(ixo^s)*qdt
6550 if (fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^l,ixo^l,
'add_source_hyperres')
6552 end subroutine add_source_hyperres
6554 subroutine add_source_glm(qdt,ixI^L,ixO^L,wCT,w,x)
6561 integer,
intent(in) :: ixi^
l, ixo^
l
6562 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6563 double precision,
intent(inout) :: w(ixi^s,1:nw)
6565 double precision:: divb(ixi^s), gradpsi(ixi^s), ba(ixo^s,1:
ndir)
6586 ba(ixo^s,1:
ndir)=wct(ixo^s,mag(1:
ndir))
6589 if(total_energy)
then
6598 w(ixo^s,
e_) = w(ixo^s,
e_)-qdt*ba(ixo^s,idir)*gradpsi(ixo^s)
6607 w(ixo^s,
mom(idir))=w(ixo^s,
mom(idir))-qdt*ba(ixo^s,idir)*divb(ixo^s)
6611 if (
fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^
l,ixo^
l,
'add_source_glm')
6613 end subroutine add_source_glm
6616 subroutine add_source_powel(qdt,ixI^L,ixO^L,wCT,w,x)
6619 integer,
intent(in) :: ixi^
l, ixo^
l
6620 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6621 double precision,
intent(inout) :: w(ixi^s,1:nw)
6623 double precision :: divb(ixi^s), ba(1:
ndir)
6624 integer :: idir, ix^
d
6630 {
do ix^db=ixomin^db,ixomax^db\}
6635 if (total_energy)
then
6641 {
do ix^db=ixomin^db,ixomax^db\}
6643 ^
c&w(ix^d,
b^
c_)=w(ix^d,
b^
c_)-qdt*wct(ix^d,
m^
c_)*divb(ix^d)\
6645 ^
c&w(ix^d,
m^
c_)=w(ix^d,
m^
c_)-qdt*wct(ix^d,
b^
c_)*divb(ix^d)\
6646 if (total_energy)
then
6648 w(ix^d,
e_)=w(ix^d,
e_)-qdt*(^
c&wct(ix^d,
m^
c_)*wct(ix^d,
b^
c_)+)*divb(ix^d)
6653 if (fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^l,ixo^l,
'add_source_powel')
6655 end subroutine add_source_powel
6657 subroutine add_source_janhunen(qdt,ixI^L,ixO^L,wCT,w,x)
6662 integer,
intent(in) :: ixi^
l, ixo^
l
6663 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6664 double precision,
intent(inout) :: w(ixi^s,1:nw)
6666 double precision :: divb(ixi^s)
6667 integer :: idir, ix^
d
6672 {
do ix^db=ixomin^db,ixomax^db\}
6677 if (fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^l,ixo^l,
'add_source_janhunen')
6679 end subroutine add_source_janhunen
6681 subroutine add_source_linde(qdt,ixI^L,ixO^L,wCT,w,x)
6686 integer,
intent(in) :: ixi^
l, ixo^
l
6687 double precision,
intent(in) :: qdt, wct(ixi^s,1:nw), x(ixi^s,1:
ndim)
6688 double precision,
intent(inout) :: w(ixi^s,1:nw)
6690 double precision :: divb(ixi^s),graddivb(ixi^s)
6691 integer :: idim, idir, ixp^
l, i^
d, iside
6692 logical,
dimension(-1:1^D&) :: leveljump
6700 if(i^
d==0|.and.) cycle
6701 if(neighbor_type(i^
d,
block%igrid)==2 .or. neighbor_type(i^
d,
block%igrid)==4)
then
6702 leveljump(i^
d)=.true.
6704 leveljump(i^
d)=.false.
6713 i^dd=kr(^dd,^d)*(2*iside-3);
6714 if (leveljump(i^dd))
then
6716 ixpmin^d=ixomin^d-i^d
6718 ixpmax^d=ixomax^d-i^d
6729 call gradient(divb,ixi^l,ixp^l,idim,graddivb)
6731 {
do i^db=ixpmin^db,ixpmax^db\}
6733 graddivb(i^d)=graddivb(i^d)*
divbdiff/(^d&1.0d0/block%ds({i^d},^d)**2+)
6735 w(i^d,mag(idim))=w(i^d,mag(idim))+graddivb(i^d)
6737 if (typedivbdiff==
'all' .and. total_energy)
then
6739 w(i^d,
e_)=w(i^d,
e_)+wct(i^d,mag(idim))*graddivb(i^d)
6744 if (fix_small_values)
call mhd_handle_small_values(.false.,w,x,ixi^l,ixo^l,
'add_source_linde')
6746 end subroutine add_source_linde
6753 integer,
intent(in) :: ixi^
l, ixo^
l
6754 double precision,
intent(in) :: w(ixi^s,1:nw)
6755 double precision :: divb(ixi^s), dsurface(ixi^s)
6757 double precision :: invb(ixo^s)
6758 integer :: ixa^
l,idims
6760 call get_divb(w,ixi^
l,ixo^
l,divb)
6762 where(invb(ixo^s)/=0.d0)
6763 invb(ixo^s)=1.d0/invb(ixo^s)
6766 divb(ixo^s)=0.5d0*abs(divb(ixo^s))*invb(ixo^s)/sum(1.d0/
dxlevel(:))
6768 ixamin^
d=ixomin^
d-1;
6769 ixamax^
d=ixomax^
d-1;
6770 dsurface(ixo^s)= sum(
block%surfaceC(ixo^s,:),dim=
ndim+1)
6772 ixa^
l=ixo^
l-
kr(idims,^
d);
6773 dsurface(ixo^s)=dsurface(ixo^s)+
block%surfaceC(ixa^s,idims)
6775 divb(ixo^s)=abs(divb(ixo^s))*invb(ixo^s)*&
6776 block%dvolume(ixo^s)/dsurface(ixo^s)
6787 integer,
intent(in) :: ixo^
l, ixi^
l
6788 double precision,
intent(in) :: w(ixi^s,1:nw)
6789 integer,
intent(out) :: idirmin
6792 double precision :: current(ixi^s,7-2*
ndir:3)
6793 integer :: idir, idirmin0
6799 if(
b0field) current(ixo^s,idirmin0:3)=current(ixo^s,idirmin0:3)+&
6800 block%J0(ixo^s,idirmin0:3)
6804 subroutine mhd_get_dt(wprim,ixI^L,ixO^L,dtnew,dx^D,x)
6812 integer,
intent(in) :: ixi^
l, ixo^
l
6813 double precision,
intent(inout) :: dtnew
6814 double precision,
intent(in) ::
dx^
d
6815 double precision,
intent(in) :: wprim(ixi^s,1:nw)
6816 double precision,
intent(in) :: x(ixi^s,1:
ndim)
6818 double precision :: dxarr(
ndim)
6819 double precision :: current(ixi^s,7-2*
ndir:3),eta(ixi^s)
6820 integer :: idirmin,idim
6838 dtdiffpar/(smalldouble+maxval(eta(ixo^s)/dxarr(idim)**2)))
6841 dtdiffpar/(smalldouble+maxval(eta(ixo^s)/
block%ds(ixo^s,idim)**2)))
6863 dtnew=min(
dtdiffpar*get_ambipolar_dt(wprim,ixi^
l,ixo^
l,
dx^
d,x),dtnew)
6874 end subroutine mhd_get_dt
6881 subroutine mhd_add_source_geom(qdt,dtfactor,ixI^L,ixO^L,wCT,wprim,w,x)
6887 integer,
intent(in) :: ixi^
l, ixo^
l
6888 double precision,
intent(in) :: qdt, dtfactor,x(ixi^s,1:
ndim)
6889 double precision,
intent(inout) :: wct(ixi^s,1:nw),wprim(ixi^s,1:nw),w(ixi^s,1:nw)
6891 double precision :: adiabs(ixi^s), gammas(ixi^s)
6892 double precision :: tmp,tmp1,invr,cot
6894 integer :: mr_,mphi_
6895 integer :: br_,bphi_
6898 br_=mag(1); bphi_=mag(1)-1+
phi_
6915 {
do ix^db=ixomin^db,ixomax^db\}
6918 invr=
block%dt(ix^
d) * dtfactor/x(ix^
d,1)
6923 tmp=wprim(ix^
d,
p_)+half*(^
c&wprim(ix^
d,
b^
c_)**2+)
6925 tmp=adiabs(ix^
d)*wprim(ix^
d,
rho_)**gammas(ix^
d)+half*(^
c&wprim(ix^
d,
b^
c_)**2+)
6928 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*(tmp-&
6929 wprim(ix^
d,bphi_)**2+wprim(ix^
d,mphi_)*wct(ix^
d,mphi_))
6930 w(ix^
d,mphi_)=w(ix^
d,mphi_)+invr*(&
6931 -wct(ix^
d,mphi_)*wprim(ix^
d,mr_) &
6932 +wprim(ix^
d,bphi_)*wprim(ix^
d,br_))
6934 w(ix^
d,bphi_)=w(ix^
d,bphi_)+invr*&
6935 (wprim(ix^
d,bphi_)*wprim(ix^
d,mr_) &
6936 -wprim(ix^
d,br_)*wprim(ix^
d,mphi_))
6939 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*tmp
6944 {
do ix^db=ixomin^db,ixomax^db\}
6946 if(local_timestep)
then
6947 invr=block%dt(ix^d) * dtfactor/x(ix^d,1)
6952 tmp1=wprim(ix^d,
p_)+half*(^
c&wprim(ix^d,
b^
c_)**2+)
6954 tmp1=adiabs(ix^d)*wprim(ix^d,
rho_)**gammas(ix^d)+half*(^
c&wprim(ix^d,
b^
c_)**2+)
6958 w(ix^d,
mom(1))=w(ix^d,
mom(1))+two*tmp1*invr
6961 w(ix^d,
mom(1))=w(ix^d,
mom(1))+invr*&
6962 (two*tmp1+(^ce&wprim(ix^d,
m^ce_)*wct(ix^d,
m^ce_)-wprim(ix^d,
b^ce_)**2+))
6966 w(ix^d,mag(1))=w(ix^d,mag(1))+invr*2.0d0*wprim(ix^d,
psi_)
6972 cot=1.d0/tan(x(ix^d,2))
6976 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*(tmp1*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
6977 +wprim(ix^d,b1_)*wprim(ix^d,b2_))
6979 if(.not.stagger_grid)
then
6980 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
6982 tmp=tmp+wprim(ix^d,
psi_)*cot
6984 w(ix^d,mag(2))=w(ix^d,mag(2))+tmp*invr
6989 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*(tmp1*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
6990 +wprim(ix^d,b1_)*wprim(ix^d,b2_)&
6991 +(wprim(ix^d,m3_)*wct(ix^d,m3_)-wprim(ix^d,b3_)**2)*cot)
6993 if(.not.stagger_grid)
then
6994 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
6996 tmp=tmp+wprim(ix^d,
psi_)*cot
6998 w(ix^d,mag(2))=w(ix^d,mag(2))+tmp*invr
7001 w(ix^d,
mom(3))=w(ix^d,
mom(3))-invr*&
7002 (wprim(ix^d,m3_)*wct(ix^d,m1_) &
7003 -wprim(ix^d,b3_)*wprim(ix^d,b1_) &
7004 +(wprim(ix^d,m2_)*wct(ix^d,m3_) &
7005 -wprim(ix^d,b2_)*wprim(ix^d,b3_))*cot)
7007 if(.not.stagger_grid)
then
7008 w(ix^d,mag(3))=w(ix^d,mag(3))+invr*&
7009 (wprim(ix^d,m1_)*wprim(ix^d,b3_) &
7010 -wprim(ix^d,m3_)*wprim(ix^d,b1_) &
7011 -(wprim(ix^d,m3_)*wprim(ix^d,b2_) &
7012 -wprim(ix^d,m2_)*wprim(ix^d,b3_))*cot)
7019 call rotating_frame_add_source(qdt,dtfactor,ixi^l,ixo^l,wprim,w,x)
7022 end subroutine mhd_add_source_geom
7029 subroutine mhd_add_source_geom_semirelati(qdt,dtfactor,ixI^L,ixO^L,wCT,wprim,w,x)
7035 integer,
intent(in) :: ixi^
l, ixo^
l
7036 double precision,
intent(in) :: qdt, dtfactor,x(ixi^s,1:
ndim)
7037 double precision,
intent(inout) :: wct(ixi^s,1:nw),wprim(ixi^s,1:nw),w(ixi^s,1:nw)
7039 double precision :: adiabs(ixi^s), gammas(ixi^s)
7040 double precision :: tmp,tmp1,tmp2,invr,cot,ef(ixo^s,1:
ndir)
7042 integer :: mr_,mphi_
7043 integer :: br_,bphi_
7046 br_=mag(1); bphi_=mag(1)-1+
phi_
7063 {
do ix^db=ixomin^db,ixomax^db\}
7066 invr=
block%dt(ix^
d) * dtfactor/x(ix^
d,1)
7073 tmp=adiabs(ix^
d)*wprim(ix^
d,
rho_)**gammas(ix^
d)
7077 ef(ix^
d,1)=wprim(ix^
d,b2_)*wprim(ix^
d,m3_)-wprim(ix^
d,b3_)*wprim(ix^
d,m2_)
7078 ef(ix^
d,2)=wprim(ix^
d,b3_)*wprim(ix^
d,m1_)-wprim(ix^
d,b1_)*wprim(ix^
d,m3_)
7079 ef(ix^
d,3)=wprim(ix^
d,b1_)*wprim(ix^
d,m2_)-wprim(ix^
d,b2_)*wprim(ix^
d,m1_)
7084 ef(ix^
d,2)=wprim(ix^
d,b1_)*wprim(ix^
d,m2_)-wprim(ix^
d,b2_)*wprim(ix^
d,m1_)
7090 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*(tmp+&
7091 half*((^
c&wprim(ix^
d,
b^
c_)**2+)+(^
c&ef(ix^
d,^
c)**2+)*inv_squared_c) -&
7092 wprim(ix^
d,bphi_)**2+wprim(ix^
d,
rho_)*wprim(ix^
d,mphi_)**2)
7093 w(ix^
d,mphi_)=w(ix^
d,mphi_)+invr*(&
7094 -wprim(ix^
d,
rho_)*wprim(ix^
d,mphi_)*wprim(ix^
d,mr_) &
7095 +wprim(ix^
d,bphi_)*wprim(ix^
d,br_)+ef(ix^
d,
phi_)*ef(ix^
d,1)*inv_squared_c)
7097 w(ix^
d,bphi_)=w(ix^
d,bphi_)+invr*&
7098 (wprim(ix^
d,bphi_)*wprim(ix^
d,mr_) &
7099 -wprim(ix^
d,br_)*wprim(ix^
d,mphi_))
7102 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*(tmp+half*((^
c&wprim(ix^
d,
b^
c_)**2+)+&
7103 (^
c&ef(ix^
d,^
c)**2+)*inv_squared_c))
7108 {
do ix^db=ixomin^db,ixomax^db\}
7110 if(local_timestep)
then
7111 invr=block%dt(ix^d)*dtfactor/x(ix^d,1)
7117 ef(ix^d,1)=wprim(ix^d,b2_)*wprim(ix^d,m3_)-wprim(ix^d,b3_)*wprim(ix^d,m2_)
7118 ef(ix^d,2)=wprim(ix^d,b3_)*wprim(ix^d,m1_)-wprim(ix^d,b1_)*wprim(ix^d,m3_)
7119 ef(ix^d,3)=wprim(ix^d,b1_)*wprim(ix^d,m2_)-wprim(ix^d,b2_)*wprim(ix^d,m1_)
7123 ef(ix^d,1)=wprim(ix^d,b1_)*wprim(ix^d,m2_)-wprim(ix^d,b2_)*wprim(ix^d,m1_)
7130 tmp1=wprim(ix^d,
p_)+half*((^
c&wprim(ix^d,
b^
c_)**2+)+(^
c&ef(ix^d,^
c)**2+)*inv_squared_c)
7132 tmp1=adiabs(ix^d)*wprim(ix^d,
rho_)**gammas(ix^d)+half*((^
c&wprim(ix^d,
b^
c_)**2+)+(^
c&ef(ix^d,^
c)**2+)*inv_squared_c)
7136 w(ix^d,m1_)=w(ix^d,m1_)+two*tmp1*invr
7139 w(ix^d,m1_)=w(ix^d,m1_)+invr*&
7140 (two*tmp1+(^ce&wprim(ix^d,
rho_)*wprim(ix^d,
m^ce_)**2-&
7141 wprim(ix^d,
b^ce_)**2-ef(ix^d,^ce)**2*inv_squared_c+))
7145 w(ix^d,b1_)=w(ix^d,b1_)+invr*2.0d0*wprim(ix^d,
psi_)
7151 cot=1.d0/tan(x(ix^d,2))
7155 w(ix^d,m2_)=w(ix^d,m2_)+invr*(tmp1*cot-wprim(ix^d,
rho_)*wprim(ix^d,m1_)*wprim(ix^d,m2_)&
7156 +wprim(ix^d,b1_)*wprim(ix^d,b2_)+ef(ix^d,1)*ef(ix^d,2)*inv_squared_c)
7158 if(.not.stagger_grid)
then
7159 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
7161 tmp=tmp+wprim(ix^d,
psi_)*cot
7163 w(ix^d,b2_)=w(ix^d,b2_)+tmp*invr
7169 w(ix^d,m2_)=w(ix^d,m2_)+invr*(tmp1*cot-wprim(ix^d,
rho_)*wprim(ix^d,m1_)*wprim(ix^d,m2_) &
7170 +wprim(ix^d,b1_)*wprim(ix^d,b2_)+ef(ix^d,1)*ef(ix^d,2)*inv_squared_c&
7171 +(wprim(ix^d,
rho_)*wprim(ix^d,m3_)**2&
7172 -wprim(ix^d,b3_)**2-ef(ix^d,3)**2*inv_squared_c)*cot)
7174 if(.not.stagger_grid)
then
7175 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
7177 tmp=tmp+wprim(ix^d,
psi_)*cot
7179 w(ix^d,b2_)=w(ix^d,b2_)+tmp*invr
7182 w(ix^d,m3_)=w(ix^d,m3_)+invr*&
7183 (-wprim(ix^d,m3_)*wprim(ix^d,m1_)*wprim(ix^d,
rho_) &
7184 +wprim(ix^d,b3_)*wprim(ix^d,b1_) &
7185 +ef(ix^d,3)*ef(ix^d,1)*inv_squared_c&
7186 +(-wprim(ix^d,m2_)*wprim(ix^d,m3_)*wprim(ix^d,
rho_) &
7187 +wprim(ix^d,b2_)*wprim(ix^d,b3_)&
7188 +ef(ix^d,2)*ef(ix^d,3)*inv_squared_c)*cot)
7190 if(.not.stagger_grid)
then
7191 w(ix^d,b3_)=w(ix^d,b3_)+invr*&
7192 (wprim(ix^d,m1_)*wprim(ix^d,b3_) &
7193 -wprim(ix^d,m3_)*wprim(ix^d,b1_) &
7194 -(wprim(ix^d,m3_)*wprim(ix^d,b2_) &
7195 -wprim(ix^d,m2_)*wprim(ix^d,b3_))*cot)
7202 call rotating_frame_add_source(qdt,dtfactor,ixi^l,ixo^l,wprim,w,x)
7205 end subroutine mhd_add_source_geom_semirelati
7214 subroutine mhd_add_source_geom_split(qdt,dtfactor,ixI^L,ixO^L,wCT,wprim,w,x)
7219 integer,
intent(in) :: ixi^
l, ixo^
l
7220 double precision,
intent(in) :: qdt, dtfactor,x(ixi^s,1:
ndim)
7221 double precision,
intent(inout) :: wct(ixi^s,1:nw),wprim(ixi^s,1:nw),w(ixi^s,1:nw)
7223 double precision :: tmp,tmp1,tmp2,invr,cot
7225 integer :: mr_,mphi_
7226 integer :: br_,bphi_
7229 br_=mag(1); bphi_=mag(1)-1+
phi_
7234 {
do ix^db=ixomin^db,ixomax^db\}
7237 invr=
block%dt(ix^
d) * dtfactor/x(ix^
d,1)
7241 tmp=wprim(ix^
d,
p_)+half*(^
c&wprim(ix^
d,
b^
c_)**2+)
7244 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*(tmp-&
7245 wprim(ix^
d,bphi_)**2+wprim(ix^
d,mphi_)*wct(ix^
d,mphi_))
7249 w(ix^
d,mphi_)=w(ix^
d,mphi_)+invr*(&
7250 -wct(ix^
d,mphi_)*wprim(ix^
d,mr_) &
7251 +wprim(ix^
d,bphi_)*wprim(ix^
d,br_))
7253 w(ix^
d,mphi_)=w(ix^
d,mphi_)+invr*(
block%B0(ix^
d,
phi_,0)*wprim(ix^
d,br_)+wprim(ix^
d,bphi_)*
block%B0(ix^
d,
r_,0))
7256 w(ix^
d,bphi_)=w(ix^
d,bphi_)+invr*&
7257 (wprim(ix^
d,bphi_)*wprim(ix^
d,mr_) &
7258 -wprim(ix^
d,br_)*wprim(ix^
d,mphi_))
7260 w(ix^
d,bphi_)=w(ix^
d,bphi_)+invr*&
7266 w(ix^
d,mr_)=w(ix^
d,mr_)+invr*tmp
7271 {
do ix^db=ixomin^db,ixomax^db\}
7273 if(local_timestep)
then
7274 invr=block%dt(ix^d) * dtfactor/x(ix^d,1)
7278 tmp1=wprim(ix^d,
p_)+half*(^
c&wprim(ix^d,
b^
c_)**2+)
7279 if(b0field) tmp2=(^
c&block%B0(ix^d,^
c,0)*wprim(ix^d,
b^
c_)+)
7282 w(ix^d,
mom(1))=w(ix^d,
mom(1))+two*tmp1*invr
7283 if(b0field) w(ix^d,
mom(1))=w(ix^d,
mom(1))+two*tmp2*invr
7287 w(ix^d,
mom(1))=w(ix^d,
mom(1))+invr*&
7288 (two*(tmp1+tmp2)+(^ce&wprim(ix^d,
m^ce_)*wct(ix^d,
m^ce_)-wprim(ix^d,
b^ce_)**2+)- &
7289 (^ce&two*block%B0(ix^d,^ce,0)*wprim(ix^d,
b^ce_)+))
7291 w(ix^d,
mom(1))=w(ix^d,
mom(1))+invr*&
7292 (two*tmp1+(^ce&wprim(ix^d,
m^ce_)*wct(ix^d,
m^ce_)-wprim(ix^d,
b^ce_)**2+))
7297 w(ix^d,mag(1))=w(ix^d,mag(1))+invr*2.0d0*wprim(ix^d,
psi_)
7303 cot=1.d0/tan(x(ix^d,2))
7308 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*((tmp1+tmp2)*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
7309 +wprim(ix^d,b1_)*wprim(ix^d,b2_)+block%B0(ix^d,1,0)*wprim(ix^d,b2_)&
7310 +wprim(ix^d,b1_)*block%B0(ix^d,2,0))
7312 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*(tmp1*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
7313 +wprim(ix^d,b1_)*wprim(ix^d,b2_))
7316 if(.not.stagger_grid)
then
7318 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)&
7319 +wprim(ix^d,m1_)*block%B0(ix^d,2,0)-wprim(ix^d,m2_)*block%B0(ix^d,1,0)
7321 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
7324 tmp=tmp+wprim(ix^d,
psi_)*cot
7326 w(ix^d,mag(2))=w(ix^d,mag(2))+tmp*invr
7332 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*((tmp1+tmp2)*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
7333 +wprim(ix^d,b1_)*wprim(ix^d,b2_)+block%B0(ix^d,1,0)*wprim(ix^d,b2_)&
7334 +wprim(ix^d,b1_)*block%B0(ix^d,2,0)&
7335 +(wprim(ix^d,m3_)*wct(ix^d,m3_)-wprim(ix^d,b3_)**2-two*block%B0(ix^d,3,0)*wprim(ix^d,b3_))*cot)
7337 w(ix^d,
mom(2))=w(ix^d,
mom(2))+invr*(tmp1*cot-wprim(ix^d,m1_)*wct(ix^d,m2_)&
7338 +wprim(ix^d,b1_)*wprim(ix^d,b2_)&
7339 +(wprim(ix^d,m3_)*wct(ix^d,m3_)-wprim(ix^d,b3_)**2)*cot)
7342 if(.not.stagger_grid)
then
7344 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)&
7345 +wprim(ix^d,m1_)*block%B0(ix^d,2,0)-wprim(ix^d,m2_)*block%B0(ix^d,1,0)
7347 tmp=wprim(ix^d,m1_)*wprim(ix^d,b2_)-wprim(ix^d,m2_)*wprim(ix^d,b1_)
7350 tmp=tmp+wprim(ix^d,
psi_)*cot
7352 w(ix^d,mag(2))=w(ix^d,mag(2))+tmp*invr
7356 w(ix^d,
mom(3))=w(ix^d,
mom(3))-invr*&
7357 (wprim(ix^d,m3_)*wct(ix^d,m1_) &
7358 -wprim(ix^d,b3_)*wprim(ix^d,b1_) &
7359 +block%B0(ix^d,1,0)*wprim(ix^d,b3_) &
7360 +wprim(ix^d,b1_)*block%B0(ix^d,3,0) &
7361 +(wprim(ix^d,m2_)*wct(ix^d,m3_) &
7362 -wprim(ix^d,b2_)*wprim(ix^d,b3_) &
7363 +block%B0(ix^d,2,0)*wprim(ix^d,b3_) &
7364 +wprim(ix^d,b2_)*block%B0(ix^d,3,0))*cot)
7366 w(ix^d,
mom(3))=w(ix^d,
mom(3))-invr*&
7367 (wprim(ix^d,m3_)*wct(ix^d,m1_) &
7368 -wprim(ix^d,b3_)*wprim(ix^d,b1_) &
7369 +(wprim(ix^d,m2_)*wct(ix^d,m3_) &
7370 -wprim(ix^d,b2_)*wprim(ix^d,b3_))*cot)
7373 if(.not.stagger_grid)
then
7375 w(ix^d,mag(3))=w(ix^d,mag(3))+invr*&
7376 (wprim(ix^d,m1_)*wprim(ix^d,b3_) &
7377 -wprim(ix^d,m3_)*wprim(ix^d,b1_) &
7378 +wprim(ix^d,m1_)*block%B0(ix^d,3,0) &
7379 -wprim(ix^d,m3_)*block%B0(ix^d,1,0) &
7380 -(wprim(ix^d,m3_)*wprim(ix^d,b2_) &
7381 -wprim(ix^d,m2_)*wprim(ix^d,b3_) &
7382 +wprim(ix^d,m3_)*block%B0(ix^d,2,0) &
7383 -wprim(ix^d,m2_)*block%B0(ix^d,3,0))*cot)
7385 w(ix^d,mag(3))=w(ix^d,mag(3))+invr*&
7386 (wprim(ix^d,m1_)*wprim(ix^d,b3_) &
7387 -wprim(ix^d,m3_)*wprim(ix^d,b1_) &
7388 -(wprim(ix^d,m3_)*wprim(ix^d,b2_) &
7389 -wprim(ix^d,m2_)*wprim(ix^d,b3_))*cot)
7397 call rotating_frame_add_source(qdt,dtfactor,ixi^l,ixo^l,wprim,w,x)
7400 end subroutine mhd_add_source_geom_split
7405 integer,
intent(in) :: ixi^
l, ixo^
l
7406 double precision,
intent(in) :: w(ixi^s, nw)
7407 double precision :: mge(ixo^s)
7410 mge = sum((w(ixo^s, mag(:))+
block%B0(ixo^s,:,
b0i))**2, dim=
ndim+1)
7412 mge = sum(w(ixo^s, mag(:))**2, dim=
ndim+1)
7416 subroutine mhd_getv_hall(w,x,ixI^L,ixO^L,vHall,partial)
7420 integer,
intent(in) :: ixi^
l, ixo^
l
7421 double precision,
intent(in) :: w(ixi^s,nw)
7422 double precision,
intent(in) :: x(ixi^s,1:
ndim)
7423 double precision,
intent(inout) :: vhall(ixi^s,1:
ndir)
7424 logical,
intent(in),
optional :: partial
7426 double precision :: current(ixi^s,7-2*
ndir:3)
7427 double precision :: rho(ixi^s)
7428 integer :: idir, idirmin, ix^
d
7429 logical :: use_partial
7432 if(
present(partial)) use_partial=partial
7434 if(.not.use_partial)
then
7445 do idir = idirmin,
ndir
7446 {
do ix^db=ixomin^db,ixomax^db\}
7447 vhall(ix^
d,idir)=-
mhd_etah*current(ix^
d,idir)/rho(ix^
d)
7451 end subroutine mhd_getv_hall
7453 subroutine mhd_modify_wlr(ixI^L,ixO^L,qt,wLC,wRC,wLp,wRp,s,idir)
7456 integer,
intent(in) :: ixi^
l, ixo^
l, idir
7457 double precision,
intent(in) :: qt
7458 double precision,
intent(inout) :: wlc(ixi^s,1:nw), wrc(ixi^s,1:nw)
7459 double precision,
intent(inout) :: wlp(ixi^s,1:nw), wrp(ixi^s,1:nw)
7462 double precision :: db(ixo^s), dpsi(ixo^s)
7466 {
do ix^db=ixomin^db,ixomax^db\}
7467 wlc(ix^
d,mag(idir))=s%ws(ix^
d,idir)
7468 wrc(ix^
d,mag(idir))=s%ws(ix^
d,idir)
7469 wlp(ix^
d,mag(idir))=s%ws(ix^
d,idir)
7470 wrp(ix^
d,mag(idir))=s%ws(ix^
d,idir)
7479 {
do ix^db=ixomin^db,ixomax^db\}
7480 db(ix^d)=wrp(ix^d,mag(idir))-wlp(ix^d,mag(idir))
7481 dpsi(ix^d)=wrp(ix^d,
psi_)-wlp(ix^d,
psi_)
7482 wlp(ix^d,mag(idir))=half*(wrp(ix^d,mag(idir))+wlp(ix^d,mag(idir))-dpsi(ix^d)/cmax_global)
7483 wlp(ix^d,
psi_)=half*(wrp(ix^d,
psi_)+wlp(ix^d,
psi_)-db(ix^d)*cmax_global)
7484 wrp(ix^d,mag(idir))=wlp(ix^d,mag(idir))
7486 if(total_energy)
then
7487 wrc(ix^d,
e_)=wrc(ix^d,
e_)-half*wrc(ix^d,mag(idir))**2
7488 wlc(ix^d,
e_)=wlc(ix^d,
e_)-half*wlc(ix^d,mag(idir))**2
7490 wrc(ix^d,mag(idir))=wlp(ix^d,mag(idir))
7492 wlc(ix^d,mag(idir))=wlp(ix^d,mag(idir))
7495 if(total_energy)
then
7496 wrc(ix^d,
e_)=wrc(ix^d,
e_)+half*wrc(ix^d,mag(idir))**2
7497 wlc(ix^d,
e_)=wlc(ix^d,
e_)+half*wlc(ix^d,mag(idir))**2
7502 if(
associated(usr_set_wlr))
call usr_set_wlr(ixi^l,ixo^l,qt,wlc,wrc,wlp,wrp,s,idir)
7504 end subroutine mhd_modify_wlr
7506 subroutine mhd_boundary_adjust(igrid,psb)
7508 integer,
intent(in) :: igrid
7511 integer :: ib, idims, iside, ixo^
l, i^
d
7520 i^
d=
kr(^
d,idims)*(2*iside-3);
7521 if (neighbor_type(i^
d,igrid)/=1) cycle
7522 ib=(idims-1)*2+iside
7540 call fixdivb_boundary(ixg^
ll,ixo^
l,psb(igrid)%w,psb(igrid)%x,ib)
7545 end subroutine mhd_boundary_adjust
7547 subroutine fixdivb_boundary(ixG^L,ixO^L,w,x,iB)
7550 integer,
intent(in) :: ixg^
l,ixo^
l,ib
7551 double precision,
intent(inout) :: w(ixg^s,1:nw)
7552 double precision,
intent(in) :: x(ixg^s,1:
ndim)
7554 double precision :: dx1x2,dx1x3,dx2x1,dx2x3,dx3x1,dx3x2
7555 integer :: ix^
d,ixf^
l
7568 do ix1=ixfmax1,ixfmin1,-1
7569 w(ix1-1,ixfmin2:ixfmax2,mag(1))=w(ix1+1,ixfmin2:ixfmax2,mag(1)) &
7570 +dx1x2*(w(ix1,ixfmin2+1:ixfmax2+1,mag(2))-&
7571 w(ix1,ixfmin2-1:ixfmax2-1,mag(2)))
7574 do ix1=ixfmax1,ixfmin1,-1
7575 w(ix1-1,ixfmin2:ixfmax2,mag(1))=( (w(ix1+1,ixfmin2:ixfmax2,mag(1))+&
7576 w(ix1,ixfmin2:ixfmax2,mag(1)))*
block%surfaceC(ix1,ixfmin2:ixfmax2,1)&
7577 +(w(ix1,ixfmin2+1:ixfmax2+1,mag(2))+w(ix1,ixfmin2:ixfmax2,mag(2)))*&
7578 block%surfaceC(ix1,ixfmin2:ixfmax2,2)&
7579 -(w(ix1,ixfmin2:ixfmax2,mag(2))+w(ix1,ixfmin2-1:ixfmax2-1,mag(2)))*&
7580 block%surfaceC(ix1,ixfmin2-1:ixfmax2-1,2) )&
7581 /
block%surfaceC(ix1-1,ixfmin2:ixfmax2,1)-w(ix1,ixfmin2:ixfmax2,mag(1))
7595 do ix1=ixfmax1,ixfmin1,-1
7596 w(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))=&
7597 w(ix1+1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1)) &
7598 +dx1x2*(w(ix1,ixfmin2+1:ixfmax2+1,ixfmin3:ixfmax3,mag(2))-&
7599 w(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,mag(2))) &
7600 +dx1x3*(w(ix1,ixfmin2:ixfmax2,ixfmin3+1:ixfmax3+1,mag(3))-&
7601 w(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,mag(3)))
7604 do ix1=ixfmax1,ixfmin1,-1
7605 w(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))=&
7606 ( (w(ix1+1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))+&
7607 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1)))*&
7608 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,1)&
7609 +(w(ix1,ixfmin2+1:ixfmax2+1,ixfmin3:ixfmax3,mag(2))+&
7610 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(2)))*&
7611 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,2)&
7612 -(w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(2))+&
7613 w(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,mag(2)))*&
7614 block%surfaceC(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,2)&
7615 +(w(ix1,ixfmin2:ixfmax2,ixfmin3+1:ixfmax3+1,mag(3))+&
7616 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(3)))*&
7617 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,3)&
7618 -(w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(3))+&
7619 w(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,mag(3)))*&
7620 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,3) )&
7621 /
block%surfaceC(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,1)-&
7622 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))
7636 do ix1=ixfmin1,ixfmax1
7637 w(ix1+1,ixfmin2:ixfmax2,mag(1))=w(ix1-1,ixfmin2:ixfmax2,mag(1)) &
7638 -dx1x2*(w(ix1,ixfmin2+1:ixfmax2+1,mag(2))-&
7639 w(ix1,ixfmin2-1:ixfmax2-1,mag(2)))
7642 do ix1=ixfmin1,ixfmax1
7643 w(ix1+1,ixfmin2:ixfmax2,mag(1))=( (w(ix1-1,ixfmin2:ixfmax2,mag(1))+&
7644 w(ix1,ixfmin2:ixfmax2,mag(1)))*
block%surfaceC(ix1-1,ixfmin2:ixfmax2,1)&
7645 -(w(ix1,ixfmin2+1:ixfmax2+1,mag(2))+w(ix1,ixfmin2:ixfmax2,mag(2)))*&
7646 block%surfaceC(ix1,ixfmin2:ixfmax2,2)&
7647 +(w(ix1,ixfmin2:ixfmax2,mag(2))+w(ix1,ixfmin2-1:ixfmax2-1,mag(2)))*&
7648 block%surfaceC(ix1,ixfmin2-1:ixfmax2-1,2) )&
7649 /
block%surfaceC(ix1,ixfmin2:ixfmax2,1)-w(ix1,ixfmin2:ixfmax2,mag(1))
7663 do ix1=ixfmin1,ixfmax1
7664 w(ix1+1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))=&
7665 w(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1)) &
7666 -dx1x2*(w(ix1,ixfmin2+1:ixfmax2+1,ixfmin3:ixfmax3,mag(2))-&
7667 w(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,mag(2))) &
7668 -dx1x3*(w(ix1,ixfmin2:ixfmax2,ixfmin3+1:ixfmax3+1,mag(3))-&
7669 w(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,mag(3)))
7672 do ix1=ixfmin1,ixfmax1
7673 w(ix1+1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))=&
7674 ( (w(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))+&
7675 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1)))*&
7676 block%surfaceC(ix1-1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,1)&
7677 -(w(ix1,ixfmin2+1:ixfmax2+1,ixfmin3:ixfmax3,mag(2))+&
7678 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(2)))*&
7679 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,2)&
7680 +(w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(2))+&
7681 w(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,mag(2)))*&
7682 block%surfaceC(ix1,ixfmin2-1:ixfmax2-1,ixfmin3:ixfmax3,2)&
7683 -(w(ix1,ixfmin2:ixfmax2,ixfmin3+1:ixfmax3+1,mag(3))+&
7684 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(3)))*&
7685 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,3)&
7686 +(w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(3))+&
7687 w(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,mag(3)))*&
7688 block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3-1:ixfmax3-1,3) )&
7689 /
block%surfaceC(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,1)-&
7690 w(ix1,ixfmin2:ixfmax2,ixfmin3:ixfmax3,mag(1))
7704 do ix2=ixfmax2,ixfmin2,-1
7705 w(ixfmin1:ixfmax1,ix2-1,mag(2))=w(ixfmin1:ixfmax1,ix2+1,mag(2)) &
7706 +dx2x1*(w(ixfmin1+1:ixfmax1+1,ix2,mag(1))-&
7707 w(ixfmin1-1:ixfmax1-1,ix2,mag(1)))
7710 do ix2=ixfmax2,ixfmin2,-1
7711 w(ixfmin1:ixfmax1,ix2-1,mag(2))=( (w(ixfmin1:ixfmax1,ix2+1,mag(2))+&
7712 w(ixfmin1:ixfmax1,ix2,mag(2)))*
block%surfaceC(ixfmin1:ixfmax1,ix2,2)&
7713 +(w(ixfmin1+1:ixfmax1+1,ix2,mag(1))+w(ixfmin1:ixfmax1,ix2,mag(1)))*&
7714 block%surfaceC(ixfmin1:ixfmax1,ix2,1)&
7715 -(w(ixfmin1:ixfmax1,ix2,mag(1))+w(ixfmin1-1:ixfmax1-1,ix2,mag(1)))*&
7716 block%surfaceC(ixfmin1-1:ixfmax1-1,ix2,1) )&
7717 /
block%surfaceC(ixfmin1:ixfmax1,ix2-1,2)-w(ixfmin1:ixfmax1,ix2,mag(2))
7731 do ix2=ixfmax2,ixfmin2,-1
7732 w(ixfmin1:ixfmax1,ix2-1,ixfmin3:ixfmax3,mag(2))=w(ixfmin1:ixfmax1,&
7733 ix2+1,ixfmin3:ixfmax3,mag(2)) &
7734 +dx2x1*(w(ixfmin1+1:ixfmax1+1,ix2,ixfmin3:ixfmax3,mag(1))-&
7735 w(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,mag(1))) &
7736 +dx2x3*(w(ixfmin1:ixfmax1,ix2,ixfmin3+1:ixfmax3+1,mag(3))-&
7737 w(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,mag(3)))
7740 do ix2=ixfmax2,ixfmin2,-1
7741 w(ixfmin1:ixfmax1,ix2-1,ixfmin3:ixfmax3,mag(2))=&
7742 ( (w(ixfmin1:ixfmax1,ix2+1,ixfmin3:ixfmax3,mag(2))+&
7743 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(2)))*&
7744 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,2)&
7745 +(w(ixfmin1+1:ixfmax1+1,ix2,ixfmin3:ixfmax3,mag(1))+&
7746 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(1)))*&
7747 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,1)&
7748 -(w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(1))+&
7749 w(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,mag(1)))*&
7750 block%surfaceC(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,1)&
7751 +(w(ixfmin1:ixfmax1,ix2,ixfmin3+1:ixfmax3+1,mag(3))+&
7752 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(3)))*&
7753 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,3)&
7754 -(w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(3))+&
7755 w(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,mag(3)))*&
7756 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,3) )&
7757 /
block%surfaceC(ixfmin1:ixfmax1,ix2-1,ixfmin3:ixfmax3,2)-&
7758 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(2))
7772 do ix2=ixfmin2,ixfmax2
7773 w(ixfmin1:ixfmax1,ix2+1,mag(2))=w(ixfmin1:ixfmax1,ix2-1,mag(2)) &
7774 -dx2x1*(w(ixfmin1+1:ixfmax1+1,ix2,mag(1))-&
7775 w(ixfmin1-1:ixfmax1-1,ix2,mag(1)))
7778 do ix2=ixfmin2,ixfmax2
7779 w(ixfmin1:ixfmax1,ix2+1,mag(2))=( (w(ixfmin1:ixfmax1,ix2-1,mag(2))+&
7780 w(ixfmin1:ixfmax1,ix2,mag(2)))*
block%surfaceC(ixfmin1:ixfmax1,ix2-1,2)&
7781 -(w(ixfmin1+1:ixfmax1+1,ix2,mag(1))+w(ixfmin1:ixfmax1,ix2,mag(1)))*&
7782 block%surfaceC(ixfmin1:ixfmax1,ix2,1)&
7783 +(w(ixfmin1:ixfmax1,ix2,mag(1))+w(ixfmin1-1:ixfmax1-1,ix2,mag(1)))*&
7784 block%surfaceC(ixfmin1-1:ixfmax1-1,ix2,1) )&
7785 /
block%surfaceC(ixfmin1:ixfmax1,ix2,2)-w(ixfmin1:ixfmax1,ix2,mag(2))
7799 do ix2=ixfmin2,ixfmax2
7800 w(ixfmin1:ixfmax1,ix2+1,ixfmin3:ixfmax3,mag(2))=w(ixfmin1:ixfmax1,&
7801 ix2-1,ixfmin3:ixfmax3,mag(2)) &
7802 -dx2x1*(w(ixfmin1+1:ixfmax1+1,ix2,ixfmin3:ixfmax3,mag(1))-&
7803 w(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,mag(1))) &
7804 -dx2x3*(w(ixfmin1:ixfmax1,ix2,ixfmin3+1:ixfmax3+1,mag(3))-&
7805 w(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,mag(3)))
7808 do ix2=ixfmin2,ixfmax2
7809 w(ixfmin1:ixfmax1,ix2+1,ixfmin3:ixfmax3,mag(2))=&
7810 ( (w(ixfmin1:ixfmax1,ix2-1,ixfmin3:ixfmax3,mag(2))+&
7811 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(2)))*&
7812 block%surfaceC(ixfmin1:ixfmax1,ix2-1,ixfmin3:ixfmax3,2)&
7813 -(w(ixfmin1+1:ixfmax1+1,ix2,ixfmin3:ixfmax3,mag(1))+&
7814 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(1)))*&
7815 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,1)&
7816 +(w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(1))+&
7817 w(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,mag(1)))*&
7818 block%surfaceC(ixfmin1-1:ixfmax1-1,ix2,ixfmin3:ixfmax3,1)&
7819 -(w(ixfmin1:ixfmax1,ix2,ixfmin3+1:ixfmax3+1,mag(3))+&
7820 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(3)))*&
7821 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,3)&
7822 +(w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(3))+&
7823 w(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,mag(3)))*&
7824 block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3-1:ixfmax3-1,3) )&
7825 /
block%surfaceC(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,2)-&
7826 w(ixfmin1:ixfmax1,ix2,ixfmin3:ixfmax3,mag(2))
7843 do ix3=ixfmax3,ixfmin3,-1
7844 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3-1,mag(3))=w(ixfmin1:ixfmax1,&
7845 ixfmin2:ixfmax2,ix3+1,mag(3)) &
7846 +dx3x1*(w(ixfmin1+1:ixfmax1+1,ixfmin2:ixfmax2,ix3,mag(1))-&
7847 w(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,mag(1))) &
7848 +dx3x2*(w(ixfmin1:ixfmax1,ixfmin2+1:ixfmax2+1,ix3,mag(2))-&
7849 w(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,mag(2)))
7852 do ix3=ixfmax3,ixfmin3,-1
7853 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3-1,mag(3))=&
7854 ( (w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3+1,mag(3))+&
7855 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(3)))*&
7856 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,3)&
7857 +(w(ixfmin1+1:ixfmax1+1,ixfmin2:ixfmax2,ix3,mag(1))+&
7858 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(1)))*&
7859 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,1)&
7860 -(w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(1))+&
7861 w(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,mag(1)))*&
7862 block%surfaceC(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,1)&
7863 +(w(ixfmin1:ixfmax1,ixfmin2+1:ixfmax2+1,ix3,mag(2))+&
7864 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(2)))*&
7865 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,2)&
7866 -(w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(2))+&
7867 w(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,mag(2)))*&
7868 block%surfaceC(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,2) )&
7869 /
block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3-1,3)-&
7870 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(3))
7885 do ix3=ixfmin3,ixfmax3
7886 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3+1,mag(3))=w(ixfmin1:ixfmax1,&
7887 ixfmin2:ixfmax2,ix3-1,mag(3)) &
7888 -dx3x1*(w(ixfmin1+1:ixfmax1+1,ixfmin2:ixfmax2,ix3,mag(1))-&
7889 w(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,mag(1))) &
7890 -dx3x2*(w(ixfmin1:ixfmax1,ixfmin2+1:ixfmax2+1,ix3,mag(2))-&
7891 w(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,mag(2)))
7894 do ix3=ixfmin3,ixfmax3
7895 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3+1,mag(3))=&
7896 ( (w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3-1,mag(3))+&
7897 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(3)))*&
7898 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3-1,3)&
7899 -(w(ixfmin1+1:ixfmax1+1,ixfmin2:ixfmax2,ix3,mag(1))+&
7900 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(1)))*&
7901 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,1)&
7902 +(w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(1))+&
7903 w(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,mag(1)))*&
7904 block%surfaceC(ixfmin1-1:ixfmax1-1,ixfmin2:ixfmax2,ix3,1)&
7905 -(w(ixfmin1:ixfmax1,ixfmin2+1:ixfmax2+1,ix3,mag(2))+&
7906 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(2)))*&
7907 block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,2)&
7908 +(w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(2))+&
7909 w(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,mag(2)))*&
7910 block%surfaceC(ixfmin1:ixfmax1,ixfmin2-1:ixfmax2-1,ix3,2) )&
7911 /
block%surfaceC(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,3)-&
7912 w(ixfmin1:ixfmax1,ixfmin2:ixfmax2,ix3,mag(3))
7918 call mpistop(
"Special boundary is not defined for this region")
7921 end subroutine fixdivb_boundary
7930 double precision,
intent(in) :: qdt
7931 double precision,
intent(in) :: qt
7932 logical,
intent(inout) :: active
7935 integer,
parameter :: max_its = 50
7936 double precision :: residual_it(max_its), max_divb
7937 double precision :: tmp(ixg^t), grad(ixg^t,
ndim)
7938 double precision :: res
7939 double precision,
parameter :: max_residual = 1
d-3
7940 double precision,
parameter :: residual_reduction = 1
d-10
7941 integer :: iigrid, igrid
7942 integer :: n, nc, lvl, ix^
l, ixc^
l, idim
7945 mg%operator_type = mg_laplacian
7953 mg%bc(n, mg_iphi)%bc_type = mg_bc_dirichlet
7954 mg%bc(n, mg_iphi)%bc_value = 0.0_dp
7957 mg%bc(n, mg_iphi)%bc_type = mg_bc_neumann
7958 mg%bc(n, mg_iphi)%bc_value = 0.0_dp
7960 mg%bc(n, mg_iphi)%bc_type = mg_bc_dirichlet
7961 mg%bc(n, mg_iphi)%bc_value = 0.0_dp
7964 mg%bc(n, mg_iphi)%bc_type = mg_bc_dirichlet
7965 mg%bc(n, mg_iphi)%bc_value = 0.0_dp
7969 write(*,*)
"mhd_clean_divb_multigrid warning: unknown boundary type"
7970 mg%bc(n, mg_iphi)%bc_type = mg_bc_dirichlet
7971 mg%bc(n, mg_iphi)%bc_value = 0.0_dp
7979 do iigrid = 1, igridstail
7980 igrid = igrids(iigrid);
7983 lvl =
mg%boxes(id)%lvl
7984 nc =
mg%box_size_lvl(lvl)
7990 call get_divb(ps(igrid)%w(ixg^t, 1:nw), ixg^
ll,
ixm^
ll, tmp, &
7992 mg%boxes(id)%cc({1:nc}, mg_irhs) = tmp(
ixm^t)
7993 max_divb = max(max_divb, maxval(abs(tmp(
ixm^t))))
7998 call mpi_allreduce(mpi_in_place, max_divb, 1, mpi_double_precision, &
8001 if (
mype == 0) print *,
"Performing multigrid divB cleaning"
8002 if (
mype == 0) print *,
"iteration vs residual"
8005 call mg_fas_fmg(
mg, n>1, max_res=residual_it(n))
8006 if (
mype == 0)
write(*,
"(I4,E11.3)") n, residual_it(n)
8007 if (residual_it(n) < residual_reduction * max_divb)
exit
8009 if (
mype == 0 .and. n > max_its)
then
8010 print *,
"divb_multigrid warning: not fully converged"
8011 print *,
"current amplitude of divb: ", residual_it(max_its)
8012 print *,
"multigrid smallest grid: ", &
8013 mg%domain_size_lvl(:,
mg%lowest_lvl)
8014 print *,
"note: smallest grid ideally has <= 8 cells"
8015 print *,
"multigrid dx/dy/dz ratio: ",
mg%dr(:, 1)/
mg%dr(1, 1)
8016 print *,
"note: dx/dy/dz should be similar"
8020 call mg_fas_vcycle(
mg, max_res=res)
8021 if (res < max_residual)
exit
8023 if (res > max_residual)
call mpistop(
"divb_multigrid: no convergence")
8028 do iigrid = 1, igridstail
8029 igrid = igrids(iigrid);
8038 tmp(ix^s) =
mg%boxes(id)%cc({:,}, mg_iphi)
8042 ixcmin^
d=ixmlo^
d-
kr(idim,^
d);
8044 call gradientf(tmp,ps(igrid)%x,ixg^
ll,ixc^
l,idim,grad(ixg^t,idim))
8046 ps(igrid)%ws(ixc^s,idim)=ps(igrid)%ws(ixc^s,idim)-grad(ixc^s,idim)
8059 ps(igrid)%w(
ixm^t, mag(1:
ndim)) = &
8060 ps(igrid)%w(
ixm^t, mag(1:
ndim)) - grad(
ixm^t, :)
8063 if(total_energy)
then
8065 tmp(
ixm^t) = 0.5_dp * (sum(ps(igrid)%w(
ixm^t, &
8068 ps(igrid)%w(
ixm^t,
e_) = ps(igrid)%w(
ixm^t,
e_) + tmp(
ixm^t)
8078 subroutine mhd_update_faces_average(ixI^L,ixO^L,qt,qdt,wp,fC,fE,sCT,s,vcts)
8082 integer,
intent(in) :: ixi^
l, ixo^
l
8083 double precision,
intent(in) :: qt,qdt
8085 double precision,
intent(in) :: wp(ixi^s,1:nw)
8086 type(state) :: sct, s
8087 type(ct_velocity) :: vcts
8088 double precision,
intent(in) :: fc(ixi^s,1:nwflux,1:
ndim)
8089 double precision,
intent(inout) :: fe(ixi^s,
sdim:3)
8091 double precision :: circ(ixi^s,1:
ndim)
8093 double precision,
dimension(ixI^S,sdim:3) :: e_resi, e_ambi
8094 integer :: ix^
d,ixc^
l,ixa^
l,i1kr^
d,i2kr^
d
8095 integer :: idim1,idim2,idir,iwdim1,iwdim2
8097 associate(bfaces=>s%ws,x=>s%x)
8104 if(
mhd_eta/=zero)
call get_resistive_electric_field(ixi^
l,ixo^
l,wp,sct,s,e_resi)
8111 i1kr^
d=
kr(idim1,^
d);
8114 i2kr^
d=
kr(idim2,^
d);
8117 if (
lvc(idim1,idim2,idir)==1)
then
8119 ixcmin^
d=ixomin^
d+
kr(idir,^
d)-1;
8121 {
do ix^db=ixcmin^db,ixcmax^db\}
8122 fe(ix^
d,idir)=quarter*&
8123 (fc(ix^
d,iwdim1,idim2)+fc({ix^
d+i1kr^
d},iwdim1,idim2)&
8124 -fc(ix^
d,iwdim2,idim1)-fc({ix^
d+i2kr^
d},iwdim2,idim1))
8126 if(
mhd_eta/=zero) fe(ix^
d,idir)=fe(ix^
d,idir)+e_resi(ix^
d,idir)
8131 fe(ix^
d,idir)=fe(ix^
d,idir)*qdt*s%dsC(ix^
d,idir)
8139 if(
associated(usr_set_electric_field)) &
8140 call usr_set_electric_field(ixi^l,ixo^l,qt,qdt,fe,sct)
8142 circ(ixi^s,1:ndim)=zero
8147 ixcmin^d=ixomin^d-kr(idim1,^d);
8149 ixa^l=ixc^l-kr(idim2,^d);
8152 if(lvc(idim1,idim2,idir)==1)
then
8154 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
8157 else if(lvc(idim1,idim2,idir)==-1)
then
8159 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
8165 {
do ix^db=ixcmin^db,ixcmax^db\}
8167 if(s%surfaceC(ix^d,idim1) > smalldouble)
then
8169 bfaces(ix^d,idim1)=bfaces(ix^d,idim1)-circ(ix^d,idim1)/s%surfaceC(ix^d,idim1)
8176 end subroutine mhd_update_faces_average
8179 subroutine mhd_update_faces_contact(ixI^L,ixO^L,qt,qdt,wp,fC,fE,sCT,s,vcts)
8184 integer,
intent(in) :: ixi^
l, ixo^
l
8185 double precision,
intent(in) :: qt, qdt
8187 double precision,
intent(in) :: wp(ixi^s,1:nw)
8188 type(state) :: sct, s
8189 type(ct_velocity) :: vcts
8190 double precision,
intent(in) :: fc(ixi^s,1:nwflux,1:
ndim)
8191 double precision,
intent(inout) :: fe(ixi^s,
sdim:3)
8193 double precision :: circ(ixi^s,1:
ndim)
8195 double precision :: ecc(ixi^s,
sdim:3)
8196 double precision :: ein(ixi^s,
sdim:3)
8198 double precision :: el(ixi^s),er(ixi^s)
8200 double precision :: elc,erc
8202 double precision,
dimension(ixI^S,sdim:3) :: e_resi, e_ambi
8204 double precision :: jce(ixi^s,
sdim:3)
8206 double precision :: xs(ixgs^t,1:
ndim)
8207 double precision :: gradi(ixgs^t)
8208 integer :: ixc^
l,ixa^
l
8209 integer :: idim1,idim2,idir,iwdim1,iwdim2,ix^
d,i1kr^
d,i2kr^
d
8211 associate(bfaces=>s%ws,x=>s%x,w=>s%w,vnorm=>vcts%vnorm,wcts=>sct%ws)
8214 if(
mhd_eta/=zero)
call get_resistive_electric_field(ixi^
l,ixo^
l,wp,sct,s,e_resi)
8220 {
do ix^db=iximin^db,iximax^db\}
8223 ecc(ix^
d,1)=(wp(ix^
d,b2_)+
block%B0(ix^
d,2,0))*wp(ix^
d,m3_)-(wp(ix^
d,b3_)+
block%B0(ix^
d,3,0))*wp(ix^
d,m2_)
8224 ecc(ix^
d,2)=(wp(ix^
d,b3_)+
block%B0(ix^
d,3,0))*wp(ix^
d,m1_)-(wp(ix^
d,b1_)+
block%B0(ix^
d,1,0))*wp(ix^
d,m3_)
8225 ecc(ix^
d,3)=(wp(ix^
d,b1_)+
block%B0(ix^
d,1,0))*wp(ix^
d,m2_)-(wp(ix^
d,b2_)+
block%B0(ix^
d,2,0))*wp(ix^
d,m1_)
8228 ecc(ix^
d,3)=wp(ix^
d,b1_)*wp(ix^
d,m2_)-wp(ix^
d,b2_)*wp(ix^
d,m1_)
8235 {
do ix^db=iximin^db,iximax^db\}
8238 ecc(ix^d,1)=wp(ix^d,b2_)*wp(ix^d,m3_)-wp(ix^d,b3_)*wp(ix^d,m2_)
8239 ecc(ix^d,2)=wp(ix^d,b3_)*wp(ix^d,m1_)-wp(ix^d,b1_)*wp(ix^d,m3_)
8240 ecc(ix^d,3)=wp(ix^d,b1_)*wp(ix^d,m2_)-wp(ix^d,b2_)*wp(ix^d,m1_)
8243 ecc(ix^d,3)=wp(ix^d,b1_)*wp(ix^d,m2_)-wp(ix^d,b2_)*wp(ix^d,m1_)
8257 i1kr^d=kr(idim1,^d);
8260 i2kr^d=kr(idim2,^d);
8263 if (lvc(idim1,idim2,idir)==1)
then
8265 ixcmin^d=ixomin^d+kr(idir,^d)-1;
8268 {
do ix^db=ixcmin^db,ixcmax^db\}
8269 fe(ix^d,idir)=quarter*&
8270 (fc(ix^d,iwdim1,idim2)+fc({ix^d+i1kr^d},iwdim1,idim2)&
8271 -fc(ix^d,iwdim2,idim1)-fc({ix^d+i2kr^d},iwdim2,idim1))
8276 ixamax^d=ixcmax^d+i1kr^d;
8277 {
do ix^db=ixamin^db,ixamax^db\}
8278 el(ix^d)=fc(ix^d,iwdim1,idim2)-ecc(ix^d,idir)
8279 er(ix^d)=fc(ix^d,iwdim1,idim2)-ecc({ix^d+i2kr^d},idir)
8282 do ix^db=ixcmin^db,ixcmax^db\}
8283 if(vnorm(ix^d,idim1)>0.d0)
then
8285 else if(vnorm(ix^d,idim1)<0.d0)
then
8286 elc=el({ix^d+i1kr^d})
8288 elc=0.5d0*(el(ix^d)+el({ix^d+i1kr^d}))
8290 if(vnorm({ix^d+i2kr^d},idim1)>0.d0)
then
8292 else if(vnorm({ix^d+i2kr^d},idim1)<0.d0)
then
8293 erc=er({ix^d+i1kr^d})
8295 erc=0.5d0*(er(ix^d)+er({ix^d+i1kr^d}))
8297 fe(ix^d,idir)=fe(ix^d,idir)+0.25d0*(elc+erc)
8302 ixamax^d=ixcmax^d+i2kr^d;
8303 {
do ix^db=ixamin^db,ixamax^db\}
8304 el(ix^d)=-fc(ix^d,iwdim2,idim1)-ecc(ix^d,idir)
8305 er(ix^d)=-fc(ix^d,iwdim2,idim1)-ecc({ix^d+i1kr^d},idir)
8308 do ix^db=ixcmin^db,ixcmax^db\}
8309 if(vnorm(ix^d,idim2)>0.d0)
then
8311 else if(vnorm(ix^d,idim2)<0.d0)
then
8312 elc=el({ix^d+i2kr^d})
8314 elc=0.5d0*(el(ix^d)+el({ix^d+i2kr^d}))
8316 if(vnorm({ix^d+i1kr^d},idim2)>0.d0)
then
8318 else if(vnorm({ix^d+i1kr^d},idim2)<0.d0)
then
8319 erc=er({ix^d+i2kr^d})
8321 erc=0.5d0*(er(ix^d)+er({ix^d+i2kr^d}))
8323 fe(ix^d,idir)=fe(ix^d,idir)+0.25d0*(elc+erc)
8327 if(
mhd_eta/=zero) fe(ix^d,idir)=fe(ix^d,idir)+e_resi(ix^d,idir)
8332 fe(ix^d,idir)=fe(ix^d,idir)*qdt*s%dsC(ix^d,idir)
8346 if (lvc(idim1,idim2,idir)==0) cycle
8348 ixcmin^d=ixomin^d+kr(idir,^d)-1;
8349 ixamax^d=ixcmax^d-kr(idir,^d)+1;
8352 xs(ixa^s,:)=x(ixa^s,:)
8353 xs(ixa^s,idim2)=x(ixa^s,idim2)+half*s%dx(ixa^s,idim2)
8354 call gradientf(wcts(ixgs^t,idim2),xs,ixgs^ll,ixc^l,idim1,gradi)
8355 if (lvc(idim1,idim2,idir)==1)
then
8356 jce(ixc^s,idir)=jce(ixc^s,idir)+gradi(ixc^s)
8358 jce(ixc^s,idir)=jce(ixc^s,idir)-gradi(ixc^s)
8365 ixcmin^d=ixomin^d+kr(idir,^d)-1;
8367 ein(ixc^s,idir)=ein(ixc^s,idir)*jce(ixc^s,idir)
8371 {
do ix^db=ixomin^db,ixomax^db\}
8372 jce(ix^d,idir)=0.25d0*(ein(ix^d,idir)+ein(ix1,ix2-1,ix3,idir)+ein(ix1,ix2,ix3-1,idir)&
8373 +ein(ix1,ix2-1,ix3-1,idir))
8374 if(jce(ix^d,idir)<0.d0) jce(ix^d,idir)=0.d0
8375 w(ix^d,
e_)=w(ix^d,
e_)+qdt*jce(ix^d,idir)
8377 else if(idir==2)
then
8378 {
do ix^db=ixomin^db,ixomax^db\}
8379 jce(ix^d,idir)=0.25d0*(ein(ix^d,idir)+ein(ix1-1,ix2,ix3,idir)+ein(ix1,ix2,ix3-1,idir)&
8380 +ein(ix1-1,ix2,ix3-1,idir))
8381 if(jce(ix^d,idir)<0.d0) jce(ix^d,idir)=0.d0
8382 w(ix^d,
e_)=w(ix^d,
e_)+qdt*jce(ix^d,idir)
8385 {
do ix^db=ixomin^db,ixomax^db\}
8386 jce(ix^d,idir)=0.25d0*(ein(ix^d,idir)+ein(ix1-1,ix2,ix3,idir)+ein(ix1,ix2-1,ix3,idir)&
8387 +ein(ix1-1,ix2-1,ix3,idir))
8388 if(jce(ix^d,idir)<0.d0) jce(ix^d,idir)=0.d0
8389 w(ix^d,
e_)=w(ix^d,
e_)+qdt*jce(ix^d,idir)
8395 {
do ix^db=ixomin^db,ixomax^db\}
8396 jce(ix^d,idir)=0.25d0*(ein(ix^d,idir)+ein(ix1-1,ix2,idir)+ein(ix1,ix2-1,idir)&
8397 +ein(ix1-1,ix2-1,idir))
8398 if(jce(ix^d,idir)<0.d0) jce(ix^d,idir)=0.d0
8399 w(ix^d,
e_)=w(ix^d,
e_)+qdt*jce(ix^d,idir)
8410 if(
associated(usr_set_electric_field)) &
8411 call usr_set_electric_field(ixi^l,ixo^l,qt,qdt,fe,sct)
8413 circ(ixi^s,1:ndim)=zero
8418 ixcmin^d=ixomin^d-kr(idim1,^d);
8420 ixa^l=ixc^l-kr(idim2,^d);
8423 if(lvc(idim1,idim2,idir)==1)
then
8425 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
8428 else if(lvc(idim1,idim2,idir)==-1)
then
8430 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
8436 {
do ix^db=ixcmin^db,ixcmax^db\}
8438 if(s%surfaceC(ix^d,idim1) > smalldouble)
then
8440 bfaces(ix^d,idim1)=bfaces(ix^d,idim1)-circ(ix^d,idim1)/s%surfaceC(ix^d,idim1)
8447 end subroutine mhd_update_faces_contact
8450 subroutine mhd_update_faces_hll(ixI^L,ixO^L,qt,qdt,wp,fC,fE,sCT,s,vcts)
8455 integer,
intent(in) :: ixi^
l, ixo^
l
8456 double precision,
intent(in) :: qt, qdt
8458 double precision,
intent(in) :: wp(ixi^s,1:nw)
8459 type(state) :: sct, s
8460 type(ct_velocity) :: vcts
8461 double precision,
intent(in) :: fc(ixi^s,1:nwflux,1:
ndim)
8462 double precision,
intent(inout) :: fe(ixi^s,
sdim:3)
8464 double precision :: vtill(ixi^s,2)
8465 double precision :: vtilr(ixi^s,2)
8466 double precision :: bfacetot(ixi^s,
ndim)
8467 double precision :: btill(ixi^s,
ndim)
8468 double precision :: btilr(ixi^s,
ndim)
8469 double precision :: cp(ixi^s,2)
8470 double precision :: cm(ixi^s,2)
8471 double precision :: circ(ixi^s,1:
ndim)
8473 double precision,
dimension(ixI^S,sdim:3) :: e_resi, e_ambi
8474 integer :: hxc^
l,ixc^
l,ixcp^
l,jxc^
l,ixcm^
l
8475 integer :: idim1,idim2,idir,ix^
d
8477 associate(bfaces=>s%ws,bfacesct=>sct%ws,x=>s%x,vbarc=>vcts%vbarC,cbarmin=>vcts%cbarmin,&
8478 cbarmax=>vcts%cbarmax)
8491 if(
mhd_eta/=zero)
call get_resistive_electric_field(ixi^
l,ixo^
l,wp,sct,s,e_resi)
8507 ixcmin^
d=ixomin^
d-1+
kr(idir,^
d);
8511 idim2=mod(idir+1,3)+1
8513 jxc^
l=ixc^
l+
kr(idim1,^
d);
8514 ixcp^
l=ixc^
l+
kr(idim2,^
d);
8518 vtill(ixi^s,2),vtilr(ixi^s,2))
8521 vtill(ixi^s,1),vtilr(ixi^s,1))
8527 bfacetot(ixi^s,idim1)=bfacesct(ixi^s,idim1)+
block%B0(ixi^s,idim1,idim1)
8528 bfacetot(ixi^s,idim2)=bfacesct(ixi^s,idim2)+
block%B0(ixi^s,idim2,idim2)
8530 bfacetot(ixi^s,idim1)=bfacesct(ixi^s,idim1)
8531 bfacetot(ixi^s,idim2)=bfacesct(ixi^s,idim2)
8534 btill(ixi^s,idim1),btilr(ixi^s,idim1))
8537 btill(ixi^s,idim2),btilr(ixi^s,idim2))
8541 cm(ixc^s,1)=max(cbarmin(ixcp^s,idim1),cbarmin(ixc^s,idim1))
8542 cp(ixc^s,1)=max(cbarmax(ixcp^s,idim1),cbarmax(ixc^s,idim1))
8544 cm(ixc^s,2)=max(cbarmin(jxc^s,idim2),cbarmin(ixc^s,idim2))
8545 cp(ixc^s,2)=max(cbarmax(jxc^s,idim2),cbarmax(ixc^s,idim2))
8549 fe(ixc^s,idir)=-(cp(ixc^s,1)*vtill(ixc^s,1)*btill(ixc^s,idim2) &
8550 + cm(ixc^s,1)*vtilr(ixc^s,1)*btilr(ixc^s,idim2) &
8551 - cp(ixc^s,1)*cm(ixc^s,1)*(btilr(ixc^s,idim2)-btill(ixc^s,idim2)))&
8552 /(cp(ixc^s,1)+cm(ixc^s,1)) &
8553 +(cp(ixc^s,2)*vtill(ixc^s,2)*btill(ixc^s,idim1) &
8554 + cm(ixc^s,2)*vtilr(ixc^s,2)*btilr(ixc^s,idim1) &
8555 - cp(ixc^s,2)*cm(ixc^s,2)*(btilr(ixc^s,idim1)-btill(ixc^s,idim1)))&
8556 /(cp(ixc^s,2)+cm(ixc^s,2))
8559 if(
mhd_eta/=zero) fe(ixc^s,idir)=fe(ixc^s,idir)+e_resi(ixc^s,idir)
8563 fe(ixc^s,idir)=qdt*s%dsC(ixc^s,idir)*fe(ixc^s,idir)
8577 circ(ixi^s,1:
ndim)=zero
8582 ixcmin^
d=ixomin^
d-
kr(idim1,^
d);
8586 if(
lvc(idim1,idim2,idir)/=0)
then
8587 hxc^
l=ixc^
l-
kr(idim2,^
d);
8589 circ(ixc^s,idim1)=circ(ixc^s,idim1)&
8590 +
lvc(idim1,idim2,idir)&
8596 {
do ix^db=ixcmin^db,ixcmax^db\}
8598 if(s%surfaceC(ix^
d,idim1) > smalldouble)
then
8600 bfaces(ix^
d,idim1)=bfaces(ix^
d,idim1)-circ(ix^
d,idim1)/s%surfaceC(ix^
d,idim1)
8606 end subroutine mhd_update_faces_hll
8609 subroutine get_resistive_electric_field(ixI^L,ixO^L,wp,sCT,s,jce)
8614 integer,
intent(in) :: ixi^
l, ixo^
l
8616 double precision,
intent(in) :: wp(ixi^s,1:nw)
8617 type(state),
intent(in) :: sct, s
8619 double precision :: jce(ixi^s,
sdim:3)
8622 double precision :: jcc(ixi^s,7-2*
ndir:3)
8624 double precision :: xs(ixgs^t,1:
ndim)
8626 double precision :: eta(ixi^s)
8627 double precision :: gradi(ixgs^t)
8628 integer :: ix^
d,ixc^
l,ixa^
l,ixb^
l,idir,idirmin,idim1,idim2
8630 associate(x=>s%x,
dx=>s%dx,w=>s%w,wct=>sct%w,wcts=>sct%ws)
8636 if (
lvc(idim1,idim2,idir)==0) cycle
8638 ixcmin^
d=ixomin^
d+
kr(idir,^
d)-1;
8639 ixbmax^
d=ixcmax^
d-
kr(idir,^
d)+1;
8642 xs(ixb^s,:)=x(ixb^s,:)
8643 xs(ixb^s,idim2)=x(ixb^s,idim2)+half*
dx(ixb^s,idim2)
8644 call gradientf(wcts(ixgs^t,idim2),xs,ixgs^
ll,ixc^
l,idim1,gradi,2)
8645 if (
lvc(idim1,idim2,idir)==1)
then
8646 jce(ixc^s,idir)=jce(ixc^s,idir)+gradi(ixc^s)
8648 jce(ixc^s,idir)=jce(ixc^s,idir)-gradi(ixc^s)
8655 jce(ixi^s,:)=jce(ixi^s,:)*
mhd_eta
8663 ixcmin^
d=ixomin^
d+
kr(idir,^
d)-1;
8664 jcc(ixc^s,idir)=0.d0
8666 if({ ix^
d==1 .and. ^
d==idir | .or.}) cycle
8667 ixamin^
d=ixcmin^
d+ix^
d;
8668 ixamax^
d=ixcmax^
d+ix^
d;
8669 jcc(ixc^s,idir)=jcc(ixc^s,idir)+eta(ixa^s)
8671 jcc(ixc^s,idir)=jcc(ixc^s,idir)*0.25d0
8672 jce(ixc^s,idir)=jce(ixc^s,idir)*jcc(ixc^s,idir)
8677 end subroutine get_resistive_electric_field
8680 subroutine get_ambipolar_electric_field(ixI^L,ixO^L,w,x,fE)
8683 integer,
intent(in) :: ixi^
l, ixo^
l
8684 double precision,
intent(in) :: w(ixi^s,1:nw)
8685 double precision,
intent(in) :: x(ixi^s,1:
ndim)
8686 double precision,
intent(out) :: fe(ixi^s,
sdim:3)
8688 double precision :: jxbxb(ixi^s,1:3)
8689 integer :: idir,ixa^
l,ixc^
l,ix^
d
8692 call mhd_get_jxbxb(w,x,ixi^
l,ixa^
l,jxbxb)
8699 ixcmin^
d=ixomin^
d+
kr(idir,^
d)-1;
8702 if({ ix^
d==1 .and. ^
d==idir | .or.}) cycle
8703 ixamin^
d=ixcmin^
d+ix^
d;
8704 ixamax^
d=ixcmax^
d+ix^
d;
8705 fe(ixc^s,idir)=fe(ixc^s,idir)+jxbxb(ixa^s,idir)
8707 fe(ixc^s,idir)=fe(ixc^s,idir)*0.25d0
8710 end subroutine get_ambipolar_electric_field
8716 integer,
intent(in) :: ixo^
l
8726 do ix^db=ixomin^db,ixomax^db\}
8728 s%w(ix^
d,b1_)=half/s%surface(ix^
d,1)*(s%ws(ix^
d,1)*s%surfaceC(ix^
d,1)&
8729 +s%ws(ix1-1,ix2,ix3,1)*s%surfaceC(ix1-1,ix2,ix3,1))
8730 s%w(ix^
d,b2_)=half/s%surface(ix^
d,2)*(s%ws(ix^
d,2)*s%surfaceC(ix^
d,2)&
8731 +s%ws(ix1,ix2-1,ix3,2)*s%surfaceC(ix1,ix2-1,ix3,2))
8732 s%w(ix^
d,b3_)=half/s%surface(ix^
d,3)*(s%ws(ix^
d,3)*s%surfaceC(ix^
d,3)&
8733 +s%ws(ix1,ix2,ix3-1,3)*s%surfaceC(ix1,ix2,ix3-1,3))
8736 s%w(ix^
d,b1_)=half/s%surface(ix^
d,1)*(s%ws(ix^
d,1)*s%surfaceC(ix^
d,1)&
8737 +s%ws(ix1-1,ix2,1)*s%surfaceC(ix1-1,ix2,1))
8738 s%w(ix^
d,b2_)=half/s%surface(ix^
d,2)*(s%ws(ix^
d,2)*s%surfaceC(ix^
d,2)&
8739 +s%ws(ix1,ix2-1,2)*s%surfaceC(ix1,ix2-1,2))
8782 integer,
intent(in) :: ixis^
l, ixi^
l, ixo^
l
8783 double precision,
intent(inout) :: ws(ixis^s,1:nws)
8784 double precision,
intent(in) :: x(ixi^s,1:
ndim)
8786 double precision :: adummy(ixis^s,1:3)
8792 subroutine rfactor_from_temperature_ionization(w,x,ixI^L,ixO^L,Rfactor)
8795 integer,
intent(in) :: ixi^
l, ixo^
l
8796 double precision,
intent(in) :: w(ixi^s,1:nw)
8797 double precision,
intent(in) :: x(ixi^s,1:
ndim)
8798 double precision,
intent(out):: rfactor(ixi^s)
8800 double precision :: iz_h(ixo^s),iz_he(ixo^s)
8804 rfactor(ixo^s)=(1.d0+iz_h(ixo^s)+0.1d0*(1.d0+iz_he(ixo^s)*(1.d0+iz_he(ixo^s))))/(2.d0+3.d0*
he_abundance)
8806 end subroutine rfactor_from_temperature_ionization
8808 subroutine rfactor_from_constant_ionization(w,x,ixI^L,ixO^L,Rfactor)
8810 integer,
intent(in) :: ixi^
l, ixo^
l
8811 double precision,
intent(in) :: w(ixi^s,1:nw)
8812 double precision,
intent(in) :: x(ixi^s,1:
ndim)
8813 double precision,
intent(out):: rfactor(ixi^s)
8817 end subroutine rfactor_from_constant_ionization
Module to include CAK radiation line force in (magneto)hydrodynamic models Computes both the force fr...
subroutine cak_init(phys_gamma)
Initialize the module.
subroutine cak_get_dt(wprim, ixil, ixol, dtnew, dxd, x)
Check time step for total radiation contribution.
subroutine cak_add_source(qdt, ixil, ixol, wct, w, x, energy, qsourcesplit, active)
w[iw]=w[iw]+qdt*S[wCT,qtC,x] where S is the source based on wCT within ixO
subroutine, public mpistop(message)
Exit MPI-AMRVAC with an error message.
Module for physical and numeric constants.
double precision, parameter bigdouble
A very large real number.
subroutine reconstruct(ixil, ixcl, idir, q, ql, qr)
Reconstruct scalar q within ixO^L to 1/2 dx in direction idir Return both left and right reconstructe...
subroutine b_from_vector_potentiala(ixisl, ixil, ixol, ws, x, a)
calculate magnetic field from vector potential A at cell edges
subroutine add_convert_method(phys_convert_vars, nwc, dataset_names, file_suffix)
Module for flux conservation near refinement boundaries.
subroutine, public store_flux(igrid, fc, idimlim, nwfluxin)
subroutine, public store_edge(igrid, ixil, fe, idimlim)
Module for flux limited diffusion (FLD)-approximation in Radiation-(Magneto)hydrodynamics simulations...
subroutine, public fld_get_radpress(w, x, ixil, ixol, rad_pressure)
Returns Radiation Pressure as tensor NOTE: w is primitive on entry.
double precision, public fld_bisect_tol
Tolerance for bisection method for Energy sourceterms This is a percentage of the minimum of gas- and...
double precision, public fld_diff_tol
Tolerance for radiative Energy diffusion.
double precision, public fld_gamma
A copy of (m)hd_gamma.
character(len=40) fld_fluxlimiter
flux limiter choice
character(len=40) fld_opal_table
double precision, public fld_kappa0
Opacity value when using constant opacity.
character(len=40) fld_opacity_law
switches for opacity
character(len=40) fld_interaction_method
Which method to find the root for the energy interaction polynomial.
subroutine, public add_fld_rad_force(qdt, ixil, ixol, wct, wctprim, w, x, qsourcesplit, active)
w[iw]=w[iw]+qdt*S[wCT,qtC,x] where S is the source based on wCT within ixO This subroutine handles th...
logical fld_radforce_split
source split for energy interact and radforce:
subroutine, public fld_init(r_gamma)
Initialising FLD-module Read opacities Initialise Multigrid and adimensionalise kappa.
subroutine, public fld_radforce_get_dt(w, ixil, ixol, dtnew, dxd, x)
get dt limit for radiation force and FLD explicit source additions NOTE: w is primitive on entry
integer nth_for_diff_mg
diffusion coefficient stencil control
Module with basic grid data structures.
type(tree_node_ptr), dimension(:,:), allocatable, save igrid_to_node
Array to go from an [igrid, ipe] index to a node pointer.
subroutine, public get_divb(w, ixil, ixol, divb, nth_in)
Calculate div B within ixO.
integer, dimension(:), allocatable, public mag
Indices of the magnetic field.
Module with geometry-related routines (e.g., divergence, curl)
subroutine divvector(qvec, ixil, ixol, divq, nth_in)
subroutine laplacian_of_vector(qvec, ixil, ixol, lapl_qvec)
integer, parameter cylindrical
subroutine curlvector(qvec, ixil, ixol, curlvec, idirmin, idirmin0, ndir0, fourthorder)
Calculate curl of a vector qvec within ixL Options to employ standard second order CD evaluations use...
subroutine gradient(q, ixil, ixol, idir, gradq, nth_in)
subroutine gradientf(q, x, ixil, ixol, idir, gradq, nth_in, pm_in)
subroutine gradientl(q, ixil, ixol, idir, gradq)
This module contains definitions of global parameters and variables and some generic functions/subrou...
type(state), pointer block
Block pointer for using one block and its previous state.
double precision const_kappae
double precision arad_norm
Normalised radiation constant.
double precision dtdiffpar
For resistive MHD, the time step is also limited by the diffusion time: .
character(len=std_len) typegrad
double precision unit_charge
Physical scaling factor for charge.
double precision small_pressure
integer ixghi
Upper index of grid block arrays.
pure subroutine cross_product(ixil, ixol, a, b, axb)
Cross product of two vectors.
integer, dimension(3, 3, 3) lvc
Levi-Civita tensor.
double precision unit_time
Physical scaling factor for time.
double precision unit_density
Physical scaling factor for density.
double precision unit_opacity
Physical scaling factor for Opacity.
integer, parameter unitpar
file handle for IO
integer, parameter bc_asymm
double precision unit_mass
Physical scaling factor for mass.
logical use_imex_scheme
whether IMEX in use or not
integer, dimension(3, 3) kr
Kronecker delta tensor.
double precision phys_trac_mask
integer, dimension(:, :), allocatable typeboundary
Array indicating the type of boundary condition per variable and per physical boundary.
double precision unit_numberdensity
Physical scaling factor for number density.
character(len=std_len) convert_type
Which format to use when converting.
double precision unit_pressure
Physical scaling factor for pressure.
integer, parameter ndim
Number of spatial dimensions for grid variables.
double precision unit_length
Physical scaling factor for length.
logical stagger_grid
True for using stagger grid.
double precision const_rad_a
Physical factors useful for radiation fld.
double precision cmax_global
global fastest wave speed needed in fd scheme and glm method
logical use_particles
Use particles module or not.
character(len=std_len), dimension(:), allocatable par_files
Which par files are used as input.
integer icomm
The MPI communicator.
double precision bdip
amplitude of background dipolar, quadrupolar, octupolar, user's field
integer b0i
background magnetic field location indicator
integer mype
The rank of the current MPI task.
double precision, dimension(:), allocatable, parameter d
logical local_timestep
each cell has its own timestep or not
integer ndir
Number of spatial dimensions (components) for vector variables.
integer ixm
the mesh range of a physical block without ghost cells
integer ierrmpi
A global MPI error return code.
logical autoconvert
If true, already convert to output format during the run.
logical slab
Cartesian geometry or not.
integer, parameter bc_periodic
integer, parameter bc_special
boundary condition types
double precision unit_magneticfield
Physical scaling factor for magnetic field.
double precision const_sigmasb
integer nwauxio
Number of auxiliary variables that are only included in output.
double precision unit_velocity
Physical scaling factor for velocity.
double precision small_r_e
double precision c_norm
Normalised speed of light.
logical b0field
split magnetic field as background B0 field
double precision, dimension(:,:), allocatable rnode
Corner coordinates.
double precision unit_temperature
Physical scaling factor for temperature.
double precision unit_radflux
Physical scaling factor for radiation flux.
integer, parameter bc_cont
logical si_unit
Use SI units (.true.) or use cgs units (.false.)
double precision, dimension(:,:), allocatable dx
spatial steps for all dimensions at all levels
integer nghostcells
Number of ghost cells surrounding a grid.
integer, parameter sdim
starting dimension for electric field
integer, parameter bc_symm
logical phys_trac
Use TRAC for MHD or 1D HD.
logical need_global_cmax
need global maximal wave speed
logical convert
If true and restart_from_file is given, convert snapshots to other file formats.
logical fix_small_values
fix small values with average or replace methods
double precision, dimension(^nd) dxlevel
store unstretched cell size of current level
logical use_multigrid
Use multigrid (only available in 2D and 3D)
logical slab_uniform
uniform Cartesian geometry or not (stretched Cartesian)
double precision small_density
integer max_blocks
The maximum number of grid blocks in a processor.
integer r_
Indices for cylindrical coordinates FOR TESTS, negative value when not used:
integer boundspeed
bound (left/min and right.max) speed of Riemann fan
integer phys_trac_finegrid
integer, parameter unitconvert
double precision unit_erad
Physical scaling factor for radiation energy density.
integer number_equi_vars
number of equilibrium set variables, besides the mag field
integer, parameter ixglo
Lower index of grid block arrays (always 1)
Module for including gravity in (magneto)hydrodynamics simulations.
subroutine gravity_get_dt(wprim, ixil, ixol, dtnew, dxd, x)
subroutine gravity_init()
Initialize the module.
subroutine gravity_add_source(qdt, ixil, ixol, wct, wctprim, w, x, energy, qsourcesplit, active)
w[iw]=w[iw]+qdt*S[wCT,qtC,x] where S is the source based on wCT within ixO
module ionization degree - get ionization degree for given temperature
subroutine ionization_degree_from_temperature(ixil, ixol, te, iz_h, iz_he)
subroutine ionization_degree_init()
module mod_magnetofriction.t Purpose: use magnetofrictional method to relax 3D magnetic field to forc...
subroutine magnetofriction_init()
Initialize the module.
Magneto-hydrodynamics module.
subroutine, public mhd_get_trad(w, x, ixil, ixol, trad)
Calculates radiation temperature.
integer, public, protected c_
logical, public, protected mhd_gravity
Whether gravity is added.
integer, public, protected fip_
Index of the FIP passive scalar rho*fip in conserved form, fip in primitive form.
logical, public, protected mhd_internal_e
Whether internal energy is solved instead of total energy.
logical, public, protected mhd_glm_extended
Whether extended GLM-MHD is used with additional sources.
logical, public mhd_hyperbolic_tc_constant
character(len=std_len), public, protected type_ct
Method type of constrained transport.
integer, dimension(:), allocatable, public, protected mom
Indices of the momentum density.
subroutine, public mhd_clean_divb_multigrid(qdt, qt, active)
integer, public, protected qpar_
Index of the field-aligned heat flux q_parallel.
logical, public, protected mhd_radiative_cooling
Whether radiative cooling is added.
subroutine, public mhd_e_to_ei(ixil, ixol, w, x)
Transform total energy to internal energy.
double precision, public mhd_adiab
The adiabatic constant.
logical, public, protected mhd_partial_ionization
Whether plasma is partially ionized.
double precision, public divbdiff
Coefficient of diffusive divB cleaning.
double precision, public mhd_eta_hyper
The MHD hyper-resistivity.
double precision, public, protected mhd_hyperbolic_tc_bmin
Field-strength transition scale for perpendicular closure.
subroutine, public mhd_get_temperature_from_prim(w, x, ixil, ixol, res)
Calculate temperature=p/rho when in e_ the pressure p_ (primitive) is stored.
double precision, public, protected rr
double precision, public, protected h_ion_fr
Ionization fraction of H H_ion_fr = H+/(H+ + H)
double precision, public mhd_gamma
The adiabatic index.
integer, public, protected mhd_trac_finegrid
Distance between two adjacent traced magnetic field lines (in finest cell size)
subroutine, public get_normalized_divb(w, ixil, ixol, divb)
get dimensionless div B = |divB| * volume / area / |B|
logical, public numerical_resistive_heating
Whether numerical resistive heating is included when solving partial energy equation.
type(tc_fluid), allocatable, public tc_fl
type of fluid for thermal conduction
logical, public, protected mhd_rotating_frame
Whether rotating frame is activated.
logical, public, protected mhd_semirelativistic
Whether semirelativistic MHD equations (Gombosi 2002 JCP) are solved.
integer, public, protected mhd_divb_nth
Whether divB is computed with a fourth order approximation.
integer, public, protected mhd_n_tracer
Number of tracer species.
integer, public, protected te_
Indices of temperature.
integer, public, protected m
integer, public equi_rho0_
equi vars indices in the stateequi_vars array
integer, public, protected mhd_trac_type
Which TRAC method is used.
logical, public, protected mhd_cak_force
Whether CAK radiation line force is activated.
logical, public, protected source_split_divb
Whether divB cleaning sources are added splitting from fluid solver.
logical, public, protected mhd_hall
Whether Hall-MHD is used.
type(te_fluid), allocatable, public te_fl_mhd
type of fluid for thermal emission synthesis
logical, public, protected mhd_ambipolar
Whether Ambipolar term is used.
logical, public, protected mhd_hyperbolic_tc
Whether thermal conduction is used.
logical, public, protected mhd_hyperbolic_tc_sat
Whether saturation is considered for hyperbolic TC.
double precision, public, protected mhd_hyperbolic_tc_kappa_perp_factor
Relative perpendicular hyperbolic-TC coefficient in fixed/strong-field limit: kappa_perp0 = mhd_hyper...
logical, public has_equi_rho_and_p
whether split off equilibrium density and pressure
double precision, public mhd_glm_alpha
GLM-MHD parameter: ratio of the diffusive and advective time scales for div b taking values within [0...
double precision function, dimension(ixo^s), public mhd_mag_en_all(w, ixil, ixol)
Compute 2 times total magnetic energy.
logical, public, protected mhd_radiation_fld
Whether radiation-gas interaction is handled using flux limited diffusion.
subroutine, public multiplyambicoef(ixil, ixol, res, w, x)
multiply res by the ambipolar coefficient The ambipolar coefficient is calculated as -mhd_eta_ambi/rh...
subroutine, public b_from_vector_potential(ixisl, ixil, ixol, ws, x)
calculate magnetic field from vector potential
double precision, public, protected he_ion_fr
Ionization fraction of He He_ion_fr = (He2+ + He+)/(He2+ + He+ + He)
logical, public, protected mhd_viscosity
Whether viscosity is added.
procedure(sub_get_pthermal), pointer, public mhd_get_rfactor
subroutine, public mhd_get_pradiation_from_prim(w, x, ixil, ixol, prad)
Calculate radiation pressure within ixO^L.
double precision, public, protected mhd_reduced_c
Reduced speed of light for semirelativistic MHD: 2% of light speed.
logical, public, protected mhd_energy
Whether an energy equation is used.
logical, public, protected mhd_ambipolar_exp
Whether Ambipolar term is implemented explicitly.
double precision, public mhd_hyperbolic_tc_kappa
The thermal conductivity kappa in hyperbolic thermal conduction.
logical, public, protected mhd_glm
Whether GLM-MHD is used to control div B.
logical, public clean_initial_divb
clean initial divB
procedure(sub_convert), pointer, public mhd_to_conserved
double precision, public mhd_eta
The MHD resistivity.
logical, public divbwave
Add divB wave in Roe solver.
logical, public, protected mhd_magnetofriction
Whether magnetofriction is added.
double precision, public, protected mhd_trac_mask
Height of the mask used in the TRAC method.
procedure(mask_subroutine), pointer, public usr_mask_ambipolar
character(len=std_len), public, protected typedivbfix
Method type to clean divergence of B.
subroutine, public mhd_get_temperature_from_etot(w, x, ixil, ixol, res)
Calculate temperature=p/rho from total energy.
logical, public, protected mhd_thermal_conduction
Whether thermal conduction is used.
procedure(sub_get_pthermal), pointer, public mhd_get_temperature
integer, public equi_pe0_
subroutine, public mhd_get_csrad2_prim(w, x, ixil, ixol, csound)
Calculate modified squared fast wave speed for FLD NOTE: w is primitive on entry here!...
integer, public, protected qperp_
Index of the perpendicular heat flux q_perp.
integer, public, protected p_
Index of the gas pressure (-1 if not present) should equal e_.
integer, public, protected c
Indices of the momentum density for the form of better vectorization.
double precision, public, protected he_ion_fr2
Ratio of number He2+ / number He+ + He2+ He_ion_fr2 = He2+/(He2+ + He+)
procedure(sub_convert), pointer, public mhd_to_primitive
logical, public, protected mhd_dump_full_vars
whether dump full variables (when splitting is used) in a separate dat file
logical, public, protected mhd_particles
Whether particles module is added.
integer, public, protected b
subroutine, public mhd_face_to_center(ixol, s)
calculate cell-center values from face-center values
logical, dimension(2 *^nd), public, protected boundary_divbfix
To control divB=0 fix for boundary.
subroutine, public get_current(w, ixil, ixol, idirmin, current)
Calculate idirmin and the idirmin:3 components of the common current array make sure that dxlevel(^D)...
double precision, public mhd_etah
Hall resistivity.
integer, public, protected mhd_hyperbolic_tc_perp_mode
Perpendicular hyperbolic-TC closure mode: 0 = off, 1 = fixed anisotropy, 2 = field-strength-dependent...
subroutine, public mhd_get_v(w, x, ixil, ixol, v)
Calculate v vector.
double precision, public mhd_eta_ambi
The MHD ambipolar coefficient.
logical, public, protected mhd_fip
Whether FIP passive scalar is enabled.
logical, public, protected mhd_hydrodynamic_e
Whether hydrodynamic energy is solved instead of total energy.
integer, public, protected r_e
Index of the radiation energy.
subroutine, public mhd_phys_init()
logical, public, protected mhd_trac
Whether TRAC method is used.
logical, public, protected eq_state_units
subroutine, public mhd_get_csrad2(w, x, ixil, ixol, csound)
Calculate modified squared sound speed for FLD NOTE: only for diagnostic purposes,...
subroutine, public mhd_get_pthermal_plus_pradiation(w, x, ixil, ixol, pth_plus_prad)
Calculates the sum of the gas pressure and the max Prad tensor element.
type(rc_fluid), allocatable, public rc_fl
type of fluid for radiative cooling
integer, dimension(:), allocatable, public, protected tracer
Indices of the tracers.
integer, public, protected rho_
Index of the density (in the w array)
logical, public, protected b0field_forcefree
B0 field is force-free.
integer, dimension(2 *^nd), public, protected boundary_divbfix_skip
To skip * layer of ghost cells during divB=0 fix for boundary.
integer, public, protected tweight_
logical, public, protected mhd_ambipolar_sts
Whether Ambipolar term is implemented using supertimestepping.
procedure(sub_get_pthermal), pointer, public mhd_get_pthermal
logical, public, protected mhd_hyperbolic_tc_use_perp
Whether the perpendicular hyperbolic-TC channel is enabled.
subroutine, public mhd_ei_to_e(ixil, ixol, w, x)
Transform internal energy to total energy.
integer, public, protected e_
Index of the energy density (-1 if not present)
double precision, public, protected he_abundance
Helium abundance over Hydrogen.
integer, public, protected tcoff_
Index of the cutoff temperature for the TRAC method.
subroutine, public mhd_get_rho(w, x, ixil, ixol, rho)
integer, public, protected psi_
Indices of the GLM psi.
logical, public mhd_equi_thermal
Module to couple the octree-mg library to AMRVAC. This file uses the VACPP preprocessor,...
type(mg_t) mg
Data structure containing the multigrid tree.
Module containing all the particle routines.
subroutine particles_init()
Initialize particle data and parameters.
This module defines the procedures of a physics module. It contains function pointers for the various...
module radiative cooling – add optically thin radiative cooling
subroutine radiative_cooling_init_params(phys_gamma, he_abund)
Radiative cooling initialization.
subroutine radiative_cooling_init(fl, read_params)
subroutine radiative_cooling_add_source(qdt, ixil, ixol, wct, wctprim, w, x, qsourcesplit, active, fl)
Module for including rotating frame in (magneto)hydrodynamics simulations The rotation vector is assu...
subroutine rotating_frame_add_source(qdt, dtfactor, ixil, ixol, wct, w, x)
w[iw]=w[iw]+qdt*S[wCT,qtC,x] where S is the source based on wCT within ixO
subroutine rotating_frame_init()
Initialize the module.
Module for handling problematic values in simulations, such as negative pressures.
subroutine, public small_values_average(ixil, ixol, w, x, w_flag, windex)
logical, public trace_small_values
trace small values in the source file using traceback flag of compiler
subroutine, public small_values_error(wprim, x, ixil, ixol, w_flag, subname)
logical, dimension(:), allocatable, public small_values_fix_iw
Whether to apply small value fixes to certain variables.
character(len=20), public small_values_method
How to handle small values.
Generic supertimestepping method which can be used for multiple source terms in the governing equatio...
subroutine, public add_sts_method(sts_getdt, sts_set_sources, startvar, nflux, startwbc, nwbc, evolve_b)
subroutine which added programatically a term to be calculated using STS Params: sts_getdt function c...
subroutine, public set_conversion_methods_to_head(sts_before_first_cycle, sts_after_last_cycle)
Set the hooks called before the first cycle and after the last cycle in the STS update This method sh...
subroutine, public set_error_handling_to_head(sts_error_handling)
Set the hook of error handling in the STS update. This method is called before updating the BC....
subroutine, public sts_init()
Initialize sts module.
Thermal conduction for HD and MHD or RHD and RMHD or twofl (plasma-neutral) module Adaptation of mod_...
double precision function, public get_tc_dt_mhd(w, ixil, ixol, dxd, x, fl)
Get the explicit timestep for the TC (mhd implementation) Note: for multi-D MHD (1D MHD will use HD f...
double precision function, public get_tc_dt_hd(w, ixil, ixol, dxd, x, fl)
Get the explicit timestep for the TC (hd implementation) Note: also used in 1D MHD (or for neutrals i...
subroutine tc_init_params(phys_gamma)
subroutine, public sts_set_source_tc_hd(ixil, ixol, w, x, wres, fix_conserve_at_step, my_dt, igrid, nflux, fl)
subroutine, public sts_set_source_tc_mhd(ixil, ixol, w, x, wres, fix_conserve_at_step, my_dt, igrid, nflux, fl)
anisotropic thermal conduction with slope limited symmetric scheme Sharma 2007 Journal of Computation...
subroutine, public tc_get_mhd_params(fl, read_mhd_params)
Init TC coefficients: MHD case.
subroutine get_euv_image(qunit, fl)
subroutine get_sxr_image(qunit, fl)
subroutine get_euv_spectrum(qunit, fl)
subroutine get_whitelight_image(qunit, fl)
Module with all the methods that users can customize in AMRVAC.
procedure(rfactor), pointer usr_rfactor
procedure(special_resistivity), pointer usr_special_resistivity
procedure(set_adiab), pointer usr_set_adiab
procedure(set_adiab), pointer usr_set_gamma
procedure(phys_gravity), pointer usr_gravity
procedure(set_equi_vars), pointer usr_set_equi_vars
procedure(set_electric_field), pointer usr_set_electric_field
The module add viscous source terms and check time step.
subroutine, public viscosity_get_dt(wprim, ixil, ixol, dtnew, dxd, x)
procedure(sub_add_source), pointer, public viscosity_add_source
subroutine, public viscosity_init(phys_wider_stencil)
Initialize the module.
The data structure that contains information about a tree node/grid block.