Routine to read the response matrix for this supercell from netcdf file.
Type | Intent | Optional | Attributes | Name | ||
---|---|---|---|---|---|---|
class(supercell_type), | intent(inout) | :: | self |
The instance of the supercell class |
||
logical, | intent(out) | :: | could_read |
Flag to indicate if the file was successfully read |
||
character(len=*), | intent(in), | optional | :: | suffix |
If passed then use as part of file suffix |
subroutine sc_read_from_file(self, could_read, suffix)
use gs2_save, only: gs2_restore_response
use mp, only: broadcast_sub, proc0
use fields_arrays, only: get_specific_response_file_name, time_read_response
use gs2_time, only: code_dt
use file_utils, only: error_unit
use job_manage, only: time_message
implicit none
!> The instance of the supercell class
class(supercell_type), intent(in out) :: self
!> Flag to indicate if the file was successfully read
logical, intent(out) :: could_read
!> If passed then use as part of file suffix
character(len=*), optional, intent(in) :: suffix
complex, dimension(:,:), allocatable :: tmp_arr
character(len = 256) :: file_name
logical :: file_found
real :: file_time_step
! Initialise reading state.
could_read = .true.
! Construct the expected file name
file_name = adjustl(get_specific_response_file_name(self%ik_ind, self%is_ind, code_dt, suffix))
! First check if the expected file exists, if not then exit
inquire( file = trim(file_name), exist = file_found)
if (.not. file_found) then
if(proc0) write(error_unit(), &
'("Could not find response file ",A,", reverting to calculation.")') trim(file_name)
! Set the flag indicating if we could read the file. Note if this processor
! doesn't require this data (i.e. it considers this empty) then we ignore
! the presence of the file as we don't care. This is mostly important for
! the ky=kx=0 file which may not be present but also isn't required for any
! processor.
could_read = .false. .or. self%is_empty
return
end if
! We start timing after an initial early exit
call time_message(.false.,time_read_response,' Field Read')
!Now allocate array -- for big problems this might be an issue
allocate(tmp_arr(self%nrow,self%ncol))
!Now if on head proc read
if (self%is_head) then
call gs2_restore_response(tmp_arr, file_name, file_time_step, self%condition_number)
! Should perhaps double check that file_time_step == code_dt?
end if
!Now we need to broadcast the data to everyone with supercell.
!NOTE: Really we would want a supercell bound method which will do
!this so that this module level routine is insensitive to communicators etc.
!Furthermore we are lazy and use a broadcast_sub to send data to everyone
!NOTE: The processors which consider this to supercell to be empty (i.e. which
!don't have any associated work) shouldn't need to take part in this communication.
!If we can promise that only non-empty processors could be the head that should
!work fine, provided we have a suitable communicator (sc_sub_pd?).
call broadcast_sub(tmp_arr,self%head_iproc,self%sc_sub_all%id)
!Now push array to local storage
call self%push_arr_to_rows(tmp_arr)
deallocate(tmp_arr)
call time_message(.false.,time_read_response,' Field Read')
end subroutine sc_read_from_file