27 integer,
intent(in) :: global_indices(:)
28 integer,
intent(in) :: ndivs
29 integer,
intent(out) :: layout(:)
31 integer :: isg, ieg, jsg, jeg, isz, jsz, idiv, jdiv
33 if(
size(global_indices(:)) .NE. 4)
call mpp_error(fatal,
"mpp_define_layout2D: size of global_indices should be 4")
34 if(
size(layout(:)) .NE. 2)
call mpp_error(fatal,
"mpp_define_layout2D: size of layout should be 2")
36 isg = global_indices(1)
37 ieg = global_indices(2)
38 jsg = global_indices(3)
39 jeg = global_indices(4)
44 idiv = nint( sqrt(float(ndivs*isz)/jsz) )
46 do while( mod(ndivs,idiv).NE.0 )
51 layout = (/ idiv, jdiv /)
62 integer,
dimension(:),
intent(in) :: sizes
63 integer,
dimension(:),
intent(inout) :: pe_start, pe_end
64 integer,
dimension(:),
intent(in),
optional :: pelist, costpertile
65 integer,
dimension(size(sizes(:))) :: costs
66 integer,
dimension(:),
allocatable :: pes
67 integer :: ntiles, npes, totcosts, avgcost
68 integer :: ntiles_left, npes_left, pos, n, tile
69 integer :: cost_on_tile, cost_on_pe, npes_used, errunit
71 ntiles =
size(sizes(:))
72 if(
size(pe_start(:)) .NE. ntiles .OR.
size(pe_end(:)) .NE. ntiles )
then
73 call mpp_error(fatal,
"mpp_define_mosaic_pelist: size mismatch between pe_start/pe_end and sizes")
76 if(
present(costpertile))
then
77 if(
size(costpertile(:)) .NE. ntiles )
then
78 call mpp_error(fatal,
"mpp_define_mosaic_pelist: size mismatch between costpertile and sizes")
80 costs = sizes*costpertile
85 if(
PRESENT(pelist) )
then
86 if( .NOT.any(pelist.EQ.
mpp_pe()) )
then
88 write( errunit,* )
'pe=',
mpp_pe(),
' pelist=', pelist
89 call mpp_error( fatal,
'mpp_define_mosaic_pelist: pe must be in pelist.' )
91 npes =
size(pelist(:))
92 allocate( pes(0:npes-1) )
96 allocate( pes(0:npes-1) )
97 call mpp_get_current_pelist(pes)
104 do while( ntiles_left > 0 )
105 if( npes_left == 1 )
then
107 if(costs(n) > 0)
then
116 totcosts = sum(costs)
117 avgcost = ceiling(real(totcosts)/npes_left )
118 tile = minval(maxloc(costs))
119 cost_on_tile = costs(tile)
121 ntiles_left = ntiles_left - 1
123 totcosts = totcosts - cost_on_tile
124 if(cost_on_tile .GE. avgcost )
then
125 npes_used = min(ceiling(real(cost_on_tile)/avgcost), npes_left)
126 if( ntiles_left > 0 .AND. npes_used == npes_left ) npes_used = npes_used - 1
127 pe_end(tile) = pos + npes_used - 1
128 npes_left = npes_left - npes_used
129 pos = pos + npes_used
133 cost_on_pe = cost_on_tile
134 do while(ntiles_left>npes_left)
135 tile = minval(minloc(costs, costs> 0 ))
136 cost_on_tile = costs(tile)
137 cost_on_pe = cost_on_pe + cost_on_tile
138 if(cost_on_pe > avgcost )
exit
141 ntiles_left = ntiles_left - 1
143 totcosts = totcosts - cost_on_tile
145 npes_left = npes_left - 1
151 if(npes_left .NE. 0 )
call mpp_error(fatal,
"mpp_define_mosaic_pelist: the left npes should be zero")
161 integer,
intent(in) :: isg, ieg, ndivs
162 integer,
dimension(:),
intent(out) :: ibegin, iend
170 is = ie - ceiling( real(ie-isg+1)/ndiv ) + 1
174 if( ie.LT.is )
call mpp_error( fatal, &
175 'MPP_DEFINE_DOMAINS(mpp_compute_block_extent): domain extents must be positive definite.' )
176 if( ndiv.EQ.1 .AND. ibegin(ndiv) .NE. isg ) &
177 call mpp_error( fatal,
'mpp_compute_block_extent: domain extents do not span space completely.' )
187 integer,
intent(in) :: isg, ieg, ndivs
188 integer,
dimension(0:),
intent(out) :: ibegin, iend
189 integer,
dimension(0:),
intent(in),
optional :: extent
191 integer :: ndiv, imax, ndmax, ndmirror
193 logical :: symmetrize, use_extent
196 even(n) = (mod(n,2).EQ.0)
197 odd(n) = (mod(n,2).EQ.1)
200 if(
PRESENT(extent))
then
201 if(
size(extent(:)).NE.ndivs ) &
202 call mpp_error( fatal,
'mpp_compute_extent: extent array size must equal number of domain divisions.' )
204 if(all(extent ==0)) use_extent = .false.
211 if(extent(ndiv) .LE. 0)
call mpp_error( fatal, &
212 &
'mpp_compute_extent: domain extents must be positive definite.' )
213 iend(ndiv) = ibegin(ndiv) + extent(ndiv) - 1
214 ibegin(ndiv+1) = iend(ndiv) + 1
216 iend(ndivs-1) = ibegin(ndivs-1) + extent(ndivs-1) - 1
217 if(iend(ndivs-1) .NE. ieg)
call mpp_error(fatal, &
218 &
'mpp_compute_extent: extent array limits do not match global domain.' )
232 symmetrize = ( even(ndivs) .AND. even(ieg-isg+1) ) .OR. &
233 ( odd(ndivs) .AND. odd(ieg-isg+1) ) .OR. &
234 ( odd(ndivs) .AND. even(ieg-isg+1) .AND. ndivs.LT.(ieg-isg+1)/2 )
243 if( ndiv.LT.(ndivs-1)/2+1 )
then
245 ie = is + ceiling( real(imax-is+1)/(ndmax-ndiv) ) - 1
246 ndmirror = (ndivs-1) - ndiv
247 if( ndmirror.GT.ndiv .AND. symmetrize )
then
249 ibegin(ndmirror) = max( isg+ieg-ie, ie+1 )
250 iend(ndmirror) = max( isg+ieg-is, ie+1 )
251 imax = ibegin(ndmirror) - 1
260 ie = is + ceiling( real(imax-is+1)/(ndmax-ndiv) ) - 1
265 if( ie.LT.is )
call mpp_error( fatal, &
266 'MPP_DEFINE_DOMAINS(mpp_compute_extent): domain extents must be positive definite.' )
267 if( ndiv.EQ.ndivs-1 .AND. iend(ndiv).NE.ieg ) &
268 call mpp_error( fatal,
'mpp_compute_extent: domain extents do not span space completely.' )
281 memory_size, begin_halo, end_halo )
282 integer,
intent(in) :: global_indices(:)
283 integer,
intent(in) :: ndivs
284 type(domain1d),
intent(inout) :: domain
286 integer,
intent(in),
optional :: pelist(0:)
289 integer,
intent(in),
optional :: flags, halo
293 integer,
intent(in),
optional :: extent(0:)
295 logical,
intent(in),
optional :: maskmap(0:)
300 integer,
intent(in),
optional :: memory_size
301 integer,
intent(in),
optional :: begin_halo, end_halo
303 logical :: compute_domain_is_global, data_domain_is_global
304 integer :: ndiv, n, isg, ieg
305 integer,
allocatable :: pes(:)
306 integer :: ibegin(0:ndivs-1), iend(0:ndivs-1)
307 logical :: mask(0:ndivs-1)
308 integer :: halosz, halobegin, haloend
311 if( .NOT.module_is_initialized )
call mpp_error( fatal, &
312 &
'MPP_DEFINE_DOMAINS1D: You must first call mpp_domains_init.' )
313 if(
size(global_indices(:)) .NE. 2)
call mpp_error(fatal,
"mpp_define_domains1D: size of global_indices should be 2")
315 isg = global_indices(1)
316 ieg = global_indices(2)
317 if( ndivs.GT.ieg-isg+1 )
call mpp_error( fatal, &
318 &
'MPP_DEFINE_DOMAINS1D: more divisions requested than rows available.' )
320 if(
PRESENT(pelist) )
then
321 if( .NOT.any(pelist.EQ.
mpp_pe()) )
then
323 write( errunit,* )
'pe=',
mpp_pe(),
' pelist=', pelist
324 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS1D: pe must be in pelist.' )
326 allocate( pes(0:
size(pelist(:))-1) )
330 call mpp_get_current_pelist(pes)
336 if(
PRESENT(maskmap) )
then
337 if(
size(maskmap(:)).NE.ndivs ) &
338 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS1D: maskmap array size must equal number of domain divisions.' )
341 if( count(mask).NE.
size(pes(:)) ) &
342 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS1D: number of TRUEs in maskmap array must match PE count.' )
346 if(
PRESENT(halo) )
then
349 if(
present(begin_halo) .OR.
present(end_halo) )
call mpp_error(fatal, &
350 "mpp_domains_define.inc: when halo is present, begin_halo and end_halo should not present")
352 halobegin = halosz; haloend = halosz
353 if(
present(begin_halo)) halobegin = begin_halo
354 if(
present(end_halo)) haloend = end_halo
355 halosz = max(halobegin, haloend)
357 compute_domain_is_global = .false.
358 data_domain_is_global = .false.
359 domain%cyclic = .false.
362 if(
PRESENT(flags) )
then
365 compute_domain_is_global = ndivs.EQ.1
367 data_domain_is_global = btest(flags,global) .OR. compute_domain_is_global
368 domain%cyclic = btest(flags,cyclic) .AND. halosz.NE.0
369 if(btest(flags,cyclic)) domain%goffset = 0
373 allocate( domain%list(0:ndivs-1) )
376 domain%list(:)%global%begin = isg
377 domain%list(:)%global%end = ieg
378 domain%list(:)%global%size = ieg-isg+1
379 domain%list(:)%global%max_size = ieg-isg+1
380 domain%list(:)%global%is_global = .true.
383 if( compute_domain_is_global )
then
384 domain%list(:)%compute%begin = isg
385 domain%list(:)%compute%end = ieg
386 domain%list(:)%compute%is_global = .true.
387 domain%list(:)%pe = pes(:)
390 domain%list(:)%compute%is_global = .false.
394 domain%list(ndiv)%compute%begin = ibegin(ndiv)
395 domain%list(ndiv)%compute%end = iend(ndiv)
397 domain%list(ndiv)%pe = pes(n)
398 if(
mpp_pe().EQ.pes(n) )domain%pos = ndiv
401 domain%list(ndiv)%pe = null_pe
406 domain%list(:)%compute%size = domain%list(:)%compute%end - domain%list(:)%compute%begin + 1
410 domain%list(:)%domain_data%begin = domain%list(:)%compute%begin
411 domain%list(:)%domain_data%end = domain%list(:)%compute%end
412 domain%list(:)%domain_data%is_global = .false.
414 if( data_domain_is_global )
then
415 domain%list(:)%domain_data%begin = isg
416 domain%list(:)%domain_data%end = ieg
417 domain%list(:)%domain_data%is_global = .true.
420 domain%list(:)%domain_data%begin = domain%list(:)%domain_data%begin - halobegin
421 domain%list(:)%domain_data%end = domain%list(:)%domain_data%end + haloend
422 domain%list(:)%domain_data%size = domain%list(:)%domain_data%end - domain%list(:)%domain_data%begin + 1
427 domain%list(:)%memory%begin = domain%list(:)%domain_data%begin
428 domain%list(:)%memory%end = domain%list(:)%domain_data%end
429 if(
present(memory_size) )
then
430 if(memory_size > 0)
then
431 if( domain%list(domain%pos)%domain_data%size > memory_size )
call mpp_error(fatal, &
432 "mpp_domains_define.inc: data domain size is larger than memory domain size on this pe")
433 domain%list(:)%memory%end = domain%list(:)%memory%begin + memory_size - 1
436 domain%list(:)%memory%size = domain%list(:)%memory%end - domain%list(:)%memory%begin + 1
437 domain%list(:)%memory%is_global = domain%list(:)%domain_data%is_global
439 domain%compute = domain%list(domain%pos)%compute
440 domain%domain_data = domain%list(domain%pos)%domain_data
441 domain%global = domain%list(domain%pos)%global
442 domain%memory = domain%list(domain%pos)%memory
443 domain%compute%max_size = maxval( domain%list(:)%compute%size )
444 domain%domain_data%max_size = maxval( domain%list(:)%domain_data%size )
445 domain%global%max_size = domain%global%size
446 domain%memory%max_size = domain%memory%size
457 type(domain2d),
intent(inout) :: domain
458 integer,
intent(in ) :: io_layout(2)
460 integer :: npes_in_group
461 type(domain2d),
pointer :: io_domain=>null()
462 integer :: i, j, n, m
463 integer :: ipos, jpos, igroup, jgroup
464 integer :: ipos_beg, ipos_end, jpos_beg, jpos_end
465 integer :: whalo, ehalo, shalo, nhalo
466 integer :: npes_x, npes_y, ndivx, ndivy
467 integer,
allocatable :: posarray(:,:)
469 if(io_layout(1) * io_layout(2) .LE. 0)
then
470 call mpp_error(note, &
471 "mpp_domains_define.inc(mpp_define_io_domain): io domain will not be defined for "//trim(domain%name)// &
472 " when one or both entry of io_layout is not positive")
476 layout(1) =
size(domain%x(1)%list(:))
477 layout(2) =
size(domain%y(1)%list(:))
479 if(
ASSOCIATED(domain%io_domain))
call mpp_error(fatal, &
480 "mpp_domains_define.inc(mpp_define_io_domain): io_domain is already defined")
482 if(mod(layout(1), io_layout(1)) .NE. 0)
call mpp_error(fatal, &
483 "mpp_domains_define.inc(mpp_define_io_domain): "//trim(domain%name)// &
484 &
" domain layout(1) must be divided by io_layout(1)")
485 if(mod(layout(2), io_layout(2)) .NE. 0)
call mpp_error(fatal, &
486 "mpp_domains_define.inc(mpp_define_io_domain): "//trim(domain%name)// &
487 &
" domain layout(2) must be divided by io_layout(2)")
488 if(
size(domain%x(:)) > 1)
call mpp_error(fatal, &
489 "mpp_domains_define.inc(mpp_define_io_domain): "//trim(domain%name)// &
490 ": multiple tile per pe is not supported yet for this routine")
492 if (
associated(domain%io_domain))
deallocate(domain%io_domain)
493 allocate(domain%io_domain)
494 domain%io_layout = io_layout
495 io_domain => domain%io_domain
497 npes_x = layout(1)/io_layout(1)
498 npes_y = layout(2)/io_layout(2)
499 ipos = mod(domain%x(1)%pos, npes_x)
500 jpos = mod(domain%y(1)%pos, npes_y)
501 igroup = domain%x(1)%pos/npes_x
502 jgroup = domain%y(1)%pos/npes_y
503 ipos_beg = igroup*npes_x; ipos_end = ipos_beg + npes_x - 1
504 jpos_beg = jgroup*npes_y; jpos_end = jpos_beg + npes_y - 1
506 do j = jpos_beg, jpos_end
507 do i = ipos_beg, ipos_end
508 if(domain%pearray(i,j) .NE. null_pe) npes_in_group = npes_in_group+1
512 io_domain%whalo = domain%whalo
513 io_domain%ehalo = domain%ehalo
514 io_domain%shalo = domain%shalo
515 io_domain%nhalo = domain%nhalo
517 io_domain%pe = domain%pe
518 io_domain%symmetry = domain%symmetry
519 if (
associated(io_domain%list))
deallocate(io_domain%list)
520 allocate(io_domain%list(0:npes_in_group-1))
521 do i = 0, npes_in_group-1
522 allocate( io_domain%list(i)%x(1), io_domain%list(i)%y(1), io_domain%list(i)%tile_id(1) )
525 ndivx =
size(domain%pearray,1)
526 ndivy =
size(domain%pearray,2)
527 allocate(posarray(0:ndivx-1, 0:ndivy-1))
528 n = domain%tile_root_pe - mpp_root_pe()
532 if( domain%pearray(i,j) == null_pe) cycle
539 do j = jpos_beg, jpos_end
540 do i = ipos_beg, ipos_end
541 if( domain%pearray(i,j) == null_pe) cycle
542 io_domain%list(n)%pe = domain%pearray(i,j)
544 io_domain%list(n)%x(1)%compute = domain%list(m)%x(1)%compute
545 io_domain%list(n)%y(1)%compute = domain%list(m)%y(1)%compute
546 igroup = domain%list(m)%x(1)%pos/npes_x
547 jgroup = domain%list(m)%y(1)%pos/npes_y
548 io_domain%list(n)%tile_id(1) = jgroup*io_layout(1) + igroup
554 if (
associated(io_domain%x))
deallocate(io_domain%x)
555 if (
associated(io_domain%y))
deallocate(io_domain%y)
556 if (
associated(io_domain%tile_id))
deallocate(io_domain%tile_id)
557 allocate(io_domain%x(1), io_domain%y(1), io_domain%tile_id(1) )
558 allocate(io_domain%x(1)%list(0:npes_x-1), io_domain%y(1)%list(0:npes_y-1) )
560 do j = jpos_beg, jpos_beg+jpos
561 do i = ipos_beg, ipos_beg+ipos
562 if(domain%pearray(i,j) .NE. null_pe) n = n + 1
566 io_domain%x(1)%compute = domain%x(1)%compute
567 io_domain%x(1)%domain_data = domain%x(1)%domain_data
568 io_domain%x(1)%memory = domain%x(1)%memory
569 io_domain%y(1)%compute = domain%y(1)%compute
570 io_domain%y(1)%domain_data = domain%y(1)%domain_data
571 io_domain%y(1)%memory = domain%y(1)%memory
572 io_domain%x(1)%global%begin = domain%x(1)%list(ipos_beg)%compute%begin
573 io_domain%x(1)%global%end = domain%x(1)%list(ipos_end)%compute%end
574 io_domain%x(1)%global%size = io_domain%x(1)%global%end - io_domain%x(1)%global%begin + 1
575 io_domain%x(1)%global%max_size = io_domain%x(1)%global%size
576 io_domain%y(1)%global%begin = domain%y(1)%list(jpos_beg)%compute%begin
577 io_domain%y(1)%global%end = domain%y(1)%list(jpos_end)%compute%end
578 io_domain%y(1)%global%size = io_domain%y(1)%global%end - io_domain%y(1)%global%begin + 1
579 io_domain%y(1)%global%max_size = io_domain%y(1)%global%size
580 io_domain%x(1)%pos = ipos
581 io_domain%y(1)%pos = jpos
582 io_domain%tile_id(1) = io_domain%list(n)%tile_id(1)
583 io_domain%tile_root_pe = io_domain%list(0)%pe
608 xhalo, yhalo, xextent, yextent, maskmap, name, symmetry, memory_size, &
609 whalo, ehalo, shalo, nhalo, is_mosaic, tile_count, tile_id, complete, x_cyclic_offset, y_cyclic_offset )
610 integer,
intent(in) :: global_indices(:)
611 integer,
intent(in) :: layout(:)
612 type(domain2d),
intent(inout) :: domain
613 integer,
intent(in),
optional :: pelist(0:)
614 integer,
intent(in),
optional :: xflags, yflags
615 integer,
intent(in),
optional :: xhalo, yhalo
616 integer,
intent(in),
optional :: xextent(0:), yextent(0:)
617 logical,
intent(in),
optional :: maskmap(0:,0:)
618 character(len=*),
intent(in),
optional :: name
619 logical,
intent(in),
optional :: symmetry
620 logical,
intent(in),
optional :: is_mosaic
622 integer,
intent(in),
optional :: memory_size(:)
623 integer,
intent(in),
optional :: whalo, ehalo, shalo, nhalo
629 integer,
intent(in),
optional :: tile_count
633 integer,
intent(in),
optional :: tile_id
634 logical,
intent(in),
optional :: complete
636 integer,
intent(in),
optional :: x_cyclic_offset
639 integer,
intent(in),
optional :: y_cyclic_offset
644 integer :: i, j, m, n, xhalosz, yhalosz, memory_xsize, memory_ysize
645 integer :: whalosz, ehalosz, shalosz, nhalosz
646 integer :: ipos, jpos, pos, tile, nlist, cur_tile_id
647 type(mpi_comm) :: cur_comm
648 integer :: ndivx, ndivy, isg, ieg, jsg, jeg, ishift, jshift, errunit, logunit
649 integer :: x_offset, y_offset, start_pos, nfold
650 logical :: from_mosaic, is_complete
651 logical :: mask(0:layout(1)-1,0:layout(2)-1)
652 integer,
allocatable :: pes(:), pesall(:)
653 integer :: pearray(0:layout(1)-1,0:layout(2)-1)
654 integer :: ibegin(0:layout(1)-1), iend(0:layout(1)-1)
655 integer :: jbegin(0:layout(2)-1), jend(0:layout(2)-1)
656 character(len=8) :: text
657 type(overlapspec),
pointer :: check_T => null()
659 logical :: send(8), recv(8)
662 if( .NOT.module_is_initialized )
call mpp_error( fatal, &
663 &
'MPP_DEFINE_DOMAINS2D: You must first call mpp_domains_init.' )
664 if(
PRESENT(name))
then
665 if(len_trim(name) > name_length)
call mpp_error(fatal, &
666 "mpp_domains_define.inc(mpp_define_domains2D): the len_trim of optional argument name ="//trim(name)// &
667 " is greater than NAME_LENGTH, change the argument name or increase NAME_LENGTH")
670 if(
size(global_indices(:)) .NE. 4)
call mpp_error(fatal, &
671 "mpp_define_domains2D: size of global_indices should be 4 for "//trim(domain%name) )
672 if(
size(layout(:)) .NE. 2)
call mpp_error(fatal,
"mpp_define_domains2D: size of layout should be 2 for "// &
673 & trim(domain%name) )
675 ndivx = layout(1); ndivy = layout(2)
676 isg = global_indices(1); ieg = global_indices(2); jsg = global_indices(3); jeg = global_indices(4)
678 from_mosaic = .false.
679 if(
present(is_mosaic)) from_mosaic = is_mosaic
681 if(
present(complete)) is_complete = complete
683 if(
present(tile_count)) tile = tile_count
685 if(
present(tile_id)) cur_tile_id = tile_id
687 cur_comm = mpi_comm_null
688 if(
PRESENT(pelist) )
then
689 allocate( pes(0:
size(pelist(:))-1) )
693 call mpp_get_current_pelist(pesall, comm=cur_comm)
695 allocate( pesall(0:
size(pes(:))-1) )
697 call mpp_get_current_pelist(pesall, comm=cur_comm)
702 call mpp_get_current_pelist(pes, comm=cur_comm)
709 x_offset = 0; y_offset = 0
710 if(
PRESENT(x_cyclic_offset)) x_offset = x_cyclic_offset
711 if(
PRESENT(y_cyclic_offset)) y_offset = y_cyclic_offset
712 if(x_offset*y_offset .NE. 0)
call mpp_error(fatal, &
713 'MPP_DEFINE_DOMAINS2D: At least one of x_cyclic_offset and y_cyclic_offset must be zero for '// &
717 if(abs(x_offset) > jeg-jsg+1)
call mpp_error(fatal, &
718 'MPP_DEFINE_DOMAINS2D: absolute value of x_cyclic_offset is greater than jeg-jsg+1 for '//trim(domain%name))
719 if(abs(y_offset) > ieg-isg+1)
call mpp_error(fatal, &
720 'MPP_DEFINE_DOMAINS2D: absolute value of y_cyclic_offset is greater than ieg-isg+1 for '//trim(domain%name))
723 if( tile > 1 .AND.
size(pes(:)) > 1)
call mpp_error(fatal, &
724 'MPP_DEFINE_DOMAINS2D: there are more than one tile on this pe, '// &
725 'all the tile should be limited on this pe for '//trim(domain%name))
731 do n = 0,
size(pesall(:))-1
732 if(pesall(n) ==
mpp_pe() )
then
737 if(pos<0)
call mpp_error(fatal,
'MPP_DEFINE_DOMAINS2D: mpp_pe() is not in the pesall list')
739 domain%symmetry = .false.
740 if(
present(symmetry)) domain%symmetry = symmetry
741 if(domain%symmetry)
then
742 ishift = 1; jshift = 1
744 ishift = 0; jshift = 0
751 xhalosz = 0; yhalosz = 0
752 if(
present(xhalo)) xhalosz = xhalo
753 if(
present(yhalo)) yhalosz = yhalo
754 whalosz = xhalosz; ehalosz = xhalosz
755 shalosz = yhalosz; nhalosz = yhalosz
756 if(
present(whalo)) whalosz = whalo
757 if(
present(ehalo)) ehalosz = ehalo
758 if(
present(shalo)) shalosz = shalo
759 if(
present(nhalo)) nhalosz = nhalo
763 if(
PRESENT(maskmap) )
then
764 if(
size(maskmap,1).NE.ndivx .OR.
size(maskmap,2).NE.ndivy ) &
765 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS2D: maskmap array does not match layout for '// &
766 & trim(domain%name) )
767 mask(:,:) = maskmap(:,:)
771 if( n.NE.
size(pes(:)) )
then
772 write( text,
'(i8)' )n
773 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS2D: incorrect number of PEs assigned for ' // &
774 'this layout and maskmap. Use '//text//
' PEs for this domain decomposition for '//trim(domain%name) )
777 memory_xsize = 0; memory_ysize = 0
778 if(
present(memory_size))
then
779 if(
size(memory_size(:)) .NE. 2)
call mpp_error(fatal, &
780 "mpp_define_domains2D: size of memory_size should be 2 for "//trim(domain%name))
781 memory_xsize = memory_size(1)
782 memory_ysize = memory_size(2)
788 nlist =
size(pesall(:))
789 if( .NOT.
Associated(domain%x) )
then
790 allocate(domain%tileList(1))
791 domain%tileList(1)%xbegin = global_indices(1)
792 domain%tileList(1)%xend = global_indices(2)
793 domain%tileList(1)%ybegin = global_indices(3)
794 domain%tileList(1)%yend = global_indices(4)
795 allocate(domain%x(1), domain%y(1) )
796 allocate(domain%tile_id(1))
797 allocate(domain%tile_id_all(1))
798 domain%tile_id = cur_tile_id
799 domain%tile_id_all = cur_tile_id
800 domain%tile_comm = cur_comm
802 domain%max_ntile_pe = 1
804 domain%rotated_ninety = .false.
805 allocate( domain%list(0:nlist-1) )
807 allocate( domain%list(i)%x(1), domain%list(i)%y(1), domain%list(i)%tile_id(1))
811 domain%initialized = .true.
815 if(pesall(n) == pes(0))
then
822 pearray(:,:) = null_pe
823 ipos = null_pe; jpos = null_pe
829 pearray(i,j) = pes(n)
830 domain%list(m)%x(tile)%compute%begin = ibegin(i)
831 domain%list(m)%x(tile)%compute%end = iend(i)
832 domain%list(m)%y(tile)%compute%begin = jbegin(j)
833 domain%list(m)%y(tile)%compute%end = jend(j)
834 domain%list(m)%x(tile)%compute%size = domain%list(m)%x(tile)%compute%end &
835 & - domain%list(m)%x(tile)%compute%begin + 1
836 domain%list(m)%y(tile)%compute%size = domain%list(m)%y(tile)%compute%end &
837 & - domain%list(m)%y(tile)%compute%begin + 1
838 domain%list(m)%tile_id(tile) = cur_tile_id
839 domain%list(m)%x(tile)%pos = i
840 domain%list(m)%y(tile)%pos = j
841 domain%list(m)%tile_root_pe = pes(0)
842 domain%list(m)%pe = pesall(m)
844 if( pes(n).EQ.
mpp_pe() )
then
856 if( any(pes ==
mpp_pe()) )
then
857 domain%io_layout = layout
858 domain%tile_root_pe = pes(0)
859 domain%comm = cur_comm
860 if( ipos.EQ.null_pe .OR. jpos.EQ.null_pe ) &
861 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS2D: pelist must include this PE for '//trim(domain%name) )
864 write( errunit, * )
'pe, tile, ipos, jpos=',
mpp_pe(), tile, ipos, jpos,
' pearray(:,jpos)=', &
865 pearray(:,jpos),
' pearray(ipos,:)=', pearray(ipos,:)
870 if (
associated(domain%pearray))
deallocate(domain%pearray)
871 allocate( domain%pearray(0:ndivx-1,0:ndivy-1) )
872 domain%pearray = pearray
877 domain_cnt = domain_cnt + int(1,kind=i8_kind)
878 domain%id = domain_cnt*domain_id_base
881 call mpp_define_domains( global_indices(1:2), ndivx, domain%x(tile), &
882 pack(pearray(:,jpos),mask(:,jpos)), xflags, xhalo, xextent, mask(:,jpos), memory_xsize, whalo, ehalo )
883 call mpp_define_domains( global_indices(3:4), ndivy, domain%y(tile), &
884 pack(pearray(ipos,:),mask(ipos,:)), yflags, yhalo, yextent, mask(ipos,:), memory_ysize, shalo, nhalo )
885 if( domain%x(tile)%list(ipos)%pe.NE.domain%y(tile)%list(jpos)%pe ) &
886 call mpp_error( fatal, .NE.
'MPP_DEFINE_DOMAINS2D: domain%x%list(ipos)%pedomain%y%list(jpos)%pe.' )
889 if(x_offset .NE. 0 .OR. y_offset .NE. 0)
then
890 if(whalosz .GT. domain%x(tile)%compute%size .OR. ehalosz .GT. domain%x(tile)%compute%size ) &
891 call mpp_error(fatal,
"mpp_define_domains_2d: when x_cyclic_offset/y_cyclic_offset is set, "// &
892 "whalo and ehalo must be no larger than the x-direction computation domain size")
893 if(shalosz .GT. domain%y(tile)%compute%size .OR. nhalosz .GT. domain%y(tile)%compute%size ) &
894 call mpp_error(fatal,
"mpp_define_domains_2d: when x_cyclic_offset/y_cyclic_offset is set, "// &
895 "shalo and nhalo must be no larger than the y-direction computation domain size")
899 if(whalosz .GT. domain%x(tile)%global%size) &
900 call mpp_error(fatal,
"MPP_DEFINE_DOMAINS2D: whalo is greather global domain size")
901 if(ehalosz .GT. domain%x(tile)%global%size) &
902 call mpp_error(fatal,
"MPP_DEFINE_DOMAINS2D: ehalo is greather global domain size")
903 if(shalosz .GT. domain%x(tile)%global%size) &
904 call mpp_error(fatal,
"MPP_DEFINE_DOMAINS2D: shalo is greather global domain size")
905 if(nhalosz .GT. domain%x(tile)%global%size) &
906 call mpp_error(fatal,
"MPP_DEFINE_DOMAINS2D: nhalo is greather global domain size")
911 if(
PRESENT(xflags) )
then
912 if( btest(xflags,west) )
then
914 if(domain%x(tile)%domain_data%begin .LE. domain%x(tile)%global%begin .AND. &
915 domain%x(tile)%compute%begin > domain%x(tile)%global%begin )
then
916 call mpp_error(fatal, &
917 'MPP_DEFINE_DOMAINS: the domain could not be crossed when west is folded')
919 if( domain%x(tile)%cyclic )
call mpp_error( fatal, &
920 'MPP_DEFINE_DOMAINS: an axis cannot be both folded west and cyclic for '//trim(domain%name) )
921 domain%fold = domain%fold + fold_west_edge
924 if( btest(xflags,east) )
then
926 if(domain%x(tile)%domain_data%end .GE. domain%x(tile)%global%end .AND. &
927 domain%x(tile)%compute%end < domain%x(tile)%global%end )
then
928 call mpp_error(fatal, &
929 'MPP_DEFINE_DOMAINS: the domain could not be crossed when north is folded')
931 if( domain%x(tile)%cyclic )
call mpp_error( fatal, &
932 'MPP_DEFINE_DOMAINS: an axis cannot be both folded east and cyclic for '//trim(domain%name) )
933 domain%fold = domain%fold + fold_east_edge
937 if(
PRESENT(yflags) )
then
938 if( btest(yflags,south) )
then
940 if(domain%y(tile)%domain_data%begin .LE. domain%y(tile)%global%begin .AND. &
941 domain%y(tile)%compute%begin > domain%y(tile)%global%begin )
then
942 call mpp_error(fatal, &
943 'MPP_DEFINE_DOMAINS: the domain could not be crossed when south is folded')
945 if( domain%y(tile)%cyclic )
call mpp_error( fatal, &
946 'MPP_DEFINE_DOMAINS: an axis cannot be both folded north and cyclic for '//trim(domain%name))
947 domain%fold = domain%fold + fold_south_edge
950 if( btest(yflags,north) )
then
953 if(whalosz .GT. domain%x(tile)%compute%size .AND. whalosz .GE. domain%x(tile)%global%size/2 ) &
954 call mpp_error(fatal, .GT.
"MPP_DEFINE_DOMAINS2D: north is folded, whalo compute domain size "// &
955 .GE.
"and whalo half of global domain size")
956 if(ehalosz .GT. domain%x(tile)%compute%size .AND. ehalosz .GE. domain%x(tile)%global%size/2 ) &
957 call mpp_error(fatal, .GT.
"MPP_DEFINE_DOMAINS2D: north is folded, ehalo is compute domain size "// &
958 .GE.
"and ehalo half of global domain size")
959 if(shalosz .GT. domain%y(tile)%compute%size .AND. shalosz .GE. domain%x(tile)%global%size/2 ) &
960 call mpp_error(fatal, .GT.
"MPP_DEFINE_DOMAINS2D: north is folded, shalo compute domain size "// &
961 .GE.
"and shalo half of global domain size")
962 if(nhalosz .GT. domain%y(tile)%compute%size .AND. nhalosz .GE. domain%x(tile)%global%size/2 ) &
963 call mpp_error(fatal, .GT.
"MPP_DEFINE_DOMAINS2D: north is folded, nhalo compute domain size "// &
964 .GE.
"and nhalo half of global domain size")
967 if( domain%y(tile)%cyclic )
call mpp_error( fatal, &
968 'MPP_DEFINE_DOMAINS: an axis cannot be both folded south and cyclic for '//trim(domain%name) )
969 domain%fold = domain%fold + fold_north_edge
973 if(nfold > 1)
call mpp_error(fatal, &
974 'MPP_DEFINE_DOMAINS2D: number of folded edge is greater than 1 for '//trim(domain%name) )
977 if( x_offset .NE. 0 .OR. y_offset .NE. 0)
call mpp_error(fatal, &
978 'MPP_DEFINE_DOMAINS2D: For the foled_north/folded_south/fold_east/folded_west boundary condition, '//&
979 'x_cyclic_offset and y_cyclic_offset must be zero for '//trim(domain%name))
981 if( btest(domain%fold,south) .OR. btest(domain%fold,north) )
then
982 if( domain%y(tile)%cyclic )
call mpp_error( fatal, &
983 'MPP_DEFINE_DOMAINS: an axis cannot be both folded and cyclic for '//trim(domain%name) )
984 if( modulo(domain%x(tile)%global%size,2).NE.0 ) &
985 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS: number of points in X must be even ' // &
986 'when there is a fold in Y for '//trim(domain%name) )
991 if( domain%x(tile)%list(i)%compute%size.NE.domain%x(tile)%list(n-i)%compute%size ) &
992 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS: Folded domain boundaries ' // &
993 'must line up (mirror-symmetric extents) for '//trim(domain%name) )
996 if( btest(domain%fold,west) .OR. btest(domain%fold,east) )
then
997 if( domain%x(tile)%cyclic )
call mpp_error( fatal, &
998 'MPP_DEFINE_DOMAINS: an axis cannot be both folded and cyclic for '//trim(domain%name) )
999 if( modulo(domain%y(tile)%global%size,2).NE.0 ) &
1000 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS: number of points in Y must be even '//&
1001 'when there is a fold in X for '//trim(domain%name) )
1006 if( domain%y(tile)%list(i)%compute%size.NE.domain%y(tile)%list(n-i)%compute%size ) &
1007 call mpp_error( fatal,
'MPP_DEFINE_DOMAINS: Folded domain boundaries must '//&
1008 'line up (mirror-symmetric extents) for '//trim(domain%name) )
1013 if(
mpp_pe().EQ.pes(0) .AND.
PRESENT(name) )
then
1015 write( logunit,
'(/a,i5,a,i5)' )trim(name)//
' domain decomposition: ', ndivx,
' X', ndivy
1016 write( logunit,
'(3x,a)' )
'pe, is, ie, js, je, isd, ied, jsd, jed'
1020 if(is_complete)
then
1021 domain%whalo = whalosz; domain%ehalo = ehalosz
1022 domain%shalo = shalosz; domain%nhalo = nhalosz
1023 if (
associated(domain%update_T))
deallocate(domain%update_T)
1024 if (
associated(domain%update_E))
deallocate(domain%update_E)
1025 if (
associated(domain%update_C))
deallocate(domain%update_C)
1026 if (
associated(domain%update_N))
deallocate(domain%update_N)
1027 allocate(domain%update_T, domain%update_E, domain%update_C, domain%update_N)
1028 domain%update_T%next => null()
1029 domain%update_E%next => null()
1030 domain%update_C%next => null()
1031 domain%update_N%next => null()
1032 if (
associated(domain%check_E))
deallocate(domain%check_E)
1033 if (
associated(domain%check_C))
deallocate(domain%check_C)
1034 if (
associated(domain%check_N))
deallocate(domain%check_N)
1035 allocate(domain%check_E, domain%check_C, domain%check_N )
1036 domain%update_T%nsend = 0
1037 domain%update_T%nrecv = 0
1038 domain%update_C%nsend = 0
1039 domain%update_C%nrecv = 0
1040 domain%update_E%nsend = 0
1041 domain%update_E%nrecv = 0
1042 domain%update_N%nsend = 0
1043 domain%update_N%nrecv = 0
1045 if( btest(domain%fold,south) )
then
1050 else if( btest(domain%fold,west) )
then
1055 else if( btest(domain%fold,east) )
then
1061 call compute_overlaps(domain, center, domain%update_T, check_t, 0, 0, x_offset, y_offset, &
1062 domain%whalo, domain%ehalo, domain%shalo, domain%nhalo)
1063 call compute_overlaps(domain, corner, domain%update_C, domain%check_C, ishift, jshift, x_offset, y_offset, &
1064 domain%whalo, domain%ehalo, domain%shalo, domain%nhalo)
1065 call compute_overlaps(domain, east, domain%update_E, domain%check_E, ishift, 0, x_offset, y_offset, &
1066 domain%whalo, domain%ehalo, domain%shalo, domain%nhalo)
1067 call compute_overlaps(domain, north, domain%update_N, domain%check_N, 0, jshift, x_offset, y_offset, &
1068 domain%whalo, domain%ehalo, domain%shalo, domain%nhalo)
1070 call check_overlap_pe_order(domain, domain%update_T, trim(domain%name)//
" update_T in mpp_define_domains")
1071 call check_overlap_pe_order(domain, domain%update_C, trim(domain%name)//
" update_C in mpp_define_domains")
1072 call check_overlap_pe_order(domain, domain%update_E, trim(domain%name)//
" update_E in mpp_define_domains")
1073 call check_overlap_pe_order(domain, domain%update_N, trim(domain%name)//
" update_N in mpp_define_domains")
1077 if(domain%symmetry .AND. (domain%ncontacts == 0 .OR. domain%ntiles == 1) )
then
1081 if (
associated(domain%bound_E))
deallocate(domain%bound_E)
1082 if (
associated(domain%bound_C))
deallocate(domain%bound_C)
1083 if (
associated(domain%bound_N))
deallocate(domain%bound_N)
1084 allocate(domain%bound_E, domain%bound_C, domain%bound_N )
1089 call set_domain_comm_inf(domain%update_T)
1090 call set_domain_comm_inf(domain%update_E)
1091 call set_domain_comm_inf(domain%update_C)
1092 call set_domain_comm_inf(domain%update_N)
1098 if(debug_message_passing .and. (domain%ncontacts == 0 .OR. domain%ntiles == 1) )
then
1101 call check_message_size(domain, domain%update_T, send, recv,
'T')
1102 call check_message_size(domain, domain%update_E, send, recv,
'E')
1103 call check_message_size(domain, domain%update_C, send, recv,
'C')
1104 call check_message_size(domain, domain%update_N, send, recv,
'N')
1109 if(
mpp_pe() .EQ. pes(0) .AND.
PRESENT(name) )
then
1110 write(*,*) trim(name)//
' domain decomposition'
1111 write(*,
'(a,i4,a,i4,a,i4,a,i4)')
'whalo = ', whalosz,
", ehalo = ", ehalosz,
", shalo = ", shalosz, &
1112 &
", nhalo = ", nhalosz
1113 write (*,110) (domain%x(1)%list(i)%compute%size, i= 0, layout(1)-1)
1114 write (*,120) (domain%y(1)%list(i)%compute%size, i= 0, layout(2)-1)
1115 110
format (
' X-AXIS = ',24i4,/,(11x,24i4))
1116 120
format (
' Y-AXIS = ',24i4,/,(11x,24i4))
1119 deallocate( pes, pesall)
1127 subroutine check_message_size(domain, update, send, recv, position)
1128 type(domain2d),
intent(in) :: domain
1129 type(overlapspec),
intent(in) :: update
1130 logical,
intent(in) :: send(:)
1131 logical,
intent(in) :: recv(:)
1132 character,
intent(in) :: position
1134 integer,
dimension(0:size(domain%list(:))-1) :: msg1, msg2, msg3
1135 integer :: m, n, l, dir, is, ie, js, je, from_pe, msgsize
1138 nlist =
size(domain%list(:))
1143 do m = 1, update%nrecv
1145 do n = 1, update%recv(m)%count
1146 dir = update%recv(m)%dir(n)
1147 if( recv(dir) )
then
1148 is = update%recv(m)%is(n); ie = update%recv(m)%ie(n)
1149 js = update%recv(m)%js(n); je = update%recv(m)%je(n)
1150 msgsize = msgsize + (ie-is+1)*(je-js+1)
1153 from_pe = update%recv(m)%pe
1154 l = from_pe-mpp_root_pe()
1155 call mpp_recv( msg1(l), glen=1, from_pe=from_pe, block=.false., tag=comm_tag_1)
1159 do m = 1, update%nsend
1161 do n = 1, update%send(m)%count
1162 dir = update%send(m)%dir(n)
1164 is = update%send(m)%is(n); ie = update%send(m)%ie(n)
1165 js = update%send(m)%js(n); je = update%send(m)%je(n)
1166 msgsize = msgsize + (ie-is+1)*(je-js+1)
1169 l = update%send(m)%pe-mpp_root_pe()
1171 call mpp_send( msg3(l), plen=1, to_pe=update%send(m)%pe, tag=comm_tag_1)
1176 if(msg1(m) .NE. msg2(m))
then
1177 print*,
"My pe = ",
mpp_pe(),
",domain name =", trim(domain%name),
",at position=",position,
",from pe=", &
1178 domain%list(m)%pe,
":send size = ", msg1(m),
", recv size = ", msg2(m)
1179 call mpp_error(fatal,
"mpp_define_domains2D: mismatch on send and recv size")
1185 end subroutine check_message_size
1201 subroutine mpp_define_mosaic( global_indices, layout, domain, num_tile, num_contact, tile1, tile2, &
1202 istart1, iend1, jstart1, jend1, istart2, iend2, jstart2, jend2, pe_start, &
1203 pe_end, pelist, whalo, ehalo, shalo, nhalo, xextent, yextent, &
1204 maskmap, name, memory_size, symmetry, xflags, yflags, tile_id )
1205 integer,
intent(in) :: global_indices(:,:)
1209 integer,
intent(in) :: layout(:,:)
1210 type(domain2d),
intent(inout) :: domain
1211 integer,
intent(in) :: num_tile
1212 integer,
intent(in) :: num_contact
1213 integer,
intent(in) :: tile1(:), tile2(:)
1214 integer,
intent(in) :: istart1(:), iend1(:)
1215 integer,
intent(in) :: jstart1(:), jend1(:)
1216 integer,
intent(in) :: istart2(:), iend2(:)
1217 integer,
intent(in) :: jstart2(:), jend2(:)
1218 integer,
intent(in) :: pe_start(:)
1219 integer,
intent(in) :: pe_end(:)
1220 integer,
intent(in),
optional :: pelist(:)
1221 integer,
intent(in),
optional :: whalo, ehalo, shalo, nhalo
1222 integer,
intent(in),
optional :: xextent(:,:), yextent(:,:)
1223 logical,
intent(in),
optional :: maskmap(:,:,:)
1224 character(len=*),
intent(in),
optional :: name
1225 integer,
intent(in),
optional :: memory_size(2)
1226 logical,
intent(in),
optional :: symmetry
1227 integer,
intent(in),
optional :: xflags, yflags
1228 integer,
intent(in),
optional :: tile_id(:)
1230 integer :: n, m, ndivx, ndivy, nc, nlist, nt, pos, n1, n2
1231 integer :: whalosz, ehalosz, shalosz, nhalosz, xhalosz, yhalosz, t1, t2, tile
1232 integer :: flags_x, flags_y
1233 logical,
allocatable :: mask(:,:)
1234 integer,
allocatable :: pes(:), xext(:), yext(:), pelist_tile(:), ntile_per_pe(:), tile_count(:)
1235 integer,
allocatable :: tile_id_local(:)
1236 integer :: tile_base
1237 logical :: is_symmetry
1238 integer,
allocatable :: align1(:), align2(:), is1(:), ie1(:), js1(:), je1(:), is2(:), ie2(:), js2(:), je2(:)
1239 integer,
allocatable :: isgList(:), iegList(:), jsgList(:), jegList(:)
1240 real,
allocatable :: refine1(:), refine2(:)
1242 logical :: send(8), recv(8)
1245 mosaic_defined = .true.
1247 if(
size(global_indices, 1) .NE. 4)
call mpp_error(fatal, &
1248 'mpp_domains_define.inc: The size of first dimension of global_indices is not 4')
1250 if(
size(global_indices, 2) .NE. num_tile)
call mpp_error(fatal, &
1251 'mpp_domains_define.inc: The size of second dimension of global_indices is not equal num_tile')
1253 if(
size(layout, 1) .NE. 2)
call mpp_error(fatal, &
1254 'mpp_domains_define.inc: The size of first dimension of layout is not 2')
1255 if(
size(layout,2) .NE. num_tile)
call mpp_error(fatal, &
1256 'mpp_domains_define.inc: The size of second dimension of layout is not equal num_tile')
1260 allocate(pes(0:nlist-1))
1261 if(
present(pelist))
then
1262 if( nlist .NE.
size(pelist(:)))
call mpp_error(fatal, &
1263 'mpp_domains_define.inc: size of pelist is not equal mpp_npes')
1266 call mpp_get_current_pelist(pes, comm=domain%comm)
1269 if(pes(n) - pes(n-1) .NE. 1)
call mpp_error(fatal, &
1270 'mpp_domains_define.inc: pelist is not monotonic increasing by 1')
1273 is_symmetry = .false.
1274 if(
present(symmetry)) is_symmetry = symmetry
1276 if(
size(pe_start(:)) .NE. num_tile .OR.
size(pe_end(:)) .NE. num_tile )
call mpp_error(fatal, &
1277 'mpp_domains_define.inc: size of pe_start and/or pe_end is not equal num_tile')
1279 if( any( pe_start < pes(0) ) )
call mpp_error(fatal, &
1280 &
'mpp_domains_define.inc: not all the pe_start are in the pelist')
1281 if( any( pe_end > pes(nlist-1)) )
call mpp_error(fatal, &
1282 &
'mpp_domains_define.inc: not all the pe_end are in the pelist')
1285 allocate( ntile_per_pe(0:nlist-1) )
1288 do m = pe_start(n) - mpp_root_pe(), pe_end(n) - mpp_root_pe()
1289 ntile_per_pe(m) = ntile_per_pe(m) + 1
1292 if(any(ntile_per_pe == 0))
call mpp_error(fatal, &
1293 'mpp_domains_define.inc: At least one pe in pelist is not used by any tile in the mosaic')
1296 if(
PRESENT(xextent) )
then
1297 if(
size(xextent,1) .GT. maxval(layout(1,:)) )
call mpp_error(fatal, &
1298 'mpp_domains_define.inc: size mismatch between xextent and layout')
1299 if(
size(xextent,2) .NE. num_tile)
call mpp_error(fatal, &
1300 'mpp_domains_define.inc: size of xextent is not eqaul num_tile')
1302 if(
PRESENT(yextent) )
then
1303 if(
size(yextent,1) .GT. maxval(layout(2,:)) )
call mpp_error(fatal, &
1304 'mpp_domains_define.inc: size mismatch between yextent and layout')
1305 if(
size(yextent,2) .NE. num_tile)
call mpp_error(fatal, &
1306 'mpp_domains_define.inc: size of yextent is not eqaul num_tile')
1313 if(
present(maskmap))
then
1314 if(
size(maskmap,1) .GT. maxval(layout(1,:)) .or.
size(maskmap,2) .GT. maxval(layout(2,:))) &
1315 call mpp_error(fatal,
'mpp_domains_define.inc: size mismatch between maskmap and layout')
1316 if(
size(maskmap,3) .NE. num_tile)
call mpp_error(fatal, &
1317 'mpp_domains_define.inc: the third dimension of maskmap is not equal num_tile')
1320 if (
associated(domain%tileList))
deallocate(domain%tileList)
1321 allocate(domain%tileList(num_tile))
1323 domain%tileList(n)%xbegin = global_indices(1,n)
1324 domain%tileList(n)%xend = global_indices(2,n)
1325 domain%tileList(n)%ybegin = global_indices(3,n)
1326 domain%tileList(n)%yend = global_indices(4,n)
1329 nt = ntile_per_pe(
mpp_pe()-mpp_root_pe())
1330 if (
associated(domain%tile_id))
deallocate(domain%tile_id)
1331 if (
associated(domain%x))
deallocate(domain%x)
1332 if (
associated(domain%y))
deallocate(domain%y)
1333 if (
associated(domain%list))
deallocate(domain%list)
1334 allocate(domain%tile_id(nt), domain%x(nt), domain%y(nt) )
1335 allocate(domain%list(0:nlist-1))
1338 nt = ntile_per_pe(n)
1339 allocate(domain%list(n)%x(nt), domain%list(n)%y(nt), domain%list(n)%tile_id(nt))
1344 if(
PRESENT(tile_id) )
then
1345 if(
size(tile_id(:)) .NE. num_tile)
then
1346 call mpp_error(fatal, .NE.
"mpp_domains_define.inc: size(tile_id) num_tile")
1349 allocate(tile_id_local(num_tile))
1357 if(
PRESENT(tile_id))
then
1358 tile_id_local(n) = tile_id(n)
1360 tile_id_local(n) = n
1365 tile_base = minval(tile_id_local) - 1
1368 if( pe .GE. pe_start(n) .AND. pe .LE. pe_end(n))
then
1370 domain%tile_id(pos) = tile_id_local(n)
1374 if (
associated(domain%tile_id_all))
deallocate(domain%tile_id_all)
1375 allocate(domain%tile_id_all(num_tile))
1376 domain%tile_id_all(:) = tile_id_local(:)
1378 domain%initialized = .true.
1379 domain%rotated_ninety = .false.
1380 domain%ntiles = num_tile
1381 domain%max_ntile_pe = maxval(ntile_per_pe)
1382 domain%ncontacts = num_contact
1384 deallocate(ntile_per_pe)
1386 allocate(tile_count(pes(0):pes(0)+nlist-1))
1389 domain%tile_comm = mpi_comm_null
1391 allocate(mask(layout(1,n), layout(2,n)))
1392 allocate(pelist_tile(pe_start(n):pe_end(n)) )
1393 tile_count(pe_start(n)) = tile_count(pe_start(n)) + 1
1394 do m = pe_start(n), pe_end(n)
1398 if (any(pelist_tile == pe))
then
1399 call mpp_declare_pelist(pelist_tile, comm=domain%tile_comm)
1402 if(
present(maskmap)) mask = maskmap(1:layout(1,n), 1:layout(2,n), n)
1403 ndivx = layout(1,n); ndivy = layout(2,n)
1404 allocate(xext(ndivx), yext(ndivy))
1406 if(
present(xextent)) xext = xextent(1:ndivx,n)
1407 if(
present(yextent)) yext = yextent(1:ndivy,n)
1410 if(num_tile == 1)
then
1413 if(
PRESENT(xflags)) flags_x = xflags
1414 if(
PRESENT(yflags)) flags_y = yflags
1415 do m = 1, num_contact
1416 if(istart1(m) == iend1(m) )
then
1417 if(istart2(m) .NE. iend2(m) )
call mpp_error(fatal, &
1418 "mpp_domains_define: for one tile mosaic, when istart1=iend1, istart2 must equal iend2")
1419 if(istart1(m) == istart2(m) )
then
1420 if(istart1(m) == global_indices(1,n) )
then
1421 if(.NOT. btest(flags_x,west) ) flags_x = flags_x + fold_west_edge
1422 else if(istart1(m) == global_indices(2,n) )
then
1423 if(.NOT. btest(flags_x,east) ) flags_x = flags_x + fold_east_edge
1425 call mpp_error(fatal,
"mpp_domains_define: when istart1=iend1,jstart1=jend1, "//&
1426 "istart1 should equal global_indices(1) or global_indices(2)")
1429 if(.NOT. btest(flags_x,cyclic)) flags_x = flags_x + cyclic_global_domain
1431 else if( jstart1(m) == jend1(m) )
then
1432 if(jstart2(m) .NE. jend2(m) )
call mpp_error(fatal, &
1433 "mpp_domains_define: for one tile mosaic, when jstart1=jend1, jstart2 must equal jend2")
1434 if(jstart1(m) == jstart2(m) )
then
1435 if(jstart1(m) == global_indices(3,n) )
then
1436 if(.NOT. btest(flags_y,south) ) flags_y = flags_y + fold_south_edge
1437 else if(jstart1(m) == global_indices(4,n) )
then
1438 if(.NOT. btest(flags_y,north) ) flags_y = flags_y + fold_north_edge
1440 call mpp_error(fatal,
"mpp_domains_define: when istart1=iend1,jstart1=jend1, "//&
1441 "istart1 should equal global_indices(1) or global_indices(2)")
1444 if(.NOT. btest(flags_y,cyclic)) flags_y = flags_y + cyclic_global_domain
1447 call mpp_error(fatal, &
1448 "mpp_domains_define: for one tile mosaic, invalid boundary contact")
1451 call mpp_define_domains(global_indices(:,n), layout(:,n), domain, pelist=pelist_tile, xflags = flags_x, &
1452 yflags = flags_y, whalo=whalo, ehalo=ehalo, shalo=shalo, nhalo=nhalo, &
1453 xextent=xext, yextent=yext, maskmap=mask, name=name, symmetry=is_symmetry, &
1454 memory_size = memory_size, is_mosaic = .true., tile_id=tile_id_local(n))
1456 call mpp_define_domains(global_indices(:,n), layout(:,n), domain, pelist=pelist_tile, &
1457 whalo=whalo, ehalo=ehalo, shalo=shalo, nhalo=nhalo, xextent=xext, yextent=yext, &
1458 maskmap=mask, name=name, symmetry=is_symmetry, memory_size = memory_size, &
1459 is_mosaic = .true., tile_count = tile_count(pe_start(n)), tile_id=tile_id_local(n), &
1460 complete = n==num_tile)
1462 deallocate(mask, xext, yext, pelist_tile)
1465 deallocate(pes, tile_count, tile_id_local)
1467 if(num_contact == 0 .OR. num_tile == 1)
return
1471 allocate(is1(num_contact), ie1(num_contact), js1(num_contact), je1(num_contact) )
1472 allocate(is2(num_contact), ie2(num_contact), js2(num_contact), je2(num_contact) )
1473 allocate(isglist(num_tile), ieglist(num_tile), jsglist(num_tile), jeglist(num_tile) )
1474 allocate(align1(num_contact), align2(num_contact), refine1(num_contact), refine2(num_contact))
1477 isglist(n) = domain%tileList(n)%xbegin; ieglist(n) = domain%tileList(n)%xend
1478 jsglist(n) = domain%tileList(n)%ybegin; jeglist(n) = domain%tileList(n)%yend
1483 do n = 1, num_contact
1484 t1 = tile1(n) - tile_base
1485 t2 = tile2(n) - tile_base
1486 is1(n) = istart1(n) + isglist(t1) - 1; ie1(n) = iend1(n) + isglist(t1) - 1
1487 js1(n) = jstart1(n) + jsglist(t1) - 1; je1(n) = jend1(n) + jsglist(t1) - 1
1488 is2(n) = istart2(n) + isglist(t2) - 1; ie2(n) = iend2(n) + isglist(t2) - 1
1489 js2(n) = jstart2(n) + jsglist(t2) - 1; je2(n) = jend2(n) + jsglist(t2) - 1
1490 call check_alignment( is1(n), ie1(n), js1(n), je1(n), isglist(t1), ieglist(t1), jsglist(t1), &
1491 & jeglist(t1), align1(n))
1492 call check_alignment( is2(n), ie2(n), js2(n), je2(n), isglist(t2), ieglist(t2), jsglist(t2), &
1493 & jeglist(t2), align2(n))
1494 if( (align1(n) == west .or. align1(n) == east ) .NEQV. (align2(n) == west .or. align2(n) == east ) )&
1495 domain%rotated_ninety=.true.
1499 do n = 1, num_contact
1500 n1 = max(abs(iend1(n) - istart1(n)), abs(jend1(n) - jstart1(n)) ) + 1
1501 n2 = max(abs(iend2(n) - istart2(n)), abs(jend2(n) - jstart2(n)) ) + 1
1502 refine1(n) = real(n2)/n1
1503 refine2(n) = real(n1)/n2
1506 whalosz = 0; ehalosz = 0; shalosz = 0; nhalosz = 0
1507 if(
present(whalo)) whalosz = whalo
1508 if(
present(ehalo)) ehalosz = ehalo
1509 if(
present(shalo)) shalosz = shalo
1510 if(
present(nhalo)) nhalosz = nhalo
1511 xhalosz = max(whalosz, ehalosz)
1512 yhalosz = max(shalosz, nhalosz)
1515 call define_contact_point( domain, center, num_contact, tile1, tile2, align1, align2, refine1, refine2, &
1516 is1, ie1, js1, je1, is2, ie2, js2, je2, isglist, ieglist, jsglist, jeglist, tile_base )
1522 call set_domain_comm_inf(domain%update_T)
1523 call set_domain_comm_inf(domain%update_E)
1524 call set_domain_comm_inf(domain%update_C)
1525 call set_domain_comm_inf(domain%update_N)
1529 do m = 1,
size(domain%tile_id(:))
1530 tile = domain%tile_id(m)
1531 do n = 1, num_contact
1532 if( tile1(n) == tile )
then
1533 if(align1(n) == east ) domain%x(m)%goffset = 0
1534 if(align1(n) == north) domain%y(m)%goffset = 0
1536 if( tile2(n) == tile )
then
1537 if(align2(n) == east ) domain%x(m)%goffset = 0
1538 if(align2(n) == north) domain%y(m)%goffset = 0
1542 call check_overlap_pe_order(domain, domain%update_T, trim(domain%name)//
" update_T in mpp_define_mosaic")
1543 call check_overlap_pe_order(domain, domain%update_C, trim(domain%name)//
" update_C in mpp_define_mosaic")
1544 call check_overlap_pe_order(domain, domain%update_E, trim(domain%name)//
" update_E in mpp_define_mosaic")
1545 call check_overlap_pe_order(domain, domain%update_N, trim(domain%name)//
" update_N in mpp_define_mosaic")
1548 if(debug_update_level .NE. no_check)
then
1553 if(domain%symmetry)
then
1554 if (
associated(domain%bound_E))
deallocate(domain%bound_E)
1555 if (
associated(domain%bound_C))
deallocate(domain%bound_C)
1556 if (
associated(domain%bound_N))
deallocate(domain%bound_N)
1557 allocate(domain%bound_E, domain%bound_C, domain%bound_N )
1561 call check_overlap_pe_order(domain, domain%bound_C, trim(domain%name)//
" bound_C")
1562 call check_overlap_pe_order(domain, domain%bound_E, trim(domain%name)//
" bound_E")
1563 call check_overlap_pe_order(domain, domain%bound_N, trim(domain%name)//
" bound_N")
1569 if(debug_message_passing)
then
1572 call check_message_size(domain, domain%update_T, send, recv,
'T')
1573 call check_message_size(domain, domain%update_C, send, recv,
'C')
1574 call check_message_size(domain, domain%update_E, send, recv,
'E')
1575 call check_message_size(domain, domain%update_N, send, recv,
'N')
1580 deallocate(align1, align2, is1, ie1, js1, je1, is2, ie2, js2, je2 )
1581 deallocate(isglist, ieglist, jsglist, jeglist, refine1, refine2 )
1597 subroutine compute_overlaps( domain, position, update, check, ishift, jshift, x_cyclic_offset, y_cyclic_offset, &
1598 whalo, ehalo, shalo, nhalo )
1599 type(domain2d),
intent(inout) :: domain
1600 type(overlapspec),
intent(inout),
pointer :: update
1601 type(overlapspec),
intent(inout),
pointer :: check
1602 integer,
intent(in) :: position, ishift, jshift
1603 integer,
intent(in) :: x_cyclic_offset, y_cyclic_offset
1604 integer,
intent(in) :: whalo, ehalo, shalo, nhalo
1606 integer :: i, m, n, nlist, tMe, tNbr, dir
1607 integer :: is, ie, js, je, isc, iec, jsc, jec, isd, ied, jsd, jed
1608 integer :: isg, ieg, jsg, jeg, ioff, joff
1609 integer :: list, middle, ni, nj, isgd, iegd, jsgd, jegd
1610 integer :: ism, iem, jsm, jem
1611 integer :: is2, ie2, js2, je2
1612 integer :: is3, ie3, js3, je3
1613 integer :: isd3, ied3, jsd3, jed3
1614 integer :: isd2, ied2, jsd2, jed2
1615 logical :: folded, need_adjust_1, need_adjust_2, need_adjust_3, folded_north
1616 type(overlap_type) :: overlap
1617 type(overlap_type),
pointer :: overlapList(:)=>null()
1618 type(overlap_type),
pointer :: checkList(:)=>null()
1619 integer :: nsend, nrecv
1620 integer :: nsend_check, nrecv_check
1622 logical :: set_check
1627 if(
size(domain%x(:)) > 1)
return
1630 if(whalo==0 .AND. ehalo==0 .AND. shalo==0 .AND. nhalo==0)
return
1633 nlist =
size(domain%list(:))
1635 if(
ASSOCIATED(check)) set_check = .true.
1636 allocate(overlaplist(maxlist) )
1637 if(set_check)
allocate(checklist(maxlist) )
1640 call allocate_update_overlap( overlap, maxoverlap)
1642 call mpp_get_compute_domain( domain, isc, iec, jsc, jec, position=position )
1643 call mpp_get_global_domain ( domain, isg, ieg, jsg, jeg, xsize=ni, ysize=nj, position=position )
1644 call mpp_get_memory_domain ( domain, ism, iem, jsm, jem, position=position )
1646 update%xbegin = ism; update%xend = iem
1647 update%ybegin = jsm; update%yend = jem
1649 check%xbegin = ism; check%xend = iem
1650 check%ybegin = jsm; check%yend = jem
1652 update%whalo = whalo; update%ehalo = ehalo
1653 update%shalo = shalo; update%nhalo = nhalo
1657 middle = (isg+ieg)/2+1
1659 folded_north = btest(domain%fold,north)
1660 if( btest(domain%fold,south) .OR. btest(domain%fold,east) .OR. btest(domain%fold,west) )
then
1661 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps): folded south, east or west boundary condition "&
1662 &//
"is not supported, please use other version of compute_overlaps for "//trim(domain%name))
1669 m = mod( domain%pos+list, nlist )
1670 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
1673 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
1674 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
1676 if( domain%symmetry .AND. (position == north .OR. position == corner ) &
1677 .AND. ( jsc == je .or. jec == js ) )
then
1682 if( je == jeg .AND. folded_north .AND. (position == corner .OR. position == north) )
then
1683 call fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1684 isg, ieg, dir, ishift, position, ioff, middle)
1686 if(x_cyclic_offset ==0 .AND. y_cyclic_offset == 0)
then
1687 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1688 isg, ieg, dir, ioff, domain%x(tme)%cyclic, symmetry=domain%symmetry)
1690 if( ie.GT.ieg )
then
1691 if( domain%x(tme)%cyclic .AND. iec.LT.is )
then
1692 is = is-ioff; ie = ie-ioff
1696 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1697 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
1704 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
1705 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
1706 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
1709 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
1710 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
1711 if(je .LT. jsg)
then
1712 if( domain%y(tme)%cyclic )
then
1713 js = js + joff; je = je + joff
1715 else if(js .Lt. jsg)
then
1716 if( domain%y(tme)%cyclic )
then
1717 js2 = js + joff; je2 = jsg-1+joff
1721 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1722 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
1723 if(je2 .GE. js2)
call fill_overlap_send_nofold(overlap, domain, m, is, ie, js2, je2, isc, iec, jsc, jec, &
1724 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
1727 if( domain%x(tme)%cyclic .AND. iec.LT.is )
then
1728 is = is-ioff; ie = ie-ioff
1729 need_adjust_1 = .false.
1730 if(jsg .GT. js)
then
1731 if( domain%y(tme)%cyclic .AND. je.LT.jsc )
then
1732 js = js+joff; je = je+joff
1733 need_adjust_2 = .false.
1734 if(x_cyclic_offset .NE. 0)
then
1736 else if(y_cyclic_offset .NE. 0)
then
1742 need_adjust_3 = .false.
1746 if( need_adjust_3 .AND. jsg.GT.js )
then
1747 if( need_adjust_2 .AND. domain%y(tme)%cyclic .AND. je.LT.jsc )
then
1748 js = js+joff; je = je+joff
1749 if(need_adjust_1 .AND. ie.LE.ieg)
then
1754 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, isg, ieg, jsg, jeg, dir)
1759 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
1760 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
1763 if( domain%y(tme)%cyclic .AND. je.LT.jsc )
then
1764 js = js+joff; je = je+joff
1767 else if (jsg .GT. js)
then
1768 if( domain%y(tme)%cyclic)
then
1769 js2 = js + joff; je2 = jsg-1+joff
1774 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1775 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
1776 if(je2 .GE. js2)
call fill_overlap(overlap, domain, m, is, ie, js2, je2, isc, iec, jsc, jec, &
1777 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
1781 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
1782 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
1783 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
1784 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
1785 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
1786 if(je .LT. jsg)
then
1787 if( domain%y(tme)%cyclic )
then
1788 js = js + joff; je = je + joff
1790 else if(js .Lt. jsg)
then
1791 if( domain%y(tme)%cyclic )
then
1792 js2 = js + joff; je2 = jsg-1+joff
1796 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1797 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
1798 if(je2 .GE. js2)
call fill_overlap_send_nofold(overlap, domain, m, is, ie, js2, je2, isc, iec, jsc, jec, &
1799 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
1802 if( domain%x(tme)%cyclic .AND. ie.LT.isc )
then
1803 is = is+ioff; ie = ie+ioff
1804 need_adjust_1 = .false.
1805 if(jsg .GT. js)
then
1806 if( domain%y(tme)%cyclic .AND. je.LT.jsc )
then
1807 js = js+joff; je = je+joff
1808 need_adjust_2 = .false.
1809 if(x_cyclic_offset .NE. 0)
then
1811 else if(y_cyclic_offset .NE. 0)
then
1817 need_adjust_3 = .false.
1821 if( need_adjust_3 .AND. jsg.GT.js )
then
1822 if( need_adjust_2 .AND. domain%y(tme)%cyclic .AND. je.LT.jsc )
then
1823 js = js+joff; je = je+joff
1824 if(need_adjust_1 .AND. isg.LE.is )
then
1829 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, isg, ieg, jsg, jeg, dir)
1834 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
1835 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
1839 if( je == jeg .AND. folded_north .AND. (position == corner .OR. position == north))
then
1840 call fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1841 isg, ieg, dir, ishift, position, ioff, middle)
1843 if(x_cyclic_offset ==0 .AND. y_cyclic_offset == 0)
then
1844 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1845 isg, ieg, dir, ioff, domain%x(tme)%cyclic, symmetry=domain%symmetry)
1848 if( domain%x(tme)%cyclic .AND. ie.LT.isc )
then
1849 is = is+ioff; ie = ie+ioff
1853 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1854 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
1860 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
1861 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
1862 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
1863 is3 = 0; ie3 = -1; js3 = 0; je3 = -1
1865 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
1866 if(js .GT. jeg)
then
1867 if( domain%y(tme)%cyclic )
then
1868 js = js-joff; je = je-joff
1869 else if(folded_north )
then
1871 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
1873 else if(je .GT. jeg)
then
1874 if( domain%y(tme)%cyclic )
then
1875 is2 = is; ie2 = ie; js2 = js; je2 = jeg
1876 js = jeg+1-joff; je = je -joff
1877 else if(folded_north)
then
1879 is2 = is; ie2 = ie; js2 = js; je2 = jeg
1881 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
1882 if( is .GT. ieg)
then
1883 is = is - ioff; ie = ie - ioff
1884 else if( ie .GT. ieg )
then
1885 is3 = is; ie3 = ieg; js3 = js; je3 = je
1886 is = ieg+1-ioff; ie = ie - ioff
1891 if( je == jeg .AND. jec == jeg .AND. folded_north .AND. (position == corner .OR. position == north))
then
1892 call fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1893 isg, ieg, dir, ishift, position, ioff, middle)
1895 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1896 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
1898 if(ie3 .GE. is3)
call fill_overlap_send_nofold(overlap, domain, m, is3, ie3, js3, je3, &
1899 isc, iec, jsc, jec, isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
1900 if(ie2 .GE. is2)
then
1901 if(je2 == jeg .AND. jec == jeg .AND. folded_north.AND.(position == corner .OR. position == north))
then
1902 call fill_overlap_send_fold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
1903 isg, ieg, dir, ishift, position, ioff, middle)
1905 call fill_overlap_send_nofold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
1906 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
1910 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
1912 if( domain%x(tme)%cyclic .AND. ie.LT.isc )
then
1913 is = is+ioff; ie = ie+ioff
1914 need_adjust_1 = .false.
1915 if(je .GT. jeg)
then
1916 if( domain%y(tme)%cyclic .AND. jec.LT.js )
then
1917 js = js-joff; je = je-joff
1918 need_adjust_2 = .false.
1919 if(x_cyclic_offset .NE. 0)
then
1921 else if(y_cyclic_offset .NE. 0)
then
1927 need_adjust_3 = .false.
1932 if( need_adjust_3 .AND. je.GT.jeg )
then
1933 if( need_adjust_2 .AND. domain%y(tme)%cyclic .AND. jec.LT.js )
then
1934 js = js-joff; je = je-joff
1935 if( need_adjust_1 .AND. isg.LE.is)
then
1938 else if( folded_north )
then
1940 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
1943 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1944 isg, ieg, jsg, jeg, dir)
1951 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
1952 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
1957 if( domain%symmetry .AND. (position == east .OR. position == corner ) &
1958 .AND. ( isc == ie .or. iec == is ) .AND. (.not. folded_north) )
then
1962 if( js .GT. jeg)
then
1963 if( domain%y(tme)%cyclic .AND. jec.LT.js )
then
1964 js = js-joff; je = je-joff
1966 else if( folded_north )
then
1968 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
1970 else if( je.GT.jeg )
then
1971 if( domain%y(tme)%cyclic)
then
1972 is2 = is; ie2 = ie; js2 = js; je2 = jeg
1973 js = jeg+1-joff; je = je - joff
1974 else if( folded_north )
then
1976 is2 = is; ie2 = ie; js2 = js; je2 = jeg
1978 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
1981 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
1982 if( je == jeg .AND. jec == jeg .AND. folded_north .AND.(position == corner .OR. position == north))
then
1983 call fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1984 isg, ieg, dir, ishift, position, ioff, middle, domain%symmetry)
1986 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1987 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded, domain%symmetry)
1990 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
1991 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
1994 if(ie2 .GE. is2)
then
1995 if(je2 == jeg .AND. jec == jeg .AND. folded_north .AND.(position == corner .OR. position == north))
then
1996 call fill_overlap_send_fold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
1997 isg, ieg, dir, ishift, position, ioff, middle, domain%symmetry)
1999 call fill_overlap_send_nofold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
2000 isg, ieg, dir, ioff, domain%x(tme)%cyclic, symmetry=domain%symmetry)
2006 if(is .LT. isg .AND. domain%x(tme)%cyclic)
then
2017 if( folded_north .AND. (position == north .OR. position == corner) &
2018 .AND. domain%x(tme)%pos .LT. (
size(domain%x(tme)%list(:))+1)/2 )
then
2019 if( domain%list(m)%y(tnbr)%compute%end+nhalo+jshift .GE. jeg .AND. isc .LE. middle)
then
2021 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
2022 is = max(is, middle)
2023 select case (position)
2025 i=is; is = isg+ieg-ie; ie = isg+ieg-i
2027 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
2029 call insert_update_overlap(overlap, domain%list(m)%pe, &
2030 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
2032 if(debug_update_level .NE. no_check .AND. set_check)
then
2033 je = domain%list(m)%y(tnbr)%compute%end+jshift;
2035 is = max(is, isc); ie = min(ie, iec)
2036 js = max(js, jsc); je = min(je, jec)
2037 if(ie.GE.is .AND. je.GE.js )
then
2038 nsend_check = nsend_check+1
2039 if(nsend_check >
size(checklist(:)) )
then
2040 call expand_check_overlap_list(checklist, nlist)
2042 call allocate_check_overlap(checklist(nsend_check), 1)
2043 call insert_check_overlap(checklist(nsend_check), domain%list(m)%pe, &
2044 tme, 4, one_hundred_eighty, is, ie, js, je)
2052 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
2053 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
2054 is2 = 0; ie2=-1; js2=0; je2=-1
2055 is3 = 0; ie3 = -1; js3 = 0; je3 = -1
2056 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2058 if(js .GT. jeg)
then
2059 if( domain%y(tme)%cyclic )
then
2060 js = js-joff; je = je-joff
2061 else if(folded_north )
then
2063 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2065 else if(je .GT. jeg)
then
2066 if( domain%y(tme)%cyclic )
then
2067 is2 = is; ie2 = ie; js2 = js; je2 = jeg
2068 js = jeg+1-joff; je = je -joff
2069 else if(folded_north)
then
2071 is2 = is; ie2 = ie; js2 = js; je2 = jeg
2073 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2075 if( ie .LT. isg )
then
2076 is = is+ioff; ie = ie+ioff
2077 else if( is .LT. isg)
then
2078 is3 = isg; ie3 = ie; js3 = js; je3 = je
2079 is = is+ioff; ie = isg-1+ioff;
2083 if( je == jeg .AND. jec == jeg .AND. folded_north .AND. (position == corner .OR. position == north))
then
2084 call fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2085 isg, ieg, dir, ishift, position, ioff, middle)
2087 call fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2088 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2090 if(ie3 .GE. is3)
call fill_overlap_send_nofold(overlap, domain, m, is3, ie3, js3, je3, &
2091 isc, iec, jsc, jec, isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2092 if(ie2 .GE. is2)
then
2093 if(je2 == jeg .AND. jec == jeg .AND. folded_north .AND.(position == corner .OR. position == north))
then
2094 call fill_overlap_send_fold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
2095 isg, ieg, dir, ishift, position, ioff, middle)
2097 call fill_overlap_send_nofold(overlap, domain, m, is2, ie2, js2, je2, isc, iec, jsc, jec, &
2098 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2102 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
2104 if( domain%x(tme)%cyclic .AND. iec.LT.is )
then
2105 is = is-ioff; ie = ie-ioff
2106 need_adjust_1 = .false.
2107 if(je .GT. jeg)
then
2108 if( domain%y(tme)%cyclic .AND. jec.LT.js )
then
2109 js = js-joff; je = je-joff
2110 need_adjust_2 = .false.
2111 if(x_cyclic_offset .NE. 0)
then
2113 else if(y_cyclic_offset .NE. 0)
then
2119 need_adjust_3 = .false.
2124 if( need_adjust_3 .AND. je.GT.jeg )
then
2125 if( need_adjust_2 .AND. domain%y(tme)%cyclic .AND. jec.LT.js )
then
2126 js = js-joff; je = je-joff
2127 if( need_adjust_1 .AND. ie.LE.ieg)
then
2130 else if( folded_north )
then
2132 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2135 call fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2136 isg, ieg, jsg, jeg, dir)
2141 if( overlap%count > 0)
then
2143 if(nsend >
size(overlaplist(:)) )
then
2144 call mpp_error(note,
'mpp_domains_define.inc(compute_overlaps): overlapList for send is expanded')
2145 call expand_update_overlap_list(overlaplist, nlist)
2147 call add_update_overlap( overlaplist(nsend), overlap)
2148 call init_overlap_type(overlap)
2152 if(debug_message_passing)
then
2156 write(iunit, *)
"********to_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
2157 do n = 1, overlaplist(m)%count
2158 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
2159 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
2162 if(nsend >0)
flush(iunit)
2167 if (
associated(update%send))
deallocate(update%send)
2168 allocate(update%send(nsend))
2169 update%nsend = nsend
2171 call add_update_overlap( update%send(m), overlaplist(m) )
2175 if(nsend_check>0)
then
2176 check%nsend = nsend_check
2177 if (
associated(check%send))
deallocate(check%send)
2178 allocate(check%send(nsend_check))
2179 do m = 1, nsend_check
2184 do m = 1,
size(overlaplist(:))
2185 call deallocate_overlap_type(overlaplist(m))
2188 if(debug_update_level .NE. no_check .AND. set_check)
then
2189 do m = 1,
size(checklist(:))
2190 call deallocate_overlap_type(checklist(m))
2194 isgd = isg - domain%whalo
2195 iegd = ieg + domain%ehalo
2196 jsgd = jsg - domain%shalo
2197 jegd = jeg + domain%nhalo
2203 m = mod( domain%pos+nlist-list, nlist )
2204 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
2205 isc = domain%list(m)%x(1)%compute%begin; iec = domain%list(m)%x(1)%compute%end+ishift
2206 jsc = domain%list(m)%y(1)%compute%begin; jec = domain%list(m)%y(1)%compute%end+jshift
2209 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%compute%end+ehalo+ishift
2210 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
2211 is=isc; ie=iec; js=jsc; je=jec
2212 if( domain%symmetry .AND. (position == north .OR. position == corner ) &
2213 .AND. ( jsd == je .or. jed == js ) )
then
2218 if( jed == jeg .AND. folded_north .AND. (position == corner .OR. position == north) )
then
2219 call fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2220 isg, ieg, dir, ishift, position, ioff, middle)
2222 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2223 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2224 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2226 if( ied.GT.ieg )
then
2227 if( domain%x(tme)%cyclic .AND. ie.LT.isd )
then
2228 is = is+ioff; ie = ie+ioff
2232 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2233 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
2240 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%compute%end+ehalo+ishift
2241 jsd = domain%y(tme)%compute%begin-shalo; jed = domain%y(tme)%compute%begin-1
2242 is=isc; ie=iec; js=jsc; je=jec
2245 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
2246 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2247 if(jed .LT. jsg)
then
2248 if( domain%y(tme)%cyclic )
then
2249 js = js-joff; je = je-joff
2251 else if(jsd .LT. jsg)
then
2252 if( domain%y(tme)%cyclic )
then
2253 js2 = js-joff; je2 = je-joff
2256 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2257 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2258 if(je2 .GE. js2)
call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js2, je2, isd, ied, jsd, jed, &
2259 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2261 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
2262 if( jsd.LT.jsg )
then
2263 if( domain%y(tme)%cyclic .AND. js.GT.jed )
then
2264 js = js-joff; je = je-joff
2265 need_adjust_1 = .false.
2266 if( ied.GT.ieg )
then
2267 if( domain%x(tme)%cyclic .AND. ie.LT.isd )
then
2268 is = is+ioff; ie = ie+ioff
2269 need_adjust_2 = .false.
2270 if(x_cyclic_offset .NE. 0)
then
2272 else if(y_cyclic_offset .NE. 0)
then
2278 need_adjust_3 = .false.
2282 if( need_adjust_3 .AND. ied.GT.ieg )
then
2283 if( need_adjust_2 .AND. domain%x(tme)%cyclic .AND. ie.LT.isd )
then
2284 is = is+ioff; ie = ie+ioff
2285 if( need_adjust_1 .AND. jsd.GE.jsg )
then
2290 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2291 isg, ieg, jsg, jeg, dir)
2296 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
2297 jsd = domain%y(tme)%compute%begin-shalo; jed = domain%y(tme)%compute%begin-1
2298 is=isc; ie=iec; js=jsc; je=jec
2300 if( jed .LT. jsg)
then
2301 if( domain%y(tme)%cyclic )
then
2302 js = js-joff; je = je-joff
2305 else if( jsd.LT.jsg )
then
2306 if( domain%y(tme)%cyclic)
then
2307 js2 = js-joff; je2 = je-joff
2310 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2311 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
2312 if(je2 .GE. js2)
call fill_overlap(overlap, domain, m, is, ie, js2, je2, isd, ied, jsd, jed, &
2313 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
2317 isd = domain%x(tme)%compute%begin-whalo; ied = domain%x(tme)%compute%begin-1
2318 jsd = domain%y(tme)%compute%begin-shalo; jed = domain%y(tme)%compute%begin-1
2319 is=isc; ie=iec; js=jsc; je=jec
2320 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
2321 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2322 if( ied.LT.isg )
then
2323 if( domain%x(tme)%cyclic )
then
2324 is = is-ioff; ie = ie-ioff
2326 else if (isd.LT.isg )
then
2327 if( domain%x(tme)%cyclic )
then
2328 is2 = is-ioff; ie2 = ie-ioff
2331 if( jed.LT.jsg )
then
2332 if( domain%y(tme)%cyclic )
then
2333 js = js-joff; je = je-joff
2335 else if( jsd.LT.jsg )
then
2336 if( domain%y(tme)%cyclic )
then
2337 js2 = js-joff; je2 = je-joff
2341 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
2342 if( jsd.LT.jsg )
then
2343 if( domain%y(tme)%cyclic .AND. js.GT.jed )
then
2344 js = js-joff; je = je-joff
2345 need_adjust_1 = .false.
2346 if( isd.LT.isg )
then
2347 if( domain%x(tme)%cyclic .AND. is.GT.ied )
then
2348 is = is-ioff; ie = ie-ioff
2349 need_adjust_2 = .false.
2350 if(x_cyclic_offset .NE. 0)
then
2352 else if(y_cyclic_offset .NE. 0)
then
2358 need_adjust_3 = .false.
2362 if( need_adjust_3 .AND. isd.LT.isg )
then
2363 if( need_adjust_2 .AND. domain%x(tme)%cyclic .AND. is.GT.ied )
then
2364 is = is-ioff; ie = ie-ioff
2365 if(need_adjust_1 .AND. jsd.GE.jsg)
then
2371 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2372 isg, ieg, jsg, jeg, dir)
2374 if(ie2 .GE. is2)
call fill_overlap(overlap, domain, m, is2, ie2, js, je, isd, ied, jsd, jed, &
2375 isg, ieg, jsg, jeg, dir)
2376 if(je2 .GE. js2)
call fill_overlap(overlap, domain, m, is, ie, js2, je2, isd, ied, jsd, jed, &
2377 isg, ieg, jsg, jeg, dir)
2379 if(ie2 .GE. is2 .AND. je2 .GE. js2)
call fill_overlap(overlap, domain, m, is2, ie2, js2, je2, isd, ied, jsd, &
2380 & jed, isg, ieg, jsg, jeg, dir)
2385 isd = domain%x(tme)%compute%begin-whalo; ied = domain%x(tme)%compute%begin-1
2386 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
2387 is=isc; ie=iec; js=jsc; je=jec
2391 if( jed == jeg .AND. folded_north .AND. (position == corner .OR. position == north) )
then
2392 call fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2393 isg, ieg, dir, ishift, position, ioff, middle)
2395 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2396 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2397 isg, ieg, dir, ioff, domain%x(tme)%cyclic, symmetry=domain%symmetry)
2399 if( isd.LT.isg )
then
2400 if( domain%x(tme)%cyclic .AND. is.GT.ied )
then
2401 is = is-ioff; ie = ie-ioff
2405 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2406 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
2413 isd = domain%x(tme)%compute%begin-whalo; ied = domain%x(tme)%compute%begin-1
2414 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%compute%end+nhalo+jshift
2415 is=isc; ie=iec; js=jsc; je=jec
2416 is2 = 0; ie2 = -1; js2 = 0; je2 = -1
2417 is3 = 0; ie3 = -1; js3 = 0; je3 = -1
2418 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2420 if( jsd .GT. jeg )
then
2421 if( domain%y(tme)%cyclic .AND. je.LT.jsd )
then
2422 js = js+joff; je = je+joff
2424 else if( folded_north )
then
2426 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2428 else if( jed.GT.jeg )
then
2429 if( domain%y(tme)%cyclic)
then
2430 is2 = is; ie2 = ie; js2 = js; je2 = je
2431 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2432 js = js + joff; je = je + joff
2434 else if( folded_north )
then
2436 is2 = is; ie2 = ie; js2 = js; je2 = je
2437 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2439 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2440 if(isd < isg .and. ied .GE. isg .and. domain%symmetry)
then
2441 isd3 = isd; ied3 = isg-1
2442 jsd3 = jsd; jed3 = jed
2443 is3 = is-ioff; ie3=ie-ioff
2450 if( jeg .GE. js .AND. jeg .LE. je .AND. jed == jeg .AND. folded_north &
2451 .AND. (position == corner .OR. position == north))
then
2452 call fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2453 isg, ieg, dir, ishift, position, ioff, middle)
2455 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2456 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2459 if(ie3 .GE. is3)
call fill_overlap_recv_nofold(overlap, domain, m, is3, ie3, js3, je3, isd3, ied3, jsd3, &
2460 & jed3, isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2462 if(ie2 .GE. is2)
then
2463 if( jeg .GE. js2 .AND. jeg .LE. je2 .AND. jed2 == jeg .AND. folded_north &
2464 .AND. (position == corner .OR. position == north))
then
2465 call fill_overlap_recv_fold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2466 isg, ieg, dir, ishift, position, ioff, middle)
2468 call fill_overlap_recv_nofold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2469 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2473 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
2474 if( jed.GT.jeg )
then
2475 if( domain%y(tme)%cyclic .AND. je.LT.jsd )
then
2476 js = js+joff; je = je+joff
2477 need_adjust_1 = .false.
2478 if( isd.LT.isg )
then
2479 if( domain%x(tme)%cyclic .AND. is.GE.ied )
then
2480 is = is-ioff; ie = ie-ioff
2481 need_adjust_2 = .false.
2482 if(x_cyclic_offset .NE. 0)
then
2484 else if(y_cyclic_offset .NE. 0)
then
2490 need_adjust_3 = .false.
2492 else if( folded_north )
then
2494 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2497 if( need_adjust_3 .AND. isd.LT.isg )
then
2498 if( need_adjust_2 .AND. domain%x(tme)%cyclic .AND. is.GE.ied )
then
2499 is = is-ioff; ie = ie-ioff
2500 if( need_adjust_1 .AND. jed.LE.jeg )
then
2505 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2506 isg, ieg, jsg, jeg, dir)
2510 if(is .LT. isg .AND. domain%x(tme)%cyclic)
then
2512 call insert_update_overlap(overlap, domain%list(m)%pe, &
2513 is, is, js, je, isd, ied, jsd, jed, dir, folded )
2519 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
2520 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%compute%end+nhalo+jshift
2521 is=isc; ie=iec; js=jsc; je=jec
2525 if( domain%symmetry .AND. (position == east .OR. position == corner ) &
2526 .AND. (isd == ie .or. ied == is ) .AND. (.not. folded_north) )
then
2530 if( jsd .GT. jeg )
then
2531 if( domain%y(tme)%cyclic .AND. je.LT.jsd )
then
2532 js = js+joff; je = je+joff
2534 else if( folded_north )
then
2536 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2538 else if( jed.GT.jeg )
then
2539 if( domain%y(tme)%cyclic)
then
2540 is2 = is; ie2 = ie; js2 = js; je2 = je
2541 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2542 js = js + joff; je = je + joff
2544 else if( folded_north )
then
2546 is2 = is; ie2 = ie; js2 = js; je2 = je
2547 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2549 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2552 if(x_cyclic_offset == 0 .and. y_cyclic_offset == 0)
then
2553 if( jeg .GE. js .AND. jeg .LE. je .AND. jed == jeg .AND. folded_north &
2554 .AND. (position == corner .OR. position == north))
then
2555 call fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2556 isg, ieg, dir, ishift, position, ioff, middle, symmetry=domain%symmetry)
2558 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2559 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded, symmetry=domain%symmetry)
2562 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2563 isg, ieg, jsg, jeg, dir, symmetry=domain%symmetry)
2565 if(ie2 .GE. is2)
then
2566 if(jeg .GE. js2 .AND. jeg .LE. je2 .AND. jed2 == jeg .AND. folded_north &
2567 .AND. (position == corner .OR. position == north))
then
2568 call fill_overlap_recv_fold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2569 isg, ieg, dir, ishift, position, ioff, middle, symmetry=domain%symmetry)
2571 call fill_overlap_recv_nofold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2572 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded, symmetry=domain%symmetry)
2578 if(is .LT. isg .AND. domain%x(tme)%cyclic)
then
2588 if( folded_north .AND. (position == north .OR. position == corner) &
2589 .AND. domain%x(tme)%pos .GE.
size(domain%x(tme)%list(:))/2)
then
2590 if( jed .GE. jeg .AND. ied .GE. middle)
then
2591 jsd = jeg; jed = jeg
2592 is=isc; ie=iec; js = jsc; je = jec
2593 isd = max(isd, middle)
2594 select case (position)
2596 i=is; is = isg+ieg-ie; ie = isg+ieg-i
2598 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
2600 call insert_update_overlap(overlap, domain%list(m)%pe, &
2601 is, ie, js, je, isd, ied, jsd, jed, dir, .true.)
2603 if(debug_update_level .NE. no_check .AND. set_check)
then
2604 jsd = domain%y(tme)%compute%end+jshift; jed = jsd
2606 is = max(is, isd); ie = min(ie, ied)
2607 js = max(js, jsd); je = min(je, jed)
2608 if(ie.GE.is .AND. je.GE.js )
then
2609 nrecv_check = nrecv_check+1
2610 if(nrecv_check >
size(checklist(:)) )
then
2611 call expand_check_overlap_list(checklist, nlist)
2613 call allocate_check_overlap(checklist(nrecv_check), 1)
2614 call insert_check_overlap(checklist(nrecv_check), domain%list(m)%pe, &
2615 tme, 4, one_hundred_eighty, is, ie, js, je)
2625 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%compute%end+ehalo+ishift
2626 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%compute%end+nhalo+jshift
2627 is=isc; ie=iec; js=jsc; je=jec
2628 is2 = 0; ie2=-1; js2=0; je2=-1
2629 is3 = 0; ie3 = -1; js3 = 0; je3 = -1
2630 if(x_cyclic_offset == 0 .AND. y_cyclic_offset == 0)
then
2632 if( jsd .GT. jeg )
then
2633 if( domain%y(tme)%cyclic .AND. je.LT.jsd )
then
2634 js = js+joff; je = je+joff
2636 else if( folded_north )
then
2638 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2640 else if( jed.GT.jeg )
then
2641 if( domain%y(tme)%cyclic)
then
2642 is2 = is; ie2 = ie; js2 = js; je2 = je
2643 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2644 js = js + joff; je = je + joff
2646 else if( folded_north )
then
2648 is2 = is; ie2 = ie; js2 = js; je2 = je
2649 isd2 = isd; ied2 = ied; jsd2 = jsd; jed2 = jeg
2651 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2652 if(ied > ieg .and. isd .LE. ieg .and. domain%symmetry)
then
2653 isd3 = ieg+1; ied3 = ied
2654 jsd3 = jsd; jed3 = jed
2655 is3 = is+ioff; ie3=ie+ioff
2661 if( jeg .GE. js .AND. jeg .LE. je .AND. jed == jeg .AND. folded_north &
2662 .AND. (position == corner .OR. position == north))
then
2663 call fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2664 isg, ieg, dir, ishift, position, ioff, middle)
2666 call fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2667 isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2669 if(ie3 .GE. is3)
call fill_overlap_recv_nofold(overlap, domain, m, is3, ie3, js3, je3, isd3, ied3, jsd3, &
2670 & jed3, isg, ieg, dir, ioff, domain%x(tme)%cyclic, folded)
2671 if(ie2 .GE. is2)
then
2672 if(jeg .GE. js2 .AND. jeg .LE. je2 .AND. jed2 == jeg .AND. folded_north &
2673 .AND. (position == corner .OR. position == north))
then
2674 call fill_overlap_recv_fold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2675 isg, ieg, dir, ishift, position, ioff, middle)
2677 call fill_overlap_recv_nofold(overlap, domain, m, is2, ie2, js2, je2, isd2, ied2, jsd2, jed2, &
2678 isg, ieg, dir, ioff, domain%x(tme)%cyclic)
2682 need_adjust_1 = .true.; need_adjust_2 = .true.; need_adjust_3 = .true.
2683 if( jed.GT.jeg )
then
2684 if( domain%y(tme)%cyclic .AND. je.LT.jsd )
then
2685 js = js+joff; je = je+joff
2686 need_adjust_1 = .false.
2687 if( ied.GT.ieg )
then
2688 if( domain%x(tme)%cyclic .AND. ie.LT.isd )
then
2689 is = is+ioff; ie = ie+ioff
2690 need_adjust_2 = .false.
2691 if(x_cyclic_offset .NE. 0)
then
2693 else if(y_cyclic_offset .NE. 0)
then
2699 need_adjust_3 = .false.
2701 else if( folded_north )
then
2703 call get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
2706 if( need_adjust_3 .AND. ied.GT.ieg )
then
2707 if( need_adjust_2 .AND. domain%x(tme)%cyclic .AND. ie.LT.isd )
then
2708 is = is+ioff; ie = ie+ioff
2709 if( need_adjust_1 .AND. jed.LE.jeg)
then
2714 call fill_overlap(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2715 isg, ieg, jsg, jeg, dir)
2720 if( overlap%count > 0)
then
2722 if(nrecv >
size(overlaplist(:)) )
then
2723 call mpp_error(note,
'mpp_domains_define.inc(compute_overlaps): overlapList for recv is expanded')
2724 call expand_update_overlap_list(overlaplist, nlist)
2726 call add_update_overlap( overlaplist(nrecv), overlap)
2727 call init_overlap_type(overlap)
2731 if(debug_message_passing)
then
2735 write(iunit, *)
"********from_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
2736 do n = 1, overlaplist(m)%count
2737 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
2738 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
2741 if(nrecv >0)
flush(iunit)
2746 if (
associated(update%recv))
deallocate(update%recv)
2747 allocate(update%recv(nrecv))
2748 update%nrecv = nrecv
2750 call add_update_overlap( update%recv(m), overlaplist(m) )
2751 do n = 1, update%recv(m)%count
2752 if(update%recv(m)%tileNbr(n) == domain%tile_id(tme))
then
2753 if(update%recv(m)%dir(n) == 1) domain%x(tme)%loffset = 0
2754 if(update%recv(m)%dir(n) == 7) domain%y(tme)%loffset = 0
2760 if(nrecv_check>0)
then
2761 check%nrecv = nrecv_check
2762 if (
associated(check%recv))
deallocate(check%recv)
2763 allocate(check%recv(nrecv_check))
2764 do m = 1, nrecv_check
2769 call deallocate_overlap_type(overlap)
2770 do m = 1,
size(overlaplist(:))
2771 call deallocate_overlap_type(overlaplist(m))
2774 if(debug_update_level .NE. no_check .AND. set_check)
then
2775 do m = 1,
size(checklist(:))
2776 call deallocate_overlap_type(checklist(m))
2780 deallocate(overlaplist)
2781 if(set_check)
deallocate(checklist)
2782 domain%initialized = .true.
2787 subroutine fill_overlap_send_nofold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2788 isg, ieg, dir, ioff, is_cyclic, folded, symmetry)
2789 type(overlap_type),
intent(inout) :: overlap
2790 type(domain2d),
intent(inout) :: domain
2791 integer,
intent(in ) :: m, is, ie, js, je
2792 integer,
intent(in ) :: isc, iec, jsc, jec
2793 integer,
intent(in ) :: isg, ieg, dir, ioff
2794 logical,
intent(in ) :: is_cyclic
2795 logical,
optional,
intent(in ) :: folded, symmetry
2797 call insert_update_overlap( overlap, domain%list(m)%pe, &
2798 is, ie, js, je, isc, iec, jsc, jec, dir, reverse=folded, symmetry=symmetry)
2800 if(ie .GT. ieg)
then
2801 call insert_update_overlap( overlap, domain%list(m)%pe, &
2802 is-ioff, ie-ioff, js, je, isc, iec, jsc, jec, dir, reverse=folded, symmetry=symmetry)
2803 else if( is .LT. isg )
then
2804 call insert_update_overlap( overlap, domain%list(m)%pe, &
2805 is+ioff, ie+ioff, js, je, isc, iec, jsc, jec, dir, reverse=folded, symmetry=symmetry)
2809 end subroutine fill_overlap_send_nofold
2811 subroutine fill_overlap_send_fold(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2812 isg, ieg, dir, ishift, position, ioff, middle, symmetry)
2813 type(overlap_type),
intent(inout) :: overlap
2814 type(domain2d),
intent(inout) :: domain
2815 integer,
intent(in ) :: m, is, ie, js, je
2816 integer,
intent(in ) :: isc, iec, jsc, jec
2817 integer,
intent(in ) :: isg, ieg, dir, ishift, position, ioff, middle
2818 logical,
optional,
intent(in ) :: symmetry
2819 integer :: is1, ie1, is2, ie2, i
2823 if(position == corner .AND. .NOT. domain%symmetry .AND. is .LE. isg-1 .AND. ie .GE. isg-1)
then
2824 call insert_update_overlap(overlap, domain%list(m)%pe, &
2825 isg-1+ioff, isg-1+ioff, je, je, isc, iec, jsc, jec, dir, .true.)
2828 is1 = 0; ie1 = -1; is2 = 0; ie2 = -1
2831 is2 = is-ioff; ie2 = ie-ioff
2832 else if( ie > ieg )
then
2834 is2 = ieg+1-ioff; ie2 = ie-ioff
2835 else if( is .GE. middle )
then
2837 else if( ie .GE. middle )
then
2838 is1 = middle; ie1 = ie
2839 is2 = is; ie2 = middle-1
2840 else if( ie < isg )
then
2841 is1 = is+ieg-isg+1-ishift; ie1 = ie+ieg-isg+1-ishift
2842 else if( is < isg )
then
2843 is1 = is+ieg-isg+1-ishift; ie1 = isg-1+ieg-isg+1-ishift
2849 if( ie1 .GE. is1)
then
2850 call insert_update_overlap( overlap, domain%list(m)%pe, &
2851 is1, ie1, js, je-1, isc, iec, jsc, jec, dir, symmetry=symmetry)
2853 select case (position)
2855 i=is1; is1 = isg+ieg-ie1; ie1 = isg+ieg-i
2857 i=is1; is1 = isg+ieg-ie1-1+ishift; ie1 = isg+ieg-i-1+ishift
2859 call insert_update_overlap( overlap, domain%list(m)%pe, &
2860 is1, ie1, je, je, isc, iec, jsc, jec, dir, .true., symmetry=symmetry)
2863 if(ie2 .GE. is2)
then
2864 call insert_update_overlap( overlap, domain%list(m)%pe, &
2865 is2, ie2, js, je, isc, iec, jsc, jec, dir)
2868 end subroutine fill_overlap_send_fold
2872 subroutine fill_overlap_recv_nofold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2873 isg, ieg, dir, ioff, is_cyclic, folded, symmetry)
2874 type(overlap_type),
intent(inout) :: overlap
2875 type(domain2d),
intent(inout) :: domain
2876 integer,
intent(in ) :: m, is, ie, js, je
2877 integer,
intent(in ) :: isd, ied, jsd, jed
2878 integer,
intent(in ) :: isg, ieg, dir, ioff
2879 logical,
intent(in ) :: is_cyclic
2880 logical,
optional,
intent(in ) :: folded, symmetry
2881 integer :: is1, ie1, is2, ie2
2882 integer :: isd1, ied1, isd2, ied2
2884 is1 = 0; ie1 = -1; is2 = 0; ie2 = -1
2888 call insert_update_overlap( overlap, domain%list(m)%pe, &
2889 is, ie, js, je, isd, ied, jsd, jed, dir, reverse=folded, symmetry=symmetry)
2891 if(ied .GT. ieg)
then
2892 call insert_update_overlap( overlap, domain%list(m)%pe, &
2893 is+ioff, ie+ioff, js, je, isd, ied, jsd, jed, dir, reverse=folded, symmetry=symmetry)
2894 else if( isd .LT. isg )
then
2895 call insert_update_overlap( overlap, domain%list(m)%pe, &
2896 is-ioff, ie-ioff, js, je, isd, ied, jsd, jed, dir, reverse=folded, symmetry=symmetry)
2897 else if ( is .LT. isg )
then
2898 call insert_update_overlap( overlap, domain%list(m)%pe, &
2899 is+ioff, ie+ioff, js, je, isd, ied, jsd, jed, dir, reverse=folded, symmetry=symmetry)
2900 else if ( ie .GT. ieg )
then
2901 call insert_update_overlap( overlap, domain%list(m)%pe, &
2902 is-ioff, ie-ioff, js, je, isd, ied, jsd, jed, dir, reverse=folded, symmetry=symmetry)
2906 end subroutine fill_overlap_recv_nofold
2908 subroutine fill_overlap_recv_fold(overlap, domain, m, is, ie, js, je, isd, ied, jsd, jed, &
2909 isg, ieg, dir, ishift, position, ioff, middle, symmetry)
2910 type(overlap_type),
intent(inout) :: overlap
2911 type(domain2d),
intent(inout) :: domain
2912 integer,
intent(in ) :: m, is, ie, js, je
2913 integer,
intent(in ) :: isd, ied, jsd, jed
2914 integer,
intent(in ) :: isg, ieg, dir, ishift, position, ioff, middle
2915 logical,
optional,
intent(in ) :: symmetry
2916 integer :: is1, ie1, is2, ie2, is3, ie3
2917 integer :: isd1, ied1, isd2, ied2
2921 if( position == corner .AND. .NOT. domain%symmetry .AND. isd .LE. isg-1 .AND. ied .GE. isg-1 )
then
2922 call insert_update_overlap( overlap, domain%list(m)%pe, &
2923 is-ioff, ie-ioff, js, je, isg-1, isg-1, jed, jed, dir, .true.)
2926 is1 = 0; ie1 = -1; is2 = 0; ie2 = -1
2929 select case (position)
2931 is3 = isg+ieg-ie; ie3 = isg+ieg-is
2933 is3 = isg+ieg-ie-1+ishift; ie3 = isg+ieg-is-1+ishift
2936 if(isd .GT. ieg)
then
2937 is2 = is + ioff; ie2 = ie + ioff;
2938 else if(ied .GT. ieg)
then
2940 isd1 = isd; ied1 = ieg;
2941 is2 = is + ioff; ie2 = ie + ioff
2942 isd2 = ieg + 1; ied2 = ied
2943 else if(isd .GE. middle)
then
2945 else if(ied .GE. middle)
then
2947 isd1 = middle; ied1 = ied
2949 isd2 = isd; ied2 = middle-1
2950 else if(ied .LT. isg)
then
2951 is1 = is - ioff; ie1 = ie - ioff;
2952 is3 = is3 - ioff; ie3 = ie3 - ioff;
2953 else if(isd .LT. isg)
then
2954 is1 = is - ioff; ie1 = ie - ioff;
2955 is3 = is3 - ioff; ie3 = ie3 - ioff;
2956 isd1 = isd; ied1 = isg-1
2958 isd2 = isg; ied2 = ied
2961 isd2 = isd; ied2 = ied
2964 if( ie1 .GE. is1)
then
2965 call insert_update_overlap( overlap, domain%list(m)%pe, &
2966 is1, ie1, js, je, isd1, ied1, jsd, jed-1, dir, symmetry=symmetry)
2968 call insert_update_overlap( overlap, domain%list(m)%pe, &
2969 is3, ie3, js, je, isd1, ied1, jed, jed, dir, .true., symmetry=symmetry)
2972 if(ie2 .GE. is2)
then
2973 call insert_update_overlap( overlap, domain%list(m)%pe, &
2974 is2, ie2, js, je, isd2, ied2, jsd, jed, dir)
2977 end subroutine fill_overlap_recv_fold
2980 subroutine fill_overlap(overlap, domain, m, is, ie, js, je, isc, iec, jsc, jec, &
2981 isg, ieg, jsg, jeg, dir, reverse, symmetry)
2982 type(overlap_type),
intent(inout) :: overlap
2983 type(domain2d),
intent(inout) :: domain
2984 integer,
intent(in ) :: m, is, ie, js, je
2985 integer,
intent(in ) :: isc, iec, jsc, jec
2986 integer,
intent(in ) :: isg, ieg, jsg, jeg
2987 integer,
intent(in ) :: dir
2988 logical,
optional,
intent(in ) :: reverse, symmetry
2992 call insert_update_overlap( overlap, domain%list(m)%pe, &
2993 is, ie, jsg, je, isc, iec, jsc, jec, dir, reverse, symmetry)
2994 call insert_update_overlap( overlap, domain%list(m)%pe, &
2995 is, ie, js, jeg, isc, iec, jsc, jec, dir, reverse, symmetry)
2996 else if(is > ie)
then
2998 call insert_update_overlap( overlap, domain%list(m)%pe, &
2999 is, ieg, js, je, isc, iec, jsc, jec, dir, reverse, symmetry)
3000 call insert_update_overlap( overlap, domain%list(m)%pe, &
3001 isg, ie, js, je, isc, iec, jsc, jec, dir, reverse, symmetry)
3003 call insert_update_overlap( overlap, domain%list(m)%pe, &
3004 is, ie, js, je, isc, iec, jsc, jec, dir, reverse, symmetry)
3008 end subroutine fill_overlap
3015 type(domain2d),
intent(inout) :: domain
3016 integer,
intent(in) :: position, ishift, jshift
3018 integer :: i, m, n, nlist, tMe, tNbr, dir
3019 integer :: is, ie, js, je, isc, iec, jsc, jec, isd, ied, jsd, jed
3020 integer :: isg, ieg, jsg, jeg, ioff, joff
3021 integer :: list, middle, ni, nj, isgd, iegd, jsgd, jegd
3022 integer :: ism, iem, jsm, jem, whalo, ehalo, shalo, nhalo
3024 type(overlap_type) :: overlap
3025 type(overlapspec),
pointer :: update=>null()
3026 type(overlap_type),
pointer :: overlapList(:)=>null()
3027 type(overlap_type),
pointer :: checkList(:)=>null()
3028 type(overlapspec),
pointer :: check =>null()
3029 integer :: nsend, nrecv
3030 integer :: nsend_check, nrecv_check
3036 if(
size(domain%x(:)) > 1)
return
3039 if(domain%whalo==0 .AND. domain%ehalo==0 .AND. domain%shalo==0 .AND. domain%nhalo==0)
return
3042 nlist =
size(domain%list(:))
3044 select case(position)
3046 update => domain%update_T
3049 update => domain%update_C
3050 check => domain%check_C
3052 update => domain%update_E
3053 check => domain%check_E
3055 update => domain%update_N
3056 check => domain%check_N
3058 call mpp_error(fatal, &
3059 "mpp_domains_define.inc(compute_overlaps_fold_south): the value of position should be CENTER, EAST, &
3063 allocate(overlaplist(maxlist) )
3064 allocate(checklist(maxlist) )
3067 call allocate_update_overlap( overlap, maxoverlap)
3070 call mpp_get_compute_domain( domain, isc, iec, jsc, jec, position=position )
3071 call mpp_get_global_domain ( domain, isg, ieg, jsg, jeg, xsize=ni, ysize=nj, position=position )
3072 call mpp_get_memory_domain ( domain, ism, iem, jsm, jem, position=position )
3073 update%xbegin = ism; update%xend = iem
3074 update%ybegin = jsm; update%yend = jem
3075 if(
ASSOCIATED(check))
then
3076 check%xbegin = ism; check%xend = iem
3077 check%ybegin = jsm; check%yend = jem
3079 update%whalo = domain%whalo; update%ehalo = domain%ehalo
3080 update%shalo = domain%shalo; update%nhalo = domain%nhalo
3081 whalo = domain%whalo; ehalo = domain%ehalo
3082 shalo = domain%shalo; nhalo = domain%nhalo
3087 middle = (isg+ieg)/2+1
3090 if(.NOT. btest(domain%fold,south))
then
3091 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_south): "//&
3092 "boundary condition in y-direction should be folded-south for "//trim(domain%name))
3094 if(.NOT. domain%x(tme)%cyclic)
then
3095 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_south): "//&
3096 "boundary condition in x-direction should be cyclic for "//trim(domain%name))
3099 if(.not. domain%symmetry)
then
3100 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_south): "//&
3101 "when south boundary is folded, the domain must be symmetry for "//trim(domain%name))
3107 m = mod( domain%pos+list, nlist )
3108 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
3111 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3112 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
3114 if( (position == north .OR. position == corner ) .AND. ( jsc == je .or. jec == js ) )
then
3117 if( ie.GT.ieg .AND. iec.LT.is )
then
3118 is = is-ioff; ie = ie-ioff
3122 if( js == jsg .AND. (position == corner .OR. position == north) &
3123 .AND. is .GE. middle .AND. domain%list(m)%x(tnbr)%compute%end+ehalo+jshift .LE. ieg )
then
3124 call insert_update_overlap( overlap, domain%list(m)%pe, &
3125 is, ie, js+1, je, isc, iec, jsc, jec, dir)
3126 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3128 select case (position)
3130 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3132 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3134 call insert_update_overlap( overlap, domain%list(m)%pe, &
3135 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3137 call insert_update_overlap( overlap, domain%list(m)%pe, &
3138 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3145 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3146 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3147 if( ie.GT.ieg .AND. iec.LT.is )
then
3148 is = is-ioff; ie = ie-ioff
3152 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3155 call insert_update_overlap( overlap, domain%list(m)%pe, &
3156 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
3161 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
3162 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3166 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3171 if( (position == east .OR. position == corner ) .AND. ( isc == ie .or. iec == is ) )
then
3174 call insert_update_overlap( overlap, domain%list(m)%pe, &
3175 is, ie, js, je, isc, iec, jsc, jec, dir, folded, symmetry=domain%symmetry)
3178 if(is .LT. isg)
then
3180 call insert_update_overlap( overlap, domain%list(m)%pe, &
3181 is, is, js, je, isc, iec, jsc, jec, dir, folded)
3187 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3188 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3189 if( isg.GT.is .AND. ie.LT.isc )
then
3190 is = is+ioff; ie = ie+ioff
3194 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3196 call insert_update_overlap( overlap, domain%list(m)%pe, &
3197 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
3199 if(is .LT. isg)
then
3201 call insert_update_overlap( overlap, domain%list(m)%pe, &
3202 is, is, js, je, isc, iec, jsc, jec, dir, folded)
3207 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3208 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
3211 if( (position == north .OR. position == corner ) .AND. ( jsc == je .or. jec == js ) )
then
3214 if( isg.GT.is .AND. ie.LT.isc )
then
3215 is = is+ioff; ie = ie+ioff
3219 if( js == jsg .AND. (position == corner .OR. position == north) &
3220 .AND. ( domain%list(m)%x(tnbr)%compute%begin == isg .OR. &
3221 & domain%list(m)%x(tnbr)%compute%begin-1 .GE. middle))
then
3222 call insert_update_overlap( overlap, domain%list(m)%pe, &
3223 is, ie, js+1, je, isc, iec, jsc, jec, dir)
3224 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3225 js = domain%list(m)%y(tnbr)%compute%begin; je = js
3226 if ( domain%list(m)%x(tnbr)%compute%begin == isg )
then
3227 select case (position)
3229 i=is; is = 2*isg-ie-1; ie = 2*isg-i-1
3231 i=is; is = 2*isg-ie-2+2*ishift; ie = 2*isg-i-2+2*ishift
3233 if(ie .GT. domain%x(tme)%compute%end+ishift)
call mpp_error( fatal, &
3234 'mpp_domains_define.inc(compute_overlaps_fold_south): west edge ubound error send.' )
3236 select case (position)
3238 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3240 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3243 call insert_update_overlap( overlap, domain%list(m)%pe, &
3244 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3246 call insert_update_overlap( overlap, domain%list(m)%pe, &
3247 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3253 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3254 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3255 if( isg.GT.is .AND. ie.LT.isc )
then
3256 is = is+ioff; ie = ie+ioff
3258 call insert_update_overlap( overlap, domain%list(m)%pe, &
3259 is, ie, js, je, isc, iec, jsc, jec, dir)
3263 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
3264 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3265 call insert_update_overlap( overlap, domain%list(m)%pe, &
3266 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3270 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3271 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3272 if( ie.GT.ieg .AND. iec.LT.is )
then
3273 is = is-ioff; ie = ie-ioff
3275 call insert_update_overlap( overlap, domain%list(m)%pe, &
3276 is, ie, js, je, isc, iec, jsc, jec, dir)
3280 if( ( position == north .OR. position == corner) )
then
3282 if( domain%y(tme)%domain_data%begin .LE. jsg .AND. jsg .LE. domain%y(tme)%domain_data%end+jshift )
then
3285 if( domain%x(tme)%pos .LT. (
size(domain%x(tme)%list(:))+1)/2 )
then
3286 js = domain%list(m)%y(tnbr)%compute%begin; je = js
3288 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
3289 select case (position)
3291 is = max(is, middle)
3292 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3294 is = max(is, middle)
3295 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3297 call insert_update_overlap(overlap, domain%list(m)%pe, &
3298 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3299 is = max(is, isc); ie = min(ie, iec)
3300 js = max(js, jsc); je = min(je, jec)
3301 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
3302 nsend_check = nsend_check+1
3303 call allocate_check_overlap(checklist(nsend_check), 1)
3304 call insert_check_overlap(checklist(nsend_check), domain%list(m)%pe, &
3305 tme, 2, one_hundred_eighty, is, ie, js, je)
3313 if( overlap%count > 0)
then
3315 if(nsend >
size(overlaplist(:)) )
then
3316 call mpp_error(note,
'mpp_domains_define.inc(compute_overlaps_south): overlapList for send is expanded')
3317 call expand_update_overlap_list(overlaplist, nlist)
3319 call add_update_overlap(overlaplist(nsend), overlap)
3320 call init_overlap_type(overlap)
3324 if(debug_message_passing)
then
3328 write(iunit, *)
"********to_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
3329 do n = 1, overlaplist(m)%count
3330 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
3331 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
3334 if( nsend > 0)
flush(iunit)
3339 if (
associated(update%send))
deallocate(update%send)
3340 allocate(update%send(nsend))
3341 update%nsend = nsend
3343 call add_update_overlap( update%send(m), overlaplist(m) )
3347 if(nsend_check>0)
then
3348 if (
associated(check%send))
deallocate(check%send)
3349 allocate(check%send(nsend_check))
3350 check%nsend = nsend_check
3351 do m = 1, nsend_check
3356 do m = 1,
size(overlaplist(:))
3357 call deallocate_overlap_type(overlaplist(m))
3360 if(debug_update_level .NE. no_check)
then
3361 do m = 1,
size(checklist(:))
3362 call deallocate_overlap_type(checklist(m))
3366 isgd = isg - domain%whalo
3367 iegd = ieg + domain%ehalo
3368 jsgd = jsg - domain%shalo
3369 jegd = jeg + domain%nhalo
3375 m = mod( domain%pos+nlist-list, nlist )
3376 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
3377 isc = domain%list(m)%x(1)%compute%begin; iec = domain%list(m)%x(1)%compute%end+ishift
3378 jsc = domain%list(m)%y(1)%compute%begin; jec = domain%list(m)%y(1)%compute%end+jshift
3381 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
3382 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
3383 is=isc; ie=iec; js=jsc; je=jec
3384 if( (position == north .OR. position == corner ) .AND. ( jsd == je .or. jed == js ) )
then
3387 if( ied.GT.ieg .AND. ie.LT.isd )
then
3388 is = is+ioff; ie = ie+ioff
3393 if( jsd == jsg .AND. (position == corner .OR. position == north) &
3394 .AND. isd .GE. middle .AND. ied .LE. ieg )
then
3395 call insert_update_overlap( overlap, domain%list(m)%pe, &
3396 is, ie, js, je, isd, ied, jsd+1, jed, dir)
3397 is=isc; ie=iec; js=jsc; je=jec
3399 select case (position)
3401 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3403 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3405 call insert_update_overlap( overlap, domain%list(m)%pe, &
3406 is, ie, js, je, isd, ied, jsd, jed, dir, .true.)
3408 call insert_update_overlap( overlap, domain%list(m)%pe, &
3409 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
3416 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
3417 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
3418 is=isc; ie=iec; js=jsc; je=jec
3419 if( jsd.LT.jsg )
then
3421 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3423 if( ied.GT.ieg .AND. ie.LT.isd )
then
3424 is = is+ioff; ie = ie+ioff
3426 call insert_update_overlap(overlap, domain%list(m)%pe, &
3427 is, ie, js, je, isd, ied, jsd, jed, dir, folded)
3432 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
3433 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
3434 is=isc; ie=iec; js=jsc; je=jec
3435 if( jsd.LT.jsg )
then
3437 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3439 if( (position == east .OR. position == corner ) .AND. (isd == ie .or. ied == is ) )
then
3442 call insert_update_overlap(overlap, domain%list(m)%pe, &
3443 is, ie, js, je, isd, ied, jsd, jed, dir, folded, symmetry=domain%symmetry)
3446 if(is .LT. isg )
then
3448 call insert_update_overlap(overlap, domain%list(m)%pe, &
3449 is, is, js, je, isd, ied, jsd, jed, dir, folded)
3455 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
3456 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
3457 is=isc; ie=iec; js=jsc; je=jec
3458 if( jsd.LT.jsg )
then
3460 call get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
3462 if( isd.LT.isg .AND. is.GT.ied )
then
3463 is = is-ioff; ie = ie-ioff
3465 call insert_update_overlap(overlap, domain%list(m)%pe, &
3466 is, ie, js, je, isd, ied, jsd, jed, dir, folded)
3468 if(is .LT. isg )
then
3470 call insert_update_overlap(overlap, domain%list(m)%pe, &
3471 is, is, js, je, isd, ied, jsd, jed, dir, folded )
3476 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
3477 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
3478 is=isc; ie=iec; js=jsc; je=jec
3479 if( (position == north .OR. position == corner ) .AND. ( jsd == je .or. jed == js ) )
then
3482 if( isd.LT.isg .AND. is.GT.ied )
then
3483 is = is-ioff; ie = ie-ioff
3487 if( jsd == jsg .AND. (position == corner .OR. position == north) &
3488 .AND. ( isd < isg .OR. ied .GE. middle ) )
then
3489 call insert_update_overlap(overlap, domain%list(m)%pe, &
3490 is, ie, js, je, isd, ied, jsd+1, jed, dir)
3491 is=isc; ie=iec; js=jsc; je=jec
3493 select case (position)
3495 i=is; is = 2*isg-ie-1; ie = 2*isg-i-1
3497 ied = ied -1 + ishift
3498 i=is; is = 2*isg-ie-2+2*ishift; ie = 2*isg-i-2+2*ishift
3500 if(ie .GT. domain%x(tme)%compute%end+ishift)
call mpp_error( fatal, &
3501 'mpp_domains_define.inc(compute_overlaps): west edge ubound error recv.' )
3503 select case (position)
3505 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3507 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3510 call insert_update_overlap(overlap, domain%list(m)%pe, &
3511 is, ie, js, je, isd, ied, jsd, jsd, dir, .true.)
3513 call insert_update_overlap(overlap, domain%list(m)%pe, &
3514 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
3520 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
3521 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
3522 is=isc; ie=iec; js=jsc; je=jec
3523 if( isd.LT.isg .AND. is.GE.ied )
then
3524 is = is-ioff; ie = ie-ioff
3527 call insert_update_overlap( overlap, domain%list(m)%pe, &
3528 is, ie, js, je, isd, ied, jsd, jed, dir)
3532 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
3533 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
3534 is=isc; ie=iec; js=jsc; je=jec
3535 call insert_update_overlap( overlap, domain%list(m)%pe, &
3536 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
3540 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
3541 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
3542 is=isc; ie=iec; js=jsc; je=jec
3543 if( ied.GT.ieg .AND. ie.LT.isd )
then
3544 is = is+ioff; ie = ie+ioff
3546 call insert_update_overlap( overlap, domain%list(m)%pe, &
3547 is, ie, js, je, isd, ied, jsd, jed, dir)
3552 if( ( position == north .OR. position == corner) )
then
3554 if( domain%y(tme)%domain_data%begin .LE. jsg .AND. jsg .LE. domain%y(tme)%domain_data%end+jshift )
then
3557 if( domain%x(tme)%pos .GE.
size(domain%x(tme)%list(:))/2 )
then
3558 jsd = domain%y(tme)%compute%begin; jed = jsd
3559 if( jsd == jsg )
then
3560 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
3561 is=isc; ie=iec; js = jsc; je = jec
3562 select case (position)
3564 isd = max(isd, middle)
3565 i=is; is = isg+ieg-ie; ie = isg+ieg-i
3567 isd = max(isd, middle)
3568 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
3570 call insert_update_overlap(overlap, domain%list(m)%pe, &
3571 is, ie, js, je, isd, ied, jsd, jed, dir, .true.)
3572 is = max(is, isd); ie = min(ie, ied)
3573 js = max(js, jsd); je = min(je, jed)
3574 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
3575 nrecv_check = nrecv_check+1
3576 call allocate_check_overlap(checklist(nrecv_check), 1)
3577 call insert_check_overlap(checklist(nrecv_check), domain%list(m)%pe, &
3578 tme, 2, one_hundred_eighty, is, ie, js, je)
3586 if( overlap%count > 0)
then
3588 if(nrecv >
size(overlaplist(:)) )
then
3589 call mpp_error(note,
'mpp_domains_define.inc(compute_overlaps_south): overlapList for recv is expanded')
3590 call expand_update_overlap_list(overlaplist, nlist)
3592 call add_update_overlap( overlaplist(nrecv), overlap)
3593 call init_overlap_type(overlap)
3597 if(debug_message_passing)
then
3601 write(iunit, *)
"********from_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
3602 do n = 1, overlaplist(m)%count
3603 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
3604 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
3607 if(nrecv >0)
flush(iunit)
3612 update%nrecv = nrecv
3613 if (
associated(update%recv))
deallocate(update%recv)
3614 allocate(update%recv(nrecv))
3616 call add_update_overlap( update%recv(m), overlaplist(m) )
3617 do n = 1, update%recv(m)%count
3618 if(update%recv(m)%tileNbr(n) == domain%tile_id(tme))
then
3619 if(update%recv(m)%dir(n) == 1) domain%x(tme)%loffset = 0
3620 if(update%recv(m)%dir(n) == 7) domain%y(tme)%loffset = 0
3626 if(nrecv_check>0)
then
3627 check%nrecv = nrecv_check
3628 if (
associated(check%recv))
deallocate(check%recv)
3629 allocate(check%recv(nrecv_check))
3630 do m = 1, nrecv_check
3635 call deallocate_overlap_type(overlap)
3637 do m = 1,
size(overlaplist(:))
3638 call deallocate_overlap_type(overlaplist(m))
3641 if(debug_update_level .NE. no_check)
then
3642 do m = 1,
size(checklist(:))
3643 call deallocate_overlap_type(checklist(m))
3647 deallocate(overlaplist)
3648 deallocate(checklist)
3651 domain%initialized = .true.
3660 type(domain2d),
intent(inout) :: domain
3661 integer,
intent(in) :: position, ishift, jshift
3663 integer :: j, m, n, nlist, tMe, tNbr, dir
3664 integer :: is, ie, js, je, isc, iec, jsc, jec, isd, ied, jsd, jed
3665 integer :: isg, ieg, jsg, jeg, ioff, joff
3666 integer :: list, middle, ni, nj, isgd, iegd, jsgd, jegd
3667 integer :: ism, iem, jsm, jem, whalo, ehalo, shalo, nhalo
3669 type(overlap_type) :: overlap
3670 type(overlapspec),
pointer :: update=>null()
3671 type(overlap_type) :: overlapList(MAXLIST)
3672 type(overlap_type) :: checkList(MAXLIST)
3673 type(overlapspec),
pointer :: check =>null()
3674 integer :: nsend, nrecv
3675 integer :: nsend_check, nrecv_check
3681 if(
size(domain%x(:)) > 1)
return
3684 if(domain%whalo==0 .AND. domain%ehalo==0 .AND. domain%shalo==0 .AND. domain%nhalo==0)
return
3687 nlist =
size(domain%list(:))
3689 select case(position)
3691 update => domain%update_T
3694 update => domain%update_C
3695 check => domain%check_C
3697 update => domain%update_E
3698 check => domain%check_E
3700 update => domain%update_N
3701 check => domain%check_N
3703 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_west):"//&
3704 &
" the value of position should be CENTER, EAST, CORNER or NORTH")
3708 call allocate_update_overlap( overlap, maxoverlap)
3711 call mpp_get_compute_domain( domain, isc, iec, jsc, jec, position=position )
3712 call mpp_get_global_domain ( domain, isg, ieg, jsg, jeg, xsize=ni, ysize=nj, position=position )
3713 call mpp_get_memory_domain ( domain, ism, iem, jsm, jem, position=position )
3714 update%xbegin = ism; update%xend = iem
3715 update%ybegin = jsm; update%yend = jem
3716 if(
ASSOCIATED(check))
then
3717 check%xbegin = ism; check%xend = iem
3718 check%ybegin = jsm; check%yend = jem
3720 update%whalo = domain%whalo; update%ehalo = domain%ehalo
3721 update%shalo = domain%shalo; update%nhalo = domain%nhalo
3722 whalo = domain%whalo; ehalo = domain%ehalo
3723 shalo = domain%shalo; nhalo = domain%nhalo
3727 middle = (jsg+jeg)/2+1
3730 if(.NOT. btest(domain%fold,west))
then
3731 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_west): "//&
3732 "boundary condition in y-direction should be folded-west for "//trim(domain%name))
3734 if(.NOT. domain%y(tme)%cyclic)
then
3735 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_west): "//&
3736 "boundary condition in y-direction should be cyclic for "//trim(domain%name))
3739 if(.not. domain%symmetry)
then
3740 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_west): "//&
3741 "when west boundary is folded, the domain must be symmetry for "//trim(domain%name))
3747 m = mod( domain%pos+list, nlist )
3748 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
3751 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3752 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
3753 call insert_update_overlap( overlap, domain%list(m)%pe, &
3754 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3758 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3759 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3760 if( js.LT.jsg .AND. jsc.GT.je )
then
3761 js = js+joff; je = je+joff
3764 call insert_update_overlap( overlap, domain%list(m)%pe, &
3765 is, ie, js, je, isc, iec, jsc, jec, dir)
3769 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
3770 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3772 if( (position == east .OR. position == corner ) .AND. ( isc == ie .or. iec == is ) )
then
3775 if( js.LT.jsg .AND. jsc.GT.je)
then
3776 js = js+joff; je = je+joff
3781 if( is == isg .AND. (position == corner .OR. position == east) &
3782 .AND. ( domain%list(m)%y(tnbr)%compute%begin == jsg .OR. &
3783 & domain%list(m)%y(tnbr)%compute%begin-1 .GE. middle))
then
3784 call insert_update_overlap( overlap, domain%list(m)%pe, &
3785 is+1, ie, js, je, isc, iec, jsc, jec, dir)
3786 is = domain%list(m)%x(tnbr)%compute%begin; ie = is
3787 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3788 if ( domain%list(m)%y(tnbr)%compute%begin == jsg )
then
3789 select case (position)
3791 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
3793 j=js; js = 2*jsg-je-2+2*jshift; je = 2*jsg-j-2+2*jshift
3795 if(je .GT. domain%y(tme)%compute%end+jshift)
call mpp_error( fatal, &
3796 'mpp_domains_define.inc(compute_overlaps_fold_west: south edge ubound error send.' )
3798 select case (position)
3800 j=js; js = jsg+jeg-je; je = jsg+jeg-j
3802 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
3805 call insert_update_overlap( overlap, domain%list(m)%pe, &
3806 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3808 call insert_update_overlap( overlap, domain%list(m)%pe, &
3809 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3816 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3817 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
3818 if( jsg.GT.js .AND. je.LT.jsc )
then
3819 js = js+joff; je = je+joff
3823 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
3825 call insert_update_overlap( overlap, domain%list(m)%pe, &
3826 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
3828 if(js .LT. jsg)
then
3830 call insert_update_overlap( overlap, domain%list(m)%pe, &
3831 is, ie, js, js, isc, iec, jsc, jec, dir, folded)
3837 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3838 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
3841 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
3846 if( (position == east .OR. position == corner ) .AND. ( jsc == je .or. jec == js ) )
then
3849 call insert_update_overlap( overlap, domain%list(m)%pe, &
3850 is, ie, js, je, isc, iec, jsc, jec, dir, folded, symmetry=domain%symmetry)
3853 if(js .LT. jsg)
then
3855 call insert_update_overlap( overlap, domain%list(m)%pe, &
3856 is, ie, js, js, isc, iec, jsc, jec, dir, folded)
3862 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
3863 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3864 if( je.GT.jeg .AND. jec.LT.js )
then
3865 js = js-joff; je = je-joff
3869 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
3872 call insert_update_overlap( overlap, domain%list(m)%pe, &
3873 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
3877 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
3878 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3880 if( (position == east .OR. position == corner ) .AND. ( isc == ie .or. iec == is ) )
then
3883 if( je.GT.jeg .AND. jec.LT.js)
then
3884 js = js-joff; je = je-joff
3888 if( is == isg .AND. (position == corner .OR. position == east) &
3889 .AND. ( js .GE. middle .AND. domain%list(m)%y(tnbr)%compute%end+nhalo+jshift .LE. jeg ) )
then
3890 call insert_update_overlap( overlap, domain%list(m)%pe, &
3891 is+1, ie, js, je, isc, iec, jsc, jec, dir)
3892 is = domain%list(m)%x(tnbr)%compute%begin; ie = is
3893 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3894 select case (position)
3896 j=js; js = jsg+jeg-je; je = jsg+jeg-j
3898 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
3900 call insert_update_overlap( overlap, domain%list(m)%pe, &
3901 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3903 call insert_update_overlap( overlap, domain%list(m)%pe, &
3904 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
3910 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
3911 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
3912 if( je.GT.jeg .AND. jec.LT.js )
then
3913 js = js-joff; je = je-joff
3915 call insert_update_overlap( overlap, domain%list(m)%pe, &
3916 is, ie, js, je, isc, iec, jsc, jec, dir)
3920 if( ( position == east .OR. position == corner) )
then
3922 if( domain%x(tme)%compute%begin-whalo .LE. isg .AND. isg .LE. domain%x(tme)%domain_data%end+ishift )
then
3925 if( domain%y(tme)%pos .LT. (
size(domain%y(tme)%list(:))+1)/2 )
then
3926 is = domain%list(m)%x(tnbr)%compute%begin; ie = is
3928 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
3929 select case (position)
3931 js = max(js, middle)
3932 j=js; js = jsg+jeg-je; je = jsg+jeg-j
3934 js = max(js, middle)
3935 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
3937 call insert_update_overlap(overlap, domain%list(m)%pe, &
3938 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
3939 is = max(is, isc); ie = min(ie, iec)
3940 js = max(js, jsc); je = min(je, jec)
3941 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
3942 nsend_check = nsend_check+1
3943 call allocate_check_overlap(checklist(nsend_check), 1)
3944 call insert_check_overlap(checklist(nsend_check), domain%list(m)%pe, &
3945 tme, 3, one_hundred_eighty, is, ie, js, je)
3953 if( overlap%count > 0)
then
3955 if(nsend > maxlist)
call mpp_error(fatal, &
3956 "mpp_domains_define.inc(compute_overlaps_west): nsend is greater than MAXLIST, increase MAXLIST")
3957 call add_update_overlap(overlaplist(nsend), overlap)
3958 call init_overlap_type(overlap)
3962 if(debug_message_passing)
then
3966 write(iunit, *)
"********to_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
3967 do n = 1, overlaplist(m)%count
3968 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
3969 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
3972 if(nsend >0)
flush(iunit)
3977 update%nsend = nsend
3978 if (
associated(update%send))
deallocate(update%send)
3979 allocate(update%send(nsend))
3981 call add_update_overlap( update%send(m), overlaplist(m) )
3985 if(nsend_check>0)
then
3986 check%nsend = nsend_check
3987 if (
associated(check%send))
deallocate(check%send)
3988 allocate(check%send(nsend_check))
3989 do m = 1, nsend_check
3995 call deallocate_overlap_type(overlaplist(m))
3996 if(debug_update_level .NE. no_check)
call deallocate_overlap_type(checklist(m))
3999 isgd = isg - domain%whalo
4000 iegd = ieg + domain%ehalo
4001 jsgd = jsg - domain%shalo
4002 jegd = jeg + domain%nhalo
4008 m = mod( domain%pos+nlist-list, nlist )
4009 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
4010 isc = domain%list(m)%x(1)%compute%begin; iec = domain%list(m)%x(1)%compute%end+ishift
4011 jsc = domain%list(m)%y(1)%compute%begin; jec = domain%list(m)%y(1)%compute%end+jshift
4014 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4015 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4016 is=isc; ie=iec; js=jsc; je=jec
4017 call insert_update_overlap( overlap, domain%list(m)%pe, &
4018 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4022 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4023 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4024 is=isc; ie=iec; js=jsc; je=jec
4025 if( jsd.LT.jsg .AND. js.GE.jed )
then
4026 js = js-joff; je = je-joff
4028 call insert_update_overlap(overlap, domain%list(m)%pe, &
4029 is, ie, js, je, isd, ied, jsd, jed, dir)
4034 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
4035 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4036 is=isc; ie=iec; js=jsc; je=jec
4038 if( (position == east .OR. position == corner ) .AND. ( isd == ie .or. ied == is ) )
then
4041 if( jsd.LT.jsg .AND. js .GT. jed)
then
4042 js = js-joff; je = je-joff
4046 if( isd == isg .AND. (position == corner .OR. position == east) &
4047 .AND. ( jsd < jsg .OR. jed .GE. middle ) )
then
4048 call insert_update_overlap( overlap, domain%list(m)%pe, &
4049 is, ie, js, je, isd+1, ied, jsd, jed, dir)
4050 is=isc; ie=iec; js=jsc; je=jec
4052 select case (position)
4054 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
4056 j=js; js = 2*jsg-je-2+2*jshift; je = 2*jsg-j-2+2*jshift
4058 if(je .GT. domain%y(tme)%compute%end+jshift)
call mpp_error( fatal, &
4059 'mpp_domains_define.inc(compute_overlaps_fold_west: south edge ubound error recv.' )
4061 select case (position)
4063 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4065 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4068 call insert_update_overlap( overlap, domain%list(m)%pe, &
4069 is, ie, js, je, isd, isd, jsd, jed, dir, .true.)
4071 call insert_update_overlap( overlap, domain%list(m)%pe, &
4072 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4079 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4080 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4081 is=isc; ie=iec; js=jsc; je=jec
4082 if( isd.LT.isg )
then
4084 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
4086 if( jsd.LT.jsg .AND. js.GT.jed )
then
4087 js = js-joff; je = je-joff
4089 call insert_update_overlap(overlap, domain%list(m)%pe, &
4090 is, ie, js, je, isd, ied, jsd, jed, dir, folded)
4092 if(js .LT. jsg )
then
4094 call insert_update_overlap(overlap, domain%list(m)%pe, &
4095 is, ie, js, js, isd, ied, jsd, jed, dir, folded )
4101 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4102 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4103 is=isc; ie=iec; js=jsc; je=jec
4104 if( isd.LT.isg )
then
4106 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
4108 if( (position == east .OR. position == corner ) .AND. (jsd == je .or. jed == js ) )
then
4111 call insert_update_overlap(overlap, domain%list(m)%pe, &
4112 is, ie, js, je, isd, ied, jsd, jed, dir, folded, symmetry=domain%symmetry)
4115 if(js .LT. jsg )
then
4117 call insert_update_overlap(overlap, domain%list(m)%pe, &
4118 is, ie, js, js, isd, ied, jsd, jed, dir, folded)
4124 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4125 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4126 is=isc; ie=iec; js=jsc; je=jec
4127 if( isd.LT.isg)
then
4129 call get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
4131 if( jed.GT.jeg .AND. je.LT.jsd )
then
4132 js = js+joff; je = je+joff
4135 call insert_update_overlap( overlap, domain%list(m)%pe, &
4136 is, ie, js, je, isd, ied, jsd, jed, dir)
4141 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
4142 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4143 is=isc; ie=iec; js=jsc; je=jec
4144 if( (position == east .OR. position == corner ) .AND. ( isd == ie .or. ied == is ) )
then
4147 if( jed.GT.jeg .AND. je.LT.jsd)
then
4148 js = js+joff; je = je+joff
4152 if( isd == isg .AND. (position == corner .OR. position == east) &
4153 .AND. jsd .GE. middle .AND. jed .LE. jeg )
then
4154 call insert_update_overlap( overlap, domain%list(m)%pe, &
4155 is, ie, js, je, isd+1, ied, jsd, jed, dir)
4156 is=isc; ie=iec; js=jsc; je=jec
4157 select case (position)
4159 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4161 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4163 call insert_update_overlap( overlap, domain%list(m)%pe, &
4164 is, ie, js, je, isd, isd, jsd, jed, dir, .true.)
4166 call insert_update_overlap( overlap, domain%list(m)%pe, &
4167 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4173 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4174 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4175 is=isc; ie=iec; js=jsc; je=jec
4176 if( jed.GT.jeg .AND. je.LT.jsd )
then
4177 js = js+joff; je = je+joff
4179 call insert_update_overlap( overlap, domain%list(m)%pe, &
4180 is, ie, js, je, isd, ied, jsd, jed, dir)
4185 if( ( position == east .OR. position == corner) )
then
4187 if( domain%x(tme)%domain_data%begin .LE. isg .AND. isg .LE. domain%x(tme)%domain_data%end+ishift )
then
4190 if( domain%y(tme)%pos .GE.
size(domain%y(tme)%list(:))/2 )
then
4191 isd = domain%x(tme)%compute%begin; ied = isd
4192 if( isd == isg )
then
4193 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4194 is=isc; ie=iec; js = jsc; je = jec
4195 select case (position)
4197 jsd = max(jsd, middle)
4198 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4200 jsd = max(jsd, middle)
4201 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4203 call insert_update_overlap(overlap, domain%list(m)%pe, &
4204 is, ie, js, je, isd, ied, jsd, jed, dir, .true.)
4205 is = max(is, isd); ie = min(ie, ied)
4206 js = max(js, jsd); je = min(je, jed)
4207 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
4208 nrecv_check = nrecv_check+1
4209 call allocate_check_overlap(checklist(nrecv_check), 1)
4210 call insert_check_overlap(checklist(nrecv_check), domain%list(m)%pe, &
4211 tme, 3, one_hundred_eighty, is, ie, js, je)
4219 if( overlap%count > 0)
then
4221 if(nrecv > maxlist)
call mpp_error(fatal, &
4222 "mpp_domains_define.inc(compute_overlaps_west): nrecv is greater than MAXLIST, increase MAXLIST")
4223 call add_update_overlap( overlaplist(nrecv), overlap)
4224 call init_overlap_type(overlap)
4228 if(debug_message_passing)
then
4232 write(iunit, *)
"********from_pe = " ,overlaplist(m)%pe,
" count = ",overlaplist(m)%count
4233 do n = 1, overlaplist(m)%count
4234 write(iunit, *) overlaplist(m)%is(n), overlaplist(m)%ie(n), overlaplist(m)%js(n), overlaplist(m)%je(n), &
4235 overlaplist(m)%dir(n), overlaplist(m)%rotation(n)
4238 if(nrecv >0)
flush(iunit)
4243 update%nrecv = nrecv
4244 if (
associated(update%recv))
deallocate(update%recv)
4245 allocate(update%recv(nrecv))
4247 call add_update_overlap( update%recv(m), overlaplist(m) )
4248 do n = 1, update%recv(m)%count
4249 if(update%recv(m)%tileNbr(n) == domain%tile_id(tme))
then
4250 if(update%recv(m)%dir(n) == 1) domain%x(tme)%loffset = 0
4251 if(update%recv(m)%dir(n) == 7) domain%y(tme)%loffset = 0
4257 if(nrecv_check>0)
then
4258 check%nrecv = nrecv_check
4259 if (
associated(check%recv))
deallocate(check%recv)
4260 allocate(check%recv(nrecv_check))
4261 do m = 1, nrecv_check
4266 call deallocate_overlap_type(overlap)
4268 call deallocate_overlap_type(overlaplist(m))
4269 if(debug_update_level .NE. no_check)
call deallocate_overlap_type(checklist(m))
4274 domain%initialized = .true.
4284 type(domain2d),
intent(inout) :: domain
4285 integer,
intent(in) :: position, ishift, jshift
4287 integer :: j, m, n, nlist, tMe, tNbr, dir
4288 integer :: is, ie, js, je, isc, iec, jsc, jec, isd, ied, jsd
4289 integer :: jed, isg, ieg, jsg, jeg, ioff, joff
4290 integer :: list, middle, ni, nj, isgd, iegd, jsgd, jegd
4291 integer :: ism, iem, jsm, jem, whalo, ehalo, shalo, nhalo
4293 type(overlap_type) :: overlap
4294 type(overlapspec),
pointer :: update=>null()
4295 type(overlap_type) :: overlapList(MAXLIST)
4296 type(overlap_type) :: checkList(MAXLIST)
4297 type(overlapspec),
pointer :: check =>null()
4298 integer :: nsend, nrecv
4299 integer :: nsend_check, nrecv_check
4304 if(
size(domain%x(:)) > 1)
return
4307 if(domain%whalo==0 .AND. domain%ehalo==0 .AND. domain%shalo==0 .AND. domain%nhalo==0)
return
4310 nlist =
size(domain%list(:))
4312 select case(position)
4314 update => domain%update_T
4316 update => domain%update_C
4317 check => domain%check_C
4319 update => domain%update_E
4320 check => domain%check_E
4322 update => domain%update_N
4323 check => domain%check_N
4325 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_east):"// &
4326 &
" the value of position should be CENTER, EAST, CORNER or NORTH")
4330 call allocate_update_overlap( overlap, maxoverlap)
4333 call mpp_get_compute_domain( domain, isc, iec, jsc, jec, position=position )
4334 call mpp_get_global_domain ( domain, isg, ieg, jsg, jeg, xsize=ni, ysize=nj, position=position )
4335 call mpp_get_memory_domain ( domain, ism, iem, jsm, jem, position=position )
4336 update%xbegin = ism; update%xend = iem
4337 update%ybegin = jsm; update%yend = jem
4338 if(
ASSOCIATED(check))
then
4339 check%xbegin = ism; check%xend = iem
4340 check%ybegin = jsm; check%yend = jem
4342 update%whalo = domain%whalo; update%ehalo = domain%ehalo
4343 update%shalo = domain%shalo; update%nhalo = domain%nhalo
4344 whalo = domain%whalo; ehalo = domain%ehalo
4345 shalo = domain%shalo; nhalo = domain%nhalo
4349 middle = (jsg+jeg)/2+1
4352 if(.NOT. btest(domain%fold,east))
then
4353 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_east): "//&
4354 "boundary condition in y-direction should be folded-east for "//trim(domain%name))
4356 if(.NOT. domain%y(tme)%cyclic)
then
4357 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_east): "//&
4358 "boundary condition in y-direction should be cyclic for "//trim(domain%name))
4360 if(.not. domain%symmetry)
then
4361 call mpp_error(fatal,
"mpp_domains_define.inc(compute_overlaps_fold_east): "//&
4362 "when east boundary is folded, the domain must be symmetry for "//trim(domain%name))
4368 m = mod( domain%pos+list, nlist )
4369 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
4373 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
4374 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
4377 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4382 if( (position == east .OR. position == corner ) .AND. ( jsc == je .or. jec == js ) )
then
4385 call insert_update_overlap( overlap, domain%list(m)%pe, &
4386 is, ie, js, je, isc, iec, jsc, jec, dir, folded, symmetry=domain%symmetry)
4389 if(js .LT. jsg)
then
4391 call insert_update_overlap( overlap, domain%list(m)%pe, &
4392 is, ie, js, js, isc, iec, jsc, jec, dir, folded)
4398 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
4399 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
4400 if( jsg.GT.js .AND. je.LT.jsc )
then
4401 js = js+joff; je = je+joff
4406 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4409 call insert_update_overlap( overlap, domain%list(m)%pe, &
4410 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
4412 if(js .LT. jsg)
then
4414 call insert_update_overlap( overlap, domain%list(m)%pe, &
4415 is, ie, js, js, isc, iec, jsc, jec, dir, folded)
4420 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
4421 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
4423 if( (position == east .OR. position == corner ) .AND. ( isc == ie .or. iec == is ) )
then
4426 if( js.LT.jsg .AND. jsc.GT.je)
then
4427 js = js+joff; je = je+joff
4431 if( ie == ieg .AND. (position == corner .OR. position == east) &
4432 .AND. ( domain%list(m)%y(tnbr)%compute%begin == jsg .OR. &
4433 domain%list(m)%y(tnbr)%compute%begin-1 .GE. middle ) )
then
4434 call insert_update_overlap( overlap, domain%list(m)%pe, &
4435 is, ie-1, js, je, isc, iec, jsc, jec, dir)
4438 if(position == corner .AND. .NOT. domain%symmetry .AND. domain%list(m)%y(tnbr)%compute%begin==jsg)
then
4439 call insert_update_overlap(overlap, domain%list(m)%pe, &
4440 ie, ie, je, je, isc, iec, jsc, jec, dir, .true.)
4443 ie = domain%list(m)%x(tnbr)%compute%end+ishift; is = ie
4444 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
4445 if ( domain%list(m)%y(tnbr)%compute%begin == jsg )
then
4446 select case (position)
4448 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
4450 j=js; js = 2*jsg-je-2+2*jshift; je = 2*jsg-j-2+2*jshift
4452 if(je .GT. domain%y(tme)%compute%end+jshift)
call mpp_error( fatal, &
4453 'mpp_domains_define.inc(compute_overlaps_fold_east: south edge ubound error send.' )
4455 select case (position)
4457 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4459 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4462 call insert_update_overlap( overlap, domain%list(m)%pe, &
4463 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
4465 call insert_update_overlap( overlap, domain%list(m)%pe, &
4466 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
4472 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
4473 js = domain%list(m)%y(tnbr)%compute%begin-shalo; je = domain%list(m)%y(tnbr)%compute%begin-1
4474 if( js.LT.jsg .AND. jsc.GT.je )
then
4475 js = js+joff; je = je+joff
4477 call insert_update_overlap( overlap, domain%list(m)%pe, &
4478 is, ie, js, je, isc, iec, jsc, jec, dir)
4482 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
4483 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
4484 call insert_update_overlap( overlap, domain%list(m)%pe, &
4485 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
4489 is = domain%list(m)%x(tnbr)%compute%begin-whalo; ie = domain%list(m)%x(tnbr)%compute%begin-1
4490 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
4491 if( je.GT.jeg .AND. jec.LT.js )
then
4492 js = js-joff; je = je-joff
4494 call insert_update_overlap( overlap, domain%list(m)%pe, &
4495 is, ie, js, je, isc, iec, jsc, jec, dir)
4500 is = domain%list(m)%x(tnbr)%compute%begin; ie = domain%list(m)%x(tnbr)%compute%end+ishift
4501 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
4503 if( (position == east .OR. position == corner ) .AND. ( isc == ie .or. iec == is ) )
then
4506 if( je.GT.jeg .AND. jec.LT.js)
then
4507 js = js-joff; je = je-joff
4511 if( ie == ieg .AND. (position == corner .OR. position == east) &
4512 .AND. ( js .GE. middle .AND. domain%list(m)%y(tnbr)%compute%end+nhalo+jshift .LE. jeg ) )
then
4513 call insert_update_overlap( overlap, domain%list(m)%pe, &
4514 is, ie-1, js, je, isc, iec, jsc, jec, dir)
4515 ie = domain%list(m)%x(tnbr)%compute%end+ishift; is = ie
4516 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
4517 select case (position)
4519 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4521 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4523 call insert_update_overlap( overlap, domain%list(m)%pe, &
4524 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
4526 call insert_update_overlap( overlap, domain%list(m)%pe, &
4527 is, ie, js, je, isc, iec, jsc, jec, dir, symmetry=domain%symmetry)
4534 is = domain%list(m)%x(tnbr)%compute%end+1+ishift; ie = domain%list(m)%x(tnbr)%compute%end+ehalo+ishift
4535 js = domain%list(m)%y(tnbr)%compute%end+1+jshift; je = domain%list(m)%y(tnbr)%compute%end+nhalo+jshift
4536 if( je.GT.jeg .AND. jec.LT.js )
then
4537 js = js-joff; je = je-joff
4541 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4544 call insert_update_overlap( overlap, domain%list(m)%pe, &
4545 is, ie, js, je, isc, iec, jsc, jec, dir, folded)
4549 if( ( position == east .OR. position == corner) )
then
4551 if( domain%x(tme)%domain_data%begin .LE. ieg .AND. ieg .LE. domain%x(tme)%domain_data%end+ishift )
then
4554 if( domain%y(tme)%pos .LT. (
size(domain%y(tme)%list(:))+1)/2 )
then
4555 ie = domain%list(m)%x(tnbr)%compute%end+ishift; is = ie
4557 js = domain%list(m)%y(tnbr)%compute%begin; je = domain%list(m)%y(tnbr)%compute%end+jshift
4558 select case (position)
4560 js = max(js, middle)
4561 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4563 js = max(js, middle)
4564 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4566 call insert_update_overlap(overlap, domain%list(m)%pe, &
4567 is, ie, js, je, isc, iec, jsc, jec, dir, .true.)
4568 is = max(is, isc); ie = min(ie, iec)
4569 js = max(js, jsc); je = min(je, jec)
4570 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
4571 nsend_check = nsend_check+1
4572 call allocate_check_overlap(checklist(nsend_check), 1)
4573 call insert_check_overlap(checklist(nsend_check), domain%list(m)%pe, &
4574 tme, 1, one_hundred_eighty, is, ie, js, je)
4582 if( overlap%count > 0)
then
4584 if(nsend > maxlist)
call mpp_error(fatal, &
4585 "mpp_domains_define.inc(compute_overlaps_east): nsend is greater than MAXLIST, increase MAXLIST")
4586 call add_update_overlap(overlaplist(nsend), overlap)
4587 call init_overlap_type(overlap)
4593 update%nsend = nsend
4594 if (
associated(update%send))
deallocate(update%send)
4595 allocate(update%send(nsend))
4597 call add_update_overlap( update%send(m), overlaplist(m) )
4601 if(nsend_check>0)
then
4602 check%nsend = nsend_check
4603 if (
associated(check%send))
deallocate(check%send)
4604 allocate(check%send(nsend_check))
4605 do m = 1, nsend_check
4611 call deallocate_overlap_type(overlaplist(m))
4612 if(debug_update_level .NE. no_check)
call deallocate_overlap_type(checklist(m))
4615 isgd = isg - domain%whalo
4616 iegd = ieg + domain%ehalo
4617 jsgd = jsg - domain%shalo
4618 jegd = jeg + domain%nhalo
4624 m = mod( domain%pos+nlist-list, nlist )
4625 if(domain%list(m)%tile_id(tnbr) == domain%tile_id(tme) )
then
4626 isc = domain%list(m)%x(1)%compute%begin; iec = domain%list(m)%x(1)%compute%end+ishift
4627 jsc = domain%list(m)%y(1)%compute%begin; jec = domain%list(m)%y(1)%compute%end+jshift
4631 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4632 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4633 is=isc; ie=iec; js=jsc; je=jec
4634 if( ied.GT.ieg )
then
4636 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4638 if( (position == east .OR. position == corner ) .AND. (jsd == je .or. jed == js ) )
then
4641 call insert_update_overlap(overlap, domain%list(m)%pe, &
4642 is, ie, js, je, isd, ied, jsd, jed, dir, folded, symmetry=domain%symmetry)
4645 if(js .LT. jsg )
then
4647 call insert_update_overlap(overlap, domain%list(m)%pe, &
4648 is, ie, js, js, isd, ied, jsd, jed, dir, folded)
4654 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4655 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4656 is=isc; ie=iec; js=jsc; je=jec
4657 if( ied.GT.ieg )
then
4659 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4661 if( jsd.LT.jsg .AND. js.GT.jed )
then
4662 js = js-joff; je = je-joff
4664 call insert_update_overlap(overlap, domain%list(m)%pe, &
4665 is, ie, js, je, isd, ied, jsd, jed, dir, folded)
4667 if(js .LT. jsg )
then
4669 call insert_update_overlap(overlap, domain%list(m)%pe, &
4670 is, ie, js, js, isd, ied, jsd, jed, dir, folded )
4676 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
4677 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4678 is=isc; ie=iec; js=jsc; je=jec
4680 if( (position == east .OR. position == corner ) .AND. ( isd == ie .or. ied == is ) )
then
4683 if( jsd.LT.jsg .AND. js .GT. jed)
then
4684 js = js-joff; je = je-joff
4688 if( ied == ieg .AND. (position == corner .OR. position == east) &
4689 .AND. ( jsd < jsg .OR. jed .GE. middle ) )
then
4690 call insert_update_overlap( overlap, domain%list(m)%pe, &
4691 is, ie, js, je, isd, ied-1, jsd, jed, dir)
4692 is=isc; ie=iec; js=jsc; je=jec
4694 select case (position)
4696 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
4698 j=js; js = 2*jsg-je-2+2*jshift; je = 2*jsg-j-2+2*jshift
4700 if(je .GT. domain%y(tme)%compute%end+jshift)
call mpp_error( fatal, &
4701 'mpp_domains_define.inc(compute_overlaps_fold_west: south edge ubound error recv.' )
4703 select case (position)
4705 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4707 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4710 call insert_update_overlap( overlap, domain%list(m)%pe, &
4711 is, ie, js, je, ied, ied, jsd, jed, dir, .true.)
4713 call insert_update_overlap( overlap, domain%list(m)%pe, &
4714 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4720 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4721 jsd = domain%y(tme)%domain_data%begin; jed = domain%y(tme)%compute%begin-1
4722 is=isc; ie=iec; js=jsc; je=jec
4723 if( jsd.LT.jsg .AND. js.GE.jed )
then
4724 js = js-joff; je = je-joff
4726 call insert_update_overlap(overlap, domain%list(m)%pe, &
4727 is, ie, js, je, isd, ied, jsd, jed, dir)
4731 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4732 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4733 is=isc; ie=iec; js=jsc; je=jec
4734 call insert_update_overlap( overlap, domain%list(m)%pe, &
4735 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4740 isd = domain%x(tme)%domain_data%begin; ied = domain%x(tme)%compute%begin-1
4741 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4742 is=isc; ie=iec; js=jsc; je=jec
4743 if( jed.GT.jeg .AND. je.LT.jsd )
then
4744 js = js+joff; je = je+joff
4746 call insert_update_overlap( overlap, domain%list(m)%pe, &
4747 is, ie, js, je, isd, ied, jsd, jed, dir)
4752 isd = domain%x(tme)%compute%begin; ied = domain%x(tme)%compute%end+ishift
4753 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4754 is=isc; ie=iec; js=jsc; je=jec
4755 if( (position == east .OR. position == corner ) .AND. ( isd == ie .or. ied == is ) )
then
4758 if( jed.GT.jeg .AND. je.LT.jsd)
then
4759 js = js+joff; je = je+joff
4763 if( ied == ieg .AND. (position == corner .OR. position == east) &
4764 .AND. jsd .GE. middle .AND. jed .LE. jeg )
then
4765 call insert_update_overlap( overlap, domain%list(m)%pe, &
4766 is, ie, js, je, isd, ied-1, jsd, jed, dir)
4767 is=isc; ie=iec; js=jsc; je=jec
4768 select case (position)
4770 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4772 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4774 call insert_update_overlap( overlap, domain%list(m)%pe, &
4775 is, ie, js, je, ied, ied, jsd, jed, dir, .true.)
4777 call insert_update_overlap( overlap, domain%list(m)%pe, &
4778 is, ie, js, je, isd, ied, jsd, jed, dir, symmetry=domain%symmetry)
4785 isd = domain%x(tme)%compute%end+1+ishift; ied = domain%x(tme)%domain_data%end+ishift
4786 jsd = domain%y(tme)%compute%end+1+jshift; jed = domain%y(tme)%domain_data%end+jshift
4787 is=isc; ie=iec; js=jsc; je=jec
4788 if( ied.GT.ieg)
then
4790 call get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4792 if( jed.GT.jeg .AND. je.LT.jsd )
then
4793 js = js+joff; je = je+joff
4796 call insert_update_overlap( overlap, domain%list(m)%pe, &
4797 is, ie, js, je, isd, ied, jsd, jed, dir)
4801 if( ( position == east .OR. position == corner) )
then
4803 if( domain%x(tme)%domain_data%begin .LE. ieg .AND. ieg .LE. domain%x(tme)%domain_data%end+ishift )
then
4806 if( domain%y(tme)%pos .GE.
size(domain%y(tme)%list(:))/2 )
then
4807 ied = domain%x(tme)%compute%end+ishift; isd = ied
4808 if( ied == ieg )
then
4809 jsd = domain%y(tme)%compute%begin; jed = domain%y(tme)%compute%end+jshift
4810 is=isc; ie=iec; js = jsc; je = jec
4811 select case (position)
4813 jsd = max(jsd, middle)
4814 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4816 jsd = max(jsd, middle)
4817 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4819 call insert_update_overlap(overlap, domain%list(m)%pe, &
4820 is, ie, js, je, isd, ied, jsd, jed, dir, .true.)
4821 is = max(is, isd); ie = min(ie, ied)
4822 js = max(js, jsd); je = min(je, jed)
4823 if(debug_update_level .NE. no_check .AND. ie.GE.is .AND. je.GE.js )
then
4824 nrecv_check = nrecv_check+1
4825 call allocate_check_overlap(checklist(nrecv_check), 1)
4826 call insert_check_overlap(checklist(nrecv_check), domain%list(m)%pe, &
4827 tme, 3, one_hundred_eighty, is, ie, js, je)
4835 if( overlap%count > 0)
then
4837 if(nrecv > maxlist)
call mpp_error(fatal, &
4838 "mpp_domains_define.inc(compute_overlaps_east): nrecv is greater than MAXLIST, increase MAXLIST")
4839 call add_update_overlap( overlaplist(nrecv), overlap)
4840 call init_overlap_type(overlap)
4846 update%nrecv = nrecv
4847 if (
associated(update%recv))
deallocate(update%recv)
4848 allocate(update%recv(nrecv))
4850 call add_update_overlap( update%recv(m), overlaplist(m) )
4851 do n = 1, update%recv(m)%count
4852 if(update%recv(m)%tileNbr(n) == domain%tile_id(tme))
then
4853 if(update%recv(m)%dir(n) == 1) domain%x(tme)%loffset = 0
4854 if(update%recv(m)%dir(n) == 7) domain%y(tme)%loffset = 0
4860 if(nrecv_check>0)
then
4861 check%nrecv = nrecv_check
4862 if (
associated(check%recv))
deallocate(check%recv)
4863 allocate(check%recv(nrecv_check))
4864 do m = 1, nrecv_check
4869 call deallocate_overlap_type(overlap)
4871 call deallocate_overlap_type(overlaplist(m))
4872 if(debug_update_level .NE. no_check)
call deallocate_overlap_type(checklist(m))
4878 domain%initialized = .true.
4883 subroutine get_fold_index_west(jsg, jeg, isg, jshift, position, is, ie, js, je)
4884 integer,
intent(in) :: jsg, jeg, isg, jshift, position
4885 integer,
intent(inout) :: is, ie, js, je
4888 select case(position)
4890 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4891 i=is; is = 2*isg-ie-1; ie = 2*isg-i-1
4893 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4894 i=is; is = 2*isg-ie; ie = 2*isg-i
4896 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4897 i=is; is = 2*isg-ie-1; ie = 2*isg-i-1
4899 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4900 i=is; is = 2*isg-ie; ie = 2*isg-i
4903 end subroutine get_fold_index_west
4906 subroutine get_fold_index_east(jsg, jeg, ieg, jshift, position, is, ie, js, je)
4907 integer,
intent(in) :: jsg, jeg, ieg, jshift, position
4908 integer,
intent(inout) :: is, ie, js, je
4911 select case(position)
4913 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4914 i=is; is = 2*ieg-ie+1; ie = 2*ieg-i+1
4916 j=js; js = jsg+jeg-je; je = jsg+jeg-j
4917 i=is; is = 2*ieg-ie; ie = 2*ieg-i
4919 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4920 i=is; is = 2*ieg-ie+1; ie = 2*ieg-i+1
4922 j=js; js = jsg+jeg-je-1+jshift; je = jsg+jeg-j-1+jshift
4923 i=is; is = 2*ieg-ie; ie = 2*ieg-i
4926 end subroutine get_fold_index_east
4929 subroutine get_fold_index_south(isg, ieg, jsg, ishift, position, is, ie, js, je)
4930 integer,
intent(in) :: isg, ieg, jsg, ishift, position
4931 integer,
intent(inout) :: is, ie, js, je
4934 select case(position)
4936 i=is; is = isg+ieg-ie; ie = isg+ieg-i
4937 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
4939 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
4940 j=js; js = 2*jsg-je-1; je = 2*jsg-j-1
4942 i=is; is = isg+ieg-ie; ie = isg+ieg-i
4943 j=js; js = 2*jsg-je; je = 2*jsg-j
4945 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
4946 j=js; js = 2*jsg-je; je = 2*jsg-j
4949 end subroutine get_fold_index_south
4951 subroutine get_fold_index_north(isg, ieg, jeg, ishift, position, is, ie, js, je)
4952 integer,
intent(in) :: isg, ieg, jeg, ishift, position
4953 integer,
intent(inout) :: is, ie, js, je
4956 select case(position)
4958 i=is; is = isg+ieg-ie; ie = isg+ieg-i
4959 j=js; js = 2*jeg-je+1; je = 2*jeg-j+1
4961 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
4962 j=js; js = 2*jeg-je+1; je = 2*jeg-j+1
4964 i=is; is = isg+ieg-ie; ie = isg+ieg-i
4965 j=js; js = 2*jeg-je; je = 2*jeg-j
4967 i=is; is = isg+ieg-ie-1+ishift; ie = isg+ieg-i-1+ishift
4968 j=js; js = 2*jeg-je; je = 2*jeg-j
4971 end subroutine get_fold_index_north
4977 integer,
intent(inout) :: lstart, lend
4978 integer,
intent(in ) :: offset, gstart, gend, gsize
4980 lstart = lstart + offset
4981 if(lstart > gend) lstart = lstart - gsize
4982 if(lstart < gstart) lstart = lstart + gsize
4983 lend = lend + offset
4984 if(lend > gend) lend = lend - gsize
4985 if(lend < gstart) lend = lend + gsize
4998 subroutine set_overlaps(domain, overlap_in, overlap_out, whalo_out, ehalo_out, shalo_out, nhalo_out)
4999 type(domain2d),
intent(in) :: domain
5000 type(overlapspec),
intent(in) :: overlap_in
5001 type(overlapspec),
intent(inout) :: overlap_out
5002 integer,
intent(in) :: whalo_out, ehalo_out, shalo_out, nhalo_out
5003 integer :: nlist, m, n, isoff, ieoff, jsoff, jeoff, rotation
5004 integer :: whalo_in, ehalo_in, shalo_in, nhalo_in
5006 type(overlap_type) :: overlap
5007 type(overlap_type),
allocatable :: send(:), recv(:)
5008 type(overlap_type),
pointer :: ptrIn => null()
5009 integer :: nsend, nrecv, nsend_in, nrecv_in
5011 if( domain%fold .NE. 0)
call mpp_error(fatal,
"mpp_domains_define.inc(set_overlaps):"// &
5012 &
" folded domain is not implemented for arbitrary halo update, contact developer")
5014 whalo_in = domain%whalo
5015 ehalo_in = domain%ehalo
5016 shalo_in = domain%shalo
5017 nhalo_in = domain%nhalo
5019 if( .NOT. domain%initialized)
call mpp_error(fatal, &
5020 "mpp_domains_define.inc: domain is not defined yet")
5022 nlist =
size(domain%list(:))
5023 isoff = whalo_in - abs(whalo_out)
5024 ieoff = ehalo_in - abs(ehalo_out)
5025 jsoff = shalo_in - abs(shalo_out)
5026 jeoff = nhalo_in - abs(nhalo_out)
5029 nsend_in = overlap_in%nsend
5030 nrecv_in = overlap_in%nrecv
5031 if(nsend_in>0)
allocate(send(nsend_in))
5032 if(nrecv_in>0)
allocate(recv(nrecv_in))
5033 call allocate_update_overlap(overlap, maxoverlap)
5035 overlap_out%whalo = whalo_out
5036 overlap_out%ehalo = ehalo_out
5037 overlap_out%shalo = shalo_out
5038 overlap_out%nhalo = nhalo_out
5039 overlap_out%xbegin = overlap_in%xbegin
5040 overlap_out%xend = overlap_in%xend
5041 overlap_out%ybegin = overlap_in%ybegin
5042 overlap_out%yend = overlap_in%yend
5046 ptrin => overlap_in%send(m)
5047 if(ptrin%count .LE. 0)
call mpp_error(fatal,
"mpp_domains_define.inc(set_overlaps):"// &
5048 " number of overlap for send should be a positive number for"//trim(domain%name) )
5049 do n = 1, ptrin%count
5051 rotation = ptrin%rotation(n)
5054 if(ehalo_out > 0)
then
5055 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, 0, n, dir, rotation)
5056 else if(ehalo_out<0)
then
5057 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, 0, n, dir, rotation)
5060 if(ehalo_out>0 .AND. shalo_out > 0)
then
5061 call set_single_overlap(ptrin, overlap, 0, -ieoff, jsoff, 0, n, dir, rotation)
5062 else if(ehalo_out<0 .AND. shalo_out < 0)
then
5063 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, shalo_out, n, dir, rotation)
5064 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, jsoff, 0, n, dir-1, rotation)
5065 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, shalo_out, n, dir+1, rotation)
5068 if(shalo_out > 0)
then
5069 call set_single_overlap(ptrin, overlap, 0, 0, jsoff, 0, n, dir, rotation)
5070 else if(shalo_out<0)
then
5071 call set_single_overlap(ptrin, overlap, 0, 0, 0, shalo_out, n, dir, rotation)
5074 if(whalo_out>0 .AND. shalo_out > 0)
then
5075 call set_single_overlap(ptrin, overlap, isoff, 0, jsoff, 0, n, dir, rotation)
5076 else if(whalo_out<0 .AND. shalo_out < 0)
then
5077 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, shalo_out, n, dir, rotation)
5078 call set_single_overlap(ptrin, overlap, isoff, 0, 0, shalo_out, n, dir-1, rotation)
5079 call set_single_overlap(ptrin, overlap, 0, whalo_out, jsoff, 0, n, dir+1, rotation)
5082 if(whalo_out > 0)
then
5083 call set_single_overlap(ptrin, overlap, isoff, 0, 0, 0, n, dir, rotation)
5084 else if(whalo_out<0)
then
5085 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, 0, n, dir, rotation)
5088 if(whalo_out>0 .AND. nhalo_out > 0)
then
5089 call set_single_overlap(ptrin, overlap, isoff, 0, 0, -jeoff, n, dir, rotation)
5090 else if(whalo_out<0 .AND. nhalo_out < 0)
then
5091 call set_single_overlap(ptrin, overlap, 0, whalo_out, -nhalo_out, 0, n, dir, rotation)
5092 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, -jeoff, n, dir-1, rotation)
5093 call set_single_overlap(ptrin, overlap, isoff, 0, -nhalo_out, 0, n, dir+1, rotation)
5096 if(nhalo_out > 0)
then
5097 call set_single_overlap(ptrin, overlap, 0, 0, 0, -jeoff, n, dir, rotation)
5098 else if(nhalo_out<0)
then
5099 call set_single_overlap(ptrin, overlap, 0, 0, -nhalo_out, 0, n, dir, rotation)
5102 if(ehalo_out>0 .AND. nhalo_out > 0)
then
5103 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, -jeoff, n, dir, rotation)
5104 else if(ehalo_out<0 .AND. nhalo_out < 0)
then
5105 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, -nhalo_out, 0, n, dir, rotation)
5106 call set_single_overlap(ptrin, overlap, 0, -ieoff, -nhalo_out, 0, n, dir-1, rotation)
5107 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, -jeoff, n, 1, rotation)
5111 if(overlap%count>0)
then
5113 call add_update_overlap(send(nsend), overlap)
5114 call init_overlap_type(overlap)
5119 overlap_out%nsend = nsend
5120 if (
associated(overlap_out%send))
deallocate(overlap_out%send)
5121 allocate(overlap_out%send(nsend));
5123 call add_update_overlap(overlap_out%send(n), send(n) )
5126 overlap_out%nsend = 0
5135 ptrin => overlap_in%recv(m)
5136 if(ptrin%count .LE. 0)
call mpp_error(fatal, &
5137 "mpp_domains_define.inc(set_overlaps): number of overlap for recv should be a positive number")
5139 do n = 1, ptrin%count
5141 rotation = ptrin%rotation(n)
5144 if(ehalo_out > 0)
then
5145 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, 0, n, dir)
5146 else if(ehalo_out<0)
then
5147 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, 0, n, dir)
5150 if(ehalo_out>0 .AND. shalo_out > 0)
then
5151 call set_single_overlap(ptrin, overlap, 0, -ieoff, jsoff, 0, n, dir)
5152 else if(ehalo_out<0 .AND. shalo_out < 0)
then
5153 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, shalo_out, n, dir)
5154 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, jsoff, 0, n, dir-1)
5155 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, shalo_out, n, dir+1)
5158 if(shalo_out > 0)
then
5159 call set_single_overlap(ptrin, overlap, 0, 0, jsoff, 0, n, dir)
5160 else if(shalo_out<0)
then
5161 call set_single_overlap(ptrin, overlap, 0, 0, 0, shalo_out, n, dir)
5164 if(whalo_out>0 .AND. shalo_out > 0)
then
5165 call set_single_overlap(ptrin, overlap, isoff, 0, jsoff, 0, n, dir)
5166 else if(whalo_out<0 .AND. shalo_out < 0)
then
5167 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, shalo_out, n, dir)
5168 call set_single_overlap(ptrin, overlap, isoff, 0, 0, shalo_out, n, dir-1)
5169 call set_single_overlap(ptrin, overlap, 0, whalo_out, jsoff, 0, n, dir+1)
5172 if(whalo_out > 0)
then
5173 call set_single_overlap(ptrin, overlap, isoff, 0, 0, 0, n, dir)
5174 else if(whalo_out<0)
then
5175 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, 0, n, dir)
5178 if(whalo_out>0 .AND. nhalo_out > 0)
then
5179 call set_single_overlap(ptrin, overlap, isoff, 0, 0, -jeoff, n, dir)
5180 else if(whalo_out<0 .AND. nhalo_out < 0)
then
5181 call set_single_overlap(ptrin, overlap, 0, whalo_out, -nhalo_out, 0, n, dir)
5182 call set_single_overlap(ptrin, overlap, 0, whalo_out, 0, -jeoff, n, dir-1)
5183 call set_single_overlap(ptrin, overlap, isoff, 0, -nhalo_out, 0, n, dir+1)
5186 if(nhalo_out > 0)
then
5187 call set_single_overlap(ptrin, overlap, 0, 0, 0, -jeoff, n, dir)
5188 else if(nhalo_out<0)
then
5189 call set_single_overlap(ptrin, overlap, 0, 0, -nhalo_out, 0, n, dir)
5192 if(ehalo_out>0 .AND. nhalo_out > 0)
then
5193 call set_single_overlap(ptrin, overlap, 0, -ieoff, 0, -jeoff, n, dir)
5194 else if(ehalo_out<0 .AND. nhalo_out < 0)
then
5195 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, -nhalo_out, 0, n, dir)
5196 call set_single_overlap(ptrin, overlap, 0, -ieoff, -nhalo_out, 0, n, dir-1)
5197 call set_single_overlap(ptrin, overlap, -ehalo_out, 0, 0, -jeoff, n, 1)
5201 if(overlap%count>0)
then
5203 call add_update_overlap(recv(nrecv), overlap)
5204 call init_overlap_type(overlap)
5209 overlap_out%nrecv = nrecv
5210 if (
associated(overlap_out%recv))
deallocate(overlap_out%recv)
5211 allocate(overlap_out%recv(nrecv));
5213 call add_update_overlap(overlap_out%recv(n), recv(n) )
5216 overlap_out%nrecv = 0
5219 call deallocate_overlap_type(overlap)
5221 call deallocate_overlap_type(send(n))
5224 call deallocate_overlap_type(recv(n))
5226 if(
allocated(send))
deallocate(send)
5227 if(
allocated(recv))
deallocate(recv)
5230 call set_domain_comm_inf(overlap_out)
5236 subroutine set_single_overlap(overlap_in, overlap_out, isoff, ieoff, jsoff, jeoff, index, dir, rotation)
5237 type(overlap_type),
intent(in) :: overlap_in
5238 type(overlap_type),
intent(inout) :: overlap_out
5239 integer,
intent(in) :: isoff, jsoff, ieoff, jeoff
5240 integer,
intent(in) :: index
5241 integer,
intent(in) :: dir
5242 integer,
optional,
intent(in) :: rotation
5246 if( overlap_out%pe == null_pe )
then
5247 overlap_out%pe = overlap_in%pe
5249 if(overlap_out%pe .NE. overlap_in%pe)
call mpp_error(fatal, &
5250 "mpp_domains_define.inc(set_single_overlap): mismatch of pe between overlap_in and overlap_out")
5253 if(isoff .NE. 0 .and. ieoff .NE. 0)
call mpp_error(fatal, &
5254 "mpp_domains_define.inc(set_single_overlap): both isoff and ieoff are non-zero")
5255 if(jsoff .NE. 0 .and. jeoff .NE. 0)
call mpp_error(fatal, &
5256 "mpp_domains_define.inc(set_single_overlap): both jsoff and jeoff are non-zero")
5259 overlap_out%count = overlap_out%count + 1
5260 count = overlap_out%count
5261 if(count > maxoverlap)
call mpp_error(fatal, &
5262 "set_single_overlap: number of overlap is greater than MAXOVERLAP, increase MAXOVERLAP")
5264 if(
present(rotation)) rotate = rotation
5265 overlap_out%rotation (count) = overlap_in%rotation(index)
5266 overlap_out%dir (count) = dir
5267 overlap_out%tileMe (count) = overlap_in%tileMe(index)
5268 overlap_out%tileNbr (count) = overlap_in%tileNbr(index)
5272 overlap_out%is(count) = overlap_in%is(index) + isoff
5273 overlap_out%ie(count) = overlap_in%ie(index) + ieoff
5274 overlap_out%js(count) = overlap_in%js(index) + jsoff
5275 overlap_out%je(count) = overlap_in%je(index) + jeoff
5277 overlap_out%is(count) = overlap_in%is(index) - jeoff
5278 overlap_out%ie(count) = overlap_in%ie(index) - jsoff
5279 overlap_out%js(count) = overlap_in%js(index) + isoff
5280 overlap_out%je(count) = overlap_in%je(index) + ieoff
5282 overlap_out%is(count) = overlap_in%is(index) + jsoff
5283 overlap_out%ie(count) = overlap_in%ie(index) + jeoff
5284 overlap_out%js(count) = overlap_in%js(index) - ieoff
5285 overlap_out%je(count) = overlap_in%je(index) - isoff
5287 call mpp_error(fatal,
"mpp_domains_define.inc: the value of rotation should be ZERO, NINETY or MINUS_NINETY")
5290 end subroutine set_single_overlap
5295 refine1, refine2, istart1, iend1, jstart1, jend1, istart2, iend2, jstart2, jend2, &
5296 isgList, iegList, jsgList, jegList, tile_base )
5297 type(domain2d),
intent(inout) :: domain
5298 integer,
intent(in) :: position
5299 integer,
intent(in) :: num_contact
5300 integer,
dimension(:),
intent(in) :: tile1, tile2
5301 integer,
dimension(:),
intent(in) :: align1, align2
5302 real,
dimension(:),
intent(in) :: refine1, refine2
5303 integer,
dimension(:),
intent(in) :: istart1, iend1
5304 integer,
dimension(:),
intent(in) :: jstart1, jend1
5305 integer,
dimension(:),
intent(in) :: istart2, iend2
5306 integer,
dimension(:),
intent(in) :: jstart2, jend2
5307 integer,
dimension(:),
intent(in) :: isgList, iegList
5308 integer,
dimension(:),
intent(in) :: jsgList, jegList
5309 integer,
intent(in) :: tile_base
5311 integer :: isc, iec, jsc, jec, isd, ied, jsd, jed
5312 integer :: isc1, iec1, jsc1, jec1, isc2, iec2, jsc2, jec2
5313 integer :: isd1, ied1, jsd1, jed1, isd2, ied2, jsd2, jed2
5314 integer :: is, ie, js, je, ioff, joff
5315 integer :: ntiles, max_contact
5316 integer :: nlist, list, m, n, l, count, numS, numR
5317 integer :: whalo, ehalo, shalo, nhalo
5318 integer :: t1, t2, tt, pos
5319 integer :: ntileMe, ntileNbr, tMe, tNbr, tileMe, dir
5320 integer :: nxd, nyd, nxc, nyc, ism, iem, jsm, jem
5321 integer :: dirlist(8)
5324 integer,
dimension(4*num_contact) :: is1Send, ie1Send, js1Send, je1Send
5325 integer,
dimension(4*num_contact) :: is2Send, ie2Send, js2Send, je2Send
5326 integer,
dimension(4*num_contact) :: is2Recv, ie2Recv, js2Recv, je2Recv
5327 integer,
dimension(4*num_contact) :: is1Recv, ie1Recv, js1Recv, je1Recv
5328 integer,
dimension(4*num_contact) :: align1Recv, align2Recv, align1Send, align2Send
5329 real,
dimension(4*num_contact) :: refineRecv, refineSend
5330 integer,
dimension(4*num_contact) :: rotateSend, rotateRecv, tileSend, tileRecv
5331 integer :: nsend, nrecv, nsend2, nrecv2
5332 type(contact_type),
dimension(domain%ntiles) :: eCont, wCont, sCont, nCont
5333 type(overlap_type),
dimension(0:size(domain%list(:))-1) :: overlapSend, overlapRecv
5336 if( position .NE. center )
call mpp_error(fatal,
"mpp_domains_define.inc: " //&
5337 "routine define_contact_point can only be used to calculate overlapping for cell center.")
5339 ntiles = domain%ntiles
5341 econt(:)%ncontact = 0
5344 econt(n)%ncontact = 0; scont(n)%ncontact = 0; wcont(n)%ncontact = 0; ncont(n)%ncontact = 0;
5345 allocate(econt(n)%tile(num_contact), wcont(n)%tile(num_contact) )
5346 allocate(ncont(n)%tile(num_contact), scont(n)%tile(num_contact) )
5347 allocate(econt(n)%align1(num_contact), econt(n)%align2(num_contact) )
5348 allocate(wcont(n)%align1(num_contact), wcont(n)%align2(num_contact) )
5349 allocate(scont(n)%align1(num_contact), scont(n)%align2(num_contact) )
5350 allocate(ncont(n)%align1(num_contact), ncont(n)%align2(num_contact) )
5351 allocate(econt(n)%refine1(num_contact), econt(n)%refine2(num_contact) )
5352 allocate(wcont(n)%refine1(num_contact), wcont(n)%refine2(num_contact) )
5353 allocate(scont(n)%refine1(num_contact), scont(n)%refine2(num_contact) )
5354 allocate(ncont(n)%refine1(num_contact), ncont(n)%refine2(num_contact) )
5355 allocate(econt(n)%is1(num_contact), econt(n)%ie1(num_contact), econt(n)%js1(num_contact), &
5356 & econt(n)%je1(num_contact))
5357 allocate(econt(n)%is2(num_contact), econt(n)%ie2(num_contact), econt(n)%js2(num_contact), &
5358 & econt(n)%je2(num_contact))
5359 allocate(wcont(n)%is1(num_contact), wcont(n)%ie1(num_contact), wcont(n)%js1(num_contact), &
5360 & wcont(n)%je1(num_contact))
5361 allocate(wcont(n)%is2(num_contact), wcont(n)%ie2(num_contact), wcont(n)%js2(num_contact), &
5362 & wcont(n)%je2(num_contact))
5363 allocate(scont(n)%is1(num_contact), scont(n)%ie1(num_contact), scont(n)%js1(num_contact), &
5364 & scont(n)%je1(num_contact))
5365 allocate(scont(n)%is2(num_contact), scont(n)%ie2(num_contact), scont(n)%js2(num_contact), &
5366 & scont(n)%je2(num_contact))
5367 allocate(ncont(n)%is1(num_contact), ncont(n)%ie1(num_contact), ncont(n)%js1(num_contact), &
5368 & ncont(n)%je1(num_contact))
5369 allocate(ncont(n)%is2(num_contact), ncont(n)%ie2(num_contact), ncont(n)%js2(num_contact), &
5370 & ncont(n)%je2(num_contact))
5374 do n = 1, num_contact
5375 t1 = tile1(n) - tile_base
5376 t2 = tile2(n) - tile_base
5377 select case(align1(n))
5379 call fill_contact( econt(t1), tile2(n), istart1(n), iend1(n), jstart1(n), jend1(n), istart2(n), iend2(n), &
5380 jstart2(n), jend2(n), align1(n), align2(n), refine1(n), refine2(n))
5382 call fill_contact( wcont(t1), tile2(n), istart1(n), iend1(n), jstart1(n), jend1(n), istart2(n), iend2(n), &
5383 jstart2(n), jend2(n), align1(n), align2(n), refine1(n), refine2(n))
5385 call fill_contact( scont(t1), tile2(n), istart1(n), iend1(n), jstart1(n), jend1(n), istart2(n), iend2(n), &
5386 jstart2(n), jend2(n), align1(n), align2(n), refine1(n), refine2(n))
5388 call fill_contact( ncont(t1), tile2(n), istart1(n), iend1(n), jstart1(n), jend1(n), istart2(n), iend2(n), &
5389 jstart2(n), jend2(n), align1(n), align2(n), refine1(n), refine2(n))
5391 select case(align2(n))
5393 call fill_contact( econt(t2), tile1(n), istart2(n), iend2(n), jstart2(n), jend2(n), istart1(n), iend1(n), &
5394 jstart1(n), jend1(n), align2(n), align1(n), refine2(n), refine1(n))
5396 call fill_contact( wcont(t2), tile1(n), istart2(n), iend2(n), jstart2(n), jend2(n), istart1(n), iend1(n), &
5397 jstart1(n), jend1(n), align2(n), align1(n), refine2(n), refine1(n))
5399 call fill_contact( scont(t2), tile1(n), istart2(n), iend2(n), jstart2(n), jend2(n), istart1(n), iend1(n), &
5400 jstart1(n), jend1(n), align2(n), align1(n), refine2(n), refine1(n))
5402 call fill_contact( ncont(t2), tile1(n), istart2(n), iend2(n), jstart2(n), jend2(n), istart1(n), iend1(n), &
5403 jstart1(n), jend1(n), align2(n), align1(n), refine2(n), refine1(n))
5408 whalo = domain%whalo
5409 ehalo = domain%ehalo
5410 shalo = domain%shalo
5411 nhalo = domain%nhalo
5414 nlist =
size(domain%list(:))
5416 max_contact = 4*num_contact
5418 ntileme =
size(domain%x(:))
5419 refinesend = 1; refinerecv = 1
5425 do n = 1, domain%update_T%nsend
5426 pos = domain%update_T%send(n)%pe - mpp_root_pe()
5427 call add_update_overlap(overlapsend(pos), domain%update_T%send(n) )
5429 do n = 1, domain%update_T%nrecv
5430 pos = domain%update_T%recv(n)%pe - mpp_root_pe()
5431 call add_update_overlap(overlaprecv(pos), domain%update_T%recv(n) )
5434 call mpp_get_memory_domain(domain, ism, iem, jsm, jem)
5435 domain%update_T%xbegin = ism; domain%update_T%xend = iem
5436 domain%update_T%ybegin = jsm; domain%update_T%yend = jem
5437 domain%update_T%whalo = whalo; domain%update_T%ehalo = ehalo
5438 domain%update_T%shalo = shalo; domain%update_T%nhalo = nhalo
5441 tileme = domain%tile_id(tme) - tile_base
5442 rotatesend = zero; rotaterecv = zero
5446 do n = 1, econt(tileme)%ncontact
5448 tilerecv(count) = econt(tileme)%tile(n); tilesend(count) = econt(tileme)%tile(n)
5449 align1recv(count) = econt(tileme)%align1(n); align2recv(count) = econt(tileme)%align2(n)
5450 align1send(count) = econt(tileme)%align1(n); align2send(count) = econt(tileme)%align2(n)
5451 refinesend(count) = econt(tileme)%refine2(n); refinerecv(count) = econt(tileme)%refine1(n)
5452 is1recv(count) = econt(tileme)%is1(n) + 1; ie1recv(count) = is1recv(count) + ehalo - 1
5453 js1recv(count) = econt(tileme)%js1(n); je1recv(count) = econt(tileme)%je1(n)
5454 select case(econt(tileme)%align2(n))
5456 is2recv(count) = econt(tileme)%is2(n); ie2recv(count) = is2recv(count) + ehalo - 1
5457 js2recv(count) = econt(tileme)%js2(n); je2recv(count) = econt(tileme)%je2(n)
5458 ie1send(count) = econt(tileme)%is1(n); is1send(count) = ie1send(count) - whalo + 1
5459 js1send(count) = econt(tileme)%js1(n); je1send(count) = econt(tileme)%je1(n)
5460 ie2send(count) = econt(tileme)%is2(n) - 1; is2send(count) = ie2send(count) - whalo + 1
5461 js2send(count) = econt(tileme)%js2(n); je2send(count) = econt(tileme)%je2(n)
5463 rotaterecv(count) = ninety; rotatesend(count) = minus_ninety
5464 js2recv(count) = econt(tileme)%js2(n); je2recv(count) = js2recv(count) + ehalo -1
5465 is2recv(count) = econt(tileme)%is2(n); ie2recv(count) = econt(tileme)%ie2(n)
5466 ie1send(count) = econt(tileme)%is1(n); is1send(count) = ie1send(count) - shalo + 1
5467 js1send(count) = econt(tileme)%js1(n); je1send(count) = econt(tileme)%je1(n)
5468 is2send(count) = econt(tileme)%is2(n); ie2send(count) = econt(tileme)%ie2(n)
5469 je2send(count) = econt(tileme)%js2(n) - 1; js2send(count) = je2send(count) - shalo + 1
5473 do n = 1, scont(tileme)%ncontact
5475 tilerecv(count) = scont(tileme)%tile(n); tilesend(count) = scont(tileme)%tile(n)
5476 align1recv(count) = scont(tileme)%align1(n); align2recv(count) = scont(tileme)%align2(n);
5477 align1send(count) = scont(tileme)%align1(n); align2send(count) = scont(tileme)%align2(n);
5478 refinesend(count) = scont(tileme)%refine2(n); refinerecv(count) = scont(tileme)%refine1(n)
5479 is1recv(count) = scont(tileme)%is1(n); ie1recv(count) = scont(tileme)%ie1(n)
5480 je1recv(count) = scont(tileme)%js1(n) - 1; js1recv(count) = je1recv(count) - shalo + 1
5481 select case(scont(tileme)%align2(n))
5483 is2recv(count) = scont(tileme)%is2(n); ie2recv(count) = scont(tileme)%ie2(n)
5484 je2recv(count) = scont(tileme)%je2(n); js2recv(count) = je2recv(count) - shalo + 1
5485 is1send(count) = scont(tileme)%is1(n); ie1send(count) = scont(tileme)%ie1(n)
5486 js1send(count) = scont(tileme)%js1(n); je1send(count) = js1send(count) + nhalo -1
5487 is2send(count) = scont(tileme)%is2(n); ie2send(count) = scont(tileme)%ie2(n)
5488 js2send(count) = scont(tileme)%je2(n)+1; je2send(count) = js2send(count) + nhalo - 1
5490 rotaterecv(count) = minus_ninety; rotatesend(count) = ninety
5491 ie2recv(count) = scont(tileme)%ie2(n); is2recv(count) = ie2recv(count) - shalo + 1
5492 js2recv(count) = scont(tileme)%js2(n); je2recv(count) = scont(tileme)%je2(n)
5493 is1send(count) = scont(tileme)%is1(n); ie1send(count) = scont(tileme)%ie1(n)
5494 js1send(count) = scont(tileme)%js1(n); je1send(count) = js1send(count) + ehalo - 1
5495 is2send(count) = scont(tileme)%ie2(n)+1; ie2send(count) = is2send(count) + ehalo - 1
5496 js2send(count) = scont(tileme)%js2(n); je2send(count) = scont(tileme)%je2(n)
5500 do n = 1, wcont(tileme)%ncontact
5502 tilerecv(count) = wcont(tileme)%tile(n); tilesend(count) = wcont(tileme)%tile(n)
5503 align1recv(count) = wcont(tileme)%align1(n); align2recv(count) = wcont(tileme)%align2(n);
5504 align1send(count) = wcont(tileme)%align1(n); align2send(count) = wcont(tileme)%align2(n);
5505 refinesend(count) = wcont(tileme)%refine2(n); refinerecv(count) = wcont(tileme)%refine1(n)
5506 ie1recv(count) = wcont(tileme)%is1(n) - 1; is1recv(count) = ie1recv(count) - whalo + 1
5507 js1recv(count) = wcont(tileme)%js1(n); je1recv(count) = wcont(tileme)%je1(n)
5508 select case(wcont(tileme)%align2(n))
5510 ie2recv(count) = wcont(tileme)%ie2(n); is2recv(count) = ie2recv(count) - whalo + 1
5511 js2recv(count) = wcont(tileme)%js2(n); je2recv(count) = wcont(tileme)%je2(n)
5512 is1send(count) = wcont(tileme)%is1(n); ie1send(count) = is1send(count) + ehalo - 1
5513 js1send(count) = wcont(tileme)%js1(n); je1send(count) = wcont(tileme)%je1(n)
5514 is2send(count) = wcont(tileme)%ie2(n)+1; ie2send(count) = is2send(count) + ehalo - 1
5515 js2send(count) = wcont(tileme)%js2(n); je2send(count) = wcont(tileme)%je2(n)
5517 rotaterecv(count) = ninety; rotatesend(count) = minus_ninety
5518 je2recv(count) = wcont(tileme)%je2(n); js2recv(count) = je2recv(count) - whalo + 1
5519 is2recv(count) = wcont(tileme)%is2(n); ie2recv(count) = wcont(tileme)%ie2(n)
5520 is1send(count) = wcont(tileme)%is1(n); ie1send(count) = is1send(count) + nhalo - 1
5521 js1send(count) = wcont(tileme)%js1(n); je1send(count) = wcont(tileme)%je1(n)
5522 js2send(count) = wcont(tileme)%je2(n)+1; je2send(count) = js2send(count) + nhalo - 1
5523 is2send(count) = wcont(tileme)%is2(n); ie2send(count) = wcont(tileme)%ie2(n)
5527 do n = 1, ncont(tileme)%ncontact
5529 tilerecv(count) = ncont(tileme)%tile(n); tilesend(count) = ncont(tileme)%tile(n)
5530 align1recv(count) = ncont(tileme)%align1(n); align2recv(count) = ncont(tileme)%align2(n);
5531 align1send(count) = ncont(tileme)%align1(n); align2send(count) = ncont(tileme)%align2(n);
5532 refinesend(count) = ncont(tileme)%refine2(n); refinerecv(count) = ncont(tileme)%refine1(n)
5533 is1recv(count) = ncont(tileme)%is1(n); ie1recv(count) = ncont(tileme)%ie1(n)
5534 js1recv(count) = ncont(tileme)%je1(n)+1; je1recv(count) = js1recv(count) + nhalo - 1
5535 select case(ncont(tileme)%align2(n))
5537 is2recv(count) = ncont(tileme)%is2(n); ie2recv(count) = ncont(tileme)%ie2(n)
5538 js2recv(count) = ncont(tileme)%js2(n); je2recv(count) = js2recv(count) + nhalo - 1
5539 is1send(count) = ncont(tileme)%is1(n); ie1send(count) = ncont(tileme)%ie1(n)
5540 je1send(count) = ncont(tileme)%je1(n); js1send(count) = je1send(count) - shalo + 1
5541 is2send(count) = ncont(tileme)%is2(n); ie2send(count) = ncont(tileme)%ie2(n)
5542 je2send(count) = ncont(tileme)%js2(n)-1; js2send(count) = je2send(count) - shalo + 1
5544 rotaterecv(count) = minus_ninety; rotatesend(count) = ninety
5545 is2recv(count) = ncont(tileme)%ie2(n); ie2recv(count) = is2recv(count) + nhalo - 1
5546 js2recv(count) = ncont(tileme)%js2(n); je2recv(count) = ncont(tileme)%je2(n)
5547 is1send(count) = ncont(tileme)%is1(n); ie1send(count) = ncont(tileme)%ie1(n)
5548 je1send(count) = ncont(tileme)%je1(n); js1send(count) = je1send(count) - whalo + 1
5549 ie2send(count) = ncont(tileme)%is2(n)-1; is2send(count) = ie2send(count) - whalo + 1
5550 js2send(count) = ncont(tileme)%js2(n); je2send(count) = ncont(tileme)%je2(n)
5559 if(.NOT. domain%rotated_ninety)
then
5560 call fill_corner_contact(econt, scont, wcont, ncont, isglist, ieglist, jsglist, jeglist, numr, nums, &
5561 tilerecv, tilesend, is1recv, ie1recv, js1recv, je1recv, is2recv, ie2recv, &
5562 js2recv, je2recv, is1send, ie1send, js1send, je1send, is2send, ie2send, &
5563 js2send, je2send, align1recv, align2recv, align1send, align2send, &
5564 whalo, ehalo, shalo, nhalo, tileme )
5567 isc = domain%x(tme)%compute%begin; iec = domain%x(tme)%compute%end
5568 jsc = domain%y(tme)%compute%begin; jec = domain%y(tme)%compute%end
5572 do list = 0, nlist-1
5573 m = mod( domain%pos+list, nlist )
5574 ntilenbr =
size(domain%list(m)%x(:))
5575 do tnbr = 1, ntilenbr
5576 if( domain%list(m)%tile_id(tnbr) .NE. tilesend(n) ) cycle
5577 isc1 = max(isc, is1send(n)); iec1 = min(iec, ie1send(n))
5578 jsc1 = max(jsc, js1send(n)); jec1 = min(jec, je1send(n))
5579 if( isc1 > iec1 .OR. jsc1 > jec1 ) cycle
5585 if( align2send(n) .NE. east ) cycle
5586 isd = domain%list(m)%x(tnbr)%compute%end+1; ied = domain%list(m)%x(tnbr)%compute%end+ehalo
5587 jsd = domain%list(m)%y(tnbr)%compute%begin; jed = domain%list(m)%y(tnbr)%compute%end
5589 isd = domain%list(m)%x(tnbr)%compute%end+1; ied = domain%list(m)%x(tnbr)%compute%end+ehalo
5590 jsd = domain%list(m)%y(tnbr)%compute%begin-shalo; jed = domain%list(m)%y(tnbr)%compute%begin-1
5592 if( align2send(n) .NE. south ) cycle
5593 isd = domain%list(m)%x(tnbr)%compute%begin; ied = domain%list(m)%x(tnbr)%compute%end
5594 jsd = domain%list(m)%y(tnbr)%compute%begin-shalo; jed = domain%list(m)%y(tnbr)%compute%begin-1
5596 isd = domain%list(m)%x(tnbr)%compute%begin-whalo; ied = domain%list(m)%x(tnbr)%compute%begin-1
5597 jsd = domain%list(m)%y(tnbr)%compute%begin-shalo; jed = domain%list(m)%y(tnbr)%compute%begin-1
5599 if( align2send(n) .NE. west ) cycle
5600 isd = domain%list(m)%x(tnbr)%compute%begin-whalo; ied = domain%list(m)%x(tnbr)%compute%begin-1
5601 jsd = domain%list(m)%y(tnbr)%compute%begin; jed = domain%list(m)%y(tnbr)%compute%end
5603 isd = domain%list(m)%x(tnbr)%compute%begin-whalo; ied = domain%list(m)%x(tnbr)%compute%begin-1
5604 jsd = domain%list(m)%y(tnbr)%compute%end+1; jed = domain%list(m)%y(tnbr)%compute%end+nhalo
5606 if( align2send(n) .NE. north ) cycle
5607 isd = domain%list(m)%x(tnbr)%compute%begin; ied = domain%list(m)%x(tnbr)%compute%end
5608 jsd = domain%list(m)%y(tnbr)%compute%end+1; jed = domain%list(m)%y(tnbr)%compute%end+nhalo
5610 isd = domain%list(m)%x(tnbr)%compute%end+1; ied = domain%list(m)%x(tnbr)%compute%end+ehalo
5611 jsd = domain%list(m)%y(tnbr)%compute%end+1; jed = domain%list(m)%y(tnbr)%compute%end+nhalo
5613 isd = max(isd, is2send(n)); ied = min(ied, ie2send(n))
5614 jsd = max(jsd, js2send(n)); jed = min(jed, je2send(n))
5615 if( isd > ied .OR. jsd > jed ) cycle
5619 select case ( align2send(n) )
5621 ioff = isd - is2send(n)
5622 joff = jsd - js2send(n)
5623 case ( south, north )
5624 ioff = isd - is2send(n)
5625 joff = jsd - js2send(n)
5629 select case ( rotatesend(n) )
5631 isc2 = is1send(n) + ioff; iec2 = isc2 + nxd - 1
5632 jsc2 = js1send(n) + joff; jec2 = jsc2 + nyd - 1
5634 iec2 = ie1send(n) - joff; isc2 = iec2 - nyd + 1
5635 jsc2 = js1send(n) + ioff; jec2 = jsc2 + nxd - 1
5636 case ( minus_ninety )
5637 isc2 = is1send(n) + joff; iec2 = isc2 + nyd - 1
5638 jec2 = je1send(n) - ioff; jsc2 = jec2 - nxd + 1
5640 is = max(isc1,isc2); ie = min(iec1,iec2)
5641 js = max(jsc1,jsc2); je = min(jec1,jec2)
5642 if(ie.GE.is .AND. je.GE.js )
then
5643 if(.not.
associated(overlapsend(m)%tileMe))
call allocate_update_overlap(overlapsend(m), &
5645 call insert_overlap_type(overlapsend(m), domain%list(m)%pe, tme, tnbr, &
5646 is, ie, js, je, dir, rotatesend(n), .true. )
5655 do list = 0, nlist-1
5656 m = mod( domain%pos+nlist-list, nlist )
5657 ntilenbr =
size(domain%list(m)%x(:))
5658 do tnbr = 1, ntilenbr
5659 if( domain%list(m)%tile_id(tnbr) .NE. tilerecv(n) ) cycle
5660 isc = domain%list(m)%x(tnbr)%compute%begin; iec = domain%list(m)%x(tnbr)%compute%end
5661 jsc = domain%list(m)%y(tnbr)%compute%begin; jec = domain%list(m)%y(tnbr)%compute%end
5662 isc = max(isc, is2recv(n)); iec = min(iec, ie2recv(n))
5663 jsc = max(jsc, js2recv(n)); jec = min(jec, je2recv(n))
5664 if( isc > iec .OR. jsc > jec ) cycle
5667 nxc = iec - isc + 1; nyc = jec - jsc + 1
5668 select case ( align2recv(n) )
5670 if(align2recv(n) == west)
then
5671 ioff = isc - is2recv(n)
5673 ioff = ie2recv(n) - iec
5675 joff = jsc - js2recv(n)
5676 case ( north, south )
5677 ioff = isc - is2recv(n)
5678 if(align2recv(n) == south)
then
5679 joff = jsc - js2recv(n)
5681 joff = je2recv(n) - jec
5686 select case ( rotaterecv(n) )
5688 isd1 = is1recv(n) + ioff; ied1 = isd1 + nxc - 1
5689 jsd1 = js1recv(n) + joff; jed1 = jsd1 + nyc - 1
5690 if( align1recv(n) == west )
then
5691 ied1 = ie1recv(n)-ioff; isd1 = ied1 - nxc + 1
5693 if( align1recv(n) == south )
then
5694 jed1 = je1recv(n)-joff; jsd1 = jed1 - nyc + 1
5697 if( align1recv(n) == west )
then
5698 ied1 = ie1recv(n)-joff; isd1 = ied1 - nyc + 1
5700 isd1 = is1recv(n)+joff; ied1 = isd1 + nyc - 1
5702 jed1 = je1recv(n) - ioff; jsd1 = jed1 - nxc + 1
5703 case ( minus_ninety )
5704 ied1 = ie1recv(n) - joff; isd1 = ied1 - nyc + 1
5705 if( align1recv(n) == south )
then
5706 jed1 = je1recv(n)-ioff; jsd1 = jed1 - nxc + 1
5708 jsd1 = js1recv(n)+ioff; jed1 = jsd1 + nxc - 1
5716 if( align1recv(n) .NE. east ) cycle
5717 isd2 = domain%x(tme)%compute%end+1; ied2 = domain%x(tme)%domain_data%end
5718 jsd2 = domain%y(tme)%compute%begin; jed2 = domain%y(tme)%compute%end
5720 isd2 = domain%x(tme)%compute%end+1; ied2 = domain%x(tme)%domain_data%end
5721 jsd2 = domain%y(tme)%domain_data%begin; jed2 = domain%y(tme)%compute%begin-1
5723 if( align1recv(n) .NE. south ) cycle
5724 isd2 = domain%x(tme)%compute%begin; ied2 = domain%x(tme)%compute%end
5725 jsd2 = domain%y(tme)%domain_data%begin; jed2 = domain%y(tme)%compute%begin-1
5727 isd2 = domain%x(tme)%domain_data%begin; ied2 = domain%x(tme)%compute%begin-1
5728 jsd2 = domain%y(tme)%domain_data%begin; jed2 = domain%y(tme)%compute%begin-1
5730 if( align1recv(n) .NE. west ) cycle
5731 isd2 = domain%x(tme)%domain_data%begin; ied2 = domain%x(tme)%compute%begin-1
5732 jsd2 = domain%y(tme)%compute%begin; jed2 = domain%y(tme)%compute%end
5734 isd2 = domain%x(tme)%domain_data%begin; ied2 = domain%x(tme)%compute%begin-1
5735 jsd2 = domain%y(tme)%compute%end+1; jed2 = domain%y(tme)%domain_data%end
5737 if( align1recv(n) .NE. north ) cycle
5738 isd2 = domain%x(tme)%compute%begin; ied2 = domain%x(tme)%compute%end
5739 jsd2 = domain%y(tme)%compute%end+1; jed2 = domain%y(tme)%domain_data%end
5741 isd2 = domain%x(tme)%compute%end+1; ied2 = domain%x(tme)%domain_data%end
5742 jsd2 = domain%y(tme)%compute%end+1; jed2 = domain%y(tme)%domain_data%end
5744 is = max(isd1,isd2); ie = min(ied1,ied2)
5745 js = max(jsd1,jsd2); je = min(jed1,jed2)
5746 if(ie.GE.is .AND. je.GE.js )
then
5747 if(.not.
associated(overlaprecv(m)%tileMe))
call allocate_update_overlap(overlaprecv(m), &
5749 call insert_overlap_type(overlaprecv(m), domain%list(m)%pe, tme, tnbr, &
5750 is, ie, js, je, dir, rotaterecv(n), .true.)
5751 count = overlaprecv(m)%count
5760 nsend = 0; nsend2 = 0
5761 do list = 0, nlist-1
5762 m = mod( domain%pos+list, nlist )
5763 if(overlapsend(m)%count>0) nsend = nsend + 1
5766 if(debug_message_passing)
then
5769 do list = 0, nlist-1
5770 m = mod( domain%pos+list, nlist )
5771 if(overlapsend(m)%count==0) cycle
5772 write(iunit, *)
"********to_pe = " ,overlapsend(m)%pe,
" count = ",overlapsend(m)%count
5773 do n = 1, overlapsend(m)%count
5774 write(iunit, *) overlapsend(m)%is(n), overlapsend(m)%ie(n), overlapsend(m)%js(n), overlapsend(m)%je(n), &
5775 overlapsend(m)%dir(n), overlapsend(m)%rotation(n)
5778 if(nsend >0)
flush(iunit)
5781 dirlist(1) = 1; dirlist(2) = 3; dirlist(3) = 5; dirlist(4) = 7
5782 dirlist(5) = 2; dirlist(6) = 4; dirlist(7) = 6; dirlist(8) = 8
5786 if(
associated(domain%update_T%send))
then
5787 do m = 1, domain%update_T%nsend
5788 call deallocate_overlap_type(domain%update_T%send(m))
5790 deallocate(domain%update_T%send)
5792 domain%update_T%nsend = nsend
5793 allocate(domain%update_T%send(nsend))
5794 do list = 0, nlist-1
5795 m = mod( domain%pos+list, nlist )
5796 ntilenbr =
size(domain%list(m)%x(:))
5798 if(overlapsend(m)%count > 0)
then
5800 if(nsend2>nsend)
call mpp_error(fatal, &
5801 "mpp_domains_define.inc(define_contact_point): nsend2 is greater than nsend")
5802 call allocate_update_overlap(domain%update_T%send(nsend2), overlapsend(m)%count)
5804 do tnbr = 1, ntilenbr
5806 if(domain%list(m)%pe == domain%pe)
then
5808 if(tme > ntileme) tme = tme - ntileme
5813 do l = 1, overlapsend(m)%count
5814 if(overlapsend(m)%tileMe(l) .NE. tme) cycle
5815 if(overlapsend(m)%tileNbr(l) .NE. tnbr) cycle
5816 if(overlapsend(m)%dir(l) .NE. dirlist(n) ) cycle
5817 call insert_overlap_type(domain%update_T%send(nsend2), overlapsend(m)%pe, &
5818 overlapsend(m)%tileMe(l), overlapsend(m)%tileNbr(l), overlapsend(m)%is(l), &
5819 overlapsend(m)%ie(l), overlapsend(m)%js(l), overlapsend(m)%je(l), overlapsend(m)%dir(l),&
5820 overlapsend(m)%rotation(l), overlapsend(m)%from_contact(l) )
5829 if(nsend2 .NE. nsend)
call mpp_error(fatal, &
5830 "mpp_domains_define.inc(define_contact_point): nsend2 does not equal to nsend")
5832 nrecv = 0; nrecv2 = 0
5833 do list = 0, nlist-1
5834 m = mod( domain%pos+list, nlist )
5835 if(overlaprecv(m)%count>0) nrecv = nrecv + 1
5838 if(debug_message_passing)
then
5839 do list = 0, nlist-1
5840 m = mod( domain%pos+list, nlist )
5841 if(overlaprecv(m)%count==0) cycle
5842 write(iunit, *)
"********from_pe = " ,overlaprecv(m)%pe,
" count = ",overlaprecv(m)%count
5843 do n = 1, overlaprecv(m)%count
5844 write(iunit, *) overlaprecv(m)%is(n), overlaprecv(m)%ie(n), overlaprecv(m)%js(n), overlaprecv(m)%je(n), &
5845 overlaprecv(m)%dir(n), overlaprecv(m)%rotation(n)
5848 if(nrecv >0)
flush(iunit)
5852 if(
associated(domain%update_T%recv))
then
5853 do m = 1, domain%update_T%nrecv
5854 call deallocate_overlap_type(domain%update_T%recv(m))
5856 deallocate(domain%update_T%recv)
5858 domain%update_T%nrecv = nrecv
5859 allocate(domain%update_T%recv(nrecv))
5861 do list = 0, nlist-1
5862 m = mod( domain%pos+nlist-list, nlist )
5863 ntilenbr =
size(domain%list(m)%x(:))
5864 if(overlaprecv(m)%count > 0)
then
5866 if(nrecv2>nrecv)
call mpp_error(fatal, &
5867 "mpp_domains_define.inc(define_contact_point): nrecv2 is greater than nrecv")
5868 call allocate_update_overlap(domain%update_T%recv(nrecv2), overlaprecv(m)%count)
5872 if(domain%list(m)%pe == domain%pe)
then
5874 if(tnbr>ntilenbr) tnbr = tnbr - ntilenbr
5879 do l = 1, overlaprecv(m)%count
5880 if(overlaprecv(m)%tileMe(l) .NE. tme) cycle
5881 if(overlaprecv(m)%tileNbr(l) .NE. tnbr) cycle
5882 if(overlaprecv(m)%dir(l) .NE. dirlist(n) ) cycle
5883 call insert_overlap_type(domain%update_T%recv(nrecv2), overlaprecv(m)%pe, &
5884 overlaprecv(m)%tileMe(l), overlaprecv(m)%tileNbr(l), overlaprecv(m)%is(l), &
5885 overlaprecv(m)%ie(l), overlaprecv(m)%js(l), overlaprecv(m)%je(l), overlaprecv(m)%dir(l),&
5886 overlaprecv(m)%rotation(l), overlaprecv(m)%from_contact(l))
5887 count = domain%update_T%recv(nrecv2)%count
5896 if(nrecv2 .NE. nrecv)
call mpp_error(fatal, &
5897 "mpp_domains_define.inc(define_contact_point): nrecv2 does not equal to nrecv")
5900 call deallocate_overlap_type(overlapsend(m))
5901 call deallocate_overlap_type(overlaprecv(m))
5905 deallocate(econt(n)%tile, wcont(n)%tile, scont(n)%tile, ncont(n)%tile )
5906 deallocate(econt(n)%align1, wcont(n)%align1, scont(n)%align1, ncont(n)%align1)
5907 deallocate(econt(n)%align2, wcont(n)%align2, scont(n)%align2, ncont(n)%align2)
5908 deallocate(econt(n)%refine1, wcont(n)%refine1, scont(n)%refine1, ncont(n)%refine1)
5909 deallocate(econt(n)%refine2, wcont(n)%refine2, scont(n)%refine2, ncont(n)%refine2)
5910 deallocate(econt(n)%is1, econt(n)%ie1, econt(n)%js1, econt(n)%je1 )
5911 deallocate(econt(n)%is2, econt(n)%ie2, econt(n)%js2, econt(n)%je2 )
5912 deallocate(wcont(n)%is1, wcont(n)%ie1, wcont(n)%js1, wcont(n)%je1 )
5913 deallocate(wcont(n)%is2, wcont(n)%ie2, wcont(n)%js2, wcont(n)%je2 )
5914 deallocate(scont(n)%is1, scont(n)%ie1, scont(n)%js1, scont(n)%je1 )
5915 deallocate(scont(n)%is2, scont(n)%ie2, scont(n)%js2, scont(n)%je2 )
5916 deallocate(ncont(n)%is1, ncont(n)%ie1, ncont(n)%js1, ncont(n)%je1 )
5917 deallocate(ncont(n)%is2, ncont(n)%ie2, ncont(n)%js2, ncont(n)%je2 )
5920 domain%initialized = .true.
5927 subroutine fill_contact(Contact, tile, is1, ie1, js1, je1, is2, ie2, js2, je2, align1, align2, refine1, refine2 )
5928 type(contact_type),
intent(inout) :: Contact
5929 integer,
intent(in) :: tile
5930 integer,
intent(in) :: is1, ie1, js1, je1
5931 integer,
intent(in) :: is2, ie2, js2, je2
5932 integer,
intent(in) :: align1, align2
5933 real,
intent(in) :: refine1, refine2
5936 do pos = 1, contact%ncontact
5939 if( js1 < contact%js1(pos) )
exit
5941 if( is1 < contact%is1(pos) )
exit
5945 contact%ncontact = contact%ncontact + 1
5946 do n = contact%ncontact, pos+1, -1
5947 contact%tile(n) = contact%tile(n-1)
5948 contact%align1(n) = contact%align1(n-1)
5949 contact%align2(n) = contact%align2(n-1)
5950 contact%is1(n) = contact%is1(n-1); contact%ie1(n) = contact%ie1(n-1)
5951 contact%js1(n) = contact%js1(n-1); contact%je1(n) = contact%je1(n-1)
5952 contact%is2(n) = contact%is2(n-1); contact%ie2(n) = contact%ie2(n-1)
5953 contact%js2(n) = contact%js2(n-1); contact%je2(n) = contact%je2(n-1)
5956 contact%tile(pos) = tile
5957 contact%align1(pos) = align1
5958 contact%align2(pos) = align2
5959 contact%refine1(pos) = refine1
5960 contact%refine2(pos) = refine2
5961 contact%is1(pos) = is1; contact%ie1(pos) = ie1
5962 contact%js1(pos) = js1; contact%je1(pos) = je1
5963 contact%is2(pos) = is2; contact%ie2(pos) = ie2
5964 contact%js2(pos) = js2; contact%je2(pos) = je2
5971 type(domain2d),
intent(inout) :: domain
5972 integer,
intent(in) :: position
5974 integer :: ishift, jshift, nlist, list, m, n
5975 integer :: ntileMe, tMe, dir, count, pos, nsend, nrecv
5976 integer :: isoff1, ieoff1, jsoff1, jeoff1
5977 type(overlap_type),
pointer :: ptrIn => null()
5978 type(overlapspec),
pointer :: update_in => null()
5979 type(overlapspec),
pointer :: update_out => null()
5980 type(overlap_type) :: overlapList(0:size(domain%list(:))-1)
5981 type(overlap_type) :: overlap
5984 update_in => domain%update_T
5985 select case(position)
5987 update_out => domain%update_C
5989 update_out => domain%update_E
5991 update_out => domain%update_N
5993 call mpp_error(fatal,
"mpp_domains_define.inc(set_contact_point): the position should be CORNER, EAST or NORTH")
5996 update_out%xbegin = update_in%xbegin; update_out%xend = update_in%xend + ishift
5997 update_out%ybegin = update_in%ybegin; update_out%yend = update_in%yend + jshift
5998 update_out%whalo = update_in%whalo; update_out%ehalo = update_in%ehalo
5999 update_out%shalo = update_in%shalo; update_out%nhalo = update_in%nhalo
6001 nlist =
size(domain%list(:))
6002 ntileme =
size(domain%x(:))
6003 call allocate_update_overlap(overlap, maxoverlap)
6005 call init_overlap_type(overlaplist(m))
6009 nsend = update_out%nsend
6011 pos = update_out%send(m)%pe - mpp_root_pe()
6012 call add_update_overlap(overlaplist(pos), update_out%send(m))
6013 call deallocate_overlap_type(update_out%send(m))
6015 if(
ASSOCIATED(update_out%send) )
deallocate(update_out%send)
6018 nsend = update_in%nsend
6020 ptrin => update_in%send(m)
6021 pos = ptrin%pe - mpp_root_pe()
6022 do n = 1, ptrin%count
6025 if(ptrin%from_contact(n))
then
6028 select case(ptrin%rotation(n))
6030 isoff1 = ishift; ieoff1 = ishift; jsoff1 = 0; jeoff1 = jshift
6032 isoff1 = 0; ieoff1 = jshift; jsoff1 = ishift; jeoff1 = ishift
6035 select case(ptrin%rotation(n))
6037 isoff1 = ishift; ieoff1 = ishift; jsoff1 = 0; jeoff1 = 0
6039 isoff1 = jshift; ieoff1 = jshift; jsoff1 = ishift; jeoff1 = ishift
6041 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = 0
6044 select case(ptrin%rotation(n))
6046 isoff1 = 0; ieoff1 = ishift; jsoff1 = 0; jeoff1 = 0
6048 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = ishift
6051 select case(ptrin%rotation(n))
6053 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = 0
6055 isoff1 = jshift; ieoff1 = jshift; jsoff1 = 0; jeoff1 = 0
6057 isoff1 = 0; ieoff1 = 0; jsoff1 = ishift; jeoff1 = ishift
6060 select case(ptrin%rotation(n))
6062 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = jshift
6064 isoff1 = 0; ieoff1 = jshift; jsoff1 = 0; jeoff1 = 0
6067 select case(ptrin%rotation(n))
6069 isoff1 = 0; ieoff1 = 0; jsoff1 = jshift; jeoff1 = jshift
6071 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = 0
6073 isoff1 = jshift; ieoff1 = jshift; jsoff1 = ishift; jeoff1 = ishift
6076 select case(ptrin%rotation(n))
6078 isoff1 = 0; ieoff1 = ishift; jsoff1 = jshift; jeoff1 = jshift
6080 isoff1 = jshift; ieoff1 = jshift; jsoff1 = 0; jeoff1 = ishift
6083 select case(ptrin%rotation(n))
6085 isoff1 = ishift; ieoff1 = ishift; jsoff1 = jshift; jeoff1 = jshift
6087 isoff1 = 0; ieoff1 = 0; jsoff1 = ishift; jeoff1 = ishift
6089 isoff1 = jshift; ieoff1 = jshift; jsoff1 = 0; jeoff1 = 0
6092 call insert_overlap_type(overlap, ptrin%pe, ptrin%tileMe(n), ptrin%tileNbr(n), &
6093 ptrin%is(n) + isoff1, ptrin%ie(n) + ieoff1, ptrin%js(n) + jsoff1, &
6094 ptrin%je(n) + jeoff1, ptrin%dir(n), ptrin%rotation(n), ptrin%from_contact(n))
6097 if(overlap%count > 0)
then
6098 call add_update_overlap(overlaplist(pos), overlap)
6099 call init_overlap_type(overlap)
6104 do list = 0, nlist-1
6105 m = mod( domain%pos+list, nlist )
6106 if(overlaplist(m)%count>0) nsend = nsend+1
6109 update_out%nsend = nsend
6111 if (
associated(update_out%send))
deallocate(update_out%send)
6112 allocate(update_out%send(nsend))
6114 do list = 0, nlist-1
6115 m = mod( domain%pos+list, nlist )
6116 if(overlaplist(m)%count>0)
then
6118 if(pos>nsend)
call mpp_error(fatal, &
6119 "mpp_domains_define.inc(set_contact_point): pos should be no larger than nsend")
6120 call add_update_overlap(update_out%send(pos), overlaplist(m))
6121 call deallocate_overlap_type(overlaplist(m))
6124 if(pos .NE. nsend)
call mpp_error(fatal, &
6125 "mpp_domains_define.inc(set_contact_point): pos should equal to nsend")
6131 nrecv = update_out%nrecv
6133 pos = update_out%recv(m)%pe - mpp_root_pe()
6134 call add_update_overlap(overlaplist(pos), update_out%recv(m))
6135 call deallocate_overlap_type(update_out%recv(m))
6137 if(
ASSOCIATED(update_out%recv) )
deallocate(update_out%recv)
6140 nrecv = update_in%nrecv
6142 ptrin => update_in%recv(m)
6143 pos = ptrin%pe - mpp_root_pe()
6144 do n = 1, ptrin%count
6147 if(ptrin%from_contact(n))
then
6150 isoff1 = ishift; ieoff1 = ishift; jsoff1 = 0; jeoff1 = jshift
6152 isoff1 = ishift; ieoff1 = ishift; jsoff1 = 0; jeoff1 = 0
6154 isoff1 = 0; ieoff1 = ishift; jsoff1 = 0; jeoff1 = 0
6156 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = 0
6158 isoff1 = 0; ieoff1 = 0; jsoff1 = 0; jeoff1 = jshift
6160 isoff1 = 0; ieoff1 = 0; jsoff1 = jshift; jeoff1 = jshift
6162 isoff1 = 0; ieoff1 = ishift; jsoff1 = jshift; jeoff1 = jshift
6164 isoff1 = ishift; ieoff1 = ishift; jsoff1 = jshift; jeoff1 = jshift
6166 call insert_overlap_type(overlap, ptrin%pe, ptrin%tileMe(n), ptrin%tileNbr(n), &
6167 ptrin%is(n) + isoff1, ptrin%ie(n) + ieoff1, ptrin%js(n) + jsoff1, &
6168 ptrin%je(n) + jeoff1, ptrin%dir(n), ptrin%rotation(n), ptrin%from_contact(n))
6169 count = overlap%count
6172 if(overlap%count > 0)
then
6173 call add_update_overlap(overlaplist(pos), overlap)
6174 call init_overlap_type(overlap)
6176 do tme = 1,
size(domain%x(:))
6177 do n = 1, overlap%count
6178 if(overlap%tileMe(n) == tme)
then
6179 if(overlap%dir(n) == 1 ) domain%x(tme)%loffset = 0
6180 if(overlap%dir(n) == 7 ) domain%y(tme)%loffset = 0
6187 do list = 0, nlist-1
6188 m = mod( domain%pos+nlist-list, nlist )
6189 if(overlaplist(m)%count>0) nrecv = nrecv+1
6192 update_out%nrecv = nrecv
6194 if (
associated(update_out%recv))
deallocate(update_out%recv)
6195 allocate(update_out%recv(nrecv))
6197 do list = 0, nlist-1
6198 m = mod( domain%pos+nlist-list, nlist )
6199 if(overlaplist(m)%count>0)
then
6201 if(pos>nrecv)
call mpp_error(fatal, &
6202 "mpp_domains_define.inc(set_contact_point): pos should be no larger than nrecv")
6203 call add_update_overlap(update_out%recv(pos), overlaplist(m))
6204 call deallocate_overlap_type(overlaplist(m))
6207 if(pos .NE. nrecv)
call mpp_error(fatal, &
6208 "mpp_domains_define.inc(set_contact_point): pos should equal to nrecv")
6211 call deallocate_overlap_type(overlap)
6219 type(domain2d),
intent(in) :: domain
6220 integer,
intent(in) :: position
6221 integer :: nlist, m, n
6222 integer,
parameter :: MAXCOUNT = 100
6223 integer :: is, ie, js, je
6224 integer :: nsend, nrecv, pos, maxsize, rotation
6225 type(overlap_type) :: overlap
6226 type(overlapspec),
pointer :: update => null()
6227 type(overlapspec),
pointer :: check => null()
6229 select case(position)
6231 update => domain%update_C
6232 check => domain%check_C
6234 update => domain%update_E
6235 check => domain%check_E
6237 update => domain%update_N
6238 check => domain%check_N
6240 call mpp_error(fatal,
"mpp_domains_define.inc(set_check_overlap): position should be CORNER, EAST or NORTH")
6243 check%xbegin = update%xbegin; check%xend = update%xend
6244 check%ybegin = update%ybegin; check%yend = update%yend
6247 if( .NOT. domain%symmetry )
return
6251 do m = 1, update%nsend
6252 do n = 1, update%send(m)%count
6253 if( update%send(m)%rotation(n) == one_hundred_eighty ) cycle
6254 if( ( (position == east .OR. position == corner) .AND. update%send(m)%dir(n) == 1 ) .OR. &
6255 ( (position == north .OR. position == corner) .AND. update%send(m)%dir(n) == 7 ) )
then
6256 maxsize = max(maxsize, update%send(m)%count)
6264 if (
associated(check%send))
deallocate(check%send)
6265 allocate(check%send(nsend))
6266 call allocate_check_overlap(overlap, maxsize)
6270 nlist =
size(domain%list(:))
6273 do m = 1, update%nsend
6274 do n = 1, update%send(m)%count
6275 if( update%send(m)%rotation(n) == one_hundred_eighty ) cycle
6277 if( (position == east .OR. position == corner) .AND. update%send(m)%dir(n) == 1 )
then
6278 rotation = update%send(m)%rotation(n)
6279 select case( rotation )
6281 is = update%send(m)%is(n) - 1
6283 js = update%send(m)%js(n)
6284 je = update%send(m)%je(n)
6286 is = update%send(m)%is(n)
6287 ie = update%send(m)%ie(n)
6288 js = update%send(m)%js(n) - 1
6291 call insert_check_overlap(overlap, update%send(m)%pe, &
6292 update%send(m)%tileMe(n), 1, rotation, is, ie, js, je)
6296 if( (position == north .OR. position == corner) .AND. update%send(m)%dir(n) == 7 )
then
6297 rotation = update%send(m)%rotation(n)
6298 select case( rotation )
6300 is = update%send(m)%is(n)
6301 ie = update%send(m)%ie(n)
6302 js = update%send(m)%js(n) - 1
6304 case( minus_ninety )
6305 is = update%send(m)%is(n) - 1
6307 js = update%send(m)%js(n)
6308 je = update%send(m)%je(n)
6310 call insert_check_overlap(overlap, update%send(m)%pe, &
6311 update%send(m)%tileMe(n), 4, rotation, is, ie, js, je)
6314 if(overlap%count>0)
then
6316 if(pos>nsend)
call mpp_error(fatal,
"mpp_domains_define.inc(set_check_overlap): pos is greater than nsend")
6318 call init_overlap_type(overlap)
6322 if(pos .NE. nsend)
call mpp_error(fatal,
"mpp_domains_define.inc(set_check_overlap): pos is greater than nsend")
6326 do m = 1, update%nrecv
6327 do n = 1, update%recv(m)%count
6328 if( update%recv(m)%rotation(n) == one_hundred_eighty ) cycle
6329 if( ( (position == east .OR. position == corner) .AND. update%recv(m)%dir(n) == 1 ) .OR. &
6330 ( (position == north .OR. position == corner) .AND. update%recv(m)%dir(n) == 7 ) )
then
6331 maxsize = max(maxsize, update%recv(m)%count)
6338 if(nsend>0)
call deallocate_overlap_type(overlap)
6341 if (
associated(check%recv))
deallocate(check%recv)
6342 allocate(check%recv(nrecv))
6343 call allocate_check_overlap(overlap, maxsize)
6347 do m = 1, update%nrecv
6348 do n = 1, update%recv(m)%count
6349 if( update%recv(m)%rotation(n) == one_hundred_eighty ) cycle
6350 if( (position == east .OR. position == corner) .AND. update%recv(m)%dir(n) == 1 )
then
6351 is = update%recv(m)%is(n) - 1
6353 js = update%recv(m)%js(n)
6354 je = update%recv(m)%je(n)
6355 call insert_check_overlap(overlap, update%recv(m)%pe, &
6356 update%recv(m)%tileMe(n), 1, update%recv(m)%rotation(n), is, ie, js, je)
6358 if( (position == north .OR. position == corner) .AND. update%recv(m)%dir(n) == 7 )
then
6359 is = update%recv(m)%is(n)
6360 ie = update%recv(m)%ie(n)
6361 js = update%recv(m)%js(n) - 1
6363 call insert_check_overlap(overlap, update%recv(m)%pe, &
6364 update%recv(m)%tileMe(n), 3, update%recv(m)%rotation(n), is, ie, js, je)
6367 if(overlap%count>0)
then
6369 if(pos>nrecv)
call mpp_error(fatal,
"mpp_domains_define.inc(set_check_overlap): pos is greater than nrecv")
6371 call init_overlap_type(overlap)
6375 if(pos .NE. nrecv)
call mpp_error(fatal,
"mpp_domains_define.inc(set_check_overlap): pos is greater than nrecv")
6376 if(nrecv>0)
call deallocate_overlap_type(overlap)
6383 type(domain2d),
intent(inout) :: domain
6384 integer,
intent(in) :: position
6385 integer :: m, n, l, count, dr, tMe
6386 integer,
parameter :: MAXCOUNT = 100
6387 integer,
dimension(MAXCOUNT) :: dir, rotation, is, ie, js, je, tileMe, index
6388 integer,
dimension(size(domain%x(:)), 4) :: nrecvl
6389 integer,
dimension(size(domain%x(:)), 4, MAXCOUNT) :: isl, iel, jsl, jel
6390 type(overlap_type),
pointer :: overlap => null()
6391 type(overlapspec),
pointer :: update => null()
6392 type(overlapspec),
pointer :: bound => null()
6393 integer :: nlist_send, nlist_recv, ishift, jshift
6394 integer :: ism, iem, jsm, jem, nsend, nrecv
6395 integer :: isg, ieg, jsg, jeg, nlist, list
6396 integer :: npes_x, npes_y, ipos, jpos, inbr, jnbr
6397 integer :: isc, iec, jsc, jec, my_pe
6398 integer :: pe_south1, pe_south2, pe_west0, pe_west1, pe_west2
6399 integer :: is_south1, ie_south1, js_south1, je_south1
6400 integer :: is_south2, ie_south2, js_south2, je_south2
6401 integer :: is_west0, ie_west0, js_west0, je_west0
6402 integer :: is_west1, ie_west1, js_west1, je_west1
6403 integer :: is_west2, ie_west2, js_west2, je_west2
6404 logical :: x_cyclic, y_cyclic, folded_north
6406 is_south1=0; ie_south1=0; js_south1=0; je_south1=0
6407 is_south2=0; ie_south2=0; js_south2=0; je_south2=0
6408 is_west0=0; ie_west0=0; js_west0=0; je_west0=0
6409 is_west1=0; ie_west1=0; js_west1=0; je_west1=0
6410 is_west2=0; ie_west2=0; js_west2=0; je_west2=0
6413 if( position == center .OR. .NOT. domain%symmetry )
return
6415 call mpp_get_global_domain(domain, isg, ieg, jsg, jeg)
6416 call mpp_get_memory_domain ( domain, ism, iem, jsm, jem )
6418 select case(position)
6420 update => domain%update_C
6421 bound => domain%bound_C
6423 update => domain%update_E
6424 bound => domain%bound_E
6426 update => domain%update_N
6427 bound => domain%bound_N
6429 call mpp_error( fatal,
"mpp_domains_mod(set_bound_overlap): invalid option of position")
6432 bound%xbegin = ism; bound%xend = iem + ishift
6433 bound%ybegin = jsm; bound%yend = jem + jshift
6435 nlist_send = max(update%nsend,4)
6436 nlist_recv = max(update%nrecv,4)
6437 bound%nsend = nlist_send
6438 bound%nrecv = nlist_recv
6439 if(nlist_send >0)
then
6440 if (
associated(bound%send))
deallocate(bound%send)
6441 allocate(bound%send(nlist_send))
6442 bound%send(:)%count = 0
6444 if(nlist_recv >0)
then
6445 if (
associated(bound%recv))
deallocate(bound%recv)
6446 allocate(bound%recv(nlist_recv))
6447 bound%recv(:)%count = 0
6450 nlist =
size(domain%list(:))
6452 npes_x =
size(domain%x(1)%list(:))
6453 npes_y =
size(domain%y(1)%list(:))
6454 x_cyclic = domain%x(1)%cyclic
6455 y_cyclic = domain%y(1)%cyclic
6456 folded_north = btest(domain%fold,north)
6457 ipos = domain%x(1)%pos
6458 jpos = domain%y(1)%pos
6459 isc = domain%x(1)%compute%begin; iec = domain%x(1)%compute%end
6460 jsc = domain%y(1)%compute%begin; jec = domain%y(1)%compute%end
6463 if(domain%ntiles == 1)
then
6467 pe_south1 = null_pe; pe_south2 = null_pe
6468 if( position == north .OR. position == corner )
then
6469 inbr = ipos; jnbr = jpos + 1
6470 if( jnbr == npes_y .AND. y_cyclic) jnbr = 0
6471 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6472 pe_south1 = domain%pearray(inbr,jnbr)
6473 is_south1 = isc + ishift; ie_south1 = iec+ishift
6474 js_south1 = jec + jshift; je_south1 = js_south1
6478 if( position == corner )
then
6479 inbr = ipos + 1; jnbr = jpos + 1
6480 if( inbr == npes_x .AND. x_cyclic) inbr = 0
6481 if( jnbr == npes_y .AND. y_cyclic) jnbr = 0
6482 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6483 pe_south2 = domain%pearray(inbr,jnbr)
6484 is_south2 = iec + ishift; ie_south2 = is_south2
6485 js_south2 = jec + jshift; je_south2 = js_south2
6490 pe_west0 = null_pe; pe_west1 = null_pe; pe_west2 = null_pe
6491 if( position == east )
then
6492 inbr = ipos+1; jnbr = jpos
6493 if( inbr == npes_x .AND. x_cyclic) inbr = 0
6494 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6495 pe_west1 = domain%pearray(inbr,jnbr)
6496 is_west1 = iec + ishift; ie_west1 = is_west1
6497 js_west1 = jsc + jshift; je_west1 = jec + jshift
6499 else if ( position == corner )
then
6501 if( folded_north .AND. jec == jeg .AND. ipos .LT. (npes_x-1)/2 )
then
6502 inbr = npes_x - ipos - 1; jnbr = jpos
6503 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6504 pe_west0 = domain%pearray(inbr,jnbr)
6505 is_west0 = iec+ishift; ie_west0 = is_west0
6506 js_west0 = jec+jshift; je_west0 = js_west0
6510 if( folded_north .AND. jec == jeg .AND. ipos .GE. npes_x/2 .AND. ipos .LT. (npes_x-1) )
then
6511 inbr = ipos+1; jnbr = jpos
6512 if( inbr == npes_x .AND. x_cyclic) inbr = 0
6513 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6514 pe_west1 = domain%pearray(inbr,jnbr)
6515 is_west1 = iec + ishift; ie_west1 = is_west1
6516 js_west1 = jsc + jshift; je_west1 = jec
6519 inbr = ipos+1; jnbr = jpos
6520 if( inbr == npes_x .AND. x_cyclic) inbr = 0
6521 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6522 pe_west1 = domain%pearray(inbr,jnbr)
6523 is_west1 = iec + ishift; ie_west1 = is_west1
6524 js_west1 = jsc + jshift; je_west1 = jec + jshift
6529 if( position == corner )
then
6530 inbr = ipos + 1; jnbr = jpos + 1
6531 if( inbr == npes_x .AND. x_cyclic) inbr = 0
6532 if( jnbr == npes_y .AND. y_cyclic) jnbr = 0
6533 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6534 pe_west2 = domain%pearray(inbr,jnbr)
6535 is_west2 = iec + ishift; ie_west2 = is_west2
6536 js_west2 = jec + jshift; je_west2 = js_west2
6541 m = mod( domain%pos+list, nlist )
6543 my_pe = domain%list(m)%pe
6544 if(my_pe == pe_south1)
then
6546 is(count) = is_south1; ie(count) = ie_south1
6547 js(count) = js_south1; je(count) = je_south1
6549 rotation(count) = zero
6551 if(my_pe == pe_south2)
then
6553 is(count) = is_south2; ie(count) = ie_south2
6554 js(count) = js_south2; je(count) = je_south2
6556 rotation(count) = zero
6559 if(my_pe == pe_west0)
then
6561 is(count) = is_west0; ie(count) = ie_west0
6562 js(count) = js_west0; je(count) = je_west0
6564 rotation(count) = one_hundred_eighty
6566 if(my_pe == pe_west1)
then
6568 is(count) = is_west1; ie(count) = ie_west1
6569 js(count) = js_west1; je(count) = je_west1
6571 rotation(count) = zero
6573 if(my_pe == pe_west2)
then
6575 is(count) = is_west2; ie(count) = ie_west2
6576 js(count) = js_west2; je(count) = je_west2
6578 rotation(count) = zero
6583 if(nsend > nlist_send)
call mpp_error(fatal,
"set_bound_overlap: nsend > nlist_send")
6584 bound%send(nsend)%count = count
6585 bound%send(nsend)%pe = my_pe
6586 if (
associated(bound%send(nsend)%is))
deallocate(bound%send(nsend)%is)
6587 if (
associated(bound%send(nsend)%ie))
deallocate(bound%send(nsend)%ie)
6588 if (
associated(bound%send(nsend)%js))
deallocate(bound%send(nsend)%js)
6589 if (
associated(bound%send(nsend)%je))
deallocate(bound%send(nsend)%je)
6590 if (
associated(bound%send(nsend)%dir))
deallocate(bound%send(nsend)%dir)
6591 if (
associated(bound%send(nsend)%rotation))
deallocate(bound%send(nsend)%rotation)
6592 if (
associated(bound%send(nsend)%tileMe))
deallocate(bound%send(nsend)%tileMe)
6593 allocate(bound%send(nsend)%is(count), bound%send(nsend)%ie(count) )
6594 allocate(bound%send(nsend)%js(count), bound%send(nsend)%je(count) )
6595 allocate(bound%send(nsend)%dir(count), bound%send(nsend)%rotation(count) )
6596 allocate(bound%send(nsend)%tileMe(count))
6597 bound%send(nsend)%is(:) = is(1:count)
6598 bound%send(nsend)%ie(:) = ie(1:count)
6599 bound%send(nsend)%js(:) = js(1:count)
6600 bound%send(nsend)%je(:) = je(1:count)
6601 bound%send(nsend)%dir(:) = dir(1:count)
6602 bound%send(nsend)%tileMe(:) = 1
6603 bound%send(nsend)%rotation(:) = rotation(1:count)
6608 do m = 1, update%nsend
6609 overlap => update%send(m)
6610 if( overlap%count == 0 ) cycle
6612 do n = 1, overlap%count
6614 if( overlap%rotation(n) == one_hundred_eighty ) cycle
6615 if( (position == east .OR. position == corner) .AND. overlap%dir(n) == 1)
then
6618 rotation(count) = overlap%rotation(n)
6619 tileme(count) = overlap%tileMe(n)
6620 select case( rotation(count) )
6622 is(count) = overlap%is(n) - 1
6623 ie(count) = is(count)
6624 js(count) = overlap%js(n)
6625 je(count) = overlap%je(n)
6627 is(count) = overlap%is(n)
6628 ie(count) = overlap%ie(n)
6629 js(count) = overlap%js(n) - 1
6630 je(count) = js(count)
6633 if( (position == north .OR. position == corner) .AND. overlap%dir(n) == 3 )
then
6636 rotation(count) = overlap%rotation(n)
6637 tileme(count) = overlap%tileMe(n)
6638 select case( rotation(count) )
6640 is(count) = overlap%is(n)
6641 ie(count) = overlap%ie(n)
6642 js(count) = overlap%je(n) + 1
6643 je(count) = js(count)
6644 case( minus_ninety )
6645 is(count) = overlap%ie(n) + 1
6646 ie(count) = is(count)
6647 js(count) = overlap%js(n)
6648 je(count) = overlap%je(n)
6651 if( (position == east .OR. position == corner) .AND. overlap%dir(n) == 5 )
then
6654 rotation(count) = overlap%rotation(n)
6655 tileme(count) = overlap%tileMe(n)
6656 select case( rotation(count) )
6658 is(count) = overlap%ie(n) + 1
6659 ie(count) = is(count)
6660 js(count) = overlap%js(n)
6661 je(count) = overlap%je(n)
6663 is(count) = overlap%is(n)
6664 ie(count) = overlap%ie(n)
6665 js(count) = overlap%je(n) + 1
6666 je(count) = js(count)
6669 if( (position == north .OR. position == corner) .AND. overlap%dir(n) == 7 )
then
6672 rotation(count) = overlap%rotation(n)
6673 tileme(count) = overlap%tileMe(n)
6674 select case( rotation(count) )
6676 is(count) = overlap%is(n)
6677 ie(count) = overlap%ie(n)
6678 js(count) = overlap%js(n) - 1
6679 je(count) = js(count)
6680 case( minus_ninety )
6681 is(count) = overlap%is(n) - 1
6682 ie(count) = is(count)
6683 js(count) = overlap%js(n)
6684 je(count) = overlap%je(n)
6690 bound%send(nsend)%count = count
6691 bound%send(nsend)%pe = overlap%pe
6692 if (
associated(bound%send(nsend)%is))
deallocate(bound%send(nsend)%is)
6693 if (
associated(bound%send(nsend)%ie))
deallocate(bound%send(nsend)%ie)
6694 if (
associated(bound%send(nsend)%js))
deallocate(bound%send(nsend)%js)
6695 if (
associated(bound%send(nsend)%je))
deallocate(bound%send(nsend)%je)
6696 if (
associated(bound%send(nsend)%dir))
deallocate(bound%send(nsend)%dir)
6697 if (
associated(bound%send(nsend)%rotation))
deallocate(bound%send(nsend)%rotation)
6698 if (
associated(bound%send(nsend)%tileMe))
deallocate(bound%send(nsend)%tileMe)
6699 allocate(bound%send(nsend)%is(count), bound%send(nsend)%ie(count) )
6700 allocate(bound%send(nsend)%js(count), bound%send(nsend)%je(count) )
6701 allocate(bound%send(nsend)%dir(count), bound%send(nsend)%rotation(count) )
6702 allocate(bound%send(nsend)%tileMe(count))
6703 bound%send(nsend)%is(:) = is(1:count)
6704 bound%send(nsend)%ie(:) = ie(1:count)
6705 bound%send(nsend)%js(:) = js(1:count)
6706 bound%send(nsend)%je(:) = je(1:count)
6707 bound%send(nsend)%dir(:) = dir(1:count)
6708 bound%send(nsend)%tileMe(:) = tileme(1:count)
6709 bound%send(nsend)%rotation(:) = rotation(1:count)
6720 if( domain%ntiles == 1 )
then
6724 pe_south1 = null_pe; pe_south2 = null_pe
6725 if( position == north .OR. position == corner )
then
6726 inbr = ipos; jnbr = jpos - 1
6727 if( jnbr == -1 .AND. y_cyclic) jnbr = npes_y-1
6728 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6729 pe_south1 = domain%pearray(inbr,jnbr)
6730 is_south1 = isc + ishift; ie_south1 = iec+ishift
6731 js_south1 = jsc; je_south1 = js_south1
6736 if( position == corner )
then
6737 inbr = ipos - 1; jnbr = jpos - 1
6738 if( inbr == -1 .AND. x_cyclic) inbr = npes_x-1
6739 if( jnbr == -1 .AND. y_cyclic) jnbr = npes_y-1
6740 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6741 pe_south2 = domain%pearray(inbr,jnbr)
6742 is_south2 = isc; ie_south2 = is_south2
6743 js_south2 = jsc; je_south2 = js_south2
6749 pe_west0 = null_pe; pe_west1 = null_pe; pe_west2 = null_pe
6750 if( position == east )
then
6751 inbr = ipos-1; jnbr = jpos
6752 if( inbr == -1 .AND. x_cyclic) inbr = npes_x-1
6753 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6754 pe_west1 = domain%pearray(inbr,jnbr)
6755 is_west1 = isc; ie_west1 = is_west1
6756 js_west1 = jsc + jshift; je_west1 = jec + jshift
6758 else if ( position == corner )
then
6760 if( folded_north .AND. jec == jeg .AND. ipos .GT. npes_x/2 )
then
6761 inbr = npes_x - ipos - 1; jnbr = jpos
6762 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6763 pe_west0 = domain%pearray(inbr,jnbr)
6764 is_west0 = isc; ie_west0 = is_west0
6765 js_west0 = jec+jshift; je_west0 = js_west0
6767 inbr = ipos-1; jnbr = jpos
6768 if( inbr == -1 .AND. x_cyclic) inbr = npes_x-1
6769 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6770 pe_west1 = domain%pearray(inbr,jnbr)
6771 is_west1 = isc; ie_west1 = is_west1
6772 js_west1 = jsc + jshift; je_west1 = jec
6775 inbr = ipos-1; jnbr = jpos
6776 if( inbr == -1 .AND. x_cyclic) inbr = npes_x-1
6777 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6778 pe_west1 = domain%pearray(inbr,jnbr)
6779 is_west1 = isc; ie_west1 = is_west1
6780 js_west1 = jsc + jshift; je_west1 = jec+jshift
6786 if( position == corner )
then
6787 inbr = ipos - 1; jnbr = jpos - 1
6788 if( inbr == -1 .AND. x_cyclic) inbr = npes_x - 1
6789 if( jnbr == -1 .AND. y_cyclic) jnbr = npes_y - 1
6790 if( inbr .GE. 0 .AND. inbr .LT. npes_x .AND. jnbr .GE. 0 .AND. jnbr .LT. npes_y )
then
6791 pe_west2 = domain%pearray(inbr,jnbr)
6792 is_west2 = isc; ie_west2 = is_west2
6793 js_west2 = jsc; je_west2 = js_west2
6799 m = mod( domain%pos+nlist-list, nlist )
6801 my_pe = domain%list(m)%pe
6802 if(my_pe == pe_south1)
then
6804 is(count) = is_south1; ie(count) = ie_south1
6805 js(count) = js_south1; je(count) = je_south1
6807 rotation(count) = zero
6808 index(count) = 1 + ishift
6810 if(my_pe == pe_south2)
then
6812 is(count) = is_south2; ie(count) = ie_south2
6813 js(count) = js_south2; je(count) = je_south2
6815 rotation(count) = zero
6818 if(my_pe == pe_west0)
then
6820 is(count) = is_west0; ie(count) = ie_west0
6821 js(count) = js_west0; je(count) = je_west0
6823 rotation(count) = one_hundred_eighty
6824 index(count) = jec-jsc+1+jshift
6826 if(my_pe == pe_west1)
then
6828 is(count) = is_west1; ie(count) = ie_west1
6829 js(count) = js_west1; je(count) = je_west1
6831 rotation(count) = zero
6832 index(count) = 1 + jshift
6834 if(my_pe == pe_west2)
then
6836 is(count) = is_west2; ie(count) = ie_west2
6837 js(count) = js_west2; je(count) = je_west2
6839 rotation(count) = zero
6845 if(nrecv > nlist_recv)
call mpp_error(fatal,
"set_bound_overlap: nrecv > nlist_recv")
6846 bound%recv(nrecv)%count = count
6847 bound%recv(nrecv)%pe = my_pe
6848 if (
associated(bound%recv(nrecv)%is))
deallocate(bound%recv(nrecv)%is)
6849 if (
associated(bound%recv(nrecv)%ie))
deallocate(bound%recv(nrecv)%ie)
6850 if (
associated(bound%recv(nrecv)%js))
deallocate(bound%recv(nrecv)%js)
6851 if (
associated(bound%recv(nrecv)%je))
deallocate(bound%recv(nrecv)%je)
6852 if (
associated(bound%recv(nrecv)%dir))
deallocate(bound%recv(nrecv)%dir)
6853 if (
associated(bound%recv(nrecv)%index))
deallocate(bound%recv(nrecv)%index)
6854 if (
associated(bound%recv(nrecv)%tileMe))
deallocate(bound%recv(nrecv)%tileMe)
6855 if (
associated(bound%recv(nrecv)%rotation))
deallocate(bound%recv(nrecv)%rotation)
6856 allocate(bound%recv(nrecv)%is(count), bound%recv(nrecv)%ie(count) )
6857 allocate(bound%recv(nrecv)%js(count), bound%recv(nrecv)%je(count) )
6858 allocate(bound%recv(nrecv)%dir(count), bound%recv(nrecv)%index(count) )
6859 allocate(bound%recv(nrecv)%tileMe(count), bound%recv(nrecv)%rotation(count) )
6861 bound%recv(nrecv)%is(:) = is(1:count)
6862 bound%recv(nrecv)%ie(:) = ie(1:count)
6863 bound%recv(nrecv)%js(:) = js(1:count)
6864 bound%recv(nrecv)%je(:) = je(1:count)
6865 bound%recv(nrecv)%dir(:) = dir(1:count)
6866 bound%recv(nrecv)%tileMe(:) = 1
6867 bound%recv(nrecv)%rotation(:) = rotation(1:count)
6868 bound%recv(nrecv)%index(:) = index(1:count)
6872 do m = 1, update%nrecv
6873 overlap => update%recv(m)
6874 if( overlap%count == 0 ) cycle
6876 do n = 1, overlap%count
6878 if( overlap%rotation(n) == one_hundred_eighty ) cycle
6879 if( (position == east .OR. position == corner) .AND. overlap%dir(n) == 1)
then
6882 rotation(count) = overlap%rotation(n)
6883 tileme(count) = overlap%tileMe(n)
6884 is(count) = overlap%is(n) - 1
6885 ie(count) = is(count)
6886 js(count) = overlap%js(n)
6887 je(count) = overlap%je(n)
6889 nrecvl(tme, 1) = nrecvl(tme,1) + 1
6890 isl(tme,1,nrecvl(tme, 1)) = is(count)
6891 iel(tme,1,nrecvl(tme, 1)) = ie(count)
6892 jsl(tme,1,nrecvl(tme, 1)) = js(count)
6893 jel(tme,1,nrecvl(tme, 1)) = je(count)
6896 if( (position == north .OR. position == corner) .AND. overlap%dir(n) == 3)
then
6899 rotation(count) = overlap%rotation(n)
6900 tileme(count) = overlap%tileMe(n)
6901 is(count) = overlap%is(n)
6902 ie(count) = overlap%ie(n)
6903 js(count) = overlap%je(n) + 1
6904 je(count) = js(count)
6906 nrecvl(tme, 2) = nrecvl(tme,2) + 1
6907 isl(tme,2,nrecvl(tme, 2)) = is(count)
6908 iel(tme,2,nrecvl(tme, 2)) = ie(count)
6909 jsl(tme,2,nrecvl(tme, 2)) = js(count)
6910 jel(tme,2,nrecvl(tme, 2)) = je(count)
6913 if( (position == east .OR. position == corner) .AND. overlap%dir(n) == 5)
then
6916 rotation(count) = overlap%rotation(n)
6917 tileme(count) = overlap%tileMe(n)
6918 is(count) = overlap%ie(n) + 1
6919 ie(count) = is(count)
6920 js(count) = overlap%js(n)
6921 je(count) = overlap%je(n)
6923 nrecvl(tme, 3) = nrecvl(tme,3) + 1
6924 isl(tme,3,nrecvl(tme, 3)) = is(count)
6925 iel(tme,3,nrecvl(tme, 3)) = ie(count)
6926 jsl(tme,3,nrecvl(tme, 3)) = js(count)
6927 jel(tme,3,nrecvl(tme, 3)) = je(count)
6930 if( (position == north .OR. position == corner) .AND. overlap%dir(n) == 7)
then
6933 rotation(count) = overlap%rotation(n)
6934 tileme(count) = overlap%tileMe(n)
6935 is(count) = overlap%is(n)
6936 ie(count) = overlap%ie(n)
6937 js(count) = overlap%js(n) - 1
6938 je(count) = js(count)
6940 nrecvl(tme, 4) = nrecvl(tme,4) + 1
6941 isl(tme,4,nrecvl(tme, 4)) = is(count)
6942 iel(tme,4,nrecvl(tme, 4)) = ie(count)
6943 jsl(tme,4,nrecvl(tme, 4)) = js(count)
6944 jel(tme,4,nrecvl(tme, 4)) = je(count)
6949 bound%recv(nrecv)%count = count
6950 bound%recv(nrecv)%pe = overlap%pe
6951 if (
associated(bound%recv(nrecv)%is))
deallocate(bound%recv(nrecv)%is)
6952 if (
associated(bound%recv(nrecv)%ie))
deallocate(bound%recv(nrecv)%ie)
6953 if (
associated(bound%recv(nrecv)%js))
deallocate(bound%recv(nrecv)%js)
6954 if (
associated(bound%recv(nrecv)%je))
deallocate(bound%recv(nrecv)%je)
6955 if (
associated(bound%recv(nrecv)%dir))
deallocate(bound%recv(nrecv)%dir)
6956 if (
associated(bound%recv(nrecv)%index))
deallocate(bound%recv(nrecv)%index)
6957 if (
associated(bound%recv(nrecv)%tileMe))
deallocate(bound%recv(nrecv)%tileMe)
6958 if (
associated(bound%recv(nrecv)%rotation))
deallocate(bound%recv(nrecv)%rotation)
6959 allocate(bound%recv(nrecv)%is(count), bound%recv(nrecv)%ie(count) )
6960 allocate(bound%recv(nrecv)%js(count), bound%recv(nrecv)%je(count) )
6961 allocate(bound%recv(nrecv)%dir(count), bound%recv(nrecv)%index(count) )
6962 allocate(bound%recv(nrecv)%tileMe(count), bound%recv(nrecv)%rotation(count) )
6963 bound%recv(nrecv)%is(:) = is(1:count)
6964 bound%recv(nrecv)%ie(:) = ie(1:count)
6965 bound%recv(nrecv)%js(:) = js(1:count)
6966 bound%recv(nrecv)%je(:) = je(1:count)
6967 bound%recv(nrecv)%dir(:) = dir(1:count)
6968 bound%recv(nrecv)%tileMe(:) = tileme(1:count)
6969 bound%recv(nrecv)%rotation(:) = rotation(1:count)
6974 do n = 1, bound%recv(m)%count
6975 tme = bound%recv(m)%tileMe(n)
6976 dr = bound%recv(m)%dir(n)
6977 bound%recv(m)%index(n) = 1
6978 do l = 1, nrecvl(tme,dr)
6979 if(dr == 1 .OR. dr == 3)
then
6980 if( bound%recv(m)%js(n) > jsl(tme, dr, l) )
then
6981 if( bound%recv(m)%rotation(n) == one_hundred_eighty )
then
6982 bound%recv(m)%index(n) = bound%recv(m)%index(n) + &
6983 max(abs(jel(tme, dr, l)-jsl(tme, dr, l))+1, &
6984 abs(iel(tme, dr, l)-isl(tme, dr, l))+1)
6986 bound%recv(m)%index(n) = bound%recv(m)%index(n) + &
6987 max(abs(jel(tme, dr, l)-jsl(tme, dr, l)), &
6988 abs(iel(tme, dr, l)-isl(tme, dr, l))) + 1 - jshift
6992 if( bound%recv(m)%is(n) > isl(tme, dr, l) )
then
6993 bound%recv(m)%index(n) = bound%recv(m)%index(n) + &
6994 max(abs(jel(tme, dr, l)-jsl(tme, dr, l)), &
6995 abs(iel(tme, dr, l)-isl(tme, dr, l))) + 1 - ishift
7011 subroutine fill_corner_contact(eCont, sCont, wCont, nCont, isg, ieg, jsg, jeg, numR, numS, tileRecv, tileSend, &
7012 is1Recv, ie1Recv, js1Recv, je1Recv, is2Recv, ie2Recv, js2Recv, je2Recv, &
7013 is1Send, ie1Send, js1Send, je1Send, is2Send, ie2Send, js2Send, je2Send, &
7014 align1Recv, align2Recv, align1Send, align2Send, &
7015 whalo, ehalo, shalo, nhalo, tileMe)
7016 type(contact_type),
dimension(:),
intent(in) :: eCont, sCont, wCont, nCont
7017 integer,
dimension(:),
intent(in) :: isg, ieg, jsg, jeg
7018 integer,
intent(inout) :: numR, numS
7019 integer,
dimension(:),
intent(inout) :: tileRecv, tileSend
7020 integer,
dimension(:),
intent(inout) :: is1Recv, ie1Recv, js1Recv, je1Recv
7021 integer,
dimension(:),
intent(inout) :: is2Recv, ie2Recv, js2Recv, je2Recv
7022 integer,
dimension(:),
intent(inout) :: is1Send, ie1Send, js1Send, je1Send
7023 integer,
dimension(:),
intent(inout) :: is2Send, ie2Send, js2Send, je2Send
7024 integer,
dimension(:),
intent(inout) :: align1Recv, align2Recv, align1Send, align2Send
7025 integer,
intent(in) :: tileMe, whalo, ehalo, shalo, nhalo
7026 integer :: is1, ie1, js1, je1, is2, ie2, js2, je2
7027 integer :: tn, tc, n, m
7028 logical :: found_corner
7030 found_corner = .false.
7032 if(econt(tileme)%ncontact > 0)
then
7033 if(econt(tileme)%js1(1) == jsg(tileme) )
then
7034 tn = econt(tileme)%tile(1)
7035 if(econt(tileme)%js2(1) > jsg(tn) )
then
7036 if( econt(tileme)%js2(1) - jsg(tn) < shalo )
call mpp_error(fatal, &
7037 "mpp_domains_define.inc: southeast tile for recv 1 is not tiled properly")
7038 found_corner = .true.; tc = tn
7039 is1 = econt(tileme)%ie1(1) + 1; je1 = econt(tileme)%js1(1) - 1
7040 is2 = econt(tileme)%is2(1); je2 = econt(tileme)%js2(1) - 1
7041 else if(scont(tn)%ncontact >0)
then
7042 if(scont(tn)%is1(1) == isg(tn))
then
7043 found_corner = .true.; tc = scont(tn)%tile(1)
7044 is1 = econt(tileme)%ie1(1) + 1; je1 = econt(tileme)%js1(1) - 1
7045 is2 = scont(tn)%is2(1); je2 = scont(tn)%je2(1)
7050 if( .not. found_corner )
then
7051 n = scont(tileme)%ncontact
7053 if( scont(tileme)%ie1(n) == ieg(tileme))
then
7054 tn = scont(tileme)%tile(n)
7055 if(scont(tileme)%ie2(n) < ieg(tn) )
then
7056 if(ieg(tn) - scont(tileme)%ie2(n) < ehalo )
call mpp_error(fatal, &
7057 "mpp_domains_define.inc: southeast tile for recv 2 is not tiled properly")
7058 found_corner = .true.; tc = tn
7059 is1 = scont(tileme)%ie1(n) + 1; je1 = scont(tileme)%js1(n) - 1
7060 is2 = scont(tileme)%ie2(n) + 1; je2 = scont(tileme)%je2(n)
7061 else if(econt(tn)%ncontact >0)
then
7062 m = econt(tn)%ncontact
7063 if(econt(tn)%je1(m) == jeg(tn))
then
7064 found_corner = .true.; tc = econt(tn)%tile(m)
7065 is1 = scont(tileme)%ie1(n) + 1; je1 = scont(tileme)%js1(n) - 1
7066 is2 = econt(tn)%is2(m); je2 = econt(tn)%je2(m)
7072 if(found_corner)
then
7074 tilerecv(numr) = tc; align1recv(numr) = south_east; align2recv(numr) = north_west
7075 is1recv(numr) = is1; ie1recv(numr) = is1 + ehalo - 1
7076 js1recv(numr) = je1 - shalo + 1; je1recv(numr) = je1
7077 is2recv(numr) = is2; ie2recv(numr) = is2 + ehalo - 1
7078 js2recv(numr) = je2 - shalo + 1; je2recv(numr) = je2
7082 found_corner = .false.
7083 if(wcont(tileme)%ncontact > 0)
then
7084 if(wcont(tileme)%js1(1) == jsg(tileme) )
then
7085 tn = wcont(tileme)%tile(1)
7086 if(wcont(tileme)%js2(1) > jsg(tn) )
then
7087 if( wcont(tileme)%js2(1) - jsg(tn) < shalo )
call mpp_error(fatal, &
7088 "mpp_domains_define.inc: southwest tile for recv 1 is not tiled properly")
7089 found_corner = .true.; tc = tn
7090 ie1 = wcont(tileme)%is1(1) - 1; je1 = wcont(tileme)%js1(1) - 1
7091 ie2 = wcont(tileme)%is2(1); je2 = wcont(tileme)%js2(1) - 1
7092 else if(scont(tn)%ncontact >0)
then
7093 n = scont(tn)%ncontact
7094 if(scont(tn)%ie1(n) == ieg(tn))
then
7095 found_corner = .true.; tc = scont(tn)%tile(n)
7096 ie1 = wcont(tileme)%is1(1) - 1; je1 = wcont(tileme)%js1(1) - 1
7097 ie2 = scont(tn)%ie2(1); je2 = scont(tn)%je2(1)
7102 if( .not. found_corner )
then
7103 n = scont(tileme)%ncontact
7105 if( scont(tileme)%is1(1) == isg(tileme))
then
7106 tn = scont(tileme)%tile(1)
7107 if(scont(tileme)%is2(1) > isg(tn) )
then
7108 if( scont(tileme)%is2(1)-isg(tn) < whalo )
call mpp_error(fatal, &
7109 "mpp_domains_define.inc: southwest tile for recv 1 is not tiled properly")
7110 found_corner = .true.; tc = tn
7111 ie1 = scont(tileme)%is1(1) - 1; je1 = scont(tileme)%js1(1) - 1
7112 ie2 = scont(tileme)%is2(1) - 1; je2 = scont(tileme)%js2(1)
7113 else if(wcont(tn)%ncontact >0)
then
7114 m = wcont(tn)%ncontact
7115 if(wcont(tn)%je1(m) == jeg(tn))
then
7116 found_corner = .true.; tc = wcont(tn)%tile(m)
7117 ie1 = scont(tileme)%is1(1) - 1; je1 = scont(tileme)%js1(1) - 1
7118 ie2 = wcont(tn)%ie2(m); je2 = wcont(tn)%je2(m)
7124 if(found_corner)
then
7126 tilerecv(numr) = tc; align1recv(numr) = south_west; align2recv(numr) = north_east
7127 is1recv(numr) = ie1 - whalo + 1; ie1recv(numr) = ie1
7128 js1recv(numr) = je1 - shalo + 1; je1recv(numr) = je1
7129 is2recv(numr) = ie2 - whalo + 1; ie2recv(numr) = ie2
7130 js2recv(numr) = je2 - shalo + 1; je2recv(numr) = je2
7134 found_corner = .false.
7135 n = wcont(tileme)%ncontact
7137 if(wcont(tileme)%je1(n) == jeg(tileme) )
then
7138 tn = wcont(tileme)%tile(n)
7139 if(wcont(tileme)%je2(n) < jeg(tn) )
then
7140 if( jeg(tn) - wcont(tileme)%je2(n) < nhalo )
call mpp_error(fatal, &
7141 "mpp_domains_define.inc: northwest tile for recv 1 is not tiled properly")
7142 found_corner = .true.; tc = tn
7143 ie1 = wcont(tileme)%is1(n) - 1; js1 = wcont(tileme)%je1(n) + 1
7144 ie2 = wcont(tileme)%is2(n); js2 = wcont(tileme)%je2(n) + 1
7145 else if(ncont(tn)%ncontact >0)
then
7146 m = ncont(tn)%ncontact
7147 if(ncont(tn)%ie1(m) == ieg(tn))
then
7148 found_corner = .true.; tc = ncont(tn)%tile(m)
7149 ie1 = wcont(tileme)%is1(n) - 1; js1 = wcont(tileme)%je1(n) + 1
7150 ie2 = ncont(tn)%ie2(m); js2 = ncont(tn)%js2(m)
7155 if( .not. found_corner )
then
7156 if( ncont(tileme)%ncontact > 0)
then
7157 if( ncont(tileme)%is1(1) == isg(tileme))
then
7158 tn = ncont(tileme)%tile(1)
7159 if(ncont(tileme)%is2(1) > isg(tn) )
then
7160 if( ncont(tileme)%is2(1)-isg(tn) < whalo )
call mpp_error(fatal, &
7161 "mpp_domains_define.inc: northwest tile for recv 2 is not tiled properly")
7162 found_corner = .true.; tc = tn
7163 ie1 = ncont(tileme)%is1(1) - 1; js1 = ncont(tileme)%je1(1) + 1
7164 ie2 = ncont(tileme)%is2(1) - 1; js2 = ncont(tileme)%js2(1)
7165 else if(wcont(tn)%ncontact >0)
then
7166 if(wcont(tn)%js1(1) == jsg(tn))
then
7167 found_corner = .true.; tc = wcont(tn)%tile(1)
7168 ie1 = ncont(tileme)%is1(1) - 1; js1 = ncont(tileme)%je1(1) + 1
7169 ie2 = wcont(tn)%ie2(1); js2 = wcont(tn)%js2(1)
7175 if(found_corner)
then
7177 tilerecv(numr) = tc; align1recv(numr) =north_west; align2recv(numr) = south_east
7178 is1recv(numr) = ie1 - whalo + 1; ie1recv(numr) = ie1
7179 js1recv(numr) = js1; je1recv(numr) = js1 + nhalo - 1
7180 is2recv(numr) = ie2 - whalo + 1; ie2recv(numr) = ie2
7181 js2recv(numr) = js2; je2recv(numr) = js2 + nhalo - 1
7185 found_corner = .false.
7186 n = econt(tileme)%ncontact
7188 if(econt(tileme)%je1(n) == jeg(tileme) )
then
7189 tn = econt(tileme)%tile(n)
7190 if(econt(tileme)%je2(n) < jeg(tn) )
then
7191 if( jeg(tn) - econt(tileme)%je2(n) < nhalo )
call mpp_error(fatal, &
7192 "mpp_domains_define.inc: northeast tile for recv 1 is not tiled properly")
7193 found_corner = .true.; tc = tn
7194 is1 = econt(tileme)%ie1(n) + 1; js1 = econt(tileme)%je1(n) + 1
7195 is2 = econt(tileme)%is2(1); js2 = econt(tileme)%je2(1) + 1
7196 else if(ncont(tn)%ncontact >0)
then
7197 if(ncont(tn)%is1(1) == isg(tn))
then
7198 found_corner = .true.; tc = ncont(tn)%tile(1)
7199 is1 = econt(tileme)%ie1(n) + 1; js1 = econt(tileme)%je1(n) + 1
7200 is2 = ncont(tn)%is2(1); js2 = ncont(tn)%js2(1)
7205 if( .not. found_corner )
then
7206 n = ncont(tileme)%ncontact
7208 if( ncont(tileme)%ie1(n) == ieg(tileme))
then
7209 tn = ncont(tileme)%tile(n)
7210 if(ncont(tileme)%ie2(n) < ieg(tn) )
then
7211 if(ieg(tn) - scont(tileme)%ie2(n) < ehalo )
call mpp_error(fatal, &
7212 "mpp_domains_define.inc: northeast tile for recv 2 is not tiled properly")
7213 found_corner = .true.; tc = tn
7214 is1 = scont(tileme)%ie1(n) + 1; js1 = scont(tileme)%je1(n) + 1
7215 is2 = scont(tileme)%ie2(n) + 1; js2 = scont(tileme)%js2(n)
7216 else if(econt(tn)%ncontact >0)
then
7217 if(econt(tn)%js1(1) == jsg(tn))
then
7218 found_corner = .true.; tc = econt(tn)%tile(1)
7219 is1 = scont(tileme)%ie1(n) + 1; js1 = scont(tileme)%je1(n) + 1
7220 is2 = econt(tn)%is2(m); js2 = econt(tn)%js2(m)
7226 if(found_corner)
then
7228 tilerecv(numr) = tc; align1recv(numr) =north_east; align2recv(numr) = south_west
7229 is1recv(numr) = is1; ie1recv(numr) = is1 + ehalo - 1
7230 js1recv(numr) = js1; je1recv(numr) = js1 + nhalo - 1
7231 is2recv(numr) = is2; ie2recv(numr) = is2 + ehalo - 1
7232 js2recv(numr) = js2; je2recv(numr) = js2 + nhalo - 1
7236 do n = 1, wcont(tileme)%ncontact
7237 tn = wcont(tileme)%tile(n)
7238 if(wcont(tileme)%js2(n) == jsg(tn) )
then
7239 if(wcont(tileme)%js1(n) > jsg(tileme) )
then
7240 if( wcont(tileme)%js1(n) - jsg(tileme) < shalo )
call mpp_error(fatal, &
7241 "mpp_domains_define.inc: southeast tile for send 1 is not tiled properly")
7242 nums = nums+1; tilesend(nums) = tn
7243 align1send(nums) = north_west; align2send(nums) = south_east
7244 is1send(nums) = wcont(tileme)%is1(n); ie1send(nums) = is1send(nums) + ehalo - 1
7245 je1send(nums) = wcont(tileme)%js1(n) - 1; js1send(nums) = je1send(nums) - shalo + 1
7246 is2send(nums) = wcont(tileme)%ie2(n) + 1; ie2send(nums) = is2send(nums) + ehalo - 1
7247 je2send(nums) = wcont(tileme)%js2(n) - 1; js2send(nums) = je2send(nums) - shalo + 1
7251 do n = 1, ncont(tileme)%ncontact
7252 tn = ncont(tileme)%tile(n)
7253 if(ncont(tileme)%ie2(n) == ieg(tn) )
then
7254 if(ncont(tileme)%ie1(n) < ieg(tileme) )
then
7255 if( ieg(tileme) - ncont(tileme)%ie1(n) < ehalo )
call mpp_error(fatal, &
7256 "mpp_domains_define.inc: southeast tile for send 2 is not tiled properly")
7257 nums = nums+1; tilesend(nums) = tn
7258 align1send(nums) = north_west; align2send(nums) = south_east
7259 is1send(nums) = ncont(tileme)%ie1(n) + 1; ie1send(nums) = is1send(nums) + ehalo - 1
7260 je1send(nums) = ncont(tileme)%je1(n) ; js1send(nums) = je1send(nums) - shalo + 1
7261 is2send(nums) = ncont(tileme)%ie2(n) + 1; ie2send(nums) = is2send(nums) + ehalo - 1
7262 je2send(nums) = ncont(tileme)%je2(n) - 1; js2send(nums) = je2send(nums) - shalo + 1
7268 n = wcont(tileme)%ncontact
7269 found_corner = .false.
7271 tn = wcont(tileme)%tile(n)
7272 if( wcont(tileme)%je1(n) == jeg(tileme) .AND. wcont(tileme)%je2(n) == jeg(tn) )
then
7273 m = ncont(tn)%ncontact
7275 tc = ncont(tn)%tile(m)
7276 if( ncont(tn)%ie1(m) == ieg(tn) .AND. ncont(tn)%ie2(m) == ieg(tc) ) found_corner = .true.
7280 if( .not. found_corner )
then
7281 if( ncont(tileme)%ncontact > 0)
then
7282 tn = ncont(tileme)%tile(1)
7283 if( ncont(tileme)%is1(1) == isg(tileme) .AND. ncont(tileme)%is2(1) == isg(tn) )
then
7284 if(wcont(tn)%ncontact >0)
then
7285 tc = wcont(tn)%tile(1)
7286 if( wcont(tn)%js1(1) == jsg(tn) .AND. wcont(tn)%js2(1) == jsg(tc) ) found_corner = .true.
7292 if(found_corner)
then
7293 nums = nums+1; tilesend(nums) = tc
7294 align1send(nums) = north_west; align2send(nums) = south_east
7295 is1send(nums) = isg(tileme); ie1send(nums) = is1send(nums) + ehalo - 1
7296 je1send(nums) = jeg(tileme); js1send(nums) = je1send(nums) - shalo + 1
7297 is2send(nums) = ieg(tc) + 1; ie2send(nums) = is2send(nums) + ehalo - 1
7298 je2send(nums) = jsg(tc) - 1; js2send(nums) = je2send(nums) - shalo + 1
7302 do n = 1, econt(tileme)%ncontact
7303 tn = econt(tileme)%tile(n)
7304 if(econt(tileme)%js2(n) == jsg(tn) )
then
7305 if(econt(tileme)%js1(n) > jsg(tileme) )
then
7306 if( econt(tileme)%js1(n) - jsg(tileme) < shalo )
call mpp_error(fatal, &
7307 "mpp_domains_define.inc: southwest tile for send 1 is not tiled properly")
7308 nums = nums+1; tilesend(nums) = tn
7309 align1send(nums) = north_east; align2send(nums) = south_west
7310 ie1send(nums) = econt(tileme)%ie1(n); is1send(nums) = ie1send(nums) - whalo + 1
7311 je1send(nums) = econt(tileme)%js1(n) - 1; js1send(nums) = je1send(nums) - shalo + 1
7312 ie2send(nums) = econt(tileme)%is2(n) - 1; is2send(nums) = ie2send(nums) - whalo + 1
7313 je2send(nums) = econt(tileme)%js2(n) - 1; js2send(nums) = je2send(nums) - shalo + 1
7317 do n = 1, ncont(tileme)%ncontact
7318 tn = ncont(tileme)%tile(n)
7319 if(ncont(tileme)%is2(n) == isg(tn) )
then
7320 if(ncont(tileme)%is1(n) > isg(tileme) )
then
7321 if( ncont(tileme)%is1(n) - isg(tileme) < whalo )
call mpp_error(fatal, &
7322 "mpp_domains_define.inc: southwest tile for send 2 is not tiled properly")
7323 nums = nums+1; tilesend(nums) = tn
7324 align1send(nums) = north_east; align2send(nums) = south_west
7325 ie1send(nums) = ncont(tileme)%is1(n) - 1; is1send(nums) = ie1send(nums) - whalo + 1
7326 ie1send(nums) = ncont(tileme)%je1(n) ; js1send(nums) = je1send(nums) - shalo + 1
7327 ie2send(nums) = ncont(tileme)%is2(n) - 1; is2send(nums) = je2send(nums) - whalo + 1
7328 je2send(nums) = ncont(tileme)%js2(n) - 1; js2send(nums) = je2send(nums) - shalo + 1
7334 n = econt(tileme)%ncontact
7335 found_corner = .false.
7337 tn = econt(tileme)%tile(n)
7338 if( econt(tileme)%je1(n) == jeg(tileme) .AND. econt(tileme)%je2(n) == jeg(tn) )
then
7339 if(ncont(tn)%ncontact >0)
then
7340 tc = ncont(tn)%tile(1)
7341 if( ncont(tn)%is1(1) == isg(tn) .AND. ncont(tn)%is2(n) == isg(tc) ) found_corner = .true.
7345 if( .not. found_corner )
then
7346 n = ncont(tileme)%ncontact
7348 tn = ncont(tileme)%tile(n)
7349 if( ncont(tileme)%ie1(n) == ieg(tileme) .AND. ncont(tileme)%ie2(n) == ieg(tn) )
then
7350 if(econt(tn)%ncontact >0)
then
7351 tc = econt(tn)%tile(1)
7352 if( econt(tn)%js1(1) == jsg(tn) .AND. econt(tn)%js2(n) == jsg(tc) ) found_corner = .true.
7358 if(found_corner)
then
7359 nums = nums+1; tilesend(nums) = tc
7360 align1send(nums) = north_east; align2send(nums) = south_west
7361 ie1send(nums) = ieg(tileme); is1send(nums) = ie1send(nums) - whalo + 1
7362 je1send(nums) = jeg(tileme); js1send(nums) = je1send(nums) - shalo + 1
7363 ie2send(nums) = isg(tc) - 1; is2send(nums) = ie2send(nums) - whalo + 1
7364 je2send(nums) = jsg(tc) - 1; js2send(nums) = je2send(nums) - shalo + 1
7368 do n = 1, econt(tileme)%ncontact
7369 tn = econt(tileme)%tile(n)
7370 if(econt(tileme)%je2(n) == jeg(tn) )
then
7371 if(econt(tileme)%je1(n) < jeg(tileme) )
then
7372 if( jeg(tileme) - econt(tileme)%je1(n) < nhalo )
call mpp_error(fatal, &
7373 "mpp_domains_define.inc: northwest tile for send 1 is not tiled properly")
7374 nums = nums+1; tilesend(nums) = tn
7375 align1send(nums) = south_east; align2send(nums) = north_west
7376 ie1send(nums) = econt(tileme)%ie1(n) ; is1send(nums) = ie1send(nums) - whalo + 1
7377 js1send(nums) = econt(tileme)%je1(n) + 1; je1send(nums) = js1send(nums) + nhalo - 1
7378 ie2send(nums) = econt(tileme)%is2(n) - 1; is2send(nums) = ie2send(nums) - whalo + 1
7379 js2send(nums) = econt(tileme)%je2(n) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7384 do n = 1, scont(tileme)%ncontact
7385 tn = scont(tileme)%tile(n)
7386 if(scont(tileme)%is2(n) == isg(tn) )
then
7387 if(scont(tileme)%is1(n) > isg(tileme) )
then
7388 if( scont(tileme)%is1(n) - isg(tileme) < whalo )
call mpp_error(fatal, &
7389 "mpp_domains_define.inc: southwest tile for send 2 is not tiled properly")
7390 nums = nums+1; tilesend(nums) = tn
7391 align1send(nums) = south_east; align2send(nums) = north_west
7392 ie1send(nums) = ncont(tileme)%is1(n) - 1; is1send(nums) = ie1send(nums) - whalo + 1
7393 js1send(nums) = ncont(tileme)%je1(n) ; je1send(nums) = js1send(nums) + nhalo - 1
7394 ie2send(nums) = ncont(tileme)%is2(n) - 1; is2send(nums) = ie2send(nums) - whalo + 1
7395 js2send(nums) = ncont(tileme)%je2(n) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7401 n = econt(tileme)%ncontact
7402 found_corner = .false.
7404 tn = econt(tileme)%tile(1)
7405 if( econt(tileme)%js1(1) == jsg(tileme) .AND. econt(tileme)%js2(1) == jsg(tn) )
then
7406 if(scont(tn)%ncontact >0)
then
7407 tc = scont(tn)%tile(1)
7408 if( scont(tn)%is1(1) == isg(tn) .AND. scont(tn)%is2(1) == isg(tc) ) found_corner = .true.
7412 if( .not. found_corner )
then
7413 n = scont(tileme)%ncontact
7414 found_corner = .false.
7416 tn = scont(tileme)%tile(n)
7417 if( scont(tileme)%ie1(n) == ieg(tileme) .AND. scont(tileme)%ie2(n) == ieg(tn) )
then
7418 if(econt(tn)%ncontact >0)
then
7419 tc = econt(tn)%tile(n)
7420 if( econt(tn)%je1(n) == jeg(tn) .AND. econt(tn)%je2(n) == jeg(tc) ) found_corner = .true.
7426 if(found_corner)
then
7427 nums = nums+1; tilesend(nums) = tc
7428 align1send(nums) = south_east; align2send(nums) = north_west
7429 ie1send(nums) = ieg(tileme); is1send(nums) = ie1send(nums) - whalo + 1
7430 js1send(nums) = jsg(tileme); je1send(nums) = js1send(nums) + nhalo - 1
7431 ie2send(nums) = isg(tc) - 1; is2send(nums) = ie2send(nums) - whalo + 1
7432 js2send(nums) = jeg(tc) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7436 do n = 1, wcont(tileme)%ncontact
7437 tn = wcont(tileme)%tile(n)
7438 if(wcont(tileme)%je2(n) == jeg(tn) )
then
7439 if(wcont(tileme)%je1(n) < jeg(tileme) )
then
7440 if( jeg(tileme) - wcont(tileme)%je1(n) < nhalo )
call mpp_error(fatal, &
7441 "mpp_domains_define.inc: northeast tile for send 1 is not tiled properly")
7442 nums = nums+1; tilesend(nums) = tn
7443 align1send(nums) = south_west; align2send(nums) = north_east
7444 is1send(nums) = wcont(tileme)%is1(n) ; ie1send(nums) = is1send(nums) + ehalo - 1
7445 js1send(nums) = wcont(tileme)%je1(n) + 1; je1send(nums) = js1send(nums) + nhalo - 1
7446 is2send(nums) = wcont(tileme)%ie2(n) + 1; ie2send(nums) = is2send(nums) + ehalo - 1
7447 js2send(nums) = wcont(tileme)%je2(n) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7452 do n = 1, scont(tileme)%ncontact
7453 tn = scont(tileme)%tile(n)
7454 if(scont(tileme)%ie2(n) == ieg(tn) )
then
7455 if(scont(tileme)%ie1(n) < ieg(tileme) )
then
7456 if( ieg(tileme) - scont(tileme)%ie1(n) < ehalo )
call mpp_error(fatal, &
7457 "mpp_domains_define.inc: southeast tile for send 2 is not tiled properly")
7458 nums = nums+1; tilesend(nums) = tn
7459 align1send(nums) = south_west; align2send(nums) = north_east
7460 is1send(nums) = scont(tileme)%ie1(n) + 1; ie1send(nums) = is1send(nums) + ehalo - 1
7461 js1send(nums) = scont(tileme)%js1(n) ; je1send(nums) = js1send(nums) + nhalo - 1
7462 is2send(nums) = scont(tileme)%ie2(n) + 1; ie2send(nums) = is1send(nums) + ehalo - 1
7463 js2send(nums) = scont(tileme)%je2(n) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7469 n = wcont(tileme)%ncontact
7470 found_corner = .false.
7472 tn = wcont(tileme)%tile(1)
7473 if( wcont(tileme)%js1(n) == jsg(tileme) .AND. wcont(tileme)%js2(n) == jsg(tn) )
then
7474 m = scont(tn)%ncontact
7476 tc = scont(tn)%tile(m)
7477 if( scont(tn)%ie1(m) == ieg(tn) .AND. scont(tn)%ie2(m) == ieg(tc) ) found_corner = .true.
7481 if( .not. found_corner )
then
7482 n = scont(tileme)%ncontact
7483 found_corner = .false.
7485 tn = scont(tileme)%tile(1)
7486 if( scont(tileme)%is1(1) == isg(tileme) .AND. scont(tileme)%is2(1) == isg(tn) )
then
7487 m = wcont(tn)%ncontact
7489 tc = wcont(tn)%tile(m)
7490 if( wcont(tn)%je1(m) == jeg(tn) .AND. wcont(tn)%je2(m) == jeg(tc) ) found_corner = .true.
7495 if(found_corner)
then
7496 nums = nums+1; tilesend(nums) = tc
7497 align1send(nums) = south_west; align2send(nums) = north_east
7498 is1send(nums) = isg(tileme); ie1send(nums) = is1send(nums) + ehalo - 1
7499 js1send(nums) = jsg(tileme); je1send(nums) = js1send(nums) + nhalo - 1
7500 is2send(nums) = ieg(tc) + 1; ie2send(nums) = is2send(nums) + ehalo - 1
7501 js2send(nums) = jeg(tc) + 1; je2send(nums) = js2send(nums) + nhalo - 1
7504 end subroutine fill_corner_contact
7507 subroutine check_alignment( is, ie, js, je, isg, ieg, jsg, jeg, alignment )
7508 integer,
intent(inout) :: is, ie, js, je, isg, ieg, jsg, jeg
7509 integer,
intent(out) :: alignment
7513 if ( is == ie )
then
7514 if ( is == isg )
then
7516 else if ( is == ieg )
then
7519 call mpp_error(fatal,
'mpp_domains_define.inc: The contact region is not on the x-boundary of the tile')
7522 j = js; js = je; je = j
7524 else if ( js == je )
then
7525 if ( js == jsg )
then
7527 else if ( js == jeg )
then
7530 call mpp_error(fatal,
'mpp_domains_define.inc: The contact region is not on the y-boundary of the tile')
7533 i = is; is = ie; ie = i
7536 call mpp_error(fatal,
'mpp_domains_define.inc: The contact region should be line contact' )
7539 end subroutine check_alignment
7551 type(domain1d),
intent(in) :: domain_in
7552 type(domain1d),
intent(inout) :: domain_out
7553 integer,
intent(in),
optional :: hbegin, hend
7554 integer,
intent(in),
optional :: cbegin, cend
7556 integer,
intent(in),
optional :: gbegin, gend
7558 integer :: ndivs, global_indices(2)
7561 global_indices(1) = domain_in%global%begin; global_indices(2) = domain_in%global%end
7564 ndivs =
size(domain_in%list(:))
7568 if(domain_in%cyclic) flag = flag + cyclic_global_domain
7569 if(domain_in%domain_data%is_global) flag = flag + global_data_domain
7571 call mpp_define_domains( global_indices, ndivs, domain_out, pelist = domain_in%list(:)%pe, &
7572 flags = flag, begin_halo = hbegin, end_halo = hend, extent = domain_in%list(:)%compute%size )
7574 if(
present(cbegin)) domain_out%compute%begin = cbegin
7575 if(
present(cend)) domain_out%compute%end = cend
7576 domain_out%compute%size = domain_out%compute%end - domain_out%compute%begin + 1
7577 if(
present(gbegin)) domain_out%global%begin = gbegin
7578 if(
present(gend)) domain_out%global%end = gend
7579 domain_out%global%size = domain_out%global%end - domain_out%global%begin + 1
7585 subroutine mpp_modify_domain2d(domain_in, domain_out, isc, iec, jsc, jec, isg, ieg, jsg, jeg, whalo, ehalo, &
7588 type(domain2d),
intent(in) :: domain_in
7589 type(domain2d),
intent(inout) :: domain_out
7590 integer,
intent(in),
optional :: isc, iec, jsc, jec
7592 integer,
intent(in),
optional :: isg, ieg, jsg, jeg
7594 integer,
intent(in),
optional :: whalo, ehalo, shalo, nhalo
7595 integer :: global_indices(4), layout(2)
7596 integer :: xflag, yflag, nlist, i
7598 if(
present(whalo) .or.
present(ehalo) .or.
present(shalo) .or.
present(nhalo) )
then
7600 global_indices(1) = domain_in%x(1)%global%begin; global_indices(2) = domain_in%x(1)%global%end
7601 global_indices(3) = domain_in%y(1)%global%begin; global_indices(4) = domain_in%y(1)%global%end
7604 layout(1) =
size(domain_in%x(1)%list(:)); layout(2) =
size(domain_in%y(1)%list(:))
7607 xflag = 0; yflag = 0
7608 if(domain_in%x(1)%cyclic) xflag = xflag + cyclic_global_domain
7609 if(domain_in%x(1)%domain_data%is_global) xflag = xflag + global_data_domain
7610 if(domain_in%y(1)%cyclic) yflag = yflag + cyclic_global_domain
7611 if(domain_in%y(1)%domain_data%is_global) yflag = yflag + global_data_domain
7613 call mpp_define_domains( global_indices, layout, domain_out, pelist = domain_in%list(:)%pe, &
7614 xflags = xflag, yflags = yflag, whalo = whalo, ehalo = ehalo, &
7615 shalo = shalo, nhalo = nhalo, &
7616 xextent = domain_in%x(1)%list(:)%compute%size, &
7617 yextent = domain_in%y(1)%list(:)%compute%size, &
7618 symmetry=domain_in%symmetry, &
7619 maskmap = domain_in%pearray .NE. null_pe )
7620 domain_out%ntiles = domain_in%ntiles
7621 domain_out%tile_id = domain_in%tile_id
7623 call mpp_define_null_domain(domain_out)
7624 nlist =
size(domain_in%list(:))
7625 if (
associated(domain_out%list))
deallocate(domain_out%list)
7626 allocate(domain_out%list(0:nlist-1) )
7628 allocate(domain_out%list(i)%tile_id(1))
7629 domain_out%list(i)%tile_id(1) = 1
7631 call mpp_modify_domain(domain_in%x(1), domain_out%x(1), isc, iec, isg, ieg)
7632 call mpp_modify_domain(domain_in%y(1), domain_out%y(1), jsc, jec, jsg, jeg)
7633 domain_out%ntiles = domain_in%ntiles
7634 domain_out%tile_id = domain_in%tile_id
7643 subroutine mpp_define_null_domain1d(domain)
7644 type(domain1d),
intent(inout) :: domain
7646 domain%global%begin = -1; domain%global%end = -1; domain%global%size = 0
7647 domain%domain_data%begin = -1; domain%domain_data%end = -1; domain%domain_data%size = 0
7648 domain%compute%begin = -1; domain%compute%end = -1; domain%compute%size = 0
7651 end subroutine mpp_define_null_domain1d
7656 subroutine mpp_define_null_domain2d(domain)
7657 type(domain2d),
intent(inout) :: domain
7659 allocate(domain%x(1), domain%y(1), domain%tile_id(1))
7660 call mpp_define_null_domain(domain%x(1))
7661 call mpp_define_null_domain(domain%y(1))
7663 domain%tile_id(1) = 1
7665 domain%max_ntile_pe = 1
7666 domain%ncontacts = 0
7668 end subroutine mpp_define_null_domain2d
7672 subroutine mpp_deallocate_domain1d(domain)
7673 type(domain1d),
intent(inout) :: domain
7675 if(
ASSOCIATED(domain%list))
deallocate(domain%list)
7677 end subroutine mpp_deallocate_domain1d
7681 subroutine mpp_deallocate_domain2d(domain)
7682 type(domain2d),
intent(inout) :: domain
7684 call deallocate_domain2d_local(domain)
7685 if(
ASSOCIATED(domain%io_domain) )
then
7686 call deallocate_domain2d_local(domain%io_domain)
7687 deallocate(domain%io_domain)
7690 end subroutine mpp_deallocate_domain2d
7694 subroutine deallocate_domain2d_local(domain)
7695 type(domain2d),
intent(inout) :: domain
7696 integer :: i, ntileMe
7698 ntileme =
size(domain%x(:))
7700 if(
ASSOCIATED(domain%pearray))
deallocate(domain%pearray)
7702 call mpp_deallocate_domain1d(domain%x(i))
7703 call mpp_deallocate_domain1d(domain%y(i))
7705 deallocate(domain%x, domain%y, domain%tile_id)
7708 if(
ASSOCIATED(domain%tileList))
deallocate(domain%tileList)
7709 if(
ASSOCIATED(domain%tile_id_all))
deallocate(domain%tile_id_all)
7711 if(
ASSOCIATED(domain%list))
then
7712 do i = 0,
size(domain%list(:))-1
7713 deallocate(domain%list(i)%x, domain%list(i)%y, domain%list(i)%tile_id)
7715 deallocate(domain%list)
7718 if(
ASSOCIATED(domain%check_C))
then
7719 call deallocate_overlapspec(domain%check_C)
7720 deallocate(domain%check_C)
7723 if(
ASSOCIATED(domain%check_E))
then
7724 call deallocate_overlapspec(domain%check_E)
7725 deallocate(domain%check_E)
7728 if(
ASSOCIATED(domain%check_N))
then
7729 call deallocate_overlapspec(domain%check_N)
7730 deallocate(domain%check_N)
7733 if(
ASSOCIATED(domain%bound_C))
then
7734 call deallocate_overlapspec(domain%bound_C)
7735 deallocate(domain%bound_C)
7738 if(
ASSOCIATED(domain%bound_E))
then
7739 call deallocate_overlapspec(domain%bound_E)
7740 deallocate(domain%bound_E)
7743 if(
ASSOCIATED(domain%bound_N))
then
7744 call deallocate_overlapspec(domain%bound_N)
7745 deallocate(domain%bound_N)
7748 if(
ASSOCIATED(domain%update_T))
then
7749 call deallocate_overlapspec(domain%update_T)
7750 deallocate(domain%update_T)
7753 if(
ASSOCIATED(domain%update_E))
then
7754 call deallocate_overlapspec(domain%update_E)
7755 deallocate(domain%update_E)
7758 if(
ASSOCIATED(domain%update_C))
then
7759 call deallocate_overlapspec(domain%update_C)
7760 deallocate(domain%update_C)
7763 if(
ASSOCIATED(domain%update_N))
then
7764 call deallocate_overlapspec(domain%update_N)
7765 deallocate(domain%update_N)
7768 end subroutine deallocate_domain2d_local
7772 subroutine allocate_check_overlap(overlap, count)
7773 type(overlap_type),
intent(inout) :: overlap
7774 integer,
intent(in ) :: count
7777 overlap%pe = null_pe
7778 if(
associated(overlap%tileMe))
call mpp_error(fatal, &
7779 "allocate_check_overlap(mpp_domains_define): overlap is already been allocated")
7780 if(count < 1)
call mpp_error(fatal, &
7781 "allocate_check_overlap(mpp_domains_define): count should be a positive integer")
7782 allocate(overlap%tileMe (count), overlap%dir(count) )
7783 allocate(overlap%is (count), overlap%ie (count) )
7784 allocate(overlap%js (count), overlap%je (count) )
7785 allocate(overlap%rotation(count) )
7786 overlap%rotation = zero
7788 end subroutine allocate_check_overlap
7791 subroutine insert_check_overlap(overlap, pe, tileMe, dir, rotation, is, ie, js, je)
7792 type(overlap_type),
intent(inout) :: overlap
7793 integer,
intent(in ) :: pe
7794 integer,
intent(in ) :: tileMe, dir, rotation
7795 integer,
intent(in ) :: is, ie, js, je
7798 overlap%count = overlap%count + 1
7799 count = overlap%count
7800 if(.NOT.
associated(overlap%tileMe))
call mpp_error(fatal, &
7801 "mpp_domains_define.inc(insert_check_overlap): overlap is not assigned any memory")
7802 if(count >
size(overlap%tileMe(:)) )
call mpp_error(fatal, &
7803 "mpp_domains_define.inc(insert_check_overlap): overlap%count is greater than size(overlap%tileMe)")
7804 if( overlap%pe == null_pe )
then
7807 if(overlap%pe .NE. pe)
call mpp_error(fatal, &
7808 "mpp_domains_define.inc(insert_check_overlap): mismatch on pe")
7810 overlap%tileMe (count) = tileme
7811 overlap%dir (count) = dir
7812 overlap%rotation(count) = rotation
7813 overlap%is (count) = is
7814 overlap%ie (count) = ie
7815 overlap%js (count) = js
7816 overlap%je (count) = je
7818 end subroutine insert_check_overlap
7823 type(overlap_type),
intent(inout) :: overlap_out
7824 type(overlap_type),
intent(in ) :: overlap_in
7825 type(overlap_type) :: overlap
7826 integer :: count, count_in, count_out
7829 count_in = overlap_in %count
7830 count_out = overlap_out%count
7831 count = count_in+count_out
7832 if(count_in == 0)
call mpp_error(fatal, &
7833 "add_check_overlap(mpp_domains_define): overlap_in%count is zero")
7835 if(count_out == 0)
then
7836 if(
associated(overlap_out%tileMe))
call mpp_error(fatal, &
7837 "add_check_overlap(mpp_domains_define): overlap is already been allocated but count=0")
7838 call allocate_check_overlap(overlap_out, count_in)
7839 overlap_out%pe = overlap_in%pe
7841 call allocate_check_overlap(overlap, count_out)
7842 if(overlap_out%pe .NE. overlap_in%pe)
call mpp_error(fatal, &
7843 "mpp_domains_define.inc(add_check_overlap): mismatch of pe between overlap_in and overlap_out")
7844 overlap%tileMe (1:count_out) = overlap_out%tileMe (1:count_out)
7845 overlap%is (1:count_out) = overlap_out%is (1:count_out)
7846 overlap%ie (1:count_out) = overlap_out%ie (1:count_out)
7847 overlap%js (1:count_out) = overlap_out%js (1:count_out)
7848 overlap%je (1:count_out) = overlap_out%je (1:count_out)
7849 overlap%dir (1:count_out) = overlap_out%dir (1:count_out)
7850 overlap%rotation (1:count_out) = overlap_out%rotation (1:count_out)
7851 call deallocate_overlap_type(overlap_out)
7852 call allocate_check_overlap(overlap_out, count)
7853 overlap_out%tileMe (1:count_out) = overlap%tileMe (1:count_out)
7854 overlap_out%is (1:count_out) = overlap%is (1:count_out)
7855 overlap_out%ie (1:count_out) = overlap%ie (1:count_out)
7856 overlap_out%js (1:count_out) = overlap%js (1:count_out)
7857 overlap_out%je (1:count_out) = overlap%je (1:count_out)
7858 overlap_out%dir (1:count_out) = overlap%dir (1:count_out)
7859 overlap_out%rotation (1:count_out) = overlap%rotation (1:count_out)
7860 call deallocate_overlap_type(overlap)
7862 overlap_out%count = count
7863 overlap_out%tileMe (count_out+1:count) = overlap_in%tileMe (1:count_in)
7864 overlap_out%is (count_out+1:count) = overlap_in%is (1:count_in)
7865 overlap_out%ie (count_out+1:count) = overlap_in%ie (1:count_in)
7866 overlap_out%js (count_out+1:count) = overlap_in%js (1:count_in)
7867 overlap_out%je (count_out+1:count) = overlap_in%je (1:count_in)
7868 overlap_out%dir (count_out+1:count) = overlap_in%dir (1:count_in)
7869 overlap_out%rotation (count_out+1:count) = overlap_in%rotation (1:count_in)
7874 subroutine init_overlap_type(overlap)
7875 type(overlap_type),
intent(inout) :: overlap
7878 overlap%pe = null_pe
7880 end subroutine init_overlap_type
7884 subroutine allocate_update_overlap( overlap, count)
7885 type(overlap_type),
intent(inout) :: overlap
7886 integer,
intent(in ) :: count
7889 overlap%pe = null_pe
7890 if(
associated(overlap%tileMe))
call mpp_error(fatal, &
7891 "allocate_update_overlap(mpp_domains_define): overlap is already been allocated")
7892 if(count < 1)
call mpp_error(fatal, &
7893 "allocate_update_overlap(mpp_domains_define): count should be a positive integer")
7894 allocate(overlap%tileMe (count), overlap%tileNbr (count) )
7895 allocate(overlap%is (count), overlap%ie (count) )
7896 allocate(overlap%js (count), overlap%je (count) )
7897 allocate(overlap%dir (count), overlap%rotation(count) )
7898 allocate(overlap%from_contact(count), overlap%msgsize (count) )
7899 overlap%rotation = zero
7900 overlap%from_contact = .false.
7902 end subroutine allocate_update_overlap
7905 subroutine insert_update_overlap(overlap, pe, is1, ie1, js1, je1, is2, ie2, js2, je2, dir, reverse, symmetry)
7906 type(overlap_type),
intent(inout) :: overlap
7907 integer,
intent(in ) :: pe
7908 integer,
intent(in ) :: is1, ie1, js1, je1, is2, ie2, js2, je2
7909 integer,
intent(in ) :: dir
7910 logical,
optional,
intent(in ) :: reverse, symmetry
7912 logical :: is_reverse, is_symmetry, is_overlapped
7913 integer :: is, ie, js, je, count
7915 is_reverse = .false.
7916 if(
PRESENT(reverse)) is_reverse = reverse
7917 is_symmetry = .false.
7918 if(
PRESENT(symmetry)) is_symmetry = symmetry
7920 is = max(is1,is2); ie = min(ie1,ie2)
7921 js = max(js1,js2); je = min(je1,je2)
7922 is_overlapped = .false.
7924 if(is_symmetry .AND. (dir == 1 .OR. dir == 5))
then
7925 if( ie .GE. is .AND. je .GT. js ) is_overlapped = .true.
7926 else if(is_symmetry .AND. (dir == 3 .OR. dir == 7))
then
7927 if( ie .GT. is .AND. je .GE. js ) is_overlapped = .true.
7928 else if(ie.GE.is .AND. je.GE.js )
then
7929 is_overlapped = .true.
7932 if(is_overlapped)
then
7933 if( overlap%count == 0 )
then
7936 if(overlap%pe .NE. pe)
call mpp_error(fatal, &
7937 "mpp_domains_define.inc(insert_update_overlap): mismatch on pe")
7939 overlap%count = overlap%count+1
7940 count = overlap%count
7941 if(count > maxoverlap)
call mpp_error(fatal,
"mpp_domains_define.inc(insert_update_overlap):"//&
7942 &
" number of overlap is greater than MAXOVERLAP, increase MAXOVERLAP")
7943 overlap%is(count) = is
7944 overlap%ie(count) = ie
7945 overlap%js(count) = js
7946 overlap%je(count) = je
7947 overlap%tileMe (count) = 1
7948 overlap%tileNbr(count) = 1
7949 overlap%dir(count) = dir
7951 overlap%rotation(count) = one_hundred_eighty
7953 overlap%rotation(count) = zero
7957 end subroutine insert_update_overlap
7960 subroutine insert_overlap_type(overlap, pe, tileMe, tileNbr, is, ie, js, je, dir, &
7961 rotation, from_contact)
7962 type(overlap_type),
intent(inout) :: overlap
7963 integer,
intent(in ) :: tileMe, tileNbr, pe
7964 integer,
intent(in ) :: is, ie, js, je
7965 integer,
intent(in ) :: dir, rotation
7966 logical,
intent(in ) :: from_contact
7969 if( overlap%count == 0 )
then
7972 if(overlap%pe .NE. pe)
call mpp_error(fatal, &
7973 "mpp_domains_define.inc(insert_overlap_type): mismatch on pe")
7975 overlap%count = overlap%count+1
7976 count = overlap%count
7977 if(count > maxoverlap)
call mpp_error(fatal,
"mpp_domains_define.inc(insert_overlap_type):"//&
7978 &
" number of overlap is greater than MAXOVERLAP, increase MAXOVERLAP")
7979 overlap%tileMe (count) = tileme
7980 overlap%tileNbr (count) = tilenbr
7981 overlap%is (count) = is
7982 overlap%ie (count) = ie
7983 overlap%js (count) = js
7984 overlap%je (count) = je
7985 overlap%dir (count) = dir
7986 overlap%rotation (count) = rotation
7987 overlap%from_contact(count) = from_contact
7988 overlap%msgsize (count) = (ie-is+1)*(je-js+1)
7990 end subroutine insert_overlap_type
7994 subroutine deallocate_overlap_type( overlap)
7995 type(overlap_type),
intent(inout) :: overlap
7997 if(overlap%count == 0)
then
7998 if( .NOT.
associated(overlap%tileMe))
return
8000 if( .NOT.
associated(overlap%tileMe))
call mpp_error(fatal, &
8001 "deallocate_overlap_type(mpp_domains_define): overlap is not been allocated")
8003 if(
ASSOCIATED(overlap%tileMe))
deallocate(overlap%tileMe)
8004 if(
ASSOCIATED(overlap%tileNbr))
deallocate(overlap%tileNbr)
8005 if(
ASSOCIATED(overlap%is))
deallocate(overlap%is)
8006 if(
ASSOCIATED(overlap%ie))
deallocate(overlap%ie)
8007 if(
ASSOCIATED(overlap%js))
deallocate(overlap%js)
8008 if(
ASSOCIATED(overlap%je))
deallocate(overlap%je)
8009 if(
ASSOCIATED(overlap%dir))
deallocate(overlap%dir)
8010 if(
ASSOCIATED(overlap%index))
deallocate(overlap%index)
8011 if(
ASSOCIATED(overlap%rotation))
deallocate(overlap%rotation)
8012 if(
ASSOCIATED(overlap%from_contact))
deallocate(overlap%from_contact)
8013 if(
ASSOCIATED(overlap%msgsize))
deallocate(overlap%msgsize)
8016 end subroutine deallocate_overlap_type
8019 subroutine deallocate_overlapspec(overlap)
8020 type(overlapspec),
intent(inout) :: overlap
8023 if(
ASSOCIATED(overlap%send))
then
8024 do n = 1,
size(overlap%send(:))
8025 call deallocate_overlap_type(overlap%send(n))
8027 deallocate(overlap%send)
8029 if(
ASSOCIATED(overlap%recv))
then
8030 do n = 1,
size(overlap%recv(:))
8031 call deallocate_overlap_type(overlap%recv(n))
8033 deallocate(overlap%recv)
8037 end subroutine deallocate_overlapspec
8041 subroutine add_update_overlap( overlap_out, overlap_in)
8042 type(overlap_type),
intent(inout) :: overlap_out
8043 type(overlap_type),
intent(in ) :: overlap_in
8044 type(overlap_type) :: overlap
8045 integer :: count, count_in, count_out, n
8048 count_in = overlap_in %count
8049 count_out = overlap_out%count
8050 count = count_in+count_out
8051 if(count_in == 0)
call mpp_error(fatal, &
8052 "mpp_domains_define.inc(add_update_overlap): overlap_in%count is zero")
8054 if(count_out == 0)
then
8055 if(
associated(overlap_out%tileMe))
call mpp_error(fatal, &
8056 "mpp_domains_define.inc(add_update_overlap): overlap is already been allocated but count=0")
8057 call allocate_update_overlap(overlap_out, count_in)
8058 overlap_out%pe = overlap_in%pe
8060 if(overlap_in%pe .NE. overlap_out%pe)
call mpp_error(fatal, &
8061 "mpp_domains_define.inc(add_update_overlap): mismatch of pe between overlap_in and overlap_out")
8063 call allocate_update_overlap(overlap, count_out)
8064 overlap%tileMe (1:count_out) = overlap_out%tileMe (1:count_out)
8065 overlap%tileNbr (1:count_out) = overlap_out%tileNbr (1:count_out)
8066 overlap%is (1:count_out) = overlap_out%is (1:count_out)
8067 overlap%ie (1:count_out) = overlap_out%ie (1:count_out)
8068 overlap%js (1:count_out) = overlap_out%js (1:count_out)
8069 overlap%je (1:count_out) = overlap_out%je (1:count_out)
8070 overlap%dir (1:count_out) = overlap_out%dir (1:count_out)
8071 overlap%rotation (1:count_out) = overlap_out%rotation (1:count_out)
8072 overlap%from_contact(1:count_out) = overlap_out%from_contact(1:count_out)
8073 call deallocate_overlap_type(overlap_out)
8074 call allocate_update_overlap(overlap_out, count)
8075 overlap_out%tileMe (1:count_out) = overlap%tileMe (1:count_out)
8076 overlap_out%tileNbr (1:count_out) = overlap%tileNbr (1:count_out)
8077 overlap_out%is (1:count_out) = overlap%is (1:count_out)
8078 overlap_out%ie (1:count_out) = overlap%ie (1:count_out)
8079 overlap_out%js (1:count_out) = overlap%js (1:count_out)
8080 overlap_out%je (1:count_out) = overlap%je (1:count_out)
8081 overlap_out%dir (1:count_out) = overlap%dir (1:count_out)
8082 overlap_out%rotation (1:count_out) = overlap%rotation (1:count_out)
8083 overlap_out%index (1:count_out) = overlap%index (1:count_out)
8084 overlap_out%from_contact(1:count_out) = overlap%from_contact(1:count_out)
8085 overlap_out%msgsize (1:count_out) = overlap%msgsize (1:count_out)
8086 call deallocate_overlap_type(overlap)
8088 overlap_out%count = count
8089 overlap_out%tileMe (count_out+1:count) = overlap_in%tileMe (1:count_in)
8090 overlap_out%tileNbr (count_out+1:count) = overlap_in%tileNbr (1:count_in)
8091 overlap_out%is (count_out+1:count) = overlap_in%is (1:count_in)
8092 overlap_out%ie (count_out+1:count) = overlap_in%ie (1:count_in)
8093 overlap_out%js (count_out+1:count) = overlap_in%js (1:count_in)
8094 overlap_out%je (count_out+1:count) = overlap_in%je (1:count_in)
8095 overlap_out%dir (count_out+1:count) = overlap_in%dir (1:count_in)
8096 overlap_out%rotation (count_out+1:count) = overlap_in%rotation (1:count_in)
8097 overlap_out%from_contact(count_out+1:count) = overlap_in%from_contact(1:count_in)
8099 do n = count_out+1, count
8100 overlap_out%msgsize(n) = (overlap_out%ie(n)-overlap_out%is(n)+1)*(overlap_out%je(n)-overlap_out%js(n)+1)
8104 end subroutine add_update_overlap
8107 subroutine expand_update_overlap_list(overlapList, npes)
8108 type(overlap_type),
pointer :: overlapList(:)
8109 integer,
intent(in ) :: npes
8110 type(overlap_type),
pointer,
save :: newlist(:) => null()
8111 integer :: nlist_old, nlist, m
8113 nlist_old =
size(overlaplist(:))
8114 if(nlist_old .GE. npes)
call mpp_error(fatal, &
8115 'mpp_domains_define.inc(expand_update_overlap_list): size of overlaplist should be smaller than npes')
8116 nlist = min(npes, 2*nlist_old)
8117 allocate(newlist(nlist))
8119 call add_update_overlap(newlist(m), overlaplist(m))
8120 call deallocate_overlap_type(overlaplist(m))
8123 deallocate(overlaplist)
8124 overlaplist => newlist
8129 end subroutine expand_update_overlap_list
8132 subroutine expand_check_overlap_list(overlaplist, npes)
8133 type(overlap_type),
pointer :: overlaplist(:)
8134 integer,
intent(in) :: npes
8135 type(overlap_type),
pointer,
save :: newlist(:) => null()
8136 integer :: nlist_old, nlist, m
8138 nlist_old =
size(overlaplist(:))
8139 if(nlist_old .GE. npes)
call mpp_error(fatal, &
8140 'mpp_domains_define.inc(expand_check_overlap_list): size of overlaplist should be smaller than npes')
8141 nlist = min(npes, 2*nlist_old)
8142 allocate(newlist(nlist))
8143 do m = 1,
size(overlaplist(:))
8145 call deallocate_overlap_type(overlaplist(m))
8147 deallocate(overlaplist)
8148 overlaplist => newlist
8153 end subroutine expand_check_overlap_list
8157 subroutine check_overlap_pe_order(domain, overlap, name)
8158 type(domain2d),
intent(in) :: domain
8159 type(overlapspec),
intent(in) :: overlap
8160 character(len=*),
intent(in) :: name
8165 if( overlap%nsend > maxlist)
call mpp_error(fatal, &
8166 "mpp_domains_define.inc(check_overlap_pe_order): overlap%nsend > MAXLIST, increase MAXLIST")
8167 if( overlap%nrecv > maxlist)
call mpp_error(fatal, &
8168 "mpp_domains_define.inc(check_overlap_pe_order): overlap%nrecv > MAXLIST, increase MAXLIST")
8170 do m = 2, overlap%nsend
8171 pe1 = overlap%send(m-1)%pe
8172 pe2 = overlap%send(m)%pe
8174 if( pe2 == domain%pe )
then
8175 print*, trim(name)//
" at pe = ", domain%pe,
": send pe is ", pe1, pe2
8176 call mpp_error(fatal, &
8177 "mpp_domains_define.inc(check_overlap_pe_order): send pe2 can not equal to domain%pe")
8178 else if( (pe1 > domain%pe .AND. pe2 > domain%pe) .OR. (pe1 < domain%pe .AND. pe2 < domain%pe))
then
8179 if( pe2 < pe1 )
then
8180 print*, trim(name)//
" at pe = ", domain%pe,
": send pe is ", pe1, pe2
8181 call mpp_error(fatal, &
8182 "mpp_domains_define.inc(check_overlap_pe_order): pe is not in right order for send 1")
8184 else if ( pe2 > domain%pe .AND. pe1 < domain%pe )
then
8185 print*, trim(name)//
" at pe = ", domain%pe,
": send pe is ", pe1, pe2
8186 call mpp_error(fatal, &
8187 "mpp_domains_define.inc(check_overlap_pe_order): pe is not in right order for send 2")
8192 do m = 2, overlap%nrecv
8193 pe1 = overlap%recv(m-1)%pe
8194 pe2 = overlap%recv(m)%pe
8196 if( pe2 == domain%pe )
then
8197 print*, trim(name)//
" at pe = ", domain%pe,
": recv pe is ", pe1, pe2
8198 call mpp_error(fatal, &
8199 "mpp_domains_define.inc(check_overlap_pe_order): recv pe2 can not equal to domain%pe")
8200 else if( (pe1 > domain%pe .AND. pe2 > domain%pe) .OR. (pe1 < domain%pe .AND. pe2 < domain%pe))
then
8201 if( pe2 > pe1 )
then
8202 print*, trim(name)//
" at pe = ", domain%pe,
": recv pe is ", pe1, pe2
8203 call mpp_error(fatal, &
8204 "mpp_domains_define.inc(check_overlap_pe_order): pe is not in right order for recv 1")
8206 else if ( pe2 < domain%pe .AND. pe1 > domain%pe )
then
8207 print*, trim(name)//
" at pe = ", domain%pe,
": recv pe is ", pe1, pe2
8208 call mpp_error(fatal, &
8209 "mpp_domains_define.inc(check_overlap_pe_order): pe is not in right order for recv 2")
8214 end subroutine check_overlap_pe_order
8218 subroutine set_domain_comm_inf(update)
8219 type(overlapspec),
intent(inout) :: update
8221 integer :: m, totsize, n
8227 do m = 1, update%nrecv
8229 do n = 1, update%recv(m)%count
8230 totsize = totsize + update%recv(m)%msgsize(n)
8232 update%recv(m)%totsize = totsize
8234 update%recv(m)%start_pos = 0
8236 update%recv(m)%start_pos = update%recv(m-1)%start_pos + update%recv(m-1)%totsize
8238 update%recvsize = update%recvsize + totsize
8241 do m = 1, update%nsend
8243 do n = 1, update%send(m)%count
8244 totsize = totsize + update%send(m)%msgsize(n)
8246 update%send(m)%totsize = totsize
8248 update%send(m)%start_pos = 0
8250 update%send(m)%start_pos = update%send(m-1)%start_pos + update%send(m-1)%totsize
8252 update%sendsize = update%sendsize + totsize
8258 end subroutine set_domain_comm_inf
subroutine mpp_modify_domain2d(domain_in, domain_out, isc, iec, jsc, jec, isg, ieg, jsg, jeg, whalo, ehalo, shalo, nhalo)
subroutine define_contact_point(domain, position, num_contact, tile1, tile2, align1, align2, refine1, refine2, istart1, iend1, jstart1, jend1, istart2, iend2, jstart2, jend2, isgList, iegList, jsgList, jegList, tile_base)
compute the overlapping between tiles for the T-cell.
subroutine set_check_overlap(domain, position)
set up the overlapping for boundary check if the domain is symmetry. The check will be done on curren...
subroutine apply_cyclic_offset(lstart, lend, offset, gstart, gend, gsize)
add offset to the index
logical function mpp_mosaic_defined()
Accessor function for value of mosaic_defined.
subroutine set_contact_point(domain, position)
this routine sets the overlapping between tiles for E,C,N-cell based on T-cell overlapping
subroutine mpp_define_domains1d(global_indices, ndivs, domain, pelist, flags, halo, extent, maskmap, memory_size, begin_halo, end_halo)
Define data and computational domains on a 1D set of data (isg:ieg) and assign them to PEs.
subroutine set_bound_overlap(domain, position)
set up the overlapping for boundary if the domain is symmetry.
subroutine mpp_define_mosaic_pelist(sizes, pe_start, pe_end, pelist, costpertile)
Defines a pelist for use with mosaic tiles.
subroutine mpp_define_io_domain(domain, io_layout)
Define the layout for IO pe's for the given domain.
subroutine mpp_compute_extent(isg, ieg, ndivs, ibegin, iend, extent)
Computes extents for a grid decomposition with the given indices and divisions.
subroutine mpp_modify_domain1d(domain_in, domain_out, cbegin, cend, gbegin, gend, hbegin, hend)
Modifies the exents of a domain.
subroutine compute_overlaps_fold_west(domain, position, ishift, jshift)
Computes remote domain overlaps assumes only one in each direction will calculate the overlapping for...
subroutine mpp_define_mosaic(global_indices, layout, domain, num_tile, num_contact, tile1, tile2, istart1, iend1, jstart1, jend1, istart2, iend2, jstart2, jend2, pe_start, pe_end, pelist, whalo, ehalo, shalo, nhalo, xextent, yextent, maskmap, name, memory_size, symmetry, xflags, yflags, tile_id)
Defines a domain for mosaic tile grids.
subroutine fill_contact(Contact, tile, is1, ie1, js1, je1, is2, ie2, js2, je2, align1, align2, refine1, refine2)
always fill the contact according to index order.
subroutine mpp_define_layout2d(global_indices, ndivs, layout)
subroutine add_check_overlap(overlap_out, overlap_in)
this routine adds the overlap_in into overlap_out
subroutine mpp_compute_block_extent(isg, ieg, ndivs, ibegin, iend)
Computes the extents of a grid block.
subroutine compute_overlaps(domain, position, update, check, ishift, jshift, x_cyclic_offset, y_cyclic_offset, whalo, ehalo, shalo, nhalo)
Computes remote domain overlaps.
subroutine mpp_get_domain_shift(domain, ishift, jshift, position)
Returns the shift value in x and y-direction according to domain position..
subroutine compute_overlaps_fold_east(domain, position, ishift, jshift)
computes remote domain overlaps assumes only one in each direction will calculate the overlapping for...
subroutine compute_overlaps_fold_south(domain, position, ishift, jshift)
Computes remote domain overlaps assumes only one in each direction will calculate the overlapping for...
subroutine set_overlaps(domain, overlap_in, overlap_out, whalo_out, ehalo_out, shalo_out, nhalo_out)
this routine sets up the overlapping for mpp_update_domains for arbitrary halo update....
subroutine mpp_define_domains2d(global_indices, layout, domain, pelist, xflags, yflags, xhalo, yhalo, xextent, yextent, maskmap, name, symmetry, memory_size, whalo, ehalo, shalo, nhalo, is_mosaic, tile_count, tile_id, complete, x_cyclic_offset, y_cyclic_offset)
Define 2D data and computational domain on global rectilinear cartesian domain (isg:ieg,...
subroutine mpp_sync_self(pelist, check, request, msg_size, msg_type)
This is to check if current PE's outstanding puts are complete but we can't use shmem_fence because w...
integer function stdout()
This function returns the current standard fortran unit numbers for output.
integer function stderr()
This function returns the current standard fortran unit numbers for error messages.
integer function stdlog()
This function returns the current standard fortran unit numbers for log messages. Log messages,...
integer function mpp_npes()
Returns processor count for current pelist.
integer function mpp_pe()
Returns processor ID.