FV3 Bundle
ncdr_attrs.f90
Go to the documentation of this file.
1 module ncdr_attrs
2  use ncd_kinds, only: i_long
4  use ncdr_climsg, only: ncdr_error
8  use netcdf, only: nf90_inquire_attribute, nf90_inquire_variable, &
9  nf90_inq_attname, nf90_enotatt, nf90_noerr, nf90_max_name
10 
11  implicit none
12 
14  module procedure nc_diag_read_id_check_attr, &
16  end interface nc_diag_read_check_attr
17 
19  module procedure nc_diag_read_id_get_attr_type, &
21  end interface nc_diag_read_get_attr_type
22 
24  module procedure nc_diag_read_id_ret_attr_len, &
26  end interface nc_diag_read_ret_attr_len
27 
29  module procedure nc_diag_read_id_get_attr_len, &
31  end interface nc_diag_read_get_attr_len
32 
34  module procedure nc_diag_read_id_get_attr_names, &
36  end interface nc_diag_read_get_attr_names
37 
38  contains
39  function nc_diag_read_id_check_attr(file_ncdr_id, var_name, attr_name) result(attr_exists)
40  integer(i_long), intent(in) :: file_ncdr_id
41  character(len=*), intent(in) :: var_name
42  character(len=*), intent(in) :: attr_name
43 
44  integer(i_long) :: var_id, nc_err
45 
46  logical :: attr_exists
47 
48  call ncdr_check_ncdr_id(file_ncdr_id)
49 
50  var_id = ncdr_files(file_ncdr_id)%vars( &
51  nc_diag_read_assert_var(file_ncdr_id, var_name) )%var_id
52 
53  nc_err = nf90_inquire_attribute(ncdr_files(file_ncdr_id)%ncid, &
54  var_id, attr_name)
55 
56  ! If attribute doesn't exist, return false.
57  if (nc_err == nf90_enotatt) then
58  attr_exists = .false.
59  return
60  end if
61 
62  ! Sanity check - could be another error!
63  if (nc_err /= nf90_noerr) then
64  call ncdr_nc_check(nc_err)
65  end if
66 
67  attr_exists = .true.
68  end function nc_diag_read_id_check_attr
69 
70  function nc_diag_read_noid_check_attr(var_name, attr_name) result(attr_exists)
71  character(len=*), intent(in) :: var_name
72  character(len=*), intent(in) :: attr_name
73 
74  logical :: attr_exists
75 
77 
78  attr_exists = nc_diag_read_id_check_attr(current_ncdr_id, var_name, attr_name)
79  end function nc_diag_read_noid_check_attr
80 
81  function nc_diag_read_id_get_attr_type(file_ncdr_id, var_name, attr_name) result(attr_type)
82  integer(i_long), intent(in) :: file_ncdr_id
83  character(len=*), intent(in) :: var_name
84  character(len=*), intent(in) :: attr_name
85 
86  integer(i_long) :: var_id, attr_type
87 
88  call ncdr_check_ncdr_id(file_ncdr_id)
89 
90  var_id = ncdr_files(file_ncdr_id)%vars( &
91  nc_diag_read_assert_var(file_ncdr_id, var_name) )%var_id
92 
93  call ncdr_nc_check(nf90_inquire_attribute(ncdr_files(file_ncdr_id)%ncid, &
94  var_id, attr_name, attr_type))
96 
97  function nc_diag_read_noid_get_attr_type(var_name, attr_name) result(attr_type)
98  character(len=*), intent(in) :: var_name
99  character(len=*), intent(in) :: attr_name
100 
101  integer(i_long) :: attr_type
102 
104 
105  attr_type = nc_diag_read_id_get_attr_type(current_ncdr_id, var_name, attr_name)
107 
108  function nc_diag_read_id_ret_attr_len(file_ncdr_id, var_name, attr_name) result(attr_len)
109  integer(i_long), intent(in) :: file_ncdr_id
110  character(len=*), intent(in) :: var_name
111  character(len=*), intent(in) :: attr_name
112 
113  integer(i_long) :: var_id
114  integer(i_long) :: attr_len
115 
116  call ncdr_check_ncdr_id(file_ncdr_id)
117 
118  var_id = ncdr_files(file_ncdr_id)%vars( &
119  nc_diag_read_assert_var(file_ncdr_id, var_name) )%var_id
120 
121  call ncdr_nc_check(nf90_inquire_attribute(ncdr_files(file_ncdr_id)%ncid, &
122  var_id, attr_name, len = attr_len))
123  end function nc_diag_read_id_ret_attr_len
124 
125  function nc_diag_read_noid_ret_attr_len(var_name, attr_name) result(attr_len)
126  character(len=*), intent(in) :: var_name
127  character(len=*), intent(in) :: attr_name
128  integer(i_long) :: attr_len
129 
131 
132  attr_len = nc_diag_read_id_ret_attr_len(current_ncdr_id, var_name, attr_name)
133  end function nc_diag_read_noid_ret_attr_len
134 
135  subroutine nc_diag_read_id_get_attr_len(file_ncdr_id, var_name, attr_name, attr_len)
136  integer(i_long), intent(in) :: file_ncdr_id
137  character(len=*), intent(in) :: var_name
138  character(len=*), intent(in) :: attr_name
139  integer(i_long), intent(out) :: attr_len
140 
141  integer(i_long) :: var_id
142 
143  call ncdr_check_ncdr_id(file_ncdr_id)
144 
145  var_id = ncdr_files(file_ncdr_id)%vars( &
146  nc_diag_read_assert_var(file_ncdr_id, var_name) )%var_id
147 
148  call ncdr_nc_check(nf90_inquire_attribute(ncdr_files(file_ncdr_id)%ncid, &
149  var_id, attr_name, len = attr_len))
150  end subroutine nc_diag_read_id_get_attr_len
151 
152  subroutine nc_diag_read_noid_get_attr_len(var_name, attr_name, attr_len)
153  character(len=*), intent(in) :: var_name
154  character(len=*), intent(in) :: attr_name
155  integer(i_long), intent(out) :: attr_len
156 
158 
159  call nc_diag_read_id_get_attr_len(current_ncdr_id, var_name, attr_name, attr_len)
160  end subroutine nc_diag_read_noid_get_attr_len
161 
162  subroutine nc_diag_read_id_get_attr_names(file_ncdr_id, var_name, num_attrs, attr_name_mlen, attr_names)
163  integer(i_long), intent(in) :: file_ncdr_id
164  character(len=*), intent(in) :: var_name
165  integer(i_long), intent(out), optional :: num_attrs
166  integer(i_long), intent(out), optional :: attr_name_mlen
167  character(len=:), intent(inout), dimension(:), allocatable, optional:: attr_names
168 
169  integer(i_long) :: var_id, nattrs, attr_index, max_attr_name_len
170 
171  character(len=NF90_MAX_NAME) :: attr_name
172 
173  max_attr_name_len = 0
174 
175  call ncdr_check_ncdr_id(file_ncdr_id)
176 
177  var_id = ncdr_files(file_ncdr_id)%vars( &
178  nc_diag_read_assert_var(file_ncdr_id, var_name) )%var_id
179  call ncdr_nc_check(nf90_inquire_variable(ncdr_files(file_ncdr_id)%ncid, &
180  var_id, natts = nattrs))
181 
182  if (present(num_attrs)) &
183  num_attrs = nattrs
184 
185  ! Figure out character max length
186  do attr_index = 1, nattrs
187  call ncdr_nc_check(nf90_inq_attname(ncdr_files(file_ncdr_id)%ncid, &
188  var_id, &
189  attr_index, &
190  attr_name))
191 
192  if (len_trim(attr_name) > max_attr_name_len) &
193  max_attr_name_len = len_trim(attr_name)
194  end do
195 
196  if (present(attr_name_mlen)) &
197  attr_name_mlen = max_attr_name_len
198 
199  if (present(attr_names)) then
200  if (.NOT. allocated(attr_names)) then
201  allocate(character(max_attr_name_len) :: attr_names(nattrs))
202  else
203  if (size(attr_names) /= nattrs) &
204  call ncdr_error("Invalid allocated array size for attribute names storage!")
205  if (len(attr_names) < max_attr_name_len) &
206  call ncdr_error("Invalid allocated array size for attribute names storage! (String length does not match!)")
207  end if
208 
209  do attr_index = 1, nattrs
210  call ncdr_nc_check(nf90_inq_attname(ncdr_files(file_ncdr_id)%ncid, &
211  var_id, &
212  attr_index, &
213  attr_names(attr_index)))
214  end do
215  end if
216  end subroutine nc_diag_read_id_get_attr_names
217 
218  subroutine nc_diag_read_noid_get_attr_names(var_name, num_attrs, attr_name_mlen, attr_names)
219  character(len=*), intent(in) :: var_name
220  integer(i_long), intent(out), optional :: num_attrs
221  integer(i_long), intent(out), optional :: attr_name_mlen
222  character(len=:), intent(inout), dimension(:), allocatable, optional:: attr_names
223 
225 
226  call nc_diag_read_id_get_attr_names(current_ncdr_id, var_name, num_attrs, attr_name_mlen, attr_names)
227  end subroutine nc_diag_read_noid_get_attr_names
228 end module ncdr_attrs
integer(i_long) function nc_diag_read_noid_get_attr_type(var_name, attr_name)
Definition: ncdr_attrs.f90:98
integer, parameter, public i_long
Definition: ncd_kinds.F90:47
subroutine ncdr_nc_check(status)
Definition: ncdr_check.f90:85
logical function nc_diag_read_id_check_attr(file_ncdr_id, var_name, attr_name)
Definition: ncdr_attrs.f90:40
integer(i_long) current_ncdr_id
Definition: ncdr_state.f90:7
type(ncdr_file), dimension(:), allocatable ncdr_files
Definition: ncdr_state.f90:14
subroutine ncdr_check_current_ncdr_id
Definition: ncdr_check.f90:22
subroutine nc_diag_read_noid_get_attr_names(var_name, num_attrs, attr_name_mlen, attr_names)
Definition: ncdr_attrs.f90:219
subroutine nc_diag_read_noid_get_attr_len(var_name, attr_name, attr_len)
Definition: ncdr_attrs.f90:153
integer(i_long) function nc_diag_read_id_ret_attr_len(file_ncdr_id, var_name, attr_name)
Definition: ncdr_attrs.f90:109
integer(i_long) function nc_diag_read_id_get_attr_type(file_ncdr_id, var_name, attr_name)
Definition: ncdr_attrs.f90:82
subroutine ncdr_check_ncdr_id(file_ncdr_id)
Definition: ncdr_check.f90:12
subroutine nc_diag_read_id_get_attr_names(file_ncdr_id, var_name, num_attrs, attr_name_mlen, attr_names)
Definition: ncdr_attrs.f90:163
subroutine ncdr_error(err)
Definition: ncdr_climsg.F90:13
integer(i_long) function nc_diag_read_noid_ret_attr_len(var_name, attr_name)
Definition: ncdr_attrs.f90:126
subroutine nc_diag_read_id_get_attr_len(file_ncdr_id, var_name, attr_name, attr_len)
Definition: ncdr_attrs.f90:136
logical function nc_diag_read_noid_check_attr(var_name, attr_name)
Definition: ncdr_attrs.f90:71