Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icb_oce.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icb_oce.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icb_oce.F90	(revision 4891)
@@ -96,5 +96,5 @@
    REAL(wp), PUBLIC, DIMENSION(:,:), ALLOCATABLE ::   ua_e, va_e
    REAL(wp), PUBLIC, DIMENSION(:,:), ALLOCATABLE ::   ssh_e
-#if defined key_lim2 || defined key_lim3
+#if defined key_lim2 || defined key_lim3 || defined key_cice
    REAL(wp), PUBLIC, DIMENSION(:,:), ALLOCATABLE ::   ui_e, vi_e
 #endif
@@ -144,4 +144,7 @@
    INTEGER , PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:)       ::   nicbflddest                      !: nfold destination proc
    INTEGER , PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:)       ::   nicbfldproc                      !: nfold destination proc
+   INTEGER , PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:)       ::   nicbfldnsend                     !: nfold number of bergs to send to nfold neighbour
+   INTEGER , PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:)       ::   nicbfldexpect                    !: nfold expected number of bergs
+   INTEGER , PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:)       ::   nicbfldreq                       !: nfold message handle (immediate send)
 
    REAL(wp), PUBLIC, ALLOCATABLE, SAVE, DIMENSION(:,:,:)   :: griddata                           !: work array for icbrst
@@ -162,4 +165,6 @@
       !
       icb_alloc = 0
+      ALLOCATE( berg_grid, STAT=ill )
+      icb_alloc = icb_alloc + ill
       ALLOCATE( berg_grid%calving    (jpi,jpj) , berg_grid%calving_hflx (jpi,jpj)          ,   &
          &      berg_grid%stored_heat(jpi,jpj) , berg_grid%floating_melt(jpi,jpj)          ,   &
@@ -171,5 +176,5 @@
       ALLOCATE( uo_e(0:jpi+1,0:jpj+1) , ua_e(0:jpi+1,0:jpj+1) ,   &
          &      vo_e(0:jpi+1,0:jpj+1) , va_e(0:jpi+1,0:jpj+1) ,   &
-#if defined key_lim2 || defined key_lim3
+#if defined key_lim2 || defined key_lim3 || defined key_cice
          &      ui_e(0:jpi+1,0:jpj+1) ,                            &
          &      vi_e(0:jpi+1,0:jpj+1) ,                            &
@@ -181,5 +186,6 @@
       icb_alloc = icb_alloc + ill
 
-      ALLOCATE( nicbfldpts(jpi) , nicbflddest(jpi) , nicbfldproc(jpni) , STAT=ill)
+      ALLOCATE( nicbfldpts(jpi) , nicbflddest(jpi) , nicbfldproc(jpni) , &
+         &      nicbfldnsend(jpni), nicbfldexpect(jpni) , nicbfldreq(jpni), STAT=ill)
       icb_alloc = icb_alloc + ill
 
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbdyn.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbdyn.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbdyn.F90	(revision 4891)
@@ -33,5 +33,5 @@
 CONTAINS
 
-   SUBROUTINE icb_dyn()
+   SUBROUTINE icb_dyn( kt )
       !!----------------------------------------------------------------------
       !!                  ***  ROUTINE icb_dyn  ***
@@ -50,4 +50,5 @@
       TYPE(iceberg), POINTER          ::   berg
       TYPE(point)  , POINTER          ::   pt
+      INTEGER                         ::   kt
       !!----------------------------------------------------------------------
 
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbini.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbini.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbini.F90	(revision 4891)
@@ -172,13 +172,16 @@
          DO ji = nicbdi, nicbei
             ii = nicbflddest(ji)
-            DO jn = 1, jpni
-               ! work along array until we find an empty slot
-               IF( nicbfldproc(jn) == -1 ) THEN
-                  nicbfldproc(jn) = ii
-                  EXIT                             !!gm EXIT should be avoided: use DO WHILE expression instead
-               ENDIF
-               ! before we find an empty slot, we may find processor number is already here so we exit
-               IF( nicbfldproc(jn) == ii ) EXIT
-            END DO
+            IF( ii .GT. 0 ) THEN     ! Needed because land suppression can mean
+                                     ! that unused points are not set in edge haloes
+               DO jn = 1, jpni
+                  ! work along array until we find an empty slot
+                  IF( nicbfldproc(jn) == -1 ) THEN
+                     nicbfldproc(jn) = ii
+                     EXIT                             !!gm EXIT should be avoided: use DO WHILE expression instead
+                  ENDIF
+                  ! before we find an empty slot, we may find processor number is already here so we exit
+                  IF( nicbfldproc(jn) == ii ) EXIT
+               END DO
+            ENDIF
          END DO
       ENDIF
@@ -210,4 +213,6 @@
             WRITE(numicb,*) 'north fold destination procs  '
             WRITE(numicb,*) nicbflddest
+            WRITE(numicb,*) 'north fold destination proclist  '
+            WRITE(numicb,*) nicbfldproc
          ENDIF
          CALL flush(numicb)
@@ -397,7 +402,7 @@
       ENDIF
 
-      IF( lk_lim3 .AND. ln_icebergs ) THEN
-         CALL ctl_stop( 'icb_nam: the use of ICB with LIM3 not allowed. ice thickness missing in ICB' )
-      ENDIF
+!     IF( lk_lim3 .AND. ln_icebergs ) THEN
+!        CALL ctl_stop( 'icb_nam: the use of ICB with LIM3 not allowed. ice thickness missing in ICB' )
+!     ENDIF
 
       IF(lwp) THEN                  ! control print
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icblbc.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icblbc.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icblbc.F90	(revision 4891)
@@ -280,5 +280,5 @@
          zwebergs(1) = ibergs_to_send_e
          CALL mppsend( 12, zwebergs(1), 1, ipe_E, iml_req1)
-         CALL mpprecv( 11, zewbergs(2), 1 )
+         CALL mpprecv( 11, zewbergs(2), 1, ipe_E )
          IF( l_isend ) CALL mpi_wait( iml_req1, iml_stat, iml_err )
          ibergs_rcvd_from_e = INT( zewbergs(2) )
@@ -288,6 +288,6 @@
          CALL mppsend( 11, zewbergs(1), 1, ipe_W, iml_req2)
          CALL mppsend( 12, zwebergs(1), 1, ipe_E, iml_req3)
-         CALL mpprecv( 11, zewbergs(2), 1 )
-         CALL mpprecv( 12, zwebergs(2), 1 )
+         CALL mpprecv( 11, zewbergs(2), 1, ipe_E )
+         CALL mpprecv( 12, zwebergs(2), 1, ipe_W )
          IF( l_isend ) CALL mpi_wait( iml_req2, iml_stat, iml_err )
          IF( l_isend ) CALL mpi_wait( iml_req3, iml_stat, iml_err )
@@ -297,5 +297,5 @@
          zewbergs(1) = ibergs_to_send_w
          CALL mppsend( 11, zewbergs(1), 1, ipe_W, iml_req4)
-         CALL mpprecv( 12, zwebergs(2), 1 )
+         CALL mpprecv( 12, zwebergs(2), 1, ipe_W )
          IF( l_isend ) CALL mpi_wait( iml_req4, iml_stat, iml_err )
          ibergs_rcvd_from_w = INT( zwebergs(2) )
@@ -411,5 +411,5 @@
          zsnbergs(1) = ibergs_to_send_n
          CALL mppsend( 16, zsnbergs(1), 1, ipe_N, iml_req1)
-         CALL mpprecv( 15, znsbergs(2), 1 )
+         CALL mpprecv( 15, znsbergs(2), 1, ipe_N )
          IF( l_isend ) CALL mpi_wait( iml_req1, iml_stat, iml_err )
          ibergs_rcvd_from_n = INT( znsbergs(2) )
@@ -419,6 +419,6 @@
          CALL mppsend( 15, znsbergs(1), 1, ipe_S, iml_req2)
          CALL mppsend( 16, zsnbergs(1), 1, ipe_N, iml_req3)
-         CALL mpprecv( 15, znsbergs(2), 1 )
-         CALL mpprecv( 16, zsnbergs(2), 1 )
+         CALL mpprecv( 15, znsbergs(2), 1, ipe_N )
+         CALL mpprecv( 16, zsnbergs(2), 1, ipe_S )
          IF( l_isend ) CALL mpi_wait( iml_req2, iml_stat, iml_err )
          IF( l_isend ) CALL mpi_wait( iml_req3, iml_stat, iml_err )
@@ -428,5 +428,5 @@
          znsbergs(1) = ibergs_to_send_s
          CALL mppsend( 15, znsbergs(1), 1, ipe_S, iml_req4)
-         CALL mpprecv( 16, zsnbergs(2), 1 )
+         CALL mpprecv( 16, zsnbergs(2), 1, ipe_S )
          IF( l_isend ) CALL mpi_wait( iml_req4, iml_stat, iml_err )
          ibergs_rcvd_from_s = INT( zsnbergs(2) )
@@ -581,5 +581,6 @@
       INTEGER                             :: ifldproc, iproc, ipts
       INTEGER                             :: iine, ijne
-      REAL(wp), DIMENSION(2)              :: zsbergs, znbergs
+      INTEGER                             :: jjn
+      REAL(wp), DIMENSION(0:3)            :: zsbergs, znbergs
       INTEGER                             :: iml_req1, iml_req2, iml_err
       INTEGER, DIMENSION(MPI_STATUS_SIZE) :: iml_stat
@@ -591,4 +592,93 @@
       ! its of fixed size, the first -1 marks end of list of processors
       !
+      nicbfldnsend(:) = 0
+      nicbfldexpect(:) = 0
+      nicbfldreq(:) = 0
+      !
+      ! Since each processor may be communicating with more than one northern
+      ! neighbour, cycle through the sends so that the receive order can be
+      ! controlled.
+      !
+      ! First compute how many icebergs each active neighbour should expect
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            nicbfldnsend(jn) = 0
+
+            ! Find number of bergs that need to be exchanged
+            ! Pick out exchanges with processor ifldproc
+            ! if ifldproc is this processor then don't send
+            !
+            IF( ASSOCIATED(first_berg) ) THEN
+               this => first_berg
+               DO WHILE (ASSOCIATED(this))
+                  pt => this%current_point
+                  iine = INT( pt%xi + 0.5 )
+                  ijne = INT( pt%yj + 0.5 )
+                  iproc = nicbflddest(mi1(iine))
+                  IF( ijne .GT. mjg(nicbej) ) THEN
+                     IF( iproc == ifldproc ) THEN
+                        !
+                        IF( iproc /= narea ) THEN
+                           tmpberg => this
+                           nicbfldnsend(jn) = nicbfldnsend(jn) + 1
+                        ENDIF
+                        !
+                     ENDIF
+                  ENDIF
+                  this => this%next
+               END DO
+            ENDIF
+            !
+         ENDIF
+         !
+      END DO
+      !
+      ! Now tell each active neighbour how many icebergs to expect
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            IF( ifldproc == narea ) CYCLE
+   
+            zsbergs(0) = narea
+            zsbergs(1) = nicbfldnsend(jn)
+            !IF ( nicbfldnsend(jn) .GT. 0) write(numicb,*) 'ICB sending ',nicbfldnsend(jn),' to ', ifldproc
+            CALL mppsend( 21, zsbergs(0:1), 2, ifldproc-1, nicbfldreq(jn))
+         ENDIF
+         !
+      END DO
+      !
+      ! and receive the heads-up from active neighbours preparing to send
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            IF( ifldproc == narea ) CYCLE
+
+            CALL mpprecv( 21, znbergs(1:2), 2 )
+            DO jjn = 1,jpni
+             IF( nicbfldproc(jjn) .eq. INT(znbergs(1)) ) EXIT
+            END DO
+            IF( jjn .GT. jpni ) write(numicb,*) 'ICB ERROR'
+            nicbfldexpect(jjn) = INT( znbergs(2) )
+            !IF ( nicbfldexpect(jjn) .GT. 0) write(numicb,*) 'ICB expecting ',nicbfldexpect(jjn),' from ', nicbfldproc(jjn)
+            !CALL FLUSH(numicb)
+         ENDIF
+         !
+      END DO
+      !
+      ! post the mpi waits if using immediate send protocol
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            IF( ifldproc == narea ) CYCLE
+
+            IF( l_isend ) CALL mpi_wait( nicbfldreq(jn), iml_stat, iml_err )
+         ENDIF
+         !
+      END DO
+   
+         !
+         ! Cycle through the icebergs again, this time packing and sending any
+         ! going through the north fold. They will be expected.
       DO jn = 1, jpni
          IF( nicbfldproc(jn) /= -1 ) THEN
@@ -646,19 +736,25 @@
             IF( ifldproc == narea ) CYCLE
    
-            zsbergs(1) = ibergs_to_send
-            CALL mppsend( 21, zsbergs(1), 1, ifldproc-1, iml_req1)
-            CALL mpprecv( 21, znbergs(2), 1 )
-            IF( l_isend ) CALL mpi_wait( iml_req1, iml_stat, iml_err )
-            ibergs_to_rcv = INT( znbergs(2) )
-   
             ! send bergs
    
             IF( ibergs_to_send > 0 )  &
-                CALL mppsend( 12, obuffer_f%data, ibergs_to_send*jp_buffer_width, ifldproc-1, iml_req2 )
+                CALL mppsend( 12, obuffer_f%data, ibergs_to_send*jp_buffer_width, ifldproc-1, nicbfldreq(jn) )
+            !
+         ENDIF
+         !
+      END DO
+      !
+      ! Now receive the expected number of bergs from the active neighbours
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            IF( ifldproc == narea ) CYCLE
+            ibergs_to_rcv = nicbfldexpect(jn)
+
             IF( ibergs_to_rcv  > 0 ) THEN
                CALL icb_increase_ibuffer(ibuffer_f, ibergs_to_rcv)
-               CALL mpprecv( 12, ibuffer_f%data, ibergs_to_rcv*jp_buffer_width )
-            ENDIF
-            IF( ibergs_to_send > 0 .AND. l_isend ) CALL mpi_wait( iml_req2, iml_stat, iml_err )
+               CALL mpprecv( 12, ibuffer_f%data, ibergs_to_rcv*jp_buffer_width, ifldproc-1 )
+            ENDIF
+            !
             DO jk = 1, ibergs_to_rcv
                IF( nn_verbose_level >= 4 ) THEN
@@ -668,5 +764,15 @@
                CALL icb_unpack_from_buffer(first_berg, ibuffer_f, jk )
             END DO
-            !
+         ENDIF
+         !
+      END DO
+      !
+      ! Finally post the mpi waits if using immediate send protocol
+      DO jn = 1, jpni
+         IF( nicbfldproc(jn) /= -1 ) THEN
+            ifldproc = nicbfldproc(jn)
+            IF( ifldproc == narea ) CYCLE
+
+            IF( l_isend ) CALL mpi_wait( nicbfldreq(jn), iml_stat, iml_err )
          ENDIF
          !
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbrst.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbrst.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbrst.F90	(revision 4891)
@@ -64,5 +64,5 @@
                                                                                             ! start and count arrays
       LOGICAL                      ::   ll_found_restart
-      CHARACTER(len=80)            ::   cl_filename
+      CHARACTER(len=256)           ::   cl_filename
       CHARACTER(len=NF90_MAX_NAME) ::   cl_dname
       TYPE(iceberg)                ::   localberg ! NOT a pointer but an actual local variable
@@ -228,5 +228,5 @@
       INTEGER ::   jn   ! dummy loop index
       INTEGER ::   ix_dim, iy_dim, ik_dim, in_dim
-      CHARACTER(len=80)      :: cl_filename
+      CHARACTER(len=256)     :: cl_filename
       TYPE(iceberg), POINTER :: this
       TYPE(point)  , POINTER :: pt
@@ -256,4 +256,19 @@
       IF (nret .ne. NF90_NOERR) CALL ctl_stop('icebergs, write_restart: nf_def_dim k failed')
 
+      ! global attributes
+      IF( lk_mpp ) THEN
+         ! Set domain parameters (assume jpdom_local_full)
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_number_total'   , jpnij              )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_number'         , narea-1            )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_dimensions_ids' , (/1     , 2     /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_size_global'    , (/jpiglo, jpjglo/) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_size_local'     , (/jpi   , jpj   /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_position_first' , (/nimpp , njmpp /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_position_last'  , (/nimpp + jpi - 1 , njmpp + jpj - 1  /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_halo_size_start', (/nldi - 1        , nldj - 1         /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_halo_size_end'  , (/jpi - nlei      , jpj - nlej       /) )
+         nret = NF90_PUT_ATT( ncid, NF90_GLOBAL, 'DOMAIN_type'           , 'BOX'              )
+      ENDIF
+      
       IF (associated(first_berg)) then
          nret = NF90_DEF_DIM(ncid, 'n', NF90_UNLIMITED, in_dim)
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbstp.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbstp.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbstp.F90	(revision 4891)
@@ -105,5 +105,5 @@
 !                               !==  For each berg, evolve  ==!
       !
-      IF( ASSOCIATED(first_berg) )   CALL icb_dyn()           ! ice berg dynamics
+      IF( ASSOCIATED(first_berg) )   CALL icb_dyn( kt )       ! ice berg dynamics
 
       IF( lk_mpp ) THEN          ;   CALL icb_lbc_mpp()       ! Send bergs to other PEs
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbutl.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbutl.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/ICB/icbutl.F90	(revision 4891)
@@ -76,9 +76,9 @@
       va_e(:,:) = 0._wp ;   va_e(1:jpi, 1:jpj) = vtau (:,:)
 
-      CALL lbc_lnk_e( uo_e, 'U', -1._wp, 1, 1 )
-      CALL lbc_lnk_e( vo_e, 'V', -1._wp, 1, 1 )
-      CALL lbc_lnk_e( ff_e, 'F', +1._wp, 1, 1 )
-      CALL lbc_lnk_e( ua_e, 'U', -1._wp, 1, 1 )
-      CALL lbc_lnk_e( va_e, 'V', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( uo_e, 'U', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( vo_e, 'V', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( ff_e, 'F', +1._wp, 1, 1 )
+      CALL lbc_lnk_icb( ua_e, 'U', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( va_e, 'V', -1._wp, 1, 1 )
 
 #if defined key_lim2 || defined key_lim3
@@ -86,6 +86,6 @@
       vi_e(:,:) = 0._wp ;   vi_e(1:jpi, 1:jpj) = v_ice(:,:)
 
-      CALL lbc_lnk_e( ui_e, 'U', -1._wp, 1, 1 )
-      CALL lbc_lnk_e( vi_e, 'V', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( ui_e, 'U', -1._wp, 1, 1 )
+      CALL lbc_lnk_icb( vi_e, 'V', -1._wp, 1, 1 )
 #endif
 
@@ -102,5 +102,5 @@
       ssh_e(0,jpj+1)     = ssh_e(1,jpj)
       ssh_e(jpi+1,jpj+1) = ssh_e(jpi,jpj)
-      CALL lbc_lnk_e( ssh_e, 'T', +1._wp, 1, 1 )
+      CALL lbc_lnk_icb( ssh_e, 'T', +1._wp, 1, 1 )
       !
    END SUBROUTINE icb_utl_copy
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lbclnk.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lbclnk.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lbclnk.F90	(revision 4891)
@@ -34,7 +34,12 @@
    END INTERFACE
 
+   INTERFACE lbc_lnk_icb
+      MODULE PROCEDURE mpp_lnk_2d_icb
+   END INTERFACE
+
    PUBLIC lbc_lnk       ! ocean lateral boundary conditions
    PUBLIC lbc_lnk_e
    PUBLIC lbc_bdy_lnk   ! ocean lateral BDY boundary conditions
+   PUBLIC lbc_lnk_icb
 
    !!----------------------------------------------------------------------
@@ -73,7 +78,12 @@
    END INTERFACE
 
+   INTERFACE lbc_lnk_icb
+      MODULE PROCEDURE lbc_lnk_2d_e
+   END INTERFACE
+
    PUBLIC   lbc_lnk       ! ocean/ice  lateral boundary conditions
    PUBLIC   lbc_lnk_e 
    PUBLIC   lbc_bdy_lnk   ! ocean lateral BDY boundary conditions
+   PUBLIC   lbc_lnk_icb
    
    !!----------------------------------------------------------------------
Index: branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lib_mpp.F90
===================================================================
--- branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lib_mpp.F90	(revision 4736)
+++ branches/2014/dev_r4743_NOC2_ZTS/NEMOGCM/NEMO/OPA_SRC/LBC/lib_mpp.F90	(revision 4891)
@@ -42,4 +42,5 @@
    !!   mpp_lnk_3d_gather :  Message passing manadgement for two 3D arrays
    !!   mpp_lnk_e     : interface (defined in lbclnk) for message passing of 2d array with extra halo (mpp_lnk_2d_e)
+   !!   mpp_lnk_icb   : interface for message passing of 2d arrays with extra halo for icebergs (mpp_lnk_2d_icb)
    !!   mpprecv         :
    !!   mppsend       :   SUBROUTINE mpp_ini_znl
@@ -56,4 +57,5 @@
    !!   mpp_lbc_north : north fold processors gathering
    !!   mpp_lbc_north_e : variant of mpp_lbc_north for extra outer halo
+   !!   mpp_lbc_north_icb : variant of mpp_lbc_north for extra outer halo with icebergs
    !!----------------------------------------------------------------------
    USE dom_oce        ! ocean space and time domain
@@ -74,4 +76,5 @@
    PUBLIC   mppsend, mpprecv                          ! needed by TAM and ICB routines
    PUBLIC   mpp_lnk_bdy_2d, mpp_lnk_bdy_3d
+   PUBLIC   mpp_lbc_north_icb, mpp_lnk_2d_icb
 
    !! * Interfaces
@@ -2084,5 +2087,7 @@
          IF (l_isend) THEN
             DO jr = 1,nsndto
-               IF ((nfipproc(isendto(jr),jpnj) .ne. (narea-1)) .and. (nfipproc(isendto(jr),jpnj) .ne. -1)) CALL mpi_wait(ml_req_nf(jr), ml_stat, ml_err)
+               IF ((nfipproc(isendto(jr),jpnj) .ne. (narea-1)) .and. (nfipproc(isendto(jr),jpnj) .ne. -1)) THEN
+                  CALL mpi_wait(ml_req_nf(jr), ml_stat, ml_err)
+               ENDIF    
             END DO
          ENDIF
@@ -2891,4 +2896,267 @@
    END SUBROUTINE DDPDD_MPI
 
+   SUBROUTINE mpp_lbc_north_icb( pt2d, cd_type, psgn, pr2dj)
+      !!---------------------------------------------------------------------
+      !!                   ***  routine mpp_lbc_north_icb  ***
+      !!
+      !! ** Purpose :   Ensure proper north fold horizontal bondary condition
+      !!              in mpp configuration in case of jpn1 > 1 and for 2d
+      !!              array with outer extra halo
+      !!
+      !! ** Method  :   North fold condition and mpp with more than one proc
+      !!              in i-direction require a specific treatment. We gather
+      !!              the 4+2*jpr2dj northern lines of the global domain on 1
+      !!              processor and apply lbc north-fold on this sub array.
+      !!              Then we scatter the north fold array back to the processors.
+      !!              This version accounts for an extra halo with icebergs.
+      !!
+      !!----------------------------------------------------------------------
+      REAL(wp), DIMENSION(:,:), INTENT(inout) ::   pt2d     ! 2D array with extra halo
+      CHARACTER(len=1)        , INTENT(in   ) ::   cd_type  ! nature of pt3d grid-points
+      !                                                     !   = T ,  U , V , F or W -points
+      REAL(wp)                , INTENT(in   ) ::   psgn     ! = -1. the sign change across the
+      !!                                                    ! north fold, =  1. otherwise
+      INTEGER, OPTIONAL       , INTENT(in   ) ::   pr2dj
+      INTEGER ::   ji, jj, jr
+      INTEGER ::   ierr, itaille, ildi, ilei, iilb
+      INTEGER ::   ijpj, ij, iproc, ipr2dj
+      !
+      REAL(wp), DIMENSION(:,:)  , ALLOCATABLE  ::  ztab_e, znorthloc_e
+      REAL(wp), DIMENSION(:,:,:), ALLOCATABLE  ::  znorthgloio_e
+
+      !!----------------------------------------------------------------------
+      !
+      ijpj=4
+      IF( PRESENT(pr2dj) ) THEN           ! use of additional halos
+         ipr2dj = pr2dj
+      ELSE
+         ipr2dj = 0
+      ENDIF
+      ALLOCATE( ztab_e(jpiglo,4+2*ipr2dj), znorthloc_e(jpi,4+2*ipr2dj), znorthgloio_e(jpi,4+2*ipr2dj,jpni) )
+
+      !
+      ztab_e(:,:) = 0.e0
+
+      ij=0
+      ! put in znorthloc_e the last 4 jlines of pt2d
+      DO jj = nlcj - ijpj + 1 - ipr2dj, nlcj +ipr2dj
+         ij = ij + 1
+         DO ji = 1, jpi
+            znorthloc_e(ji,ij)=pt2d(ji,jj)
+         END DO
+      END DO
+      !
+      itaille = jpi * ( ijpj + 2 * ipr2dj )
+      CALL MPI_ALLGATHER( znorthloc_e(1,1)  , itaille, MPI_DOUBLE_PRECISION,    &
+         &                znorthgloio_e(1,1,1), itaille, MPI_DOUBLE_PRECISION, ncomm_north, ierr )
+      !
+      DO jr = 1, ndim_rank_north            ! recover the global north array
+         iproc = nrank_north(jr) + 1
+         ildi = nldit (iproc)
+         ilei = nleit (iproc)
+         iilb = nimppt(iproc)
+         DO jj = 1, ijpj+2*ipr2dj
+            DO ji = ildi, ilei
+               ztab_e(ji+iilb-1,jj) = znorthgloio_e(ji,jj,jr)
+            END DO
+         END DO
+      END DO
+
+
+      ! 2. North-Fold boundary conditions
+      ! ----------------------------------
+      CALL lbc_nfd( ztab_e(:,:), cd_type, psgn, pr2dj = ipr2dj )
+
+      ij = ipr2dj
+      !! Scatter back to pt2d
+      DO jj = nlcj - ijpj + 1 , nlcj +ipr2dj
+      ij  = ij +1
+         DO ji= 1, nlci
+            pt2d(ji,jj) = ztab_e(ji+nimpp-1,ij)
+         END DO
+      END DO
+      !
+      DEALLOCATE( ztab_e, znorthloc_e, znorthgloio_e )
+      !
+   END SUBROUTINE mpp_lbc_north_icb
+
+   SUBROUTINE mpp_lnk_2d_icb( pt2d, cd_type, psgn, jpri, jprj )
+      !!----------------------------------------------------------------------
+      !!                  ***  routine mpp_lnk_2d_icb  ***
+      !!
+      !! ** Purpose :   Message passing manadgement for 2d array (with extra halo and icebergs)
+      !!
+      !! ** Method  :   Use mppsend and mpprecv function for passing mask
+      !!      between processors following neighboring subdomains.
+      !!            domain parameters
+      !!                    nlci   : first dimension of the local subdomain
+      !!                    nlcj   : second dimension of the local subdomain
+      !!                    jpri   : number of rows for extra outer halo
+      !!                    jprj   : number of columns for extra outer halo
+      !!                    nbondi : mark for "east-west local boundary"
+      !!                    nbondj : mark for "north-south local boundary"
+      !!                    noea   : number for local neighboring processors
+      !!                    nowe   : number for local neighboring processors
+      !!                    noso   : number for local neighboring processors
+      !!                    nono   : number for local neighboring processors
+      !!
+      !!----------------------------------------------------------------------
+      INTEGER                                             , INTENT(in   ) ::   jpri
+      INTEGER                                             , INTENT(in   ) ::   jprj
+      REAL(wp), DIMENSION(1-jpri:jpi+jpri,1-jprj:jpj+jprj), INTENT(inout) ::   pt2d     ! 2D array with extra halo
+      CHARACTER(len=1)                                    , INTENT(in   ) ::   cd_type  ! nature of ptab array grid-points
+      !                                                                                 ! = T , U , V , F , W and I points
+      REAL(wp)                                            , INTENT(in   ) ::   psgn     ! =-1 the sign change across the
+      !!                                                                                ! north boundary, =  1. otherwise
+      INTEGER  ::   jl   ! dummy loop indices
+      INTEGER  ::   imigr, iihom, ijhom        ! temporary integers
+      INTEGER  ::   ipreci, iprecj             ! temporary integers
+      INTEGER  ::   ml_req1, ml_req2, ml_err   ! for key_mpi_isend
+      INTEGER, DIMENSION(MPI_STATUS_SIZE) ::   ml_stat   ! for key_mpi_isend
+      !!
+      REAL(wp), DIMENSION(1-jpri:jpi+jpri,jprecj+jprj,2) :: r2dns
+      REAL(wp), DIMENSION(1-jpri:jpi+jpri,jprecj+jprj,2) :: r2dsn
+      REAL(wp), DIMENSION(1-jprj:jpj+jprj,jpreci+jpri,2) :: r2dwe
+      REAL(wp), DIMENSION(1-jprj:jpj+jprj,jpreci+jpri,2) :: r2dew
+      !!----------------------------------------------------------------------
+
+      ipreci = jpreci + jpri      ! take into account outer extra 2D overlap area
+      iprecj = jprecj + jprj
+
+
+      ! 1. standard boundary treatment
+      ! ------------------------------
+      ! Order matters Here !!!!
+      !
+      !                                      ! East-West boundaries
+      !                                           !* Cyclic east-west
+      IF( nbondi == 2 .AND. (nperio == 1 .OR. nperio == 4 .OR. nperio == 6) ) THEN
+         pt2d(1-jpri:     1    ,:) = pt2d(jpim1-jpri:  jpim1 ,:)       ! east
+         pt2d(   jpi  :jpi+jpri,:) = pt2d(     2      :2+jpri,:)       ! west
+         !
+      ELSE                                        !* closed
+         IF( .NOT. cd_type == 'F' )   pt2d(  1-jpri   :jpreci    ,:) = 0.e0    ! south except at F-point
+                                      pt2d(nlci-jpreci+1:jpi+jpri,:) = 0.e0    ! north
+      ENDIF
+      !
+
+      ! north fold treatment
+      ! -----------------------
+      IF( npolj /= 0 ) THEN
+         !
+         SELECT CASE ( jpni )
+         CASE ( 1 )     ;   CALL lbc_nfd        ( pt2d(1:jpi,1:jpj+jprj), cd_type, psgn, pr2dj=jprj )
+         CASE DEFAULT   ;   CALL mpp_lbc_north_icb( pt2d(1:jpi,1:jpj+jprj)  , cd_type, psgn , pr2dj=jprj  )
+         END SELECT
+         !
+      ENDIF
+
+      ! 2. East and west directions exchange
+      ! ------------------------------------
+      ! we play with the neigbours AND the row number because of the periodicity
+      !
+      SELECT CASE ( nbondi )      ! Read Dirichlet lateral conditions
+      CASE ( -1, 0, 1 )                ! all exept 2 (i.e. close case)
+         iihom = nlci-nreci-jpri
+         DO jl = 1, ipreci
+            r2dew(:,jl,1) = pt2d(jpreci+jl,:)
+            r2dwe(:,jl,1) = pt2d(iihom +jl,:)
+         END DO
+      END SELECT
+      !
+      !                           ! Migrations
+      imigr = ipreci * ( jpj + 2*jprj)
+      !
+      SELECT CASE ( nbondi )
+      CASE ( -1 )
+         CALL mppsend( 2, r2dwe(1-jprj,1,1), imigr, noea, ml_req1 )
+         CALL mpprecv( 1, r2dew(1-jprj,1,2), imigr, noea )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+      CASE ( 0 )
+         CALL mppsend( 1, r2dew(1-jprj,1,1), imigr, nowe, ml_req1 )
+         CALL mppsend( 2, r2dwe(1-jprj,1,1), imigr, noea, ml_req2 )
+         CALL mpprecv( 1, r2dew(1-jprj,1,2), imigr, noea )
+         CALL mpprecv( 2, r2dwe(1-jprj,1,2), imigr, nowe )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+         IF(l_isend) CALL mpi_wait(ml_req2,ml_stat,ml_err)
+      CASE ( 1 )
+         CALL mppsend( 1, r2dew(1-jprj,1,1), imigr, nowe, ml_req1 )
+         CALL mpprecv( 2, r2dwe(1-jprj,1,2), imigr, nowe )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+      END SELECT
+      !
+      !                           ! Write Dirichlet lateral conditions
+      iihom = nlci - jpreci
+      !
+      SELECT CASE ( nbondi )
+      CASE ( -1 )
+         DO jl = 1, ipreci
+            pt2d(iihom+jl,:) = r2dew(:,jl,2)
+         END DO
+      CASE ( 0 )
+         DO jl = 1, ipreci
+            pt2d(jl-jpri,:) = r2dwe(:,jl,2)
+            pt2d( iihom+jl,:) = r2dew(:,jl,2)
+         END DO
+      CASE ( 1 )
+         DO jl = 1, ipreci
+            pt2d(jl-jpri,:) = r2dwe(:,jl,2)
+         END DO
+      END SELECT
+
+
+      ! 3. North and south directions
+      ! -----------------------------
+      ! always closed : we play only with the neigbours
+      !
+      IF( nbondj /= 2 ) THEN      ! Read Dirichlet lateral conditions
+         ijhom = nlcj-nrecj-jprj
+         DO jl = 1, iprecj
+            r2dsn(:,jl,1) = pt2d(:,ijhom +jl)
+            r2dns(:,jl,1) = pt2d(:,jprecj+jl)
+         END DO
+      ENDIF
+      !
+      !                           ! Migrations
+      imigr = iprecj * ( jpi + 2*jpri )
+      !
+      SELECT CASE ( nbondj )
+      CASE ( -1 )
+         CALL mppsend( 4, r2dsn(1-jpri,1,1), imigr, nono, ml_req1 )
+         CALL mpprecv( 3, r2dns(1-jpri,1,2), imigr, nono )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+      CASE ( 0 )
+         CALL mppsend( 3, r2dns(1-jpri,1,1), imigr, noso, ml_req1 )
+         CALL mppsend( 4, r2dsn(1-jpri,1,1), imigr, nono, ml_req2 )
+         CALL mpprecv( 3, r2dns(1-jpri,1,2), imigr, nono )
+         CALL mpprecv( 4, r2dsn(1-jpri,1,2), imigr, noso )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+         IF(l_isend) CALL mpi_wait(ml_req2,ml_stat,ml_err)
+      CASE ( 1 )
+         CALL mppsend( 3, r2dns(1-jpri,1,1), imigr, noso, ml_req1 )
+         CALL mpprecv( 4, r2dsn(1-jpri,1,2), imigr, noso )
+         IF(l_isend) CALL mpi_wait(ml_req1,ml_stat,ml_err)
+      END SELECT
+      !
+      !                           ! Write Dirichlet lateral conditions
+      ijhom = nlcj - jprecj
+      !
+      SELECT CASE ( nbondj )
+      CASE ( -1 )
+         DO jl = 1, iprecj
+            pt2d(:,ijhom+jl) = r2dns(:,jl,2)
+         END DO
+      CASE ( 0 )
+         DO jl = 1, iprecj
+            pt2d(:,jl-jprj) = r2dsn(:,jl,2)
+            pt2d(:,ijhom+jl ) = r2dns(:,jl,2)
+         END DO
+      CASE ( 1 )
+         DO jl = 1, iprecj
+            pt2d(:,jl-jprj) = r2dsn(:,jl,2)
+         END DO
+      END SELECT
+
+   END SUBROUTINE mpp_lnk_2d_icb
 #else
    !!----------------------------------------------------------------------
