The main documentation of the Output_Timer Procedure contains additional explanation of this code listing.
subroutine Output_Timer (Timer, Global, Verbose, Unit)
use Caesar_Numbers_Module, only: hundred, zero
! Input variables.
type(Timer_type), intent(inout) :: Timer ! Variable to be output.
type(logical), intent(in), optional :: Global ! Global flag.
type(logical), intent(in), optional :: Verbose ! Verbosity flag.
type(integer), intent(in), optional :: Unit ! Output unit.
! Internal variables.
type(integer) :: A_Unit ! Actual output unit.
type(logical) :: A_Global ! Actual global flag.
type(logical) :: A_Verbose ! Actual verbosity flag.
type(character,80) :: Timer_Name ! Timer name.
type(integer) :: Timer_Splits ! Timer split count.
type(real) :: Timer_CPU_Max ! Timer CPU maximum.
type(real) :: Timer_CPU_Mean ! Timer CPU mean.
type(real) :: Timer_CPU_Min ! Timer CPU minimum.
type(real) :: Timer_CPU_StDev ! Timer CPU Standard Deviation.
type(real) :: Timer_CPU_Split_Max ! Timer CPU Split maximum.
type(real) :: Timer_CPU_Split_Mean ! Timer CPU Split mean.
type(real) :: Timer_CPU_Split_Min ! Timer CPU Split minimum.
type(real) :: Timer_CPU_Split_StDev ! Timer CPU Split Std Dev.
type(real) :: Timer_Machine_Capacity_Usage ! Timer machine capacity usage.
type(real) :: Timer_Wall_Clock_Max ! Timer Wall Clock maximum.
type(real) :: Timer_Wall_Clock_Min ! Timer Wall Clock minimum.
type(real) :: Timer_Wall_Clock_Mean ! Timer Wall Clock mean.
type(real) :: Timer_Wall_Clock_StDev ! Timer Wall Clock Std Dev.
type(real) :: Timer_Wall_Clock_Split_Max ! Timer Wall Clock Split max.
type(real) :: Timer_Wall_Clock_Split_Min ! Timer Wall Clock Split min.
type(real) :: Timer_Wall_Clock_Split_Mean ! Timer Wall Clock Split mean.
type(real) :: Timer_Wall_Clock_Split_StDev ! Timer Wall Clock Split StDev.
!~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
! Verify requirements.
VERIFY(Valid_State(Timer),5) ! Timer is valid.
! Set unit number.
if (PRESENT(Unit)) then
A_Unit = Unit
else
A_Unit = 6
end if
! Set global flag.
if (PRESENT(Global)) then
A_Global = Global
else
A_Global = .false.
end if
! Set verbosity flag.
if (PRESENT(Verbose)) then
A_Verbose = Verbose
else
A_Verbose = .false.
end if
! Verbose output variables.
if (A_Verbose) then
Timer_Name = Name(Timer)
Timer_Splits = Count(Timer, Global=A_Global, Split=.true.)
! CPU statistics.
Timer_CPU_Mean = &
Mean(Timer, 'CPU', Global=A_Global, Split=.false.)
Timer_CPU_StDev = &
Standard_Deviation(Timer, 'CPU', Global=A_Global, Split=.false.)
Timer_CPU_Max = &
Maximum(Timer, 'CPU', Global=A_Global, Split=.false.)
Timer_CPU_Min = &
Minimum(Timer, 'CPU', Global=A_Global, Split=.false.)
! Wall Clock statistics.
Timer_Wall_Clock_Mean = &
Mean(Timer, 'Wall_Clock', Global=A_Global, Split=.false.)
Timer_Wall_Clock_StDev = &
Standard_Deviation(Timer, 'Wall_Clock', Global=A_Global, Split=.false.)
Timer_Wall_Clock_Max = &
Maximum(Timer, 'Wall_Clock', A_Global, Split=.false.)
Timer_Wall_Clock_Min = &
Minimum(Timer, 'Wall_Clock', Global=A_Global, Split=.false.)
! Machine Capacity Usage =
! Average CPU Time per PE / Max Wall Clock Time
if (Timer_Wall_Clock_Max /= zero) then
Timer_Machine_Capacity_Usage = &
hundred * Timer_CPU_Mean / Timer_Wall_Clock_Max
else
Timer_Machine_Capacity_Usage = zero
end if
! CPU Split statistics.
Timer_CPU_Split_Mean = &
Mean(Timer, 'CPU', Global=A_Global, Split=.true.)
Timer_CPU_Split_StDev = &
Standard_Deviation(Timer, 'CPU', Global=A_Global, Split=.true.)
Timer_CPU_Split_Max = &
Maximum(Timer, 'CPU', Global=A_Global, Split=.true.)
Timer_CPU_Split_Min = &
Minimum(Timer, 'CPU', Global=A_Global, Split=.true.)
! Wall Clock Split statistics.
Timer_Wall_Clock_Split_Mean = &
Mean(Timer, 'Wall_Clock', Global=A_Global, Split=.true.)
Timer_Wall_Clock_Split_StDev = &
Standard_Deviation(Timer, 'Wall_Clock', Global=A_Global, Split=.true.)
Timer_Wall_Clock_Split_Max = &
Maximum(Timer, 'Wall_Clock', Global=A_Global, Split=.true.)
Timer_Wall_Clock_Split_Min = &
Minimum(Timer, 'Wall_Clock', Global=A_Global, Split=.true.)
! Non-verbose output variables.
else
Timer_Name = Name(Timer)
Timer_Wall_Clock_Max = &
Maximum(Timer, 'Wall_Clock', A_Global, Split=.false.)
Timer_CPU_Mean = Mean(Timer, 'CPU', Global=A_Global, Split=.false.)
end if
! Output Timer Info.
if (this_is_IO_PE) then
if (A_Verbose) then
if (A_Global) then
write (A_Unit,100) TRIM(Timer_Name), ': *Global values*'
write (A_Unit,101) 'Total number of splits = ', Timer_Splits
write (A_Unit,101) 'CPU Time / PE:'
call Output_Stats_Timer (A_Unit, Timer_CPU_Min, &
Timer_CPU_Max, Timer_CPU_Mean, Timer_CPU_StDev)
write (A_Unit,101) 'Wall Clock Time / PE:'
call Output_Stats_Timer (A_Unit, Timer_Wall_Clock_Min, &
Timer_Wall_Clock_Max, Timer_Wall_Clock_Mean, &
Timer_Wall_Clock_StDev)
write (A_Unit,101) 'CPU Time / Split:'
call Output_Stats_Timer (A_Unit, Timer_CPU_Split_Min, &
Timer_CPU_Split_Max, Timer_CPU_Split_Mean, Timer_CPU_Split_StDev)
write (A_Unit,101) 'Wall Clock Time / Split:'
call Output_Stats_Timer (A_Unit, Timer_Wall_Clock_Split_Min, &
Timer_Wall_Clock_Split_Max, Timer_Wall_Clock_Split_Mean, &
Timer_Wall_Clock_Split_StDev)
if (Timer_Machine_Capacity_Usage /= zero) then
write (A_Unit,106) 'Machine Capacity Usage = ', &
Timer_Machine_Capacity_Usage, '%'
end if
else
write (A_Unit,100) TRIM(Timer_Name), ': *Values for IO PE*'
write (A_Unit,101) 'Total number of splits = ', Timer_Splits
write (A_Unit,104) 'CPU Time (Total) = ', &
Timer_CPU_Mean
write (A_Unit,104) 'Wall Clock Time (Total) = ', &
Timer_Wall_Clock_Mean
write (A_Unit,101) 'CPU Time / Split:'
call Output_Stats_Timer (A_Unit, Timer_CPU_Split_Min, &
Timer_CPU_Split_Max, Timer_CPU_Split_Mean, Timer_CPU_Split_StDev)
write (A_Unit,101) 'Wall Clock Time / Split:'
call Output_Stats_Timer (A_Unit, Timer_Wall_Clock_Split_Min, &
Timer_Wall_Clock_Split_Max, Timer_Wall_Clock_Split_Mean, &
Timer_Wall_Clock_Split_StDev)
if (Timer_Machine_Capacity_Usage /= zero) then
write (A_Unit,106) 'Machine Capacity Usage = ', &
Timer_Machine_Capacity_Usage, '%'
end if
end if
else
write (A_Unit,107) TRIM(Timer_Name), &
': Max Tot Wall=', Timer_Wall_Clock_Max, &
', Avg Tot CPU=', Timer_CPU_Mean
end if
end if
! Format statements.
100 format (a,a)
101 format (2x,a,i7)
102 format (4x,a,1pe14.7,a,1pe15.7,a)
103 format (4x,a,1pe15.7,:,a,1pe13.7,a,0pf9.4,a)
104 format (2x,a,1pe15.7)
106 format (2x,a,f11.7,a)
107 format (a,a,1pe14.7,a,1pe14.7)
! Verify guarantees - none.
return
end subroutine Output_Timer
! Procedure: Output_Stats_Timer
!
! This supplemental private routine is only used in Output_Timer.
subroutine Output_Stats_Timer (Unit, Min, Max, Mean, StDev)
! Input variables.
type(integer), intent(in) :: Unit ! Output unit.
type(real), intent(in) :: Max ! Maximum.
type(real), intent(in) :: Mean ! Mean.
type(real), intent(in) :: Min ! Minimum.
type(real), intent(in) :: StDev ! Standard Deviation.
!~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
! Verify requirements - none. Cannot put VERIFYs here because
! this routine is called from within an "if (this_is_IO_PE)"
! block -- no global communication allowed.
! Write out statistics.
write (Unit,100) 'Range = [[', Min, ', ', Max, ' ]]'
if (Mean /= zero) then
write (Unit,101) 'Average = ', Mean, ' +/- ', StDev, ' ( +/-', &
StDev / Mean * 100.d0, '% )'
else
write (Unit,101) 'Average = ', Mean, ' +/- ', StDev
end if
if (Min /= zero) then
write (Unit,101) 'Max / Min = ', Max / Min
else
write (Unit,101) 'Max / Min = Infinite'
end if
100 format (4x,a,1pe14.7,a,1pe15.7,a)
101 format (4x,a,1pe15.7,:,a,1pe13.7,a,0pf9.4,a)
! Verify guarantees - none.
return
end subroutine Output_Stats_Timer