Skip to content

Commit cc8ffb5

Browse files
committed
Add a new logging mechanism to ModEM for debugging
This commit adds a new module, ModEM_logger, which contains an easier to use logging subroutine. There are several notable helpful features of this logger: 1. ModEM_log uses expand_string which was introduced in the last commit, easily allowing logs to write out specific arguments rather than formatting their own. 2. Using the `ModEM_log_init` subroutine, each individual task can open its own unique logging file. This can be very helpful when debugging MPI issues. I have taken the log subroutines from MPAS-Model, and thus included it's license. I have modified ModEM_log to also take a file unit, thus, instead of calling ModEM_log_init, one can just call ModEM_log on a file unit already used by ModEM (say, 0 or 6). Currently, this module is not used, and I don't have plans to replace any of ModEM's log statements with it, but I keep added it on various branches for testing, and thus figured perhaps I should open a pull request to include it into main.
1 parent 1a86a54 commit cc8ffb5

2 files changed

Lines changed: 153 additions & 2 deletions

File tree

f90/UTILS/CMakeLists.txt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,11 +5,10 @@ target_sources(${MODEM_EXE}
55
PRIVATE fields_orientation.f90
66
PRIVATE file_units.f90
77
PRIVATE math_constants.f90
8-
#PRIVATE ModEM_machine_timers.c
98
PRIVATE ModEM_timers.f90
10-
#PRIVATE ModEM_utils.f90
119
PRIVATE polpak.f90
1210
PRIVATE utilities.f90
11+
PRIVATE ModEM_logger.f90
1312
)
1413

1514
if (USE_C_TIMERS)

f90/UTILS/ModEM_logger.f90

Lines changed: 152 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,152 @@
1+
module ModEM_logger
2+
3+
use utilities
4+
use Declaration_MPI
5+
6+
implicit none
7+
8+
character (len=512), private :: log_fname
9+
integer, private :: log_fid = 0
10+
11+
contains
12+
13+
subroutine ModEM_log_init(mainOnly)
14+
15+
implicit none
16+
17+
logical, optional, intent(in) :: mainOnly
18+
character(len=*), parameter :: log_str_fmt = '(A,I4.4,A)'
19+
20+
logical :: mainOnly_lcl
21+
22+
if (present(mainOnly)) then
23+
mainOnly_lcl = mainOnly
24+
else
25+
mainOnly_lcl = .true.
26+
end if
27+
28+
if ((taskid == 0 .and. mainOnly_lcl) .or. (.not. mainOnly_lcl)) then
29+
write(log_fname, log_str_fmt) 'log.', taskid, '.modem.out'
30+
open(newunit=log_fid, file=log_fname, status='replace')
31+
call ModEM_log("Log Initalized $i - "//trim(log_fname), intArgs=(/taskid/), mainOnly=mainOnly)
32+
end if
33+
34+
end Subroutine ModEM_log_init
35+
36+
! The following License applies to ModEM_Log:
37+
!
38+
! Copyright (c) 2013-2019, Los Alamos National Security, LLC (LANS) (Ocean: LA-CC-13-047;
39+
! Land Ice: LA-CC-13-117) and the University Corporation for Atmospheric Research (UCAR).
40+
!
41+
! All rights reserved.
42+
!
43+
! LANS is the operator of the Los Alamos National Laboratory under Contract No.
44+
! DE-AC52-06NA25396 with the U.S. Department of Energy. UCAR manages the National
45+
! Center for Atmospheric Research under Cooperative Agreement ATM-0753581 with the
46+
! National Science Foundation. The U.S. Government has rights to use, reproduce,
47+
! and distribute this software. NO WARRANTY, EXPRESS OR IMPLIED IS OFFERED BY
48+
! LANS, UCAR OR THE GOVERNMENT AND NONE OF THEM ASSUME ANY LIABILITY FOR THE USE
49+
! OF THIS SOFTWARE. If software is modified to produce derivative works, such
50+
! modified software should be clearly marked, so as not to confuse it with the
51+
! version available from LANS and UCAR.
52+
!
53+
! Additionally, redistribution and use in source and binary forms, with or without
54+
! modification, are permitted provided that the following conditions are met:
55+
!
56+
! 1) Redistributions of source code must retain the above copyright notice, this
57+
! list of conditions and the following disclaimer.
58+
!
59+
! 2) Redistributions in binary form must reproduce the above copyright notice,
60+
! this list of conditions and the following disclaimer in the documentation and/or
61+
! other materials provided with the distribution.
62+
!
63+
! 3) None of the names of LANS, UCAR or the names of its contributors, if any, may
64+
! be used to endorse or promote products derived from this software without
65+
! specific prior written permission.
66+
!
67+
! THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
68+
! ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
69+
! WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
70+
! DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
71+
! ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
72+
! (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
73+
! LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
74+
! ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
75+
! (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
76+
! SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
77+
78+
!***********************************************************************
79+
!
80+
! routine ModEM_log
81+
!
82+
!> \brief Writes a message to the log file
83+
!> \author Matt Hoffman - Modified for ModEM by Miles Curry
84+
!> \date 14 February 2017, 5 Feburary 2026
85+
!> \details
86+
!> This routine writes a message to the log file. The message is the only
87+
!> required argument. A number of optional arguments control additional
88+
!> behavior:
89+
!> intArgs, int8Args, realArgs, logicArgs: arrays of variable values to be inserted into the
90+
!> message to replace the following characters: $i, $j, $r, $l
91+
!> See routine expand_string below for details.
92+
!> fid: (Optional) Instead of using the log created/opened in ModEM_log_init, write to the unit
93+
!> in found in fid
94+
!> mainOnly: flag indicating only the master task should write this message,
95+
!> regardless of if all tasks have open log files.
96+
!> flush_log: flag indicating that the log should be flushed after writing
97+
!>
98+
!
99+
!-----------------------------------------------------------------------
100+
subroutine ModEM_log(msg, intArgs, realArgs, logicArgs, fid, mainOnly, flush_log)
101+
102+
implicit none
103+
104+
character(len=*), intent(in) :: msg
105+
logical, intent(in), optional :: mainOnly
106+
integer, dimension(:), intent(in), optional :: intArgs !< Input: integer variable values to insert into message
107+
real(kind=prec), dimension(:), intent(in), optional :: realArgs !< Input: real variable values to insert into message
108+
!< Input: exponential notation variable values to insert into message
109+
logical, dimension(:), intent(in), optional :: logicArgs !< Input: logical variable values to insert into message
110+
integer, intent(in), optional :: fid
111+
logical, intent(in), optional :: flush_log
112+
113+
logical :: mainOnly_lcl
114+
logical :: flush_lcl
115+
integer :: fid_lcl
116+
117+
character(len=512) :: messageExpanded !< message after expansion of $ variable insertions
118+
119+
if (present(mainOnly)) then
120+
mainOnly_lcl = mainOnly
121+
else
122+
mainOnly_lcl = .true.
123+
end if
124+
125+
if (present(fid)) then
126+
fid_lcl = fid
127+
else
128+
fid_lcl = log_fid
129+
end if
130+
131+
132+
if (present(flush_log)) then
133+
flush_lcl = flush_log
134+
else
135+
flush_lcl = .false.
136+
end if
137+
138+
call expand_string(msg, messageExpanded, intArgs, logicArgs, realArgs)
139+
140+
if ((mainOnly_lcl .and. taskid == 0) .or. (.not. mainOnly_lcl)) then
141+
write(0,*) fid_lcl
142+
write(fid_lcl,*) trim(messageExpanded)
143+
144+
if (flush_lcl) then
145+
call flush(fid_lcl)
146+
end if
147+
end if
148+
149+
end subroutine ModEM_log
150+
151+
end module ModEM_logger
152+

0 commit comments

Comments
 (0)