subroutine uv_model_comm(line,error)
  use gildas_def
  use gbl_message
  use gkernel_interfaces
  use clean_default
  use clean_arrays
  use imager_interfaces, except_this => uv_model_comm
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !   Support routine for command
  !     MODEL [Args] [/MINVAL Value [Unit]] [/OUTPUT]
  !           [/MODE CCT|UV_FIT|IMAGE [Frequency]]
  !
  ! Dispatch to adequate routine as specified by /MODE option to   
  !  - Compute the UV_MODEL data set from the current CCT table
  ! or
  !  - Compute the UV_MODEL data set from the current UV_FIT results
  ! or
  !  - Compute the UV_MODEL data set from the specified IMAGE variable
  !
  !   If no /MODE option is specified, the operation depends on whether 
  ! CLEAN or UV_FIT was executed last.
  !
  !   The /OUTPUT option is dummy, being present only for compatibility
  ! with the UV_RESIDUAL command
  !---------------------------------------------------------------------
  character(len=*), intent(in) :: line        ! Command line
  logical, intent(inout) :: error             ! Error flag
  !
  character(len=*), parameter :: rname='MODEL'
  integer, parameter :: o_minval=1 ! 
  integer, parameter :: o_output=2 ! Must be 2 ...
  integer, parameter :: o_mode=3  
  integer, parameter :: mmode=4
  integer :: imode
  character(len=12) argu,vocs(mmode),cmode
  data vocs/'CCT','COMPONENT','IMAGE','UV_FIT'/ 
  !
  if (sic_present(o_mode,0)) then
    call sic_ke(line,o_mode,1,argu,imode,.true.,error)
    if (error) return
    call sic_ambigs(rname,argu,cmode,imode,vocs,mmode,error)
    if (error) return
  else
    cmode = last_resid ! CCT or UV_FIT
  endif
  call sic_delvariable('UV_MODEL',.false.,error)
  Print *,'CMODE ',cmode
  !
  error = .false.
  !
  uv_model_updated = .true.
  select case (cmode)
  case ('UV_FIT')    
    call uvfit_residual_model(line,'MODEL',1,error)
    return
  case ('CCT','COMPONENT')
    call cct_fast_uvmodel(line,error)
  case default
    !!Print *,'Mode IMAGE '
    call map_fast_uvmodel(line,error)
  end select
  if (error) return
  !
  huvm%loca%size = huvm%gil%dim(1)*huvm%gil%dim(2)
  call sic_mapgildas('UV_MODEL',huvm,error,duvm)
  !
end subroutine uv_model_comm
!<FF>
subroutine map_fast_uvmodel(line,error)
  use gildas_def
  use gbl_message
  use gkernel_interfaces
  use clean_arrays
  use iso_c_binding
  use imager_interfaces, except_this => map_fast_uvmodel
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !   Support routine for command
  !     MODEL ImageName [/MINVAL Value [Unit]] /MODE IMAGE [Frequency]
  !
  ! Compute the UV_MODEL data set from the specified image 
  !
  ! Uses an intermediate FFT with further interpolation for 
  !    better speed than UV_CCT
  !---------------------------------------------------------------------
  character(len=*), intent(in) :: line    ! Command line
  logical, intent(inout) :: error         ! Error flag
  !
  character(len=*), parameter :: rname='MODEL'
  real(kind=8), parameter :: pi=3.14159265358979323846d0
  integer, parameter :: o_minval=1 ! 
  integer, parameter :: o_output=2 ! Must be 2 ...
  integer, parameter :: o_mode=3   
  ! Local
  character(len=filename_length) :: namex
  logical :: large
  type(gildas) :: hmap
  complex, allocatable :: fft(:,:,:)
  real, allocatable :: dmap(:,:,:)
  real, allocatable :: work(:)
  integer :: if,nf,nx,ny,mx,my,nt,nv,mt, ier, nc
  real :: cpu0, cpu1
  real :: factor
  real(8) :: xinc, yinc, area, jyperk
  character(len=8) :: cunit
  real(8) :: freq, vres
  real :: lambda, pixel_area
  logical :: is_image, is_clean, rdonly
  type(c_ptr) :: cptr
  real, pointer :: rptr(:,:,:)
  !
  large = sic_present(0,2) ! Test
  !
  if (.not.associated(duv)) then
    call map_message(seve%e,rname,'DUV is not associated') 
    error = .true.
    return
  endif
  ! Code
  error = .false.
  call gag_cpu(cpu0)
  !
  ! Input data is the current UV Data  huv & duv
  !
  ! Input MAP is specified as first argument, or defaults to CLEAN
  call gildas_null(hmap)
  if (sic_present(0,1)) then
    call sic_ch(line,0,1,namex,nc,.true.,error)
    if (error) return
    is_clean = .false.
    is_image = .false.    ! Allow SIC variable or GILDAS Data file
    call sub_readhead (rname,namex,hmap,is_image,error,rdonly,fmt_r4)
  else
    ! Use the CLEAN image so far for a test...
    if (hclean%loca%size.eq.0) then
      call map_message(seve%w,rname,'No CLEAN image')
      error = .true.
      return
    endif
    call gdf_copy_header(hclean,hmap,error)
    is_clean = .true.
  endif
  !
  ! There must be some match of the Velocity axis (not the frequency axis)
  ! This match may imply a change of number of channels, i.e.
  ! we should be able to define the intersection of the two velocity
  ! axis.  For the time being, just assume they are identical,
  ! or take the Image axis if the UV data is just 1 channel.
  if (huv%gil%nchan.ne.1) then
    if (hmap%gil%dim(3).ne.huv%gil%nchan) then
      call map_message(seve%w,rname,'Velocity axis mis-match, using UV coverage only')
    endif
  endif
  nf = hmap%gil%dim(3) ! In all cases
  mx = hmap%gil%dim(1)
  my = hmap%gil%dim(2)
  !
  ! Then do the job as in the CCT case, except for the Scale factor...
  allocate (dmap(mx,my,nf),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'MAP Allocation error')
    error = .true.
    return
  endif
  !
  ! We need a copy because we ignore edges
  if (is_clean) then
    !!Print *,'Using CLEAN'
    dmap(:,:,:) = dclean 
  else if (is_image) then
    !!Print *,'Using an IMAGE '
    call adtoad(hmap%loca%addr,cptr,1)
    call c_f_pointer(cptr,rptr,hmap%gil%dim(1:3))
    dmap(:,:,:) = rptr
  else
    !!Print *,'Reading a data file'
    call gdf_read_data(hmap,dmap,error)
    if (error) return
  endif
  !
  ! Define observing frequency
  vres = hmap%gil%vres
  xinc = hmap%gil%inc(1)
  yinc = hmap%gil%inc(2)
  !
  ! Prepare the UV output
  call gildas_null(huvm, type = 'UVT')
  !
  ! Do we want the same frequency  layout as the UV data or that of the MAP? 
  ! The UV data specifies the appropriate UV coverage, 
  ! but the MAP specifies the Spectroscopy by default
  ! Analysis of the /MODE option yields the choice
  call gdf_copy_header(huv,huvm,error) 
  !
  ! Retrieve minimum value and Frequency
  call mod_min_image (line,hmap,huv,freq,dmap,error)
  if (error) return
  !
  ! Avoid edges by default - Do not even bother to check for a mask
  ! or whatever - It is needed to avoid aliasing in any case
  do if=1,nf
    dmap(1:(mx/8),:,if) = 0
    dmap((7*mx)/8:mx,:,if) = 0
    dmap(:,1:(my/8),if) = 0
    dmap(:,(7*my)/8:my,if) = 0
  enddo
  !
  ! Define the image size
  call mod_fft_size(large,mx,my,nx,ny)
  call gag_cpu(cpu1)
  !
  ! Get Virtual Memory & compute the FFT
  allocate (fft(nx,ny,nf),work(2*max(nx,ny)),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'FFT space allocation error')
    error = .true.
    return
  endif
  !
  ! See UV_RESTORE also for this code
  if (nx.eq.mx .and. ny.eq.my) then
    !!Print *,'NX = MX case'
    fft(:,:,:) = cmplx(dmap,0.0)
  else
    do if = 1,nf
      call plunge_real (dmap(:,:,if),mx,my,fft(:,:,if),nx,ny)
    enddo
  endif
  ! Free map - Note that we may use a Pointer for built-in buffers...
  deallocate (dmap,stat=ier)
  !
  ! Compute the FFT
  !!Print *,'NX NY NF ', nx,ny,nf
  call do_fft(nx,ny,nf,fft,work)
  call gag_cpu(cpu1)
  !
  huvm%gil%dim(1) = 7+3*nf
  huvm%gil%ref(1)  = hmap%gil%ref(3)
  huvm%gil%val(1)  = freq
  !
  ! Set the velocity resolution
  huvm%gil%vres = vres
  huvm%gil%fres = -vres*freq/299792.458d0  ! Velocity in km/s
  huvm%gil%inc(1)  = huvm%gil%fres 
  !
  huvm%gil%freq = freq
  huvm%char%line = hmap%char%line 
  huvm%gil%voff = hmap%gil%voff
  !
  ! Set the number of channels
  huvm%gil%nchan = nf
  huvm%gil%convert(:,1) = hmap%gil%convert(:,3)
  !
  ! Unit is according to Image characteristics
  !
  cunit = hmap%char%unit
  call sic_upper(cunit)
  jyperk = 1.0
  if (cunit.eq.'JY/BEAM') then
    ! Get the scale factor of the input data. We want
    ! a model image in K for the rest of the job.
    area = pi*hmap%gil%majo*hmap%gil%mino/4/log(2.0)
    if (area.ne.0) then
      jyperk = 2*1.38e3*area/(299792458d0/freq*1d-6)**2
    else
      call map_message(seve%w,rname,'No beam size, using arbitrary units')
    endif
  else if (cunit.eq.'K') then
    jyperk = 1.0
  endif
  !
  ! Define scaling factor from Brightness to Flux (2 k B^2 / l^2)
  lambda = 299792.458e3/(freq*1e6) ! in meter
  ! 1.38E3 is the Boltzmann constant times 10^26 to give result in Jy
  pixel_area = abs(xinc*yinc)   ! in radian
  factor = 2*1.38e3/lambda**2*pixel_area
  !! print *,'Factor ',factor,pixel_area
  !! if (factor.eq.0.0) factor = 1.0
  !
  factor = factor/jyperk  
  !
  huvm%gil%dim(1) = 7+3*nf
  !
  if (allocated(duvm)) deallocate(duvm)
  allocate (duvm(huvm%gil%dim(1),huvm%gil%dim(2)),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'UV Model allocation error')
    error = .true.
    return
  endif
  nt = huvm%gil%dim(1)
  nv = huvm%gil%dim(2)
  mt = huv%gil%dim(1)
  !
  ! At this stage, we just copy the DAPs and the weights.
  call copyuv (nt,nv,duvm,mt,duv)
  !
  ! Now compute the model
  call do_uvmodel(duvm, nt, nv, fft,nx,ny,nf,freq,xinc,yinc,factor)
  error = .false.
  call gag_cpu(cpu1)
  !
end subroutine map_fast_uvmodel
!<FF>
subroutine cct_fast_uvmodel(line,error)
  use gildas_def
  use gbl_message
  use gkernel_interfaces
  use clean_arrays
  use imager_interfaces, except_this => cct_fast_uvmodel
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !   Support routine for command
  !     MODEL [MaxIter] [/MINVAL Value [Unit]] [/MODE CCT [Frequency]]
  !
  ! Compute the MODEL UV data set from the current CCT table
  !
  !     Uses an intermediate FFT with further interpolation for
  !     better speed than UV_CCT
  !---------------------------------------------------------------------
  character(len=*), intent(in) :: line
  logical, intent(inout) :: error
  !
  character(len=*), parameter :: rname='MODEL'
  real(kind=8), parameter :: pi=3.14159265358979323846d0
  integer, parameter :: o_minval=1 ! 
  integer, parameter :: o_output=2 ! Must be 2 ...
  integer, parameter :: o_mode=3   
  ! Local
  integer :: nclean ! Number of clean components retained
  logical :: large
  !
  complex, allocatable :: fft(:,:,:)
  real, allocatable :: dmap(:,:,:)
  real, allocatable :: work(:)
  integer :: if,nf,nx,ny,mx,my,nt,nv,mt, ier
  real :: cpu0, cpu1
  real :: factor
  real(8) :: xinc, yinc, freq, vres
  !
  nclean = 0
  call sic_i4(line,0,1,nclean,.false.,error)
  if (error) return
  large = sic_present(0,2) ! Test
  !
  if (.not.associated(duv)) then
    call map_message(seve%e,rname,'DUV is not associated') 
    error = .true.
    return
  endif
  ! Code
  error = .false.
  call gag_cpu(cpu0)
  !
  ! Input data is the current UV Data  huv & duv
  !
  ! Input CCT is the current CCT Data (it should match the UV data)
  !
  ! Compact it into an image
  ! This depends on the CCT type, and is done in a subroutine
  !    First, define the sampling and image size 
  call cct_def_image (hcct,mx,my,nf,xinc,yinc,error)
  if (error) return
  !
  if (nf.ne.1) then
    if (nf.ne.huv%gil%nchan) then
      call map_message(seve%w,rname,'Velocity axis mis-match')
      error = .true.
      return
    endif
  endif
  !
  !    Then do the job
  allocate (dmap(mx,my,nf),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'MAP Allocation error')
    error = .true.
    return
  endif
  call cct_set_image (hcct,dcct,mx,my,nclean,xinc,yinc,nf,dmap,error)
  !
  ! Do we want the same velocity layout as the UV data or that of the MAP? 
  ! The UV data specifies the appropriate UV coverage, 
  ! but the MAP specifies the Spectroscopy 
  call gildas_null(huvm, type = 'UVT')
  call gdf_copy_header(huv,huvm,error) ! Will work in all cases
  !
  ! Retrieve minimum value
  if (hclean%loca%size.ne.0) then
    call mod_min_image (line,hclean,huv,freq,dmap,error)
  else
    call mod_min_image (line,hcct,huv,freq,dmap,error)
  endif
  if (error) return
  !
  ! Define the image size
  call mod_fft_size(large,mx,my,nx,ny)
  call gag_cpu(cpu1)
  !
  ! Get Virtual Memory & compute the FFT
  allocate (fft(nx,ny,nf),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'FFT space allocation error')
    error = .true.
    return
  endif
  !
  ! See UV_RESTORE also for this code
  if (nx.eq.mx .and. ny.eq.my) then
    fft(:,:,:) = cmplx(dmap,0.0)
  else
    do if = 1,nf
      call plunge_real (dmap(:,:,if),mx,my,fft(:,:,if),nx,ny)
    enddo
  endif
  ! Free map
  deallocate (dmap,stat=ier)
  allocate (work(2*max(nx,ny)),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'FFT work allocation error')
    error = .true.
    return
  endif
  !
  ! Compute the FFT
  call do_fft(nx,ny,nf,fft,work)
  call gag_cpu(cpu1)
  !
  !
  huvm%gil%dim(1) = 7+3*nf
  huvm%gil%ref(1)  = hcct%gil%ref(hcct%gil%faxi)
  huvm%gil%val(1)  = freq
  !
  ! Set the velocity resolution
  vres = hcct%gil%vres
  huvm%gil%vres = vres
  huvm%gil%fres = -vres*freq/299792.458d0  ! Velocity in km/s
  huvm%gil%inc(1)  = huvm%gil%fres 
  !
  huvm%gil%freq = freq
  huvm%char%line = hcct%char%line 
  huvm%gil%voff = hcct%gil%voff
  !
  ! Set the number of channels
  huvm%gil%nchan = nf
  huvm%gil%convert(:,1) = hcct%gil%convert(:,hcct%gil%faxi)
  ! 
  ! Define scaling factor to Flux: we are in Jy, so this is simple
  factor = 1.0
  !
  if (allocated(duvm)) deallocate(duvm)
  allocate (duvm(huvm%gil%dim(1),huvm%gil%dim(2)),stat=ier)
  if (ier.ne.0) then
    call map_message(seve%e,rname,'UV Model allocation error')
    error = .true.
    return
  endif
  nt = huvm%gil%dim(1)
  nv = huvm%gil%dim(2)
  mt = huv%gil%dim(1)
  !
  ! At this stage, copy the DAPs and Weights
  call copyuv (nt,nv,duvm,mt,duv)
  !
  ! Now compute the model
  call do_uvmodel(duvm, nt, nv, fft,nx,ny,nf,freq,xinc,yinc,factor)
  !
  call gag_cpu(cpu1)
  error = .false.
end subroutine cct_fast_uvmodel
!<FF>
subroutine mod_min_image(line,hmap,huv,freq,dmap,error)
  use gkernel_types
  use gkernel_interfaces
  use gbl_message
  !---------------------------------------------------------------------
  ! @ private-mandatory
  !
  ! Support routine for command MODEL
  !   Define output frequency and truncate the data range if needed
  !---------------------------------------------------------------------
  character(len=*), intent(in) :: line  ! Command line
  type(gildas), intent(in) :: hmap      ! Header of input data set
  type(gildas), intent(in) :: huv       ! Header of input UV set
  real(8), intent(inout) :: freq        ! Frequency of output    
  real, intent(inout) :: dmap(:,:,:)    ! Image data
  logical, intent(inout) :: error
  !
  integer, parameter :: o_minval=1
  integer, parameter :: o_mode=3
  real(kind=8), parameter :: pi=3.14159265358979323846d0
  character(len=*), parameter :: rname='MODEL'
  character(len=12), parameter :: cimage='IMAGE       '
  character(len=12), parameter :: cuv   ='UV_DATA     '
  
  !
  integer :: narg, nc
  real :: fmin, area, jyperk
  character(len=32) :: chain
  !
  ! Override output frequency if needed
  if (sic_present(o_mode,2)) then
    call sic_ke(line,o_mode,2,chain,nc,.true.,error)
    nc = min(nc,12)
    if (chain(1:nc).eq.cimage(1:nc)) then
      freq = hmap%gil%freq+hmap%gil%fres*((hmap%gil%dim(3)+1)*0.5-hmap%gil%ref(3))
    else if (chain(1:nc).eq.cuv(1:nc)) then
      freq = gdf_uv_frequency(huv)
    else
      call sic_r8(line,o_mode,2,freq,.false.,error)
      if (error) return
    endif
  else
    freq = hmap%gil%freq+hmap%gil%fres*((hmap%gil%dim(3)+1)*0.5-hmap%gil%ref(3))
  endif
  !
  narg = sic_narg(o_minval)  ! /MINVAL option
  if (narg.le.0) return
  !
  fmin = 0.
  call sic_r4(line,o_minval,1,fmin,.true.,error)
  if (error) return
  !
  if (narg.gt.1) then
    call sic_ch(line,o_minval,2,chain,nc,.true.,error)
    if (error) return
    if (chain(1:nc).eq.'sigma') then
      fmin = fmin * max(hmap%gil%noise,hmap%gil%rms)
    elseif (chain(1:nc).eq.'mJy') then
      fmin = 1e-3*fmin
    elseif (chain(1:nc).eq.'K') then
      if (hmap%gil%majo.ne.0) then
        area = pi*hmap%gil%majo*hmap%gil%mino/4/log(2.0)
        jyperk = 2*1.38e3*area/(299792458d0/freq*1d-6)**2
        fmin = fmin * jyperk 
      else
        call map_message(seve%e,rname,'Unit K unsupported in this context')
        error = .true.
        return
      endif      
    elseif (chain(1:nc).eq.'Jy') then
      fmin = fmin
    else
      call map_message(seve%e,rname,'Unrecognized unit '//chain(1:nc))
      error = .true.
      return
    endif
  endif
  where (dmap.lt.fmin)  dmap = 0.
end subroutine mod_min_image
!<FF>
subroutine do_uvmodel (visi,nc,nv,a,nx,ny,nf,   &
     &    freq,xinc,yinc,factor)
  !---------------------------------------------------------------------
  ! @ public
  !
  ! IMAGER
  !
  ! Compute the MODEL UV data set from the current CCT table
  !
  !     Uses an intermediate FFT with further interpolation for
  !     better speed than UV_CCT
  ! CAUTION
  !     Frequency (and hence Lambda/D) is assumed constant 
  !---------------------------------------------------------------------
  !
  integer, intent(in) :: nc                     ! Size of visibility
  integer, intent(in) :: nv                     ! Number of visibilities
  real, intent(inout) :: visi(nc,nv)            ! Visibilities
  integer, intent(in) :: nx                     ! X Size of image
  integer, intent(in) :: ny                     ! Y Size of image
  integer, intent(in) :: nf                     ! Number of frequencies
  complex, intent(in) :: a(nx,ny,nf)            ! Clean Component Image
  real(8), intent(in) :: freq                   ! Reference frequency
  real(8), intent(in) :: xinc                   ! X Pixel increment
  real(8), intent(in) :: yinc                   ! Y Pixel increment
  real, intent(in) :: factor                    ! Flux scale factor
  ! Local
  real(kind=8), parameter :: clight=299792458d0
  real(kind=8) :: kwx,kwy,stepx,stepy,lambda,bfin(2),xr,yr
  complex(kind=8) :: aplus,amoin,azero,afin
  integer :: i,if,ia,ja
  logical :: inside
  equivalence (afin,bfin)
  !
  lambda = clight/(freq*1d6)
  stepx = 1.d0/(nx*xinc)*lambda
  stepy = 1.d0/(ny*yinc)*lambda
  !
  ! Loop on visibility
  do i = 1, nv
    kwx =  visi(1,i) / stepx + dble(nx/2 + 1)
    kwy =  visi(2,i) / stepy + dble(ny/2 + 1)
    ia = int(kwx)
    ja = int(kwy)
    inside = (ia.gt.1 .and. ia.lt.nx) .and.   &
        &      (ja.gt.1 .and. ja.lt.ny)
    if (inside) then
      xr = kwx - ia
      yr = kwy - ja
      do if=1,nf
        !
        ! Interpolate (X or Y first, does not matter in this case)
        aplus = ( (a(ia+1,ja+1,if)+a(ia-1,ja+1,if)   &
            &          - 2.d0*a(ia,ja+1,if) )*xr   &
            &          + a(ia+1,ja+1,if)-a(ia-1,ja+1,if) )*xr*0.5d0   &
            &          + a(ia,ja+1,if)
        azero = ( (a(ia+1,ja,if)+a(ia-1,ja,if)   &
            &          - 2.d0*a(ia,ja,if) )*xr   &
            &          + a(ia+1,ja,if)-a(ia-1,ja,if) )*xr*0.5d0   &
            &          + a(ia,ja,if)
        amoin = ( (a(ia+1,ja-1,if)+a(ia-1,ja-1,if)   &
            &          - 2.d0*a(ia,ja-1,if) )*xr   &
            &          + a(ia+1,ja-1,if)-a(ia-1,ja-1,if) )*xr*0.5d0   &
            &          + a(ia,ja-1,if)
        ! Then Y (or X)
        afin = ( (aplus+amoin-2.d0*azero)   &
            &          *yr + aplus-amoin )*yr*0.5d0 + azero
        !
        visi(5+3*if,i) =  bfin(1)*factor
        ! There was a - sign in the precedent version
        visi(6+3*if,i) =  bfin(2)*factor
      enddo
    else
      print *,'Error Visi ',i,ia,nx,ja,ny
    endif
  enddo
end subroutine do_uvmodel
!<FF>
subroutine do_fft (nx,ny,nf,fft,work)
  integer, intent(in)  :: nx                     !
  integer, intent(in)  :: ny                     !
  integer, intent(in)  :: nf                     !
  complex, intent(inout) :: fft(nx,ny,nf)
  real, intent(inout)  :: work(2*max(nx,ny))
  ! Local
  integer :: if,dim(2)
  !
  ! Loop on channels
  dim(1) = nx
  dim(2) = ny
  do if = 1, nf
    call fourt(fft(:,:,if),dim,2,1,1,work)
    call recent(nx,ny,fft(:,:,if))
  enddo
end subroutine do_fft
!<FF>
subroutine copyuv (nco,nv,out,nci,in)
  !---------------------------------------------------------------------
  ! @ public
  !
  ! IMAGER
  !
  ! Copy structure of UV data, but not the (Real,Imag) columns
  !---------------------------------------------------------------------
  integer, intent(in)  :: nco                    ! Size of output visi.
  integer, intent(in)  :: nv                     ! Number of visibilities
  real, intent(out)  :: out(nco,nv)              ! Output Visibilities
  integer, intent(in) :: nci                     ! Size of input visi.
  real, intent(in)  :: in(nci,nv)                ! Input visibilities
  ! Local
  integer :: i,j
  !
  ! This does not handle extra columns
  do i=1,nv
    out(1:7,i) = in(1:7,i)
    do j=8,nco,3
      out(j,i) = 0
      out(j+1,i) = 0
      out(j+2,i) = in(10,i)
    enddo
  enddo
end subroutine copyuv
!
subroutine cct_def_image (hima,mx,my,nf,xinc,yinc,error)
  use image_def
  use imager_interfaces, only : map_message
  use gbl_message
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !
  ! Define Image size from CCT information.
  ! Supports both layouts of CCT tables.
  !---------------------------------------------------------------------
  type (gildas), intent(in) :: hima ! Input CCT Table
  integer, intent(out) :: mx,my,nf  ! Ouput data cube size
  real(8), intent(out) :: xinc,yinc ! Pixel size
  logical, intent(out) :: error     ! Error flag
  !
  error = .false.
  if (hima%char%code(3).eq.'COMPONENT') then
    call map_message(seve%i,'UV_FCCT','Clean Components from IMAGER')
    nf = hima%gil%dim(2)  ! Number of channels
    mx = (hima%gil%ref(1)-1)*2
    xinc = hima%gil%inc(1)
    my = (hima%gil%ref(3)-1)*2
    yinc = hima%gil%inc(3)
  else
    call map_message(seve%w,'UV_FCCT','Clean Components from old CLEAN Task')
    nf = hima%gil%dim(3)
    mx = (hima%gil%ref(1)-1)*2
    xinc = hima%gil%inc(1)
    my = (hima%gil%ref(2)-1)*2
    yinc = hima%gil%inc(2)
  endif
end subroutine cct_def_image
!
subroutine cct_set_image (hcct,clean,mx,my,mc,xinc,yinc,nf,image,error)
  use image_def
  use gbl_message
  use imager_interfaces, only : map_message
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !
  ! Fill an Image from the list of Clean Components 
  !---------------------------------------------------------------------
  type (gildas), intent(in) :: hcct         ! CCT Table header
  real clean(hcct%gil%dim(1),hcct%gil%dim(2),hcct%gil%dim(3))
  integer, intent(in) :: mx,my,nf       ! Output data cube size
  integer, intent(in) :: mc             ! Max component number
  real(8), intent(in) :: xinc,yinc      ! Pixel size
  real, intent(out) :: image(mx,my,nf)  ! Output data
  logical, intent(out) :: error         ! Error flag
  !
  integer lc,nc,kc
  integer ic,jf
  integer ix,iy
  character(len=80) :: mess
  !
  image = 0
  if (hcct%char%code(3).eq.'COMPONENT') then
    lc = hcct%gil%dim(1)
    nc = hcct%gil%dim(2)  ! Number of channels
    if (nc.ne.nf) then
      write(mess,*) 'Channel mismatch ',nc,nf
      call map_message(seve%e,'MODEL',mess)
      error = .true.
      return
    endif
    if (mc.eq.0) then
      kc = hcct%gil%dim(3)  ! Number of components
    else
      kc = min(mc,hcct%gil%dim(3))
    endif
    !
    do jf = 1,nf
      do ic = 1,kc
        if (clean(3,jf,ic).ne.0) then
          ix = nint(clean(1,jf,ic)/xinc)+mx/2+1
          iy = nint(clean(2,jf,ic)/yinc)+my/2+1
          image(ix,iy,jf) = image(ix,iy,jf) + clean(3,jf,ic)
        else
          exit ! No more components for this channel
        endif
      enddo
    enddo
  else
    lc = hcct%gil%dim(1)
    if (mc.eq.0) then
      kc = hcct%gil%dim(2)  ! Number of components
    else
      kc = min(mc,hcct%gil%dim(2))
    endif
    nc = hcct%gil%dim(3)
    if (nc.ne.nf) then
      write(mess,*) 'Channel mismatch ',nc,nf
      call map_message(seve%e,'MODEL',mess)
      error = .true.
      return
    endif
    do jf = 1,nf
      do ic = 1,kc
        if (clean(1,ic,jf).ne.0) then
          ix = nint(clean(2,ic,jf))
          iy = nint(clean(3,ic,jf))
          image(ix,iy,jf) = image(ix,iy,jf) + clean(1,ic,jf)
        else
          exit ! No more components for this channel
        endif
      enddo
    enddo
  endif
end subroutine cct_set_image
!
subroutine mod_fft_size(large,mx,my,nx,ny)
  !---------------------------------------------------------------------
  ! @ private
  !
  ! IMAGER
  !   Define the intermediate FFT size - Make it square by default
  !---------------------------------------------------------------------
  logical, intent(in) :: large    ! Should size be enlarged ?
  integer, intent(in) :: mx,my    ! Input map size
  integer, intent(out) :: nx,ny   ! Output fft size
  !
  integer :: kxy, mxy
  real :: rxy
  !
  mxy = max(mx,my)
  rxy = log(float(mxy))/log(2.0)
  kxy = nint(rxy)
  if (kxy.lt.rxy) kxy = kxy+1
  nx = 2**kxy
  if (large) nx = max(mxy,min(4*nx,4096))
  ny = nx
end subroutine mod_fft_size
