FMS  2024.03
Flexible Modeling System
fms_yaml_output.F90
1 !***********************************************************************
2 !* GNU Lesser General Public License
3 !*
4 !* This file is part of the GFDL Flexible Modeling System (FMS).
5 !*
6 !* FMS is free software: you can redistribute it and/or modify it under
7 !* the terms of the GNU Lesser General Public License as published by
8 !* the Free Software Foundation, either version 3 of the License, or (at
9 !* your option) any later version.
10 !*
11 !* FMS is distributed in the hope that it will be useful, but WITHOUT
12 !* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 !* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14 !* for more details.
15 !*
16 !* You should have received a copy of the GNU Lesser General Public
17 !* License along with FMS. If not, see <http://www.gnu.org/licenses/>.
18 !***********************************************************************
19 !> @defgroup fms_yaml_output_mod fms_yaml_output_mod
20 !> @ingroup parser
21 !> @author Tom Robinson
22 !> @description Writes a 3 tiered yaml where the first and second tier can have 1 key that has an
23 !! array of values. This is usefule for writing a diag_output.yaml Here is an example:
24 !! \verbatim
25 !! ---
26 !! basedate: 0 0 0 0 0 0 0
27 !! experiment: c192L65_exp
28 !! files:
29 !! - name: atmos_daily
30 !! freq: days
31 !! vars:
32 !! - name: temp
33 !! units: K
34 !! - name: P
35 !! longname: pressure
36 !! - name: wind
37 !! units: m/s
38 !! longname: wind velocity magnitude
39 !! - name: atmos_monthly
40 !! freq: months
41 !! vars:
42 !! - name: temp
43 !! units: K
44 !! ...
45 !! \endverbatim
46 !! In this example, basedate, experiment, and files are the level 1 (top level) keys. files is the
47 !! level2key in the keys struct. The array of structs for the files with name, freq has a size of 2, and
48 !! vars is the level2key. The key3 and var3 arrays should have a size of 4, and a3each=(\3,1\‍)
49 !! corresponding to the number of elements in each array within the yaml.
50 
51 !> @file
52 !> @brief File for @ref fms_yaml_output_mod
53 
54 !> @addtogroup fms_yaml_output_mod
55 !> @{
56 module fms_yaml_output_mod
57 #ifdef use_yaml
58 
59 use iso_c_binding
60 use fms_string_utils_mod, only: fms_f2c_string
61 implicit none
62 
63 private
64 
67 public :: yaml_out_add_level2key
68 public :: string_len_parameter
70 
71 integer, parameter :: string_len_parameter = 255 !< Max number of characters in the key and value strings.
72  !! Must match whats in yaml_output_functions.c
73 integer, parameter :: lvl2_key_parameter = 8 !< Max number of strings to be stored in lvl2keys
74  !! Must match whats in yaml_output_functions.c
75 !> Keys for the output yaml on a given level corresponding to the struct in yaml_output_functions.c
76 !! Should be set using the fms_f2c_string routine to get properly formatted c style strings
77 !! level2keys should be set with add_level2key()
78 type, bind(c) :: fmsYamlOutKeys_type
79  character (c_char) :: key1 (string_len_parameter)
80  character (c_char) :: key2 (string_len_parameter)
81  character (c_char) :: key3 (string_len_parameter)
82  character (c_char) :: key4 (string_len_parameter)
83  character (c_char) :: key5 (string_len_parameter)
84  character (c_char) :: key6 (string_len_parameter)
85  character (c_char) :: key7 (string_len_parameter)
86  character (c_char) :: key8 (string_len_parameter)
87  character (c_char) :: key9 (string_len_parameter)
88  character (c_char) :: key10 (string_len_parameter)
89  character (c_char) :: key11 (string_len_parameter)
90  character (c_char) :: key12 (string_len_parameter)
91  character (c_char) :: key13 (string_len_parameter)
92  character (c_char) :: key14 (string_len_parameter)
93  character (c_char) :: key15 (string_len_parameter)
94  character (c_char) :: key16 (string_len_parameter)
95  character (c_char) :: level2key (string_len_parameter * lvl2_key_parameter)
96  integer(c_int) :: level2key_offset
97 end type fmsyamloutkeys_type
98 !> Values for the output yaml on a given level corresponding to the struct in yaml_output_functions.c
99 type, bind(c) :: fmsYamlOutValues_type
100  character (c_char) :: val1 (string_len_parameter)
101  character (c_char) :: val2 (string_len_parameter)
102  character (c_char) :: val3 (string_len_parameter)
103  character (c_char) :: val4 (string_len_parameter)
104  character (c_char) :: val5 (string_len_parameter)
105  character (c_char) :: val6 (string_len_parameter)
106  character (c_char) :: val7 (string_len_parameter)
107  character (c_char) :: val8 (string_len_parameter)
108  character (c_char) :: val9 (string_len_parameter)
109  character (c_char) :: val10 (string_len_parameter)
110  character (c_char) :: val11 (string_len_parameter)
111  character (c_char) :: val12 (string_len_parameter)
112  character (c_char) :: val13 (string_len_parameter)
113  character (c_char) :: val14 (string_len_parameter)
114  character (c_char) :: val15 (string_len_parameter)
115  character (c_char) :: val16 (string_len_parameter)
116 end type fmsyamloutvalues_type
117 
118 
119 interface
120 subroutine write_yaml_from_struct_3 (yamlname, a1size, keys, vals, a2size, key2, val2, a3size, a3each,&
121  key3, val3, lvl2keyeach) bind(C, name="write_yaml_from_struct_3")
122 use iso_c_binding
124 character (c_char) :: yamlname !< The output yaml file name
125 integer (c_int), value :: a1size !< The size of the first yaml array
126 type (fmsYamlOutKeys_type) :: keys(a1size) !< Top level yaml keys
127 type (fmsYamlOutValues_type) :: vals(a1size) !< Values corresponding to keys
128 integer (c_int), value :: a2size !< The size of the second yaml array
129 type (fmsYamlOutKeys_type) :: key2(a2size) !< Second level keys
130 type (fmsYamlOutValues_type) :: val2(a2size) !< Values corresponding to key2
131 integer (c_int), value :: a3size !< The size of the third yaml array
132 integer (c_int) :: a3each (a2size) !< Array that has the number of elements for each level 2 key's
133  !! third level elements. If using multiple lvl2keys, a value must be
134  !! present for each key.
135 type (fmsYamlOutKeys_type) :: key3(a3size) !< Third level keys
136 type (fmsYamlOutValues_type) :: val3(a3size) !< Values corresponding to keys2
137 integer (c_int) :: lvl2keyeach(lvl2_key_parameter) !< amount of key2 'blocks' to print per level2key in keys
138 end subroutine write_yaml_from_struct_3
139 !> Adds a level 2 key (key that starts new tabbed section) to the list.
140 !! @ref yaml_out_add_level2key (wrapper routine) should be used instead.
141 subroutine yaml_out_add_level2key_c(key_length, key_name, keytype) bind(C, name="add_level2key")
142  use iso_c_binding
143  import fmsyamloutkeys_type
144  character(c_char), intent(in) :: key_name !< name of level 2 key (starts a new tabbed section) to add to list
145  integer(c_int), value :: key_length !< length of key_name
146  type(fmsyamloutkeys_type), intent(inout) :: keytype !< struct of keys to output
147 end subroutine
148 end interface
149 
150 contains
151 
152 !> Adds a level 2 key (key that starts new tabbed section) to the list.
153 !! Will print level 2 keys in the order added. See write_yaml_from_struct_3 for more details.
154 !! This routine is a wrapper for @ref yaml_out_add_level2key_c .
155 subroutine yaml_out_add_level2key(key_name, keytype)
156  character(len=*) :: key_name
157  type(fmsyamloutkeys_type), intent(inout) :: keytype
158  call yaml_out_add_level2key_c(len_trim(key_name), key_name, keytype )
159 end subroutine
160 
161 !! Initialize one instance of the fmsYamlOutKeys_type structure.
162 subroutine initialize_key_struct( yk )
163  type (fmsyamloutkeys_type), intent(inout) :: yk !< Instance of the stucture
164  call fms_f2c_string (yk%key1,"")
165  call fms_f2c_string (yk%key2,"")
166  call fms_f2c_string (yk%key3,"")
167  call fms_f2c_string (yk%key4,"")
168  call fms_f2c_string (yk%key5,"")
169  call fms_f2c_string (yk%key6,"")
170  call fms_f2c_string (yk%key7,"")
171  call fms_f2c_string (yk%key8,"")
172  call fms_f2c_string (yk%key9,"")
173  call fms_f2c_string (yk%key10,"")
174  call fms_f2c_string (yk%key11,"")
175  call fms_f2c_string (yk%key12,"")
176  call fms_f2c_string (yk%key13,"")
177  call fms_f2c_string (yk%key14,"")
178  call fms_f2c_string (yk%key15,"")
179  call fms_f2c_string (yk%key16,"")
180  call fms_f2c_string(yk%level2key,"")
181  yk%level2key_offset = -1
182 end subroutine initialize_key_struct
183 
184 !! Initialize one instance of the fmsYamlOutValues_type structure.
185 subroutine initialize_val_struct( yv)
186  type (fmsyamloutvalues_type), intent(inout):: yv !< Instance of the stucture
187  call fms_f2c_string (yv%val1,"")
188  call fms_f2c_string (yv%val2,"")
189  call fms_f2c_string (yv%val3,"")
190  call fms_f2c_string (yv%val4,"")
191  call fms_f2c_string (yv%val5,"")
192  call fms_f2c_string (yv%val6,"")
193  call fms_f2c_string (yv%val7,"")
194  call fms_f2c_string (yv%val8,"")
195  call fms_f2c_string (yv%val9,"")
196  call fms_f2c_string (yv%val10,"")
197  call fms_f2c_string (yv%val11,"")
198  call fms_f2c_string (yv%val12,"")
199  call fms_f2c_string (yv%val13,"")
200  call fms_f2c_string (yv%val14,"")
201  call fms_f2c_string (yv%val15,"")
202  call fms_f2c_string (yv%val16,"")
203 end subroutine initialize_val_struct
204 
205 #endif
206 end module fms_yaml_output_mod
207 !> @}
208 ! close documentation grouping
subroutine, public fms_f2c_string(dest, str_in)
Copies a Fortran string into a C string and puts c_null_char in any trailing spaces.
subroutine, public initialize_val_struct(yv)
integer, parameter lvl2_key_parameter
Max number of strings to be stored in lvl2keys Must match whats in yaml_output_functions....
subroutine, public initialize_key_struct(yk)
Keys for the output yaml on a given level corresponding to the struct in yaml_output_functions....
Values for the output yaml on a given level corresponding to the struct in yaml_output_functions....
Adds a level 2 key (key that starts new tabbed section) to the list. yaml_out_add_level2key (wrapper ...