!!!!!
!
!fichier g2s_g2s.f90
!
!Entree principale du module G2S.
!
!!!!!!

subroutine G2S(NENTRY,HENTRY,IENTRY,JENTRY,KENTRY)
  use my_lcmput_mod
  use salget_funs_mod
  use celluleBase
  use cellulePlaced
  use boundCond
  use ptNodes
  use pretraitement
  use derivedPSPLOT
  use track
  use segArc
  implicit none

  integer NENTRY
  integer IENTRY,JENTRY
  type(c_ptr) KENTRY
  character*12 HENTRY
  dimension IENTRY(*),JENTRY(*),KENTRY(*),HENTRY(*)

! INPUT/OUTPUT PARAMETERS:
!  NENTRY : NUMBER OF LINKED LISTS AND FILES USED BY THE MODULE.
!  HENTRY : CHARACTER*12 NAME OF EACH LINKED LIST OR FILE.
!  IENTRY : =1 LINKED LIST; =2 XSM FILE; =3 SEQUENTIAL BINARY FILE;
!           =4 SEQUENTIAL ASCII FILE; =5 DIRECT ACCESS FILE.
!  JENTRY : =0 THE LINKED LIST OR FILE IS CREATED.
!           =1 THE LINKED LIST OR FILE IS OPEN FOR MODIFICATIONS;
!           =2 THE LINKED LIST OR FILE IS OPEN IN READ-ONLY MODE.
!  KENTRY : FILE UNIT NUMBER OR LINKED LIST ADDRESS.
!           DIMENSION HENTRY(NENTRY),IENTRY(NENTRY),JENTRY(NENTRY),
!           KENTRY(NENTRY)

  integer,parameter :: dimTabCelluleBase = 1000
  integer,parameter :: dimTabSegArc = 100000

  type(c_ptr)  :: ipGeo,ipGeo_1
  integer      :: sizeB,sizeP,sizeSA,nbNode,nbCLP,ilong,nbFlux,ipSal,ipPs
  character(len=12) :: name_geom,nammy
  logical      :: empty,lcm
  logical,parameter :: drawMix = .false. ! set to .true. to draw the mix numbers
  integer,allocatable,dimension(:) :: gig,merg
  integer,dimension(10) :: datain
  integer      :: lgMaxGig=0
  if ((nentry == 2).and.(IENTRY(2) == 4)) then
     !generating ps file from Sal file
     ipPs   = FILUNIT(KENTRY(1)) ! psfile generated
     g_psp_isEpsFile = (index(HENTRY(1),'.eps')/=0) !is it an eps file ?
     ipSal  = FILUNIT(KENTRY(2)) ! salfile read
     ipGeo_1= c_null_ptr ! no geometry read
     ! check that second argumnet is file to write
     ! then the tracking object
     if ((IENTRY(1) /= 4) .or. (JENTRY(1) /= 0)) &
          call XABORT('G2S: a new file was expected for the postscript file')
     if ((IENTRY(2) /= 4) .or. (JENTRY(2) /= 2)) &
          call XABORT('G2S: expecting Sal file in read-only mode')
  else if ((nentry == 2).and.(IENTRY(2) <= 2)) then
     !generating tracking object and sal file
     ipPs   = -1        ! no postscript file
     ipSal  = FILUNIT(KENTRY(1)) ! salfile generated
     ipGeo_1= KENTRY(2) ! geometry read
     ! check that second argumnet is file to write
     ! then the tracking object
     if ((IENTRY(1) /= 4) .or. (JENTRY(1) /= 0)) &
          call XABORT('G2S: a new ASCII file was expected for writing geometry')
     if ((IENTRY(2) > 2) .or. (JENTRY(2) /= 2)) &
          call XABORT('G2S: expecting LCM geometry in read-only mode(1)')
  else if ((nentry == 3).and.(IENTRY(1) == 4)) then
     !generating sal file and ps file from LCM geometry
     ipSal  = FILUNIT(KENTRY(1)) ! salfile generated
     ipPs   = FILUNIT(KENTRY(2)) ! psfile generated
     g_psp_isEpsFile = (index(HENTRY(2),'.eps')/=0) !is it an eps file ?
     ipGeo_1= KENTRY(3) ! geometry read
     if ((IENTRY(1) /= 4) .or. (JENTRY(1) /= 0)) &
          call XABORT('G2S: a new file was expected for writing geometry')
     if ((IENTRY(2) /= 4) .or. (JENTRY(2) /= 0)) &
          call XABORT('G2S: a new file was expected for the postscript file')
     if ((IENTRY(3) > 2) .or. (JENTRY(3) /= 2)) &
          call XABORT('G2S: expecting LCM geometry in read-only mode(2)')
  else
     call XABORT('G2S: you must provide 2 or 3 arguments')
  end if

  sizeB = 0   !cellules de base
  sizeP = 0   !cellules placees
  sizeSA = 0  !elements geometriques
  if(c_associated(ipGeo_1)) then
     ! lecture of the geometry name
     call LCMINF(ipGeo_1,name_geom,nammy,empty,ilong,lcm)
  
     ! copy the input geometric object
     call lcmop(ipGeo,'geom_copy',0,1,0)
     call lcmequ(ipGeo_1,ipGeo)

     !initialisation des differents tableaux
     !write(*,*) 'debut : initializeData'
     call initializeData(dimTabCelluleBase,dimTabSegArc)
     !write(*,*) 'fin   : initializeData'

     !pretraitement des donnees lues (remplace la partie python)
     !+complession des cellules de base et remplissage du tableau
     !des cellules placees
     !write(*,*) 'debut : prepareData'
     call prepareData(ipGeo,sizeB,sizeP,lgMaxGig)
     write(*,*) 'fin   : prepareData lgMaxGig=',lgMaxGig

     !en sortie, toutes les cellules de base ont tous leurs
     !champs remplis, et le tableau des cellules placees est
     !pret

     !eclatement des cellules
     !write(*,*) 'debut : splitCells'
     call splitCells(sizeP,sizeSA)
     !write(*,*) 'fin   : splitCells'

     !creation de nouveaux segements aux interfaces des cellules
     !et elimination des doublons
     !write(*,*) 'debut : addSegsAndClean'
     call addSegsAndClean(sizeSA)
     !write(*,*) 'fin   : addSegsAndClean'

     !prise en compte des conditions aux limites
     !write(*,*) 'debut : appliBoundariConditions'
     call appliBoundariConditions(ipGeo,sizeSA,nbCLP)
     !write(*,*) 'fin   : appliBoundariConditions'

     !calcul des nodes delimites par les elements
     !write(*,*) 'debut : createNodes'
     call createNodes(sizeSA,nbNode)
     if(nbNode > dimTabCelluleBase) call XABORT('g2s_g2s: nbNode overflow')
     if(sizeSA > dimTabSegArc) call XABORT('g2s_g2s: sizeSA overflow')
     !write(*,*) 'fin   : createNodes'
     
     !calcul des arrays gig et merg
     !write(*,*) 'debut : generateTrack'
     allocate(gig(nbNode*lgMaxGig),merg(nbNode))
     call generateTrack(sizeP,sizeSA,nbNode,lgMaxGig,gig,merg)
     !write(*,*) 'fin   : generateTrack'
     nbFlux=maxval(merg)
  else
     if (JENTRY(nentry) == 0) call XABORT('G2S: an existing Salomon file is expected')
     !initialisation de TabSegArc
     call salget(datain,4,ipSal,0,'dimensions for geometry')
     nbNode=datain(3)
     sizeSA=datain(4)
     rewind(ipSal)
     !write(*,*) 'debut : initializeData'
     call initializeTabSegArc(sizeSA)
     call initializebCData()  
     !write(*,*) 'fin   : initializeData'
     allocate(merg(nbNode))
     call generateTabSegArc(ipSal,sizeSA,nbNode,nbCLP,nbFlux,merg,name_geom)
  endif

  !impression des segArc charges
  !write(*,*) 'debut : drawSegArc'
  if (ipPs /= -1) call drawSegArc(ipPs,sizeSA,.true.,drawMix)
  !write(*,*) 'fin   : drawSegArc'

  if(c_associated(ipGeo_1)) then
     !creation du fichier de commande SAL
     !write(*,*) 'debut : generateSALFile'
     call generateSALFile(ipSal,sizeSA,nbNode,nbCLP,nbFlux,merg,name_geom)
     !write(*,*) 'fin   : generateSALFile'
     deallocate(gig)
     call lcmcl(ipGeo,2)
  endif
  deallocate(merg)

  print *,"  At end of G2S:"
  print *,"    ",sizeSA,"segs or arcs"
  print *,"    ",nbNode,"nodes"
  print *,"    ",nbCLP,"boundary conditions other than default"

  !liberation de la memoire allouee
  call destroyData(sizeB,sizeP,sizeSA)
end subroutine G2S

subroutine initializeData(dimTabCelluleBase,dimTabSegArc)
  use celluleBase
  use cellulePlaced
  use boundCond
  use segArc
  implicit none
  integer,intent(in) :: dimTabCelluleBase,dimTabSegArc

  call initializeTabCelluleBase(dimTabCelluleBase)
  call initializeTabCellulePlaced()
  call initializeTabSegArc(dimTabSegArc)
  call initializebCData()  
end subroutine initializeData

subroutine destroyData(szB,szP,szSA)
  use celluleBase
  use cellulePlaced
  use boundCond
  use segArc
  implicit none
  integer,intent(in) :: szB,szP,szSA

  if(szB /= 0) call destroyTabCelluleBase(szB)
  if(szP /= 0) call destroyTabCellulePlaced(szP)
  call destroyTabSegArc(szSA)
  call destroybCData()
end subroutine destroyData
