Newer
Older
!SFX_LIC Copyright 1994-2014 CNRS, Meteo-France and Universite Paul Sabatier
!SFX_LIC This is part of the SURFEX software governed by the CeCILL-C licence
!SFX_LIC version 1. See LICENSE, CeCILL-C_V1-en.txt and CeCILL-C_V1-fr.txt
!SFX_LIC for details. version 1.
!----------------------------------------------------
!! MODIFICATIONS
!! -------------
!! Original
!! J.Escobar 10/06/2013: replace DOUBLE PRECISION by REAL to handle problem for promotion of real on IBM SP
!----------------------------------------------------
!
INTERFACE GATHER_AND_WRITE_MPI
!
SUBROUTINE GATHER_AND_WRITE_MPI_N1D(KWORK,KWORK2,KMASK)
!
INTEGER, DIMENSION(:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N1D
!
SUBROUTINE GATHER_AND_WRITE_MPI_N2D(KWORK,KWORK2,KMASK)
!
INTEGER, DIMENSION(:,:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:,:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N2D
!
SUBROUTINE GATHER_AND_WRITE_MPI_N3D(KWORK,KWORK2,KMASK)
!
INTEGER, DIMENSION(:,:,:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:,:,:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N3D
!
SUBROUTINE GATHER_AND_WRITE_MPI_X1D(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:), INTENT(IN) :: PWORK
REAL(KIND=8), DIMENSION(:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X1D
!
SUBROUTINE GATHER_AND_WRITE_MPI_X2D(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:,:), INTENT(IN) :: PWORK
REAL(KIND=8), DIMENSION(:,:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X2D
!
SUBROUTINE GATHER_AND_WRITE_MPI_X3D(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:,:,:), INTENT(IN) :: PWORK
REAL(KIND=8), DIMENSION(:,:,:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X3D
!

WAUTELET Philippe
committed
#ifndef MNH_SP4
SUBROUTINE GATHER_AND_WRITE_MPI_X1DK4(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:), INTENT(IN) :: PWORK
REAL(KIND=4), DIMENSION(:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X1DK4
!
SUBROUTINE GATHER_AND_WRITE_MPI_X2DK4(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:,:), INTENT(IN) :: PWORK
REAL(KIND=4), DIMENSION(:,:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X2DK4
!
SUBROUTINE GATHER_AND_WRITE_MPI_X3DK4(PWORK,PWORK2,KMASK)
!
REAL, DIMENSION(:,:,:), INTENT(IN) :: PWORK
REAL(KIND=4), DIMENSION(:,:,:), INTENT(OUT) :: PWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X3DK4

WAUTELET Philippe
committed
#endif
!
END INTERFACE
!
END MODULE MODI_GATHER_AND_WRITE_MPI
!
SUBROUTINE GATHER_AND_WRITE_MPI_N1D(KWORK,KWORK2,KMASK)
!
USE MODD_SURFEX_MPI, ONLY : NINDEX, NPROC, NRANK, NCOMM, NPIO, NSIZE, &
XTIME_CALC_WRITE, XTIME_COMM_WRITE, &
!
USE MODI_UNPACK_SAME_RANK
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
INCLUDE "mpif.h"
#endif
!
INTEGER, DIMENSION(:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
INTEGER, DIMENSION(NSIZE) :: IINTER
INTEGER, DIMENSION(MPI_STATUS_SIZE) :: ISTATUS
#endif
INTEGER :: ICPT
INTEGER :: I,J, IP1, IS1
INTEGER :: INFOMPI
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE, ZHOOK_HANDLE_OMP
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N1D',0,ZHOOK_HANDLE)
!
XTIME0 = MPI_WTIME()
#endif
!
IF (PRESENT(KMASK)) THEN
CALL UNPACK_SAME_RANK(KMASK,KWORK,IWORK(:))
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
#endif
!
IF (NRANK/=NPIO) THEN
!
IDX_W = IDX_W + 1
!
CALL MPI_SEND(IWORK,SIZE(IWORK)*KIND(IWORK)/4,MPI_INTEGER,NPIO,IDX_W,NCOMM,INFOMPI)
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
#endif
!
ELSE
!
CALL MPI_RECV(IINTER,SIZE(IINTER)*KIND(IINTER)/4,MPI_INTEGER,I,IDX_W,NCOMM,ISTATUS,INFOMPI)
#endif
ELSE
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
!
ICPT = 0
!
DO J=1,SIZE(NINDEX)
!
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
!
ENDDO
!
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N1D',1,ZHOOK_HANDLE)
!
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N1D
!
!**************************************************************************
!
SUBROUTINE GATHER_AND_WRITE_MPI_N2D(KWORK,KWORK2,KMASK)
!
USE MODD_SURFEX_MPI, ONLY : NINDEX, NPROC, NRANK, NCOMM, NPIO, NSIZE, &
XTIME_CALC_WRITE, XTIME_COMM_WRITE, &
!
USE MODI_UNPACK_SAME_RANK
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
#ifdef SFX_MPI
INCLUDE "mpif.h"
#endif
!
INTEGER, DIMENSION(:,:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:,:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
INTEGER, DIMENSION(NSIZE,SIZE(KWORK2,2)) :: IINTER
INTEGER, DIMENSION(NSIZE,SIZE(KWORK2,2)) :: IWORK
REAL :: XTIME0
!
#ifdef SFX_MPI
INTEGER, DIMENSION(MPI_STATUS_SIZE) :: ISTATUS
#endif
INTEGER :: I,J
INTEGER :: INFOMPI
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N2D',0,ZHOOK_HANDLE)
!
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
#endif
!
IF (SIZE(KWORK,1)>0) THEN
IF (PRESENT(KMASK)) THEN
CALL UNPACK_SAME_RANK(KMASK,KWORK,IWORK(:,:))
ENDIF
ENDIF
!
#ifdef SFX_MPI
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
#endif
!
IF (NRANK/=NPIO) THEN
!
IDX_W = IDX_W + 1
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
CALL MPI_SEND(IWORK(:,:),SIZE(IWORK)*KIND(IWORK)/4,MPI_INTEGER,NPIO,IDX_W,NCOMM,INFOMPI)
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
#endif
!
ELSE
!
IDX_W = IDX_W + 1
!
DO I=1,NPROC
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
#endif
!
IF (I<NPROC) THEN
#ifdef SFX_MPI
CALL MPI_RECV(IINTER,SIZE(IINTER)*KIND(IINTER)/4,MPI_INTEGER,I,IDX_W,NCOMM,ISTATUS,INFOMPI)
#endif
ELSE
ENDIF
!
#ifdef SFX_MPI
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
#endif
!
ICPT = 0
!
DO J=1,SIZE(NINDEX)
!
IF ( NINDEX(J)==MOD(I,NPROC) ) THEN
ICPT = ICPT + 1
ENDIF
!
ENDDO
!
#ifdef SFX_MPI
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
#endif
!
ENDDO
!
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N2D',1,ZHOOK_HANDLE)
!
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N2D
!
!**************************************************************************
!
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
SUBROUTINE GATHER_AND_WRITE_MPI_N3D(KWORK,KWORK2,KMASK)
!
USE MODD_SURFEX_MPI, ONLY : NINDEX, NPROC, NRANK, NCOMM, NPIO, NSIZE, &
XTIME_CALC_WRITE, XTIME_COMM_WRITE, &
IDX_W, WLOG_MPI
!
USE MODI_UNPACK_SAME_RANK
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
#ifdef SFX_MPI
INCLUDE "mpif.h"
#endif
!
INTEGER, DIMENSION(:,:,:), INTENT(IN) :: KWORK
INTEGER, DIMENSION(:,:,:), INTENT(OUT) :: KWORK2
!
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
INTEGER, DIMENSION(NSIZE,SIZE(KWORK2,2),SIZE(KWORK2,3)) :: IINTER
INTEGER, DIMENSION(NSIZE,SIZE(KWORK,2),SIZE(KWORK,3)) :: IWORK
!
DOUBLE PRECISION :: XTIME0
!
#ifdef SFX_MPI
INTEGER, DIMENSION(MPI_STATUS_SIZE) :: ISTATUS
#endif
INTEGER :: ICPT
INTEGER :: I,J
INTEGER :: INFOMPI
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N3D',0,ZHOOK_HANDLE)
!
IWORK(:,:,:) = 0
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
#endif
!
IF (SIZE(KWORK,1)>0) THEN
IF (PRESENT(KMASK)) THEN
CALL UNPACK_SAME_RANK(KMASK,KWORK(:,:,:),IWORK(:,:,:))
ELSE
IWORK(1:SIZE(KWORK,1),:,:) = KWORK(:,:,:)
ENDIF
ENDIF
!
#ifdef SFX_MPI
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
#endif
!
IF (NRANK/=NPIO) THEN
!
IDX_W = IDX_W + 1
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
CALL MPI_SEND(IWORK(:,:,:),SIZE(IWORK)*KIND(IWORK)/4,MPI_INTEGER,NPIO,IDX_W,NCOMM,INFOMPI)
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
#endif
!
ELSE
!
KWORK2(:,:,:) = 0
!
IDX_W = IDX_W + 1
!
DO I=0,NPROC-1
!
#ifdef SFX_MPI
XTIME0 = MPI_WTIME()
#endif
!
IF (I/=NPIO) THEN
#ifdef SFX_MPI
CALL MPI_RECV(IINTER,SIZE(IINTER)*KIND(IINTER)/4,MPI_INTEGER,I,IDX_W,NCOMM,ISTATUS,INFOMPI)
#endif
ELSE
IINTER(:,:,:) = IWORK(:,:,:)
ENDIF
!
#ifdef SFX_MPI
XTIME_COMM_WRITE = XTIME_COMM_WRITE + (MPI_WTIME() - XTIME0)
!
XTIME0 = MPI_WTIME()
#endif
!
ICPT = 0
!
DO J=1,SIZE(NINDEX)
!
IF ( NINDEX(J)==I ) THEN
ICPT = ICPT + 1
KWORK2(J,:,:) = IINTER(ICPT,:,:)
ENDIF
!
ENDDO
!
#ifdef SFX_MPI
XTIME_CALC_WRITE = XTIME_CALC_WRITE + (MPI_WTIME() - XTIME0)
#endif
!
ENDDO
!
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_N3D',1,ZHOOK_HANDLE)
!
!
END SUBROUTINE GATHER_AND_WRITE_MPI_N3D
!
!**************************************************************************
!
SUBROUTINE GATHER_AND_WRITE_MPI_X1D(PWORK,PWORK2,KMASK)
!
USE MODI_GATHER_AND_WRITE_MPI_K4
!
USE MODD_SURFEX_MPI, ONLY : NRANK, NPIO
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
REAL, DIMENSION(:), INTENT(IN) :: PWORK
REAL(KIND=KIND(PWORK)), DIMENSION(:), INTENT(OUT) :: PWORK2
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X1D',0,ZHOOK_HANDLE)
!
IF (PRESENT(KMASK)) THEN
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2,KMASK)
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2)
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X1D',1,ZHOOK_HANDLE)
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X1D
!
!**************************************************************************
!
SUBROUTINE GATHER_AND_WRITE_MPI_X2D(PWORK,PWORK2,KMASK)
!
USE MODI_GATHER_AND_WRITE_MPI_K4
!
USE MODD_SURFEX_MPI, ONLY : NRANK, NPIO
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
REAL, DIMENSION(:,:), INTENT(IN) :: PWORK
REAL(KIND=KIND(PWORK)), DIMENSION(:,:), INTENT(OUT) :: PWORK2
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X2D',0,ZHOOK_HANDLE)
!
IF (PRESENT(KMASK)) THEN
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2,KMASK)
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2)
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X2D',1,ZHOOK_HANDLE)
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X2D
!
!**************************************************************************
!
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
SUBROUTINE GATHER_AND_WRITE_MPI_X3D(PWORK,PWORK2,KMASK)
!
USE MODI_GATHER_AND_WRITE_MPI_K4
!
USE MODD_SURFEX_MPI, ONLY : NRANK, NPIO
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
REAL, DIMENSION(:,:,:), INTENT(IN) :: PWORK
REAL(KIND=KIND(PWORK)), DIMENSION(:,:,:), INTENT(OUT) :: PWORK2
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X3D',0,ZHOOK_HANDLE)
!
IF (PRESENT(KMASK)) THEN
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2,KMASK)
ELSE
CALL GATHER_AND_WRITE_MPI_K4(PWORK,PWORK2)
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X3D',1,ZHOOK_HANDLE)
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X3D
!
!**************************************************************************
!
SUBROUTINE GATHER_AND_WRITE_MPI_X1DK4(PWORK,PWORK2,KMASK)
!
USE MODI_GATHER_AND_WRITE_MPI_K4
!
USE MODD_SURFEX_MPI, ONLY : NRANK, NPIO
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
REAL, DIMENSION(:), INTENT(IN) :: PWORK
REAL(KIND=KIND(PWORK)/2), DIMENSION(:), INTENT(OUT) :: PWORK2
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
REAL, DIMENSION(:), ALLOCATABLE :: ZINTER
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X1DK4',0,ZHOOK_HANDLE)
!
IF (PRESENT(KMASK)) THEN
CALL GATHER_AND_WRITE_MPI_K4(PWORK,ZINTER,KMASK)
ELSE
CALL GATHER_AND_WRITE_MPI_K4(PWORK,ZINTER)
ENDIF
!
IF (NRANK==NPIO) THEN
PWORK2(:) = ZINTER(:)
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X1DK4',1,ZHOOK_HANDLE)
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X1DK4
!
!**************************************************************************
!
SUBROUTINE GATHER_AND_WRITE_MPI_X2DK4(PWORK,PWORK2,KMASK)
!
USE MODI_GATHER_AND_WRITE_MPI_K4
!
USE MODD_SURFEX_MPI, ONLY : NRANK, NPIO
!
USE YOMHOOK ,ONLY : LHOOK, DR_HOOK
USE PARKIND1 ,ONLY : JPRB
!
IMPLICIT NONE
!
REAL, DIMENSION(:,:), INTENT(IN) :: PWORK
REAL(KIND=KIND(PWORK)/2), DIMENSION(:,:), INTENT(OUT) :: PWORK2
INTEGER, DIMENSION(:), INTENT(IN), OPTIONAL :: KMASK
!
REAL, DIMENSION(:,:), ALLOCATABLE :: ZINTER
REAL(KIND=JPRB) :: ZHOOK_HANDLE
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X2DK4',0,ZHOOK_HANDLE)
!
ALLOCATE(ZINTER(SIZE(PWORK2,1),SIZE(PWORK2,2)))
IF (PRESENT(KMASK)) THEN
CALL GATHER_AND_WRITE_MPI_K4(PWORK,ZINTER,KMASK)
ELSE
CALL GATHER_AND_WRITE_MPI_K4(PWORK,ZINTER)
ENDIF
!
IF (NRANK==NPIO) THEN
PWORK2(:,:) = ZINTER(:,:)
ENDIF
!
IF (LHOOK) CALL DR_HOOK('GATHER_AND_WRITE_MPI_X2DK4',1,ZHOOK_HANDLE)
!
END SUBROUTINE GATHER_AND_WRITE_MPI_X2DK4