40submodule(
design) design_hdf5_io
42 use mpi_f08,
only: mpi_scan, mpi_info_null, mpi_integer8, mpi_max, mpi_min, &
44 use math,
only: abscmp
45 use device,
only: device_to_host, host_to_device
46 use comm,
only: pe_rank, pe_size
47 use num_types,
only: sp, dp
48 use scratch_registry,
only: neko_scratch_registry
49 use hdf5_session,
only: hdf5_session_init, hdf5_session_finalize
58 module subroutine design_save_checkpoint_hdf5(this, filename, overwrite)
59 class(design_t),
intent(in) :: this
60 character(len=*),
intent(in) :: filename
61 logical,
intent(in),
optional :: overwrite
62 type(vector_t),
pointer :: temp_vec
65 integer(hid_t) :: fapl_id, xf_id, file_id, dset_id, filespace, memspace, &
66 attr_id, grp_id, str_type, design_grp_id
67 integer(hid_t) :: H5T_NEKO_REAL
68 integer(hsize_t),
dimension(1) :: ddim, dcount, doffset
69 integer :: ierr, info, drank
70 logical :: file_exists, design_exists, overwrite_flag
71 integer :: n_accum, n_array(pe_size)
73 overwrite_flag = .false.
74 if (
present(overwrite)) overwrite_flag = overwrite
78 n_array(pe_rank + 1) = this%n
79 call mpi_allreduce(mpi_in_place, n_array, pe_size, mpi_integer, mpi_max, &
85 call hdf5_session_init()
86 call h5pcreate_f(h5p_file_access_f, fapl_id, ierr)
87 info = mpi_info_null%mpi_val
88 call h5pset_fapl_mpio_f(fapl_id, neko_comm%mpi_val, info, ierr)
92 inquire(file=trim(filename), exist=file_exists)
93 if (.not. file_exists)
then
94 call h5fcreate_f(trim(filename), h5f_acc_trunc_f, file_id, ierr, &
98 call h5gcreate_f(file_id,
"Design", design_grp_id, ierr)
99 call h5gcreate_f(design_grp_id,
"checkpoint", grp_id, ierr)
102 call h5fopen_f(trim(filename), h5f_acc_rdwr_f, file_id, ierr, fapl_id)
105 design_exists = .false.
106 call h5lexists_f(file_id,
'/Design', design_exists, ierr)
108 if (.not. design_exists)
then
110 call h5gcreate_f(file_id,
"Design", design_grp_id, ierr)
111 call h5gcreate_f(design_grp_id,
"checkpoint", grp_id, ierr)
114 call h5gopen_f(file_id,
'Design', design_grp_id, ierr)
115 call h5lexists_f(design_grp_id,
'checkpoint', design_exists, ierr)
117 if (design_exists .and. overwrite_flag)
then
118 call h5gunlink_f(design_grp_id,
"checkpoint", ierr)
119 call h5gcreate_f(design_grp_id,
"checkpoint", grp_id, ierr)
121 call neko_error(
'design: HDF5 file "' // trim(filename) //
'" ' &
122 //
'already contains Design group; ' &
123 //
'use overwrite option to replace')
127 call h5gclose_f(design_grp_id, ierr)
132 h5t_neko_real = h5t_native_double
134 h5t_neko_real = h5t_native_real
136 call neko_error(
'design: unsupported real kind for HDF5')
144 call h5screate_f(h5s_scalar_f, filespace, ierr)
146 call h5acreate_f(grp_id,
'n_global', h5t_native_integer, filespace, &
147 attr_id, ierr, h5p_default_f, h5p_default_f)
148 call h5awrite_f(attr_id, h5t_native_integer, this%n_global, ddim, ierr)
149 call h5aclose_f(attr_id, ierr)
154 call h5tcopy_f(h5t_fortran_s1, str_type, ierr)
155 call h5tset_strpad_f(str_type, h5t_str_spacepad_f, ierr)
157 ddim(1) = len_trim(this%name)
158 call h5tset_size_f(str_type, ddim(1), ierr)
159 call h5acreate_f(grp_id,
'name', str_type, filespace, attr_id, &
160 ierr, h5p_default_f, h5p_default_f)
161 call h5awrite_f(attr_id, str_type, this%name, ddim, ierr)
162 call h5aclose_f(attr_id, ierr)
165 call h5tclose_f(str_type, ierr)
168 call h5sclose_f(filespace, ierr)
173 call h5screate_simple_f(drank, ddim, filespace, ierr)
175 call h5acreate_f(grp_id,
'n', h5t_native_integer, filespace, attr_id, ierr)
176 call h5awrite_f(attr_id, h5t_native_integer, n_array, ddim, ierr)
177 call h5aclose_f(attr_id, ierr)
179 call h5sclose_f(filespace, ierr)
185 call mpi_scan(this%n, n_accum, 1, mpi_integer, mpi_sum, neko_comm, ierr)
189 doffset(1) = n_accum - this%n
190 ddim(1) = this%n_global
193 call h5screate_simple_f(drank, ddim, filespace, ierr)
194 call h5screate_simple_f(drank, dcount, memspace, ierr)
197 call h5pcreate_f(h5p_dataset_xfer_f, xf_id, ierr)
198 call h5pset_dxpl_mpio_f(xf_id, h5fd_mpio_collective_f, ierr)
201 call h5sselect_hyperslab_f(filespace, h5s_select_set_f, doffset, dcount, &
204 call neko_scratch_registry%request(temp_vec, temp_index, this%n, .true.)
205 call this%get_values(temp_vec)
206 call temp_vec%copy_from(device_to_host, sync = .true.)
209 call h5dcreate_f(grp_id,
'values', h5t_neko_real, &
210 filespace, dset_id, ierr)
211 call h5dwrite_f(dset_id, h5t_neko_real, temp_vec%x, ddim, ierr, &
212 file_space_id = filespace, mem_space_id = memspace, xfer_prp = xf_id)
213 call h5dclose_f(dset_id, ierr)
215 call neko_scratch_registry%relinquish(temp_index)
219 call h5sclose_f(filespace, ierr)
220 call h5sclose_f(memspace, ierr)
221 call h5pclose_f(xf_id, ierr)
226 call h5gclose_f(grp_id, ierr)
227 call h5fclose_f(file_id, ierr)
228 call h5pclose_f(fapl_id, ierr)
230 call hdf5_session_finalize()
232 end subroutine design_save_checkpoint_hdf5
237 module subroutine design_load_checkpoint_hdf5(this, filename)
238 class(design_t),
intent(inout) :: this
239 character(len=*),
intent(in) :: filename
241 type(vector_t),
pointer :: temp_vec
242 integer :: temp_index
244 character(len=64) :: name
245 integer(hid_t) :: fapl_id, file_id, dset_id, &
246 attr_id, grp_id, str_type, filespace, memspace, xf_id
247 integer(hid_t) :: H5T_NEKO_REAL
248 integer(hsize_t),
dimension(1) :: ddim, dcount, doffset
249 integer :: ierr, info, mpi_comm
250 integer :: n, n_global, n_accum, n_array(pe_size)
252 character(len=*),
parameter :: h5_group =
'/Design/checkpoint'
260 info = mpi_info_null%mpi_val
261 mpi_comm = neko_comm%mpi_val
264 call hdf5_session_init()
265 call h5pcreate_f(h5p_file_access_f, fapl_id, ierr)
266 call h5pset_fapl_mpio_f(fapl_id, mpi_comm, info, ierr)
267 call h5fopen_f(trim(filename), h5f_acc_rdonly_f, file_id, ierr, &
268 access_prp = fapl_id)
269 call h5gopen_f(file_id, h5_group, grp_id, ierr)
271 if (ierr .ne. 0)
then
272 call neko_error(
'design: unable to open HDF5 file "' // &
273 trim(filename) //
'" or group "' // trim(h5_group) //
'".')
279 h5t_neko_real = h5t_native_double
281 h5t_neko_real = h5t_native_real
283 call neko_error(
'design: unsupported real kind for HDF5')
291 call h5aopen_f(grp_id,
'n_global', attr_id, ierr)
292 call h5aread_f(attr_id, h5t_native_integer, n_global, ddim, ierr)
293 call h5aclose_f(attr_id, ierr)
296 call h5aopen_f(grp_id,
'name', attr_id, ierr)
297 call h5aget_type_f(attr_id, str_type, ierr)
298 call h5aread_f(attr_id, str_type, name, ddim, ierr)
299 call h5tclose_f(str_type, ierr)
300 call h5aclose_f(attr_id, ierr)
306 call h5aopen_f(grp_id,
'n', attr_id, ierr)
307 call h5aread_f(attr_id, h5t_native_integer, n_array, ddim, ierr)
308 call h5aclose_f(attr_id, ierr)
313 if (n_array(pe_rank + 1) .ne. this%n)
then
314 call neko_error(
'design: mismatch in n during HDF5 read')
316 if (n_global .ne. this%n_global)
then
317 call neko_error(
'design: mismatch in n_global during HDF5 read')
319 if (trim(name) .ne. trim(this%name))
then
320 call neko_error(
'design: mismatch in name during HDF5 read' // &
321 ' (file: ' // trim(name) //
', object: ' // trim(this%name) //
')')
330 call mpi_scan(this%n, n_accum, 1, mpi_integer, mpi_sum, neko_comm, ierr)
333 doffset(1) = n_accum - this%n
334 ddim(1) = this%n_global
337 call h5screate_simple_f(1, ddim, filespace, ierr)
338 call h5screate_simple_f(1, dcount, memspace, ierr)
341 call h5pcreate_f(h5p_dataset_xfer_f, xf_id, ierr)
342 call h5pset_dxpl_mpio_f(xf_id, h5fd_mpio_collective_f, ierr)
345 call h5sselect_hyperslab_f(filespace, h5s_select_set_f, doffset, dcount, &
349 call neko_scratch_registry%request(temp_vec, temp_index, this%n, .false.)
350 call h5dopen_f(grp_id,
'values', dset_id, ierr)
351 call h5dread_f(dset_id, h5t_neko_real, temp_vec%x, dcount, ierr, &
352 file_space_id = filespace, mem_space_id = memspace, xfer_prp = xf_id)
353 call h5dclose_f(dset_id, ierr)
355 call temp_vec%copy_from(host_to_device, sync = .true.)
356 call this%update_design(temp_vec)
357 call neko_scratch_registry%relinquish(temp_index)
361 call h5pclose_f(xf_id, ierr)
362 call h5sclose_f(memspace, ierr)
363 call h5sclose_f(filespace, ierr)
368 call h5gclose_f(grp_id, ierr)
369 call h5fclose_f(file_id, ierr)
370 call h5pclose_f(fapl_id, ierr)
372 call hdf5_session_finalize()
374 end subroutine design_load_checkpoint_hdf5
376end submodule design_hdf5_io