Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -665,7 +665,8 @@ description=Global mesh panel partitioning.
help=For parallel computing, the 2D global mesh is divided up into partitions.
=Each process rank runs an instance of the model on one partition. The
=partition decompostion is specified on a `per panel` basis.
=i.e. The cubedsphere has six panels; the planar mesh has one panel.
=i.e. The cubedsphere has six panels; the planar and lbc meshes
=have one panel.
ns=namelist/Model/Mesh/Partitioning
sort-key=Section-A02

Expand Down
28 changes: 23 additions & 5 deletions components/driver/source/mesh/runtime_partition_mod.f90
Original file line number Diff line number Diff line change
Expand Up @@ -20,9 +20,11 @@ module runtime_partition_mod
partitioner_interface, &
partitioner_cubedsphere_serial, &
partitioner_cubedsphere, &
partitioner_planar
partitioner_planar, &
partitioner_lfric2lfric_lbc

use panel_decomposition_mod, only: panel_decomposition_type, &
use panel_decomposition_mod, only: panel_decomposition_type, &
lfric2lfric_lbc_decomposition_type, &
calc_mapping_factor
use sci_query_mod, only: is_lbc

Expand All @@ -36,8 +38,9 @@ module runtime_partition_mod
public :: create_local_mesh
public :: create_local_mesh_maps

integer, public, parameter :: mesh_cubedsphere = 34
integer, public, parameter :: mesh_planar = 28
integer, public, parameter :: mesh_cubedsphere = 34
integer, public, parameter :: mesh_planar = 28
integer, public, parameter :: mesh_lfric2lfric_lbc = 22

contains

Expand Down Expand Up @@ -94,6 +97,12 @@ subroutine get_partition_strategy( mesh_selection, total_ranks, partitioner_ptr
call log_event( "Using planar mesh partitioner ", &
log_level_debug )

case (mesh_lfric2lfric_lbc)

partitioner_ptr => partitioner_lfric2lfric_lbc
call log_event( "Using lfric2lfric lbc mesh partitioner ", &
log_level_debug )

end select

end subroutine get_partition_strategy
Expand Down Expand Up @@ -142,6 +151,8 @@ subroutine create_local_mesh( mesh_names, &
integer(i_def) :: local_mesh_id, i
integer(i_def) :: mapping_factor

logical(l_def) :: lfric2lfric_lbc

do i=1, size(mesh_names)

global_mesh_ptr => global_mesh_collection%get_global_mesh( mesh_names(i) )
Expand All @@ -160,7 +171,14 @@ subroutine create_local_mesh( mesh_names, &
! Create local_mesh
call local_mesh%initialise( global_mesh_ptr, partition )

if ( .not. is_lbc(local_mesh) ) then
select type (decomposition)
type is (lfric2lfric_lbc_decomposition_type)
lfric2lfric_lbc = .true.
class default
lfric2lfric_lbc = .false.
end select

if ( .not. is_lbc(local_mesh) .or. lfric2lfric_lbc) then
! Make sure the local_mesh cell owner lookup is correct
! (Can only be done when the code is running on its full set of MPI tasks)
call local_mesh%init_cell_owner()
Expand Down
1 change: 1 addition & 0 deletions infrastructure/source/mesh/global_mesh_mod.F90
Original file line number Diff line number Diff line change
Expand Up @@ -1097,6 +1097,7 @@ function get_cell_id( self, cell_number, &
! y_dist cells in the y-direction
! Since the direction may have changed we need to recompute
y_index = rotate(x_index)
if ( x_cells < 0 ) y_index = opposite(y_index)
if ( y_cells < 0 ) y_index = opposite(y_index)

! y_index and y_dist
Expand Down
110 changes: 110 additions & 0 deletions infrastructure/source/mesh/panel_decomposition_mod.f90
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,13 @@ module panel_decomposition_mod
procedure, public :: get_nprocs => get_column_nprocs
end type column_decomposition_type

!> @brief Decomposition for lfric2lfric lbc meshes
type, extends(panel_decomposition_type), public :: lfric2lfric_lbc_decomposition_type
contains
procedure, public :: get_partition => get_lfric2lfric_lbc_partition
procedure, public :: get_nprocs => get_lfric2lfric_lbc_nprocs
end type lfric2lfric_lbc_decomposition_type

!> @brief Decomposition that automatically generates a nonuniform decomposition
type, extends(panel_decomposition_type), public :: auto_nonuniform_decomposition_type
contains
Expand Down Expand Up @@ -560,6 +567,109 @@ function get_column_nprocs(self) result(nprocs)

end function get_column_nprocs

!> @brief Partition the panel into an automatically determined number of x and
!> y processes for lbc meshes in lfric2lfric jobs
!> @details The lbc mesh just contains a rim of cells of width rim_width,
!> and no cells in the interior of the regional mesh.
!> We will partition the lbc mesh in rows or columns of withd equal
!> to the rim width: there are two columns of length num_cells_y -
!> rim_width, and two columns of length num_cells_x - rim_width.
!> The cells are arranged in a line starting from the SW corner
!> and moving in anticlockwise order.
!> @param[in] relative_rank The number of this rank in the order of all
!> ranks on the panel
!> @param[in] panel_ranks The total number of ranks on the panel
!> @param[in] mapping_factor The ratio between this and coarsest mesh
!> @param[in] num_cells_x The panel's size in the x direction
!> @param[in] num_cells_y The panel's size in the y direction
!> @param[in] any_maps Whether there exist maps between meshes that
!> must having aligning partitions, .false. by
!> default in this partitioning strategy
!> @param[inout] partition_width The width of the lbc rim
!> @param[inout] partition_height The partition's size in the y direction
!> @param[inout] partition_x_pos Position along the rim starting in the
!> SW corner
!> @param[inout] partition_y_pos Length of partition cells along the rim
subroutine get_lfric2lfric_lbc_partition( self, &
relative_rank, &
panel_ranks, &
mapping_factor, &
num_cells_x, &
num_cells_y, &
any_maps, &
partition_width, &
partition_height, &
partition_x_pos, &
partition_y_pos )
implicit none

class(lfric2lfric_lbc_decomposition_type), intent(in) :: self
integer(i_def), intent(in) :: relative_rank, &
panel_ranks, &
mapping_factor, &
num_cells_x, &
num_cells_y
logical, intent(in) :: any_maps
integer(i_def), intent(inout) :: partition_width, &
partition_height, &
partition_x_pos, &
partition_y_pos

integer(i_def) :: lbc_length

call log_event("Using lfric2lfric lbc decomposition", LOG_LEVEL_INFO)

! Try to partition the lbc rim in segments of the same size
lbc_length = 2*(num_cells_x+num_cells_y-2*partition_width)

if (panel_ranks > lbc_length) then
write(log_scratch_space, "(a,i0,a,i0)") &
" Too many ranks: ", panel_ranks, &
" to decompose lbc of length:", lbc_length
call log_event(log_scratch_space, LOG_LEVEL_ERROR)
end if

! length of cells within the partition
partition_y_pos = nint(real(lbc_length) / real(panel_ranks))

! if the number of ranks does not divide exactly the length
! of the lbc rim, assign the last rank a different size
! to completely fill the lbc rim length
if (panel_ranks*partition_y_pos /= lbc_length) then
if (relative_rank == panel_ranks) then
partition_y_pos = lbc_length - (panel_ranks-1)*partition_y_pos
end if
end if

! first cell position in the partition
partition_x_pos = (relative_rank - 1) * partition_y_pos + 1

write(log_scratch_space, "(a,i0,a,i0,a,i0,a,i0)") &
" partition_x_pos ", partition_x_pos, &
" partition length", partition_y_pos, &
" partition_height ", partition_width
call log_event(log_scratch_space, LOG_LEVEL_INFO)

end subroutine get_lfric2lfric_lbc_partition

!> @brief Get the number of processors in the x- and y-direction.
!! For this class the function is not needed and so only
!! returns default values
!> @result nprocs Number of processors (x-dir, y-dir)
function get_lfric2lfric_lbc_nprocs(self) result(nprocs)
use constants_mod, only: i_def

class(lfric2lfric_lbc_decomposition_type), intent(in) :: self

integer(i_def) :: nprocs(2)

! These values aren't needed for column decomposition
! (and aren't available until get_column_partition has been called)
! so just return something that won't break the code
nprocs(:) = (/ 1, 1 /)

end function get_lfric2lfric_lbc_nprocs

!> @brief Partition the panel into an automatically determined number of
! columns of partitions of variable size.
!> @param[in] relative_rank The number of this rank in the order of all
Expand Down
Loading
Loading