66 INTEGER,
PRIVATE,
PARAMETER ::
maxlen = 500
67 INTEGER,
PRIVATE,
PARAMETER ::
simtype = 1
68 CHARACTER(LEN=32),
PRIVATE,
PARAMETER ::
simname =
"fosite" 77 CLASS(fluxes_base),
ALLOCATABLE :: fluxes
78 CLASS(physics_base),
ALLOCATABLE :: physics
79 CLASS(fileio_base),
ALLOCATABLE :: datafile
80 CLASS(timedisc_base),
ALLOCATABLE :: timedisc
81 CLASS(fileio_base),
ALLOCATABLE :: logfile
82 CLASS(sources_base),
POINTER :: sources & !< list of source terms
87 LOGICAL :: aborted = .true.
88 DOUBLE PRECISION :: wall_time
89 DOUBLE PRECISION :: log_time
90 DOUBLE PRECISION :: start_time
91 DOUBLE PRECISION :: end_time
92 DOUBLE PRECISION :: run_time
93 INTEGER :: start_count
94 CHARACTER(MAXLEN) :: buffer
132 LOGICAL :: already_initialized = .false.
137 IF(.NOT.
this%Initialized()) &
138 CALL mpi_initialized(already_initialized,
this%ierror)
139 IF (.NOT.already_initialized) &
140 CALL mpi_init(
this%ierror)
143 IF(
this%Initialized()) &
144 CALL this%Finalize(.false.)
152 SUBROUTINE setup(this)
156 TYPE(
dict_typ),
POINTER :: dir, iodir, config_copy
159 IF (.NOT.
this%Initialized()) &
160 CALL this%Error(
"Setup",
"Sim is uninitialized")
164 IF (
this%GetRank().EQ.0)
THEN 166 WRITE(
this%buffer,
"(A)")&
167 "+---------------------------------------------------------+" 169 WRITE(
this%buffer,
"(A1,A29,A28,A1)")&
172 WRITE(
this%buffer,
"(A1,A35,A22,A1)")&
173 "|",trim(version),
"",
"|" 175 WRITE(
this%buffer,
"(A)")&
176 "| Solution of 3D advection problems |" 178 WRITE(
this%buffer,
"(A)")&
179 "+---------------------------------------------------------+" 181 CALL this%Info(
"Initializing simulation:")
184 CALL getattr(
this%config,
"mesh", dir)
185 IF(
ASSOCIATED(dir))
THEN 188 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"mesh", iodir)
191 CALL getattr(
this%config,
"physics", dir)
192 IF(
ASSOCIATED(dir))
THEN 195 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"physics", iodir)
198 CALL getattr(
this%config,
"fluxes", dir)
199 IF(
ASSOCIATED(dir))
THEN 202 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"fluxes", iodir)
205 CALL getattr(
this%config,
"timedisc", dir)
206 IF(
ASSOCIATED(dir))
THEN 209 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"timedisc", iodir)
212 CALL getattr(
this%config,
"boundary", dir)
213 IF(.NOT.
ASSOCIATED(dir))
THEN 214 boundary =>
dict(
"empty"/ 0)
215 CALL setattr(
this%config,
"boundary", boundary)
216 CALL getattr(
this%config,
"boundary", dir)
218 IF(
ASSOCIATED(dir))
THEN 221 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"boundary", iodir)
224 CALL getattr(
this%config,
"sources", dir)
225 IF(
ASSOCIATED(dir))
THEN 230 IF(
ASSOCIATED(iodir))
CALL setattr(
this%IO,
"sources", iodir)
234 CALL getattr(
this%config,
"datafile", dir)
235 IF(
ASSOCIATED(dir))
THEN 240 CALL getattr(
this%config,
"logfile", dir)
241 IF(
ASSOCIATED(dir))
THEN 246 CALL setattr(
this%config,
"version", trim(version))
249 CALL setattr(
this%IO,
"config", config_copy)
258 INTEGER :: datetime(8)
262 this%start_time = mpi_wtime()
264 CALL cpu_time(
this%start_time)
267 CALL system_clock(
this%start_count)
273 IF (
this%GetRank().EQ.0)
THEN 275 "===================================================================")
276 CALL this%Info(
"Starting calculation...")
277 CALL date_and_time(values = datetime)
278 WRITE(
this%buffer,
"(A,I2.2,A,I2.2,A,I4.4,A,I2.2,A,I2.2,A,I2.2)")&
280 datetime(3),
".", datetime(2),
".", datetime(1),
" ",&
281 datetime(5),
":", datetime(6),
":", datetime(7)
284 "step time n t min(dt) due to adj.")
286 "-------------------------------------------------------------------")
290 IF (
this%Mesh%FARGO.EQ.1)
THEN 292 CALL this%Timedisc%Boundary%CenterBoundary(
this%Mesh,
this%Physics,&
293 0.0,
this%Timedisc%pvar,
this%Timedisc%cvar)
294 CALL this%Timedisc%CalcBackgroundVelocity(
this%Mesh,
this%Physics, &
300 this%Timedisc%time,0.0,
this%Timedisc%pvar,
this%Timedisc%cvar, &
301 check_all,
this%Timedisc%rhs)
307 SELECT TYPE(phys =>
this%Physics)
308 CLASS IS(physics_eulerisotherm)
309 IF(phys%csiso.GT.0.)
THEN 310 IF(any(phys%bccsound%data1d(:).NE.phys%csiso))
THEN 311 CALL this%Error(
"FirstStep",
"isothermal sound speed set, but "&
312 //
"arrays bccsound and/or fcsound have been overwritten.")
321 this%Timedisc%cold =
this%Timedisc%cvar
324 IF (
this%Timedisc%time.EQ.0.0)
THEN 327 IF (
this%GetRank().EQ.0)
CALL this%PrintInfo(0,0,0.0,0.0,0,
this%Timedisc%n_adj)
330 IF(
this%Timedisc%break) &
331 CALL this%Error(
"FirstStep",
"Initial data invalid!")
341 DO WHILE((
this%Timedisc%maxiter.LE.0).OR.(
this%iter.LE.
this%Timedisc%maxiter))
347 FUNCTION step(this)
RESULT(break)
353 REAL,
DIMENSION(2) :: dt_buf
359 IF (
this%iter.EQ.0) &
360 CALL this%FirstStep()
363 IF (abs(
this%Timedisc%stoptime-
this%Timedisc%time)&
364 .LE.1.0e-05*
this%Timedisc%stoptime)
THEN 366 this%aborted = .false.
372 dt_buf(1) =
this%Timedisc%dt
373 dt_buf(2) =
this%Timedisc%dtcause
376 this%Timedisc%dt = dt_buf(1)
377 this%Timedisc%dtcause = dt_buf(2)
379 this%run_time = mpi_wtime() -
this%log_time
380 CALL mpi_allreduce(
this%run_time,
this%wall_time,1,mpi_double_precision,&
381 mpi_min,
this%Mesh%comm_cart,
this%ierror)
383 CALL cpu_time(
this%wall_time)
388 CALL this%Datafile%AdjustTimestep(
this%Timedisc%time,&
389 this%Timedisc%dt,
this%Timedisc%dtcause)
393 dt_buf(1) =
this%Timedisc%dt
394 dt_buf(2) =
this%Timedisc%dtcause
397 this%Timedisc%dt = dt_buf(1)
398 this%Timedisc%dtcause = dt_buf(2)
406 IF ((abs(
this%Datafile%time-
this%Timedisc%time)&
407 .LE.1.0e-5*
this%Datafile%time).OR.&
408 this%Timedisc%break.OR.(
this%Datafile%walltime.LE.
this%wall_time))
THEN 412 this%Timedisc%dtmin,
this%Timedisc%dtmincause,
this%Timedisc%n_adj)
415 IF(
this%Timedisc%break.AND.
this%GetRank().EQ.0)
THEN 416 CALL this%Warning(
"SolveODE",
"Time step too small, aborting.",0)
422 IF (
this%Datafile%walltime.LE.
this%wall_time)
THEN 423 this%Datafile%walltime = huge(1.0)
427 this%Timedisc%dtmin =
this%Timedisc%stoptime
428 this%Timedisc%dtmincause = -99
429 this%Timedisc%n_adj = 0
433 this%Timedisc%dtmean = 0.
434 this%Timedisc%dtstddev = 0.
435 this%Timedisc%dtaccept = 0
437 IF(
this%Timedisc%write_error) &
438 this%Timedisc%cerr_max%data1d(:) = 0.
446 SUBROUTINE finalize(this,mpifinalize_)
450 LOGICAL,
OPTIONAL,
INTENT(IN) :: mpifinalize_
452 LOGICAL :: mpifinalize = .true.
455 CALL this%ComputeRunTime()
456 CALL this%PrintBoundaryFluxes()
457 CALL this%PrintSummary()
459 CALL this%Datafile%Finalize()
460 DEALLOCATE(
this%Datafile)
461 IF (
ALLOCATED(
this%Logfile))
THEN 462 CALL this%Logfile%Finalize()
463 DEALLOCATE(
this%Logfile)
465 CALL this%Timedisc%Finalize()
466 DEALLOCATE(
this%Timedisc)
470 CALL this%Physics%Finalize()
471 DEALLOCATE(
this%Physics)
472 CALL this%Fluxes%Finalize()
473 DEALLOCATE(
this%Fluxes)
474 CALL this%Mesh%Finalize()
475 DEALLOCATE(
this%Mesh)
482 IF(
PRESENT(mpifinalize_))
THEN 483 mpifinalize = mpifinalize_
486 CALL mpi_finalize(
this%ierror)
498 this%end_time = mpi_wtime() -
this%start_time
499 CALL mpi_allreduce(
this%end_time,
this%run_time,1,mpi_double_precision,mpi_min,&
502 CALL cpu_time(
this%end_time)
509 SUBROUTINE printinfo(this,step,i,t,d,dc,na)
513 INTEGER ::
step, i, dc, na
514 CHARACTER(LEN=9) :: dtcause
517 INTEGER :: drt, c, c_rate, c_max
521 IF (
this%GetRank().EQ.0)
THEN 526 WRITE(dtcause,
"(A,I2.2,A)")
" S",dc,
" " 528 WRITE(dtcause,
"(A)")
" cfl " 530 WRITE(dtcause,
"(A)")
" err_adj " 531 CASE(dtcause_smallerr)
532 WRITE(dtcause,
"(A)")
" err " 535 WRITE(dtcause,
"(A)")
" fileio " 537 WRITE(dtcause,
"(A,I3.2,A)")
" ?", dc,
"? " 540 CALL system_clock(c,c_rate, c_max)
542 drt = (c -
this%start_count)/c_rate
544 drt = c_max/c_rate + drt
546 WRITE(
this%buffer,
"(I4.4,A,I2.2,A,I2.2,A,I2.2,A,I8,A,ES11.3,A,ES11.3,A,I5)")&
547 step,
" ", drt/3600,
":", mod(drt,3600)/60,
":", mod(drt,60),&
548 " ", i,
" ", t,
" ", d, dtcause, na
558 REAL,
DIMENSION(this%Physics%VNUM,6) :: bflux
561 bflux(:,k) =
this%Fluxes%GetBoundaryFlux(
this%Mesh,
this%Physics,k)
563 IF (
this%GetRank().EQ.0)
THEN 564 CALL this%Info(
"-------------------------------------------------------------------")
565 CALL this%Info(
"total boundary fluxes:")
566 SELECT CASE(
this%Physics%VDIM)
568 IF(
this%Mesh%INUM.GT.1)
THEN 569 CALL this%Info(
" west east")
570 DO k=1,
this%Physics%VNUM
571 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
572 bflux(k,west), bflux(k,east)
575 ELSEIF(
this%Mesh%JNUM.GT.1)
THEN 576 CALL this%Info(
" south north")
577 DO k=1,
this%Physics%VNUM
578 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
579 bflux(k,south), bflux(k,north)
582 ELSEIF(
this%Mesh%KNUM.GT.1)
THEN 583 CALL this%Info(
" bottom top")
584 DO k=1,
this%Physics%VNUM
585 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
586 bflux(k,bottom), bflux(k,top)
591 IF(
this%Mesh%INUM.EQ.1)
THEN 592 CALL this%Info(
" south north")
593 DO k=1,
this%Physics%VNUM
594 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
595 bflux(k,south), bflux(k,north)
598 CALL this%Info(
" bottom top")
599 DO k=1,
this%Physics%VNUM
600 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
601 bflux(k,bottom), bflux(k,top)
604 ELSEIF(
this%Mesh%JNUM.EQ.1)
THEN 605 CALL this%Info(
" west east")
606 DO k=1,
this%Physics%VNUM
607 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
608 bflux(k,west), bflux(k,east)
611 CALL this%Info(
" bottom top")
612 DO k=1,
this%Physics%VNUM
613 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
614 bflux(k,bottom), bflux(k,top)
617 ELSEIF(
this%Mesh%KNUM.EQ.1)
THEN 618 CALL this%Info(
" west east")
619 DO k=1,
this%Physics%VNUM
620 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
621 bflux(k,west), bflux(k,east)
624 CALL this%Info(
" south north")
625 DO k=1,
this%Physics%VNUM
626 WRITE(
this%buffer,
"(T2,A,T21,2(ES12.3))")trim(
this%Physics%cvarname(k)), &
627 bflux(k,south), bflux(k,north)
632 CALL this%Info(
" west east south")
633 DO k=1,
this%Physics%VNUM
634 WRITE(
this%buffer,
"(T2,A,T21,3(ES12.3))")trim(
this%Physics%cvarname(k)), &
635 bflux(k,west), bflux(k,east), bflux(k,south)
638 CALL this%Info(
" north bottom top")
639 DO k=1,
this%Physics%VNUM
640 WRITE(
this%buffer,
"(T2,A,T21,3(ES12.3))")trim(
this%Physics%cvarname(k)), &
641 bflux(k,north), bflux(k,bottom), bflux(k,top)
653 IF (
this%GetRank().EQ.0)
THEN 654 CALL this%Info(
"===================================================================")
655 IF ((
this%Timedisc%maxiter.LE.0).OR.(
this%iter.LT.
this%Timedisc%maxiter))
THEN 656 CALL this%Info(
"calculation finished correctly.")
658 CALL this%Info(
"too many iterations, aborting!")
660 WRITE(
this%buffer,
"(A,F10.2,A)")
" main loop runtime: ",
this%run_time,
" sec."
constructor for mesh class
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...
recursive subroutine, public copydict(root, outdir)
Copy complete Dictionary.
constructor for fileio class
integer, parameter, private maxlen
subroutine new_fileio(Fileio, Mesh, Physics, Timedisc, Sources, config, IO)
integer, save default_mpi_2real
default 2real type for MPI
type(logging_base), save this
subroutine, private printinfo(this, step, i, t, d, dc, na)
subroutine new_sources(this, Mesh, Fluxes, Physics, config, IO)
subroutine, private initfosite(this)
integer, parameter, private simtype
logical function, public haschild(root)
Check if the node 'root' has one or more children.
subroutine, private printboundaryfluxes(this)
subroutine, private printsummary(this)
subroutine, public new_boundary(Boundary, Mesh, Physics, config, IO)
constructor for sources class
subroutine new_mesh(Mesh, config, IO)
logical function, private step(this)
subroutine, private run(this)
constructor for physics class
subroutine, public new_fluxes(Fluxes, Mesh, Physics, config, IO)
subroutine, public closedict()
subroutine, private computeruntime(this)
recursive subroutine, public deletedict(root)
Delete the dictionary 'root' and all subnodes.
constructor for timedisc class
subroutine, private finalize(this, mpifinalize_)
subroutine destroy_sources(this)
Dictionary for generic data types.
subroutine new_physics(Physics, Mesh, config, IO)
allocate and initialize new physics class
subroutine, public initdict()
subroutine, private firststep(this)
subroutine new_timedisc(Timedisc, Mesh, Physics, config, IO)
subroutine, private setup(this)
constructor for reconstruction class
constructor for fluxes class
character(len=32), parameter, private simname