55 REAL,
PARAMETER :: tsim = 2.0e-2
59 REAL,
PARAMETER :: re = 1.0e+4
60 REAL,
PARAMETER :: ma = 1.0e+2
61 REAL,
PARAMETER :: mdisk = 1.0e-2
63 REAL,
PARAMETER :: rhomin = 1.0e-20
66 INTEGER,
PARAMETER :: vistype = powerlaw
67 REAL,
PARAMETER :: pl_exp = 0.0
68 REAL,
PARAMETER :: tvis = 4./3.*re
69 REAL,
PARAMETER :: tinit = 1.0e-3
81 INTEGER,
PARAMETER :: mgeo = cylindrical
84 INTEGER,
PARAMETER :: xres = 400
85 INTEGER,
PARAMETER :: yres = 1
86 INTEGER,
PARAMETER :: zres = 1
87 REAL,
PARAMETER :: rmin = 0.05
88 REAL,
PARAMETER :: rmax = 2.0
89 REAL,
PARAMETER :: gpar = 1.0
91 INTEGER,
PARAMETER :: onum = 10
92 CHARACTER(LEN=256),
PARAMETER &
94 CHARACTER(LEN=256),
PARAMETER &
97 REAL,
PARAMETER :: csiso = 1./ma
102 CLASS(
fosite),
ALLOCATABLE :: sim
103 REAL,
DIMENSION(:),
ALLOCATABLE :: sigma
104 REAL :: sum_numer, sum_denom
105 INTEGER :: n,den,vx,vy
106 REAL :: next_output_time
112 CALL sim%InitFosite()
115 IF (sim%GetRank().EQ.0)
THEN 124 CALL initdata(sim,sim%Mesh, sim%Physics, sim%Timedisc)
125 next_output_time = sim%Datafile%time
126 IF (
ASSOCIATED(sim%Timedisc%solution))
THEN 128 DO WHILE((sim%Timedisc%maxiter.LE.0).OR.(sim%iter.LE.sim%Timedisc%maxiter))
131 IF (next_output_time.LT.sim%Datafile%time)
THEN 133 next_output_time = sim%Datafile%time
134 SELECT TYPE(pvar => sim%Timedisc%solution)
135 TYPE IS (statevector_eulerisotherm)
137 DO j=sim%Mesh%JMIN,sim%Mesh%JMAX
138 DO i=sim%Mesh%IMIN,sim%Mesh%IMAX
139 IF (vistype.EQ.beta)
THEN 141 sim%Mesh%radius%bcenter(i,j,k), &
142 pvar%density%data3d(i,j,k),pvar%velocity%data4d(i,j,k,1))
145 sim%Mesh%radius%bcenter(i,j,k), &
146 pvar%density%data3d(i,j,k),pvar%velocity%data4d(i,j,k,1))
154 CALL sim%Error(
"pringle",
"computation of analytical solution requires GSL support")
159 ok = .NOT.sim%aborted
160 ALLOCATE(sigma(sim%Physics%VNUM))
162 IF (
ASSOCIATED(sim%Timedisc%solution))
THEN 163 DO n=1,sim%Physics%VNUM
166 sum_numer = sum(abs(sim%Timedisc%pvar%data4d(sim%Mesh%IMIN:sim%Mesh%IMAX,&
167 sim%Mesh%JMIN:sim%Mesh%JMAX,sim%Mesh%KMIN:sim%Mesh%KMAX,n) &
168 -sim%Timedisc%solution%data4d(sim%Mesh%IMIN:sim%Mesh%IMAX,&
169 sim%Mesh%JMIN:sim%Mesh%JMAX,sim%Mesh%KMIN:sim%Mesh%KMAX,n)))
170 sum_denom = sum(abs(sim%Timedisc%solution%data4d(sim%Mesh%IMIN:sim%Mesh%IMAX,&
171 sim%Mesh%JMIN:sim%Mesh%JMAX,sim%Mesh%KMIN:sim%Mesh%KMAX,n)))
173 IF (sim%GetRank().GT.0)
THEN 174 CALL mpi_reduce(sum_numer,sum_numer,1,default_mpi_real,mpi_sum,0,mpi_comm_world,sim%ierror)
175 CALL mpi_reduce(sum_denom,sum_denom,1,default_mpi_real,mpi_sum,0,mpi_comm_world,sim%ierror)
177 CALL mpi_reduce(mpi_in_place,sum_numer,1,default_mpi_real,mpi_sum,0,mpi_comm_world,sim%ierror)
178 CALL mpi_reduce(mpi_in_place,sum_denom,1,default_mpi_real,mpi_sum,0,mpi_comm_world,sim%ierror)
180 sigma(n) = sum_numer / sum_denom
189 den = sim%Physics%DENSITY
190 vx = sim%Physics%XVELOCITY
191 vy = sim%Physics%YVELOCITY
194 IF (sim%GetRank().EQ.0)
THEN 196 tap_check(ok,
"stoptime reached")
198 tap_check_small(sigma(den),5.0e-02,
"density deviation < 5%")
199 tap_check_small(sigma(vx),8.0e-02,
"radial velocity deviation < 8%")
201 tap_check_small(sigma(vy),2.0e-04,
"azimuthal velocity deviation < 0.02%")
207 IF (
ALLOCATED(sigma))
DEALLOCATE(sigma)
218 TYPE(Dict_TYP),
POINTER :: config
222 TYPE(Dict_TYP),
POINTER :: mesh, physics, boundary, datafile, &
223 grav, vis, timedisc, fluxes, sources
224 REAL :: x1,x2,y1,y2,z1,z2,cvis
245 bc(bottom) = no_gradients
246 bc(top) = no_gradients
249 cvis = (xres/1207.0)**1.9
257 bc(west) = no_gradients
258 bc(east) = no_gradients
261 bc(bottom) = no_gradients
262 bc(top) = no_gradients
275 bc(south) = no_gradients
276 bc(north) = no_gradients
277 bc(bottom) = periodic
281 cvis = (xres/1207.0)**1.9
283 CALL sim%Error(
"pringle::MakeConfig",
"mesh geometry not supported for Pringle disk")
288 "meshtype" / midpoint, &
305 "western" / bc(west), &
306 "eastern" / bc(east), &
307 "southern" / bc(south), &
308 "northern" / bc(north), &
309 "bottomer" / bc(bottom), &
315 "problem" / euler_isotherm, &
316 "units" / geometrical, &
323 "variables" / primitive, &
324 "limiter" / vanleer, &
329 "stype" / viscosity, &
330 "vismodel" / vistype, &
331 "dynconst" / (1./re), &
332 "exponent" / pl_exp, &
338 "pmass/gtype"/ pointmass, &
339 "pmass/mass" / 1.0, &
342 "pmass/outbound" / 0)
352 "stoptime" / (tsim * tvis), &
354 "dtlimit" / (1e-10 * tvis), &
356 "maxiter" / 100000000, &
358 "tol_abs" / (/0.0,1e-5,0.0/))
362 IF (mgeo.EQ.cylindrical) &
363 CALL setattr(timedisc,
"output/solution",1)
369 "filename" / (trim(odir) // trim(ofname)), &
374 "physics" / physics, &
375 "boundary" / boundary, &
377 "sources" / sources, &
378 "timedisc" / timedisc, &
379 "datafile" / datafile)
382 SUBROUTINE initdata(Sim,Mesh,Physics,Timedisc)
385 CLASS(fosite),
INTENT(INOUT) :: Sim
386 CLASS(physics_base),
INTENT(IN) :: Physics
387 CLASS(mesh_base),
INTENT(IN) :: Mesh
388 CLASS(timedisc_base),
INTENT(INOUT) :: Timedisc
391 CLASS(sources_base),
POINTER :: sp
392 CLASS(sources_gravity),
POINTER :: gp
394 REAL,
DIMENSION(Mesh%IGMIN:Mesh%IGMAX,Mesh%JGMIN:Mesh%JGMAX,Mesh%KGMIN:Mesh%KGMAX,3) &
396 REAL,
DIMENSION(Mesh%IGMIN:Mesh%IGMAX,Mesh%JGMIN:Mesh%JGMAX,Mesh%KGMIN:Mesh%KGMAX) :: radius
397 REAL :: r,vr,vphi,sden,mu
398 CHARACTER(LEN=64) :: value
400 IF (abs(x0).LE.tiny(x0).AND.abs(y0).LE.tiny(y0))
THEN 402 radius(:,:,:) = mesh%radius%bcenter(:,:,:)
403 posvec(:,:,:,:) = mesh%posvec%bcenter(:,:,:,:)
410 CALL mesh%Geometry%Convert2Curvilinear(mesh%bcenter,posvec,posvec)
414 posvec(:,:,:,:) = mesh%posvec%bcenter(:,:,:,:) - posvec(:,:,:,:)
416 radius(:,:,:) = sqrt(posvec(:,:,:,1)**2+posvec(:,:,:,2)**2+posvec(:,:,:,3)**2)
424 ephi(:,:,:,1) = -posvec(:,:,:,2)/radius(:,:,:)
425 ephi(:,:,:,2) = posvec(:,:,:,1)/radius(:,:,:)
429 SELECT TYPE(bwest => timedisc%Boundary%boundary(west)%p)
430 CLASS IS (boundary_custom)
431 CALL bwest%SetCustomBoundaries(mesh,physics, &
432 (/custom_nograd,custom_extrapol,custom_kepler/))
434 SELECT TYPE(beast => timedisc%Boundary%boundary(east)%p)
435 CLASS IS (boundary_custom)
436 CALL beast%SetCustomBoundaries(mesh,physics, &
437 (/custom_logexpol,custom_outflow,custom_kepler/))
443 IF (
ASSOCIATED(sp).EQV..false.)
RETURN 445 CLASS IS(sources_gravity)
451 IF (.NOT.
ASSOCIATED(sp))
CALL physics%Error(
"pringle::InitData",
"no gravity term initialized")
459 CALL timedisc%Error(
"pringle::InitData",
"only pringle and beta viscosity possible")
463 SELECT TYPE(pvar => timedisc%pvar)
464 TYPE IS(statevector_eulerisotherm)
465 DO k=mesh%KGMIN,mesh%KGMAX
466 DO j=mesh%JGMIN,mesh%JGMAX
467 DO i=mesh%IMIN,mesh%IGMAX
480 pvar%density%data3d(i,j,k) = rhomin + sden
482 pvar%velocity%data4d(i,j,k,1:2) = &
483 vr*posvec(i,j,k,1:2)/r + vphi*ephi(i,j,k,1:2)
494 CALL timedisc%Error(
"pringle::InitData",
"only isothermal physics possible")
497 IF (
ASSOCIATED(timedisc%solution))
THEN 499 timedisc%solution = timedisc%pvar
503 IF (mesh%FARGO.EQ.2) &
504 timedisc%w(:,:) = sqrt(1.0/radius(:,mesh%JMIN,:))
507 CALL physics%Convert2Conservative(timedisc%pvar,timedisc%cvar)
509 CALL mesh%Info(
" DATA-----> initial condition: " //
"pringle disk")
510 WRITE(
value,
"(ES9.3)") tvis
511 CALL mesh%Info(
" " //
"viscous timescale: " //trim(
value))
512 WRITE(
value,
"(ES9.3)") re
513 CALL mesh%Info(
" " //
"Reynolds number: " //trim(
value))
514 WRITE(
value,
"(ES9.3)") ma
515 CALL mesh%Info(
" " //
"Mach number: " //trim(
value))
523 REAL,
INTENT(IN) :: mu,tau,r
524 REAL,
INTENT(OUT) :: Sigma,vr
526 REAL :: lambda,x,r4l,invr4l
529 r4l = r**(0.25/lambda)
530 x = 2*lambda**2 / tau * r**(0.25/lambda)
532 sigma = mdisk/sqrt((4*pi)**3 * tau) * r4l**(1.5-9*lambda) &
533 * exp(-lambda**2/tau*(1.0-r4l)**2)
534 vr = -1.5/re * ((x*tau)/(2*lambda*lambda))**(4*lambda-2.) &
535 * (1.0 - 0.5*x/lambda * (x*tau/(2*lambda*lambda) - 1.0))
542 REAL,
INTENT(IN) :: mu,tau,r
543 REAL,
INTENT(OUT) :: Sigma,vr
548 r4l = r**(0.25/lambda)
549 x = 2*lambda**2 / tau * r4l
550 sigma = mdisk/(4*pi) * (lambda/tau) * r4l**2 * r**(-2.25) &
551 * exp(-lambda**2/tau*(1.0+r4l**2)) &
553 vr = -1.5/re * ((x*tau)/(2*lambda*lambda))**(4*lambda-2.) &
554 * (1.0 - 0.5*x/lambda * (x*tau/(2*lambda*lambda) &
562 REAL,
INTENT(IN) :: nu,x
567 IF (aint(nu).EQ.nu)
THEN 570 inu = fgsl_sf_bessel_icn(n,x)
574 inu = (0.5*x)**nu / fgsl_sf_gamma(1.0+nu) * fgsl_sf_hyperg_0f1(1.0+nu,(0.5*x)**2)
type(dict_typ) function, pointer, public dict(n1, n2, n3, n4, n5, n6, n7, n8, n9, n10, n11, n12, n13, n14, n15, n16, n17, n18, n19, n20)
Construct a new dictionary from several key/value pairs. Together with the Assign subroutine and over...
subroutine initdata(Mesh, Physics, Fluxes, Timedisc)
real function modified_bessel_inu(nu, x)
elemental real function, public asinh(x)
inverse hyperbolic sine function
subroutine makeconfig(Sim, config)
Dictionary for generic data types.
subroutine viscousring_analytic(mu, tau, r, Sigma, vr)
subroutine viscousring_approx(mu, tau, r, Sigma, vr)