
/* ###--------------------------------------------------------------### */
/*                                                                      */
/*    File        : flatten_beh.c                                       */
/*    Authors     : DE SMET bernard  &  GERAUD denis                    */
/*    Update      : VUONG Huu Nghia			                */
/*    date        : 13/04/1992                                          */
/*                                                                      */
/*    description : Gives a full VHDL behavioural description from a	*/
/*                  structural (lofig) view, by raising all the 	*/
/*		    equations of the leaves.                            */
/*                                                                      */
/* ###--------------------------------------------------------------### */

/* ###--------------------------------------------------------------### */
/*									*/
/*   Dec. 15 1992 :							*/
/*     - A Linkage connector maybe INOUT, this case was not considered	*/
/*       Now check if a linkage signal is INOUT, by using the BERIN	*/
/*       element of tampbefig.						*/
/*									*/
/* ###--------------------------------------------------------------### */

/* ###--------------------------------------------------------------### */
/*   									*/
/*   Nov. 10 1992 :							*/
/*     - Now, instead of generating a random unique signal name for	*/
/*       the auxilary variables and for the registers, generate a	*/
/*       path-name with the instance name.				*/
/*									*/
/* ###--------------------------------------------------------------### */

#include <stdio.h>
#include <string.h>
#include MUT_H
#include LOG_H
#include MLO_H
#include BEH_H
#include "beh_flatten.h"

/* ###--------------------------------------------------------------### */
/*                                                                     	*/
/*             GLOBALS VARIABLES                                       	*/
/*				   				       	*/
/* ###--------------------------------------------------------------### */

t_pile *FIFO = NULL;		/* The FIFO of the connectors		*/
pTH     tablesignauxtraiter; 
pTH     tablenom; 
pTH     tableinstance; 
pTH     tablelofig;

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : creer_befig()						*/
/*   Content  : Creating and initializing the befig resulted		*/
/*   Return   : pointer on the befig					*/
/*								        */
/* ###--------------------------------------------------------------### */

struct befig *creer_befig(loclofig,locnewbefig)

struct lofig *loclofig;
struct befig *locnewbefig;

  {
  struct locon *locon_courant = NULL;
  struct bepor *bepor_courant = NULL;
  struct berin *berin_courant = NULL;

  /* Creating the new befig */
  locnewbefig = beh_addbefig(locnewbefig,namealloc(loclofig->NAME));

  /* Filling the BEPOR */
  locon_courant = loclofig ->LOCON;
  while(locon_courant != NULL)
    { 
    bepor_courant = beh_addbepor(bepor_courant, locon_courant->NAME, 
                                 locon_courant->DIRECTION,'B');
    /* Filling the BERIN with the signals IN and INOUT */
    if((locon_courant->DIRECTION == 'I')||
       (locon_courant->DIRECTION == 'B')||
       (locon_courant->DIRECTION == 'T')) 
      { 
      berin_courant = beh_addberin(berin_courant,locon_courant->NAME);
      }
    locon_courant = locon_courant->NEXT;
    }
  locnewbefig->BEREG = NULL;
  locnewbefig->BEMSG = NULL;
  locnewbefig->BERIN = berin_courant;
  locnewbefig->BEOUT = NULL;
  locnewbefig->BEBUS = NULL;
  locnewbefig->BEAUX = NULL;
  locnewbefig->BEPOR = (struct bepor *)reverse(bepor_courant);
  locnewbefig->CIRCUI = NULL;
  locnewbefig->USER = NULL;
  return(locnewbefig);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : chercher_signal()					*/
/*   Content  : Search the loins using the considered signal		*/
/*   Return   : The pointer on the loins found.				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct loins *chercher_signal(signal,pt_loins,ptbef)
char *signal;
struct loins *pt_loins;
struct befig *ptbef;

  {
  struct loins *locloins;
  struct locon *loclocon;
  struct losig *loclosig;
  struct chain *locchain;
  struct befig *locbef;
  struct bepor *locbepor;

  locloins = pt_loins;
  /* scanning all the instances */
  while(locloins != NULL)
    { 
    if(searchTH(tableinstance,locloins->INSNAME) != 0)  
      { 
      /* Instance not treated yet */
      loclocon = locloins->LOCON;
      /* scanning all the locon of the instance */
      while(loclocon != NULL)
	{ 
        loclosig = loclocon->SIG;
	locchain = loclosig->NAMECHAIN;
	if(strcmp(locchain->DATA,signal) == 0)
	  {
          /* The losig use the considered signal, now check	*/
          /* than the model use this signal as output.		*/	
	  locbef = ptbef;
          /* Searching the befig */
	  while(strcmp(locloins->FIGNAME,locbef->NAME) != 0)
            {
	    locbef = locbef->NEXT;
            }
	  locbepor = locbef->BEPOR;
          /* Searching the signal in the BEPOR */
	  while (strcmp(locbepor->NAME,loclocon->NAME) != 0)
            {
	    locbepor = locbepor->NEXT;
            }
	  if((locbepor->DIRECTION == 'O') || 
             (locbepor->DIRECTION == 'Z') || 
             (locbepor->DIRECTION == 'T') || 
             (locbepor->DIRECTION == 'X') || 
             (locbepor->DIRECTION == 'B'))   
            {  
            /* Check if the connector is output */
	    return(locloins);
            }
          }
	loclocon = loclocon->NEXT;
	}
      }
    locloins = locloins->NEXT;
    }
  return(NULL);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : addOrdonneBereg()					*/
/*   Content  : Add a bereg to a bereg list with an alphabetical order	*/
/*              to permit vectorised signals				*/
/*   Return   : head pointer on the bereg list resulted			*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct bereg * addOrdonneBereg(head,pt_bereg)
struct bereg * head;
struct bereg * pt_bereg;
  {
  struct bereg * tmp_bereg;
  struct bereg * previous_tmp_bereg;

  /* Case head = NULL ==> head = pt_bereg */
  if(head == NULL)
    {
    return(pt_bereg);
    } 
  previous_tmp_bereg = NULL;
  tmp_bereg = head;
  while(tmp_bereg != NULL)
    {
    if(naturalstrcmp(pt_bereg->NAME,tmp_bereg->NAME) > 0)
      {
      /* Case insert at the first place */
      if(tmp_bereg == head)
        {
        pt_bereg->NEXT = head;
        head = pt_bereg;
        return(head);
        }
      /* General case */
      pt_bereg->NEXT = previous_tmp_bereg->NEXT;
      previous_tmp_bereg->NEXT = pt_bereg;
      return(head);
      }
    previous_tmp_bereg = tmp_bereg;
    tmp_bereg = tmp_bereg->NEXT;
    } 
  /* Inserted at the end */
  previous_tmp_bereg->NEXT = pt_bereg;
  return(head);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : addOrdonneBeaux()					*/
/*   Content  : Add a beaux to a beaux list with an alphabetical order	*/
/*              to permit vectorised signals				*/
/*   Return   : head pointer on the beaux list resulted			*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct beaux * addOrdonneBeaux(head,pt_beaux)
struct beaux * head;
struct beaux * pt_beaux;
  {
  struct beaux * tmp_beaux;
  struct beaux * previous_tmp_beaux;

  /* Case head = NULL ==> head = pt_beaux */
  if(head == NULL)
    {
    return(pt_beaux);
    } 
  previous_tmp_beaux = NULL;
  tmp_beaux = head;
  while(tmp_beaux != NULL)
    {
    if(naturalstrcmp(pt_beaux->NAME,tmp_beaux->NAME) > 0)
      {
      /* Case insert at the first place */
      if(tmp_beaux == head)
        {
        pt_beaux->NEXT = head;
        head = pt_beaux;
        return(head);
        }
      /* General case */
      pt_beaux->NEXT = previous_tmp_beaux->NEXT;
      previous_tmp_beaux->NEXT = pt_beaux;
      return(head);
      }
    previous_tmp_beaux = tmp_beaux;
    tmp_beaux = tmp_beaux->NEXT;
    } 
  /* Inserted at the end */
  previous_tmp_beaux->NEXT = pt_beaux;
  return(head);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : addOrdonneBebux()					*/
/*   Content  : Add a bebux to a bebux list with an alphabetical order	*/
/*              to permit vectorised signals				*/
/*   Return   : head pointer on the bebux list resulted			*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct bebux * addOrdonneBebux(head,pt_bebux)
struct bebux * head;
struct bebux * pt_bebux;
  {
  struct bebux * tmp_bebux;
  struct bebux * previous_tmp_bebux;

  /* Case head = NULL ==> head = pt_bebux */
  if(head == NULL)
    {
    return(pt_bebux);
    } 
  previous_tmp_bebux = NULL;
  tmp_bebux = head;
  while(tmp_bebux != NULL)
    {
    if(naturalstrcmp(pt_bebux->NAME,tmp_bebux->NAME) > 0)
      {
      /* Case insert at the first place */
      if(tmp_bebux == head)
        {
        pt_bebux->NEXT = head;
        head = pt_bebux;
        return(head);
        }
      /* General case */
      pt_bebux->NEXT = previous_tmp_bebux->NEXT;
      previous_tmp_bebux->NEXT = pt_bebux;
      return(head);
      }
    previous_tmp_bebux = tmp_bebux;
    tmp_bebux = tmp_bebux->NEXT;
    } 
  /* Inserted at the end */
  previous_tmp_bebux->NEXT = pt_bebux;
  return(head);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : sortieDeCellule()					*/
/*   Content  : See if the connector is an output of the given cell.	*/
/*   Return   : 1 if true, 0 if false					*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

int sortieDeCellule(ptbef,cellule,connecteur)
struct befig *ptbef;
char *cellule;
char *connecteur;

  { 
  struct befig *befigcourant;
  struct bepor *beporcourant;

  befigcourant = ptbef;
  /* boucle sur les befig */
  while(strcmp(cellule,befigcourant->NAME) != 0)
    {
    befigcourant = befigcourant->NEXT;
    }
  /* quand on a le befig, on cherche le nom du locon dans le BEPOR */
  beporcourant = befigcourant->BEPOR;
  /* boucle sur les bepor */
  while(strcmp(beporcourant->NAME,connecteur) != 0)
    {
    beporcourant = beporcourant->NEXT;
    }
  /* quand on trouve le nom, il faut regarder dans DIRECTION si c est OUT */
  if((beporcourant->DIRECTION == 'O') || 
     (beporcourant->DIRECTION == 'B') ||
     (beporcourant->DIRECTION == 'Z') ||
     (beporcourant->DIRECTION == 'X') ||
     (beporcourant->DIRECTION == 'T'))  
    {
    return(1);
    }
  else 
    {
    return(0);
    }
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : tstbus()						*/
/*   Content  : count the amount of output connectors connected 	*/
/*              to the treated connector.				*/
/*   Return   : the amount found					*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

int tstbus(nom,lofig,ptbef)
char *nom;
struct lofig *lofig;
struct befig *ptbef;
  {
  struct loins *locloins;
  struct locon *loclocon;
  int nb = 0;

  locloins = lofig->LOINS;
  while(locloins != NULL)
    { 
    loclocon = locloins->LOCON;
    while(loclocon != NULL)
      {
      if(strcmp((char *)loclocon->SIG->NAMECHAIN->DATA,nom) == 0)
        {
        nb = nb + sortieDeCellule(ptbef,locloins->FIGNAME,loclocon->NAME);
        }
      loclocon = loclocon->NEXT;
      }
    locloins = locloins->NEXT;
    }
  return(nb);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : lire_locon()						*/
/*   Content  : read the locon of a lofig list and push the output	*/
/*              and the bused signals in FIFO				*/
/*   Return   :								*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void lire_locon(loclofig,ptbef)
struct lofig *loclofig;
struct befig *ptbef;

  {
  struct locon *locon_courant;
  t_elem *element;
  int i,n;

  locon_courant = loclofig->LOCON;
  while (locon_courant != NULL)
    {
    if((locon_courant->DIRECTION == 'O') ||
       (locon_courant->DIRECTION == 'B') ||
       (locon_courant->DIRECTION == 'T') ||
       (locon_courant->DIRECTION == 'X') ||
       (locon_courant->DIRECTION == 'Z')) 
      {
      n = tstbus(locon_courant->NAME,loclofig,ptbef);
      if((locon_courant->DIRECTION == 'O') ||
         (locon_courant->DIRECTION == 'B'))
        {
        if(n>1)
          {
          (void)fprintf(stderr,"flatbeh error : an output signal ('%s') has multiple driver\n",
                locon_courant->NAME);
          exit(1);
          }
        }
      for(i=0;i<n;i++)
	{
	element = (t_elem *)mbkalloc(sizeof(t_elem));
	if(n == 1)
          {
	  element->signal = BEOUT;
          }
	else 
          {
          element->signal = BEBUS;
          }
	element->name = locon_courant->NAME;
	element->next = NULL;
	FIFO = addPile(FIFO,element);
	}
      }
    locon_courant = locon_courant->NEXT ;
    }
  }

/* ###--------------------------------------------------------------### */
/*									*/
/*   Function : echanger()						*/
/*   Content  : substitute the names in an ABL				*/
/*   Return   :								*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void echanger(equ,nomavant,nomapres)
struct chain *equ;
char *nomavant,*nomapres;

  {
  if (ATOM(equ))
    {
    if (strcmp(VALUE_ATOM(equ),nomavant) == 0)
    equ->DATA = (void *)nomapres;
    }
  else
    {
    while ((equ = CDR(equ)) != NULL)
      {
      echanger (CAR(equ), nomavant, nomapres); 
      }
    }
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : rajouterPile()						*/
/*   Content  : Add in the stack the inputs of the treated cell		*/
/*   Return   :								*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void rajouterPile (ptlofig,element,listebefig,newbef)

struct lofig *ptlofig;
char         *element;
struct befig *listebefig, *newbef;

  {
  struct loins *loinscourant;
  struct locon *loconcourant;
  t_elem *elem;
  struct berin *locberin;
  int flag = 0;
  int count = 0;
  int i;

  if (searchTH(tablesignauxtraiter,element) == -1)/*si pas deja dans table*/
    {
    locberin = newbef->BERIN;
    /* Verify than the treated element isn't an entry of the bloc */
    while ((locberin != NULL) && (flag == 0))
      {
      if (strcmp (element,locberin->NAME) != 0)
        {
	locberin = locberin->NEXT;
        }
      else 
        {
        flag = 1;
        }
      }

    /* It is not an entry */
    if(locberin == NULL)
      {
      /* The signal is not in the stack */
      if(searchPile(FIFO,element) == 0)
	{
	loinscourant = ptlofig->LOINS;
	while(loinscourant != NULL)
	  { 
          loconcourant = loinscourant->LOCON;
	  while(loconcourant != NULL)
	  /* If it's the good name, take in the loins the figure name */
	    { 
            if(strcmp(element,loconcourant->SIG->NAMECHAIN->DATA) == 0)
              {
              count = count + sortieDeCellule(listebefig,loinscourant->FIGNAME,
                                              loconcourant->NAME);
              }
	    loconcourant = loconcourant->NEXT;
	    }
	  loinscourant = loinscourant->NEXT;
	  }
        for(i=0;i<count;i++)
	  {
	  elem=( t_elem *)mbkalloc(sizeof(t_elem));
	  elem->name = element;
	  elem->next = NULL;
	  if(count == 1)
            {
	    elem->signal = BEAUX;
            }
	  else 
            {
            elem->signal = BEBUX;
            }
	  FIFO = addPile(FIFO,elem);
	  }
	}
      }
    }
  }

/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : recopierBiabl()						*/
/*  Content  : duplicate a biabl list					*/
/*  Return   : pointer on the biabl list 				*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

struct biabl *recopierBiabl (locbiabl)
struct biabl *locbiabl;

  {
  struct biabl *resultat;

  resultat = NULL;
  while(locbiabl != NULL)
    {
    resultat = beh_addbiabl(resultat,NULL,copyExpr(locbiabl->CNDABL), 
                            copyExpr(locbiabl->VALABL));
    locbiabl = locbiabl->NEXT;
    }
  return(resultat);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : presentDansBereg()					*/
/*   Content  : Search "nom" in the bereg list				*/
/*   Return   : the found pointer or null				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct bereg *presentDansBereg ( tetebereg , nom)
struct bereg *tetebereg;
char *nom;
  {
  struct bereg *locbereg;

  locbereg = tetebereg;
  while((locbereg != NULL) && (strcmp (locbereg->NAME,nom) != 0))
    {
    locbereg = locbereg->NEXT;
    }
  return (locbereg);
  }  

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : presentDansBebus()					*/
/*   Content  : Search "nom" in the bebus list				*/
/*   Return   : the found pointer or null				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct bebus *presentDansBebus(tetebebus,nom)
struct bebus *tetebebus;
char *nom;
  {
  struct bebus  *locbebus;

  locbebus = tetebebus;
  while((locbebus != NULL) && (strcmp (locbebus->NAME,nom) != 0))
    {
    locbebus = locbebus->NEXT;
    }
  return(locbebus);
  }  

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : presentDansBebux()					*/
/*   Content  : Search "nom" in the bebux list				*/
/*   Return   : the found pointer or null				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct bebux *presentDansBebux ( tetebebux ,nom)
struct bebux *tetebebux;
char *nom;
  {
  struct bebux *locbebux;

  locbebux = tetebebux;
  while((locbebux != NULL) && (strcmp (locbebux->NAME,nom) != 0))
    {
    locbebux = locbebux->NEXT;
    }
  return (locbebux);
  }  

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : lierBiabl()						*/
/*   Content  : link together the two list of biabl			*/
/*   Return   : pointer on the biabl list				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */
 
struct biabl *lierBiabl (tetebiabl, biablajout)
struct biabl *tetebiabl, *biablajout;
  {
  struct biabl *locbiabl,*resultbiabl;

  resultbiabl = recopierBiabl(biablajout);
  locbiabl = resultbiabl;
  while(locbiabl->NEXT != NULL)
    {
    locbiabl = locbiabl->NEXT;
    }
  locbiabl->NEXT = tetebiabl;
  tetebiabl = resultbiabl;
  return(tetebiabl);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : estDansLocon()						*/
/*   Content  : Check if a signal is in a locon list of a lofig         */
/*   Return   : 1 if false, 0 if true					*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

int estDansLocon(nom,lof)
char *nom;
struct lofig *lof;

  {
  struct locon *loc;
 
  loc = lof->LOCON;
  while(loc != NULL)
    { 
    if(strcmp(loc->NAME,nom) == 0)
      {
      return(0);
      }
    else 
      {
      loc = loc->NEXT;
      }
    }
  return(1);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : modifierBefig()						*/ 
/*   Content  : for all the output, verify if they are in the LOCON	*/
/*              if they are, do nothing.				*/
/*              if they are not, put them in auxiliary signals		*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct befig *modifierBefig(bef,lof)
struct befig *bef;
struct lofig *lof;

  {
  struct beout *locbeout,*interbeout;
  struct beaux *locbeaux;
  struct bebus *locbebus,*interbebus;
  struct bebux *locbebux;
  struct biabl *resultbiabl;

  locbeout = bef->BEOUT ;
  locbeaux = bef->BEAUX ;
  locbebus = bef->BEBUS ;
  locbebux = bef->BEBUX ;

  while(locbeout != NULL)
    {
    interbeout = locbeout;
    if(estDansLocon(interbeout->NAME,lof) == 1)
      {
      bef->BEAUX = beh_addbeaux(bef->BEAUX,interbeout->NAME,
                                copyExpr(interbeout->ABL),NULL);
      locbeout = locbeout->NEXT;
      bef->BEOUT = beh_delbeout(bef->BEOUT,interbeout,'Y');
      }
    else 
      {
      locbeout = locbeout->NEXT;
      }
    }

  while (locbebus != NULL)
    {
    interbebus = locbebus;
    if(estDansLocon(interbebus->NAME,lof) == 1)
      {
      resultbiabl = recopierBiabl(interbebus->BIABL);
      bef->BEBUX = beh_addbebux(bef->BEBUX, interbebus->NAME, resultbiabl,
				NULL, interbebus->TYPE);
      locbebus = locbebus->NEXT;
      bef->BEBUS = beh_delbebus(bef->BEBUS,interbebus,'Y');
      }
    else 
      {
      locbebus = locbebus->NEXT;
      }
    }
  return(bef);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : ajouterTampon()						*/
/*   Content  : add the befig TAMPON to the resulted BEFIG		*/
/*   Return   : 							*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void ajouterTampon(newbefig,tambefig,loclof)
struct befig *newbefig, *tambefig;
struct lofig *loclof;

  {
  struct biabl *resultbiabl;
  struct beout *locbeout;
  struct berin *locberin;
  struct bepor *newbepor;
  struct beaux *locbeaux;
  struct bereg *locbereg,*interbereg;
  struct bebus *locbebus,*interbebus;
  struct bebux *locbebux,*interbebux;
   
  tambefig = modifierBefig(tambefig,loclof);

  locberin = tambefig->BERIN;
  locbeout = tambefig->BEOUT;
  locbeaux = tambefig->BEAUX;
  locbereg = tambefig->BEREG;
  locbebus = tambefig->BEBUS;
  locbebux = tambefig->BEBUX;

  while(locberin != NULL)
    {
    newbepor = newbefig->BEPOR;
    while(newbepor != NULL)
      {
      if((newbepor->DIRECTION == 'X') && (strcmp(newbepor->NAME,locberin->NAME) == 0))
        {
        newbepor->DIRECTION = 'K';
        break;
        }
      newbepor = newbepor->NEXT;
      }
    locberin = locberin->NEXT;
    }

  while(locbeout != NULL)
    {
    newbefig->BEOUT = beh_addbeout(newbefig->BEOUT,locbeout->NAME,
                                   copyExpr(locbeout->ABL),NULL);
    locbeout = locbeout->NEXT;
    }
  while(locbeaux != NULL)
    {
    newbefig->BEAUX = addOrdonneBeaux(newbefig->BEAUX,
                                      beh_addbeaux(NULL,locbeaux->NAME,
                                                   copyExpr(locbeaux->ABL),NULL));
    locbeaux = locbeaux->NEXT;
    }
  while(locbebus != NULL)
    {
    interbebus = presentDansBebus(newbefig->BEBUS,locbebus->NAME);
    if(interbebus == NULL)
      {
      resultbiabl = recopierBiabl(locbebus->BIABL);
      newbefig->BEBUS = beh_addbebus(newbefig->BEBUS,locbebus->NAME,
                                     resultbiabl,NULL,locbebus->TYPE);
      }
    else 
      {
      interbebus->BIABL = lierBiabl(interbebus->BIABL,locbebus->BIABL);
      }
    locbebus = locbebus->NEXT;
    }
  while(locbebux != NULL)
    {
    interbebux = presentDansBebux(newbefig->BEBUX,locbebux->NAME);
    if(interbebux == NULL)
      {
      resultbiabl = recopierBiabl(locbebux->BIABL);
      newbefig->BEBUX = addOrdonneBebux(newbefig->BEBUX,
                                        beh_addbebux(NULL,locbebux->NAME,
                                                     resultbiabl,NULL,locbebux->TYPE));
      }
    else 
      {
      interbebux->BIABL = lierBiabl(interbebux->BIABL,locbebux->BIABL);
      }
    locbebux = locbebux->NEXT;
    }
  while (locbereg != NULL)
    {
    interbereg = presentDansBereg(newbefig->BEREG,locbereg->NAME);
    if(interbereg == NULL)
      {
      resultbiabl = recopierBiabl(locbereg->BIABL);
      newbefig->BEREG = addOrdonneBereg(newbefig->BEREG,
                                        beh_addbereg (NULL,locbereg->NAME,
                                           resultbiabl,NULL)); 
      }
    else 
      {
      interbereg->BIABL = lierBiabl(interbereg->BIABL,locbereg->BIABL);
      }
    locbereg = locbereg->NEXT;
    }
  }

/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : echangerDansAbl()					*/
/*  Content  : Substitute the names in an ABL by adding $		*/
/*  Return   : pointer on the ABL					*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

struct chain *echangerDansAbl (locabl)
struct chain *locabl;

  {
  struct chain *list;
  char         *tampname;
  char          name[200];

  list =  supportChain_listExpr(locabl);
  while(list != NULL)
    {
    sprintf(name,"%s%c",(char *)list->DATA,'$');
    tampname = namealloc(name);
    echanger(locabl,(char *)list->DATA,tampname);
    list = list->NEXT;
    }
  return(locabl);
  }

/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : recopierEchangerBiabl()					*/
/*  Content  : duplicating a list of biabl and changing the names ($)	*/
/*  Return   : pointer on a biabl list         				*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

struct biabl *recopierEchangerBiabl(locbiabl)
struct biabl *locbiabl;
  {
  struct biabl *resultat;
  resultat = NULL;
  while(locbiabl != NULL)
    {
    resultat = beh_addbiabl(resultat, NULL,
			    echangerDansAbl(copyExpr(locbiabl->CNDABL)),
			    echangerDansAbl(copyExpr(locbiabl->VALABL)));
    locbiabl = locbiabl->NEXT;
    }
  return(resultat);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : recopier_Befig()					*/
/*   Content  : duplicate the befig in tampbefig adding $ to the names	*/
/*   Return   :  							*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void recopier_Befig(ptlofig,locloins,locbefig,tampbefig)
struct lofig *ptlofig;
struct loins *locloins;
struct befig *locbefig;
struct befig *tampbefig;

  {
  struct befig *bef;
  struct beaux *locbeaux;
  struct beout *locbeout;
  struct bebus *locbebus;
  struct bebux *locbebux;
  struct bereg *locbereg;
  struct berin *locberin;
  struct biabl *locbiabl;
  struct biabl *resultbiabl;
  struct chain *locabl;
  char *locname;
  char name[200];
  char *tampname;

  bef = locbefig;
  locname = locloins->FIGNAME;
  addTH(tableinstance,namealloc(locloins->INSNAME),0);
  /* searching the model */
  while((strcmp(bef->NAME,locname)!=0) && (bef != NULL))
    {
    bef = bef->NEXT;
    }

  /* Duplicating and modifying the BEAUX list */
  locbeaux = bef->BEAUX;
  while(locbeaux != NULL)
    {
    locabl = locbeaux->ABL;
    sprintf(name,"%s%c",locbeaux->NAME,'$');
    tampname = namealloc(name);
    tampbefig->BEAUX = beh_addbeaux(tampbefig->BEAUX,tampname,
				    echangerDansAbl(copyExpr(locabl)),NULL);
    locbeaux = locbeaux->NEXT;
    }

  /* Duplicating and modifying the BEOUT list */
  locbeout = bef->BEOUT;
  while(locbeout != NULL)
    {
    locabl = locbeout->ABL;
    sprintf(name,"%s%c",locbeout->NAME,'$');
    tampname = namealloc(name);
    tampbefig->BEOUT = beh_addbeout(tampbefig->BEOUT,tampname,
				    echangerDansAbl(copyExpr(locabl)),NULL);
    locbeout = locbeout->NEXT;
    }

  /* Duplicating and modifying the BEBUS list */
  locbebus = bef->BEBUS;
  while(locbebus != NULL)
    {
    sprintf(name,"%s%c",locbebus->NAME,'$');
    tampname = namealloc(name);
    locbiabl = locbebus->BIABL;
    resultbiabl = recopierEchangerBiabl(locbiabl);
    tampbefig->BEBUS = beh_addbebus(tampbefig->BEBUS,tampname,resultbiabl,
				    NULL,locbebus->TYPE);
    locbebus = locbebus->NEXT;
    }

  /* Duplicating and modifying the BEBUX list */
  locbebux= bef->BEBUX;
  while(locbebux != NULL)
    {
    sprintf(name,"%s%c",locbebux->NAME,'$');
    tampname = namealloc(name);
    locbiabl = locbebux->BIABL;
    resultbiabl = recopierEchangerBiabl(locbiabl);
    tampbefig->BEBUX = beh_addbebux(tampbefig->BEBUX,tampname,resultbiabl,
	                            NULL,locbebux->TYPE);
    locbebux = locbebux->NEXT;
    }

  /* Duplicating and modifying the BEREG list */
  locbereg= bef->BEREG;
  while(locbereg != NULL)
    {
    sprintf(name,"%s%c",locbereg->NAME,'$');
    tampname = namealloc(name);
    locbiabl = locbereg->BIABL;
    resultbiabl = recopierEchangerBiabl(locbiabl);
    tampbefig->BEREG = beh_addbereg(tampbefig->BEREG,tampname,resultbiabl,NULL);
    locbereg = locbereg->NEXT;
    }

  /* Duplicating and modifying the BERIN list */
  locberin= bef->BERIN;
  while(locberin != NULL)
    {
    sprintf(name,"%s%c",locberin->NAME,'$');
    tampname = namealloc(name);
    tampbefig->BERIN = beh_addberin(tampbefig->BERIN,tampname);
    locberin = locberin->NEXT;
    }
  }

/* ###--------------------------------------------------------------### */
/*	  						                */
/*   Function : simplifierBefig()					*/
/*   Content  : Simplify the befig by substituting the auxiliary 	*/
/*              variables.						*/
/*   Return   :								*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void simplifierBefig (locnewbefig)
struct befig *locnewbefig;
  {
  struct beaux *locbeaux, *intbeaux;
  struct beout *locbeout;
  struct bebus *locbebus;
  struct bebux *locbebux;
  struct bereg *locbereg;
  chain_list *locchain;
  struct biabl *locbiabl;

  locbeaux = locnewbefig->BEAUX;

  while(locbeaux != NULL)
    {
    intbeaux = locbeaux->NEXT;
    while(intbeaux != NULL)
      {
      locchain = intbeaux->ABL;
      if(searchExpr(locchain,locbeaux->NAME) == 1)
        {
        if(!ATOM(intbeaux->ABL))
          {
   	  substPhyExpr(intbeaux->ABL,locbeaux->NAME,locbeaux->ABL);
          }
        else 
          {
          intbeaux->ABL = copyExpr(locbeaux->ABL);
          }
        }
      intbeaux = intbeaux->NEXT;
      }
    locbeout = locnewbefig->BEOUT;
    while(locbeout != NULL)
      {
      locchain = locbeout->ABL;
      if(searchExpr (locchain,locbeaux->NAME) == 1)
        {
        if(!ATOM(locbeout->ABL))
          {
   	  substPhyExpr(locbeout->ABL, locbeaux->NAME, locbeaux->ABL);
          }
        else 
          {
          locbeout->ABL = copyExpr(locbeaux->ABL);
          }
        }
      locbeout = locbeout->NEXT;
      }
    locbebus = locnewbefig->BEBUS;
    while(locbebus != NULL)
     {
     locbiabl = locbebus->BIABL;
     while(locbiabl != NULL)
       {
       locchain = locbebus->BIABL->CNDABL;
       if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM(locbiabl->CNDABL))
            {
            substPhyExpr(locbiabl->CNDABL,VALUE_ATOM(locchain),locbeaux->ABL);
            }
          else 
            {
            locbiabl->CNDABL = copyExpr(locbeaux->ABL);  
            }
          }
        locchain = locbiabl->VALABL;
        if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM(locbiabl->VALABL))
            {
    	    substPhyExpr(locbiabl->VALABL,VALUE_ATOM(locchain),locbeaux->ABL);
            }
          else 
            {
            locbiabl->VALABL = copyExpr(locbeaux->ABL);  
            }
          }
        locbiabl = locbiabl->NEXT;
        }
      locbebus = locbebus->NEXT;
      }
    locbebux = locnewbefig->BEBUX;
    while (locbebux != NULL)
      {
      locbiabl = locbebux->BIABL;
      while(locbiabl != NULL)
        {
        locchain = locbiabl->CNDABL;
        if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM (locbiabl->CNDABL))
            {
            substPhyExpr (locbiabl->CNDABL,VALUE_ATOM(locchain),locbeaux->ABL);
            }
          else 
            {
            locbiabl->CNDABL = copyExpr(locbeaux->ABL);  
            }
          }
        locchain = locbiabl->VALABL;
        if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM(locbiabl->VALABL))
            {
   	    substPhyExpr(locbiabl->VALABL,VALUE_ATOM(locchain),locbeaux->ABL);
            }
          else 
            {
            locbiabl->VALABL = copyExpr(locbeaux->ABL);  
            }
          }
        locbiabl = locbiabl->NEXT;
        }
      locbebux = locbebux->NEXT;
      }
    locbereg = locnewbefig->BEREG;
    while(locbereg != NULL)
      {
      locbiabl = locbereg->BIABL;
      while(locbiabl != NULL)
        {
        locchain = locbereg->BIABL->CNDABL;
        if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM(locbereg->BIABL->CNDABL))
            {
            substPhyExpr(locbereg->BIABL->CNDABL,VALUE_ATOM(locchain), 
                         locbeaux->ABL);
            }
          else 
            {
            locbereg->BIABL->CNDABL = copyExpr(locbeaux->ABL);
            }
          }
        locchain = locbereg->BIABL->VALABL;
        if(searchExpr(locchain,locbeaux->NAME) == 1)
          {
          if(!ATOM(locbereg->BIABL->VALABL))
            {
   	    substPhyExpr(locbereg->BIABL->VALABL,VALUE_ATOM(locchain), 
                         locbeaux->ABL);
            }
          else 
            {
            locbereg->BIABL->VALABL = copyExpr(locbeaux->ABL);
            }
          }
        locbiabl = locbiabl->NEXT;
        }  
      locbereg = locbereg->NEXT;
      }
    locbeaux = locbeaux->NEXT;
    }
  beh_frebeaux (locnewbefig->BEAUX);
  locnewbefig->BEAUX = NULL;
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : equival()						*/
/*   Content  : Searching the local name for the formal port		*/
/*   Return   : The local name or NULL					*/
/* ###--------------------------------------------------------------### */

char *equival(nomavant,locloins)
char *nomavant;
struct loins *locloins;
  {
  struct locon *locon_courant;

  locon_courant = locloins->LOCON;
  while(locon_courant != NULL)
    {
    if(strcmp(nomavant,(char *)locon_courant->NAME) == 0)
      {
      return( (char *) locon_courant->SIG->NAMECHAIN->DATA);
      }
    locon_courant = locon_courant->NEXT;
    }
  return(NULL);
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : echangerNom()						*/ 
/*   Content  : substitute all the connector's names in the given befig */
/*   Return   : 							*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

void echangerNom(tambefig,oldnom,newnom)
struct befig *tambefig;
char *oldnom, *newnom;

  {
  struct beaux *locbeaux;
  struct beout *locbeout;
  struct bebus *locbebus;
  struct bebux *locbebux;
  struct bereg *locbereg;
  struct berin *locberin;
  struct biabl *locbiabl;

  locbeout = tambefig->BEOUT;
  locbebus = tambefig->BEBUS;
  locbereg = tambefig->BEREG;
  locbebux = tambefig->BEBUX;
  locbeaux = tambefig->BEAUX;
  locberin = tambefig->BERIN;

  while(locberin != NULL)
    {
    if(strcmp(oldnom,locberin->NAME) == 0)
      { 
      locberin->NAME =  namealloc(newnom);
      }
    locberin = locberin->NEXT;
    }

  while(locbeout != NULL)
    {
    if(strcmp(oldnom,locbeout->NAME) == 0)
      { 
      locbeout->NAME =  namealloc(newnom);
      if(searchPile(FIFO,newnom) == 1)
        {
        cutPile(FIFO,newnom);
        }
      addTH(tablesignauxtraiter,newnom);
      }
    echanger(locbeout->ABL,oldnom,newnom);
    locbeout = locbeout->NEXT;
    }

  locbeaux = tambefig->BEAUX;
  while(locbeaux != NULL)
    {
    if(strcmp(oldnom,locbeaux->NAME) == 0)
      { 
      locbeaux->NAME = namealloc(newnom);
      if(searchPile (FIFO,newnom) == 1)
        {
        cutPile(FIFO,newnom);
        }
      addTH(tablesignauxtraiter,newnom);
      }
    echanger(locbeaux->ABL,oldnom,newnom);
    locbeaux = locbeaux->NEXT;
    }

  locbereg = tambefig->BEREG;
  while (locbereg != NULL)  
    {
    if(strcmp(oldnom,locbereg->NAME) == 0)
      { 
      locbereg->NAME =  namealloc(newnom);
      if(searchPile(FIFO,newnom) == 1)
        {
        cutPile(FIFO,newnom);
        }
      addTH(tablesignauxtraiter,newnom);
      }
    locbiabl = locbereg->BIABL; 
    while(locbiabl != NULL)
      {   
      echanger(locbiabl->CNDABL,oldnom,newnom);
      echanger(locbiabl->VALABL,oldnom,newnom);
      locbiabl = locbiabl->NEXT;
      }
    locbereg = locbereg->NEXT;
    }

  locbebus = tambefig->BEBUS;
  while (locbebus != NULL)
    {
    if(strcmp(oldnom,locbebus->NAME) == 0)
      { 
      locbebus->NAME =  namealloc(newnom);
      if(searchPile (FIFO,newnom) == 1)
        {
        cutPile(FIFO,newnom);
        }
      addTH(tablesignauxtraiter,newnom);
      }
    locbiabl = locbebus->BIABL; 
    while(locbiabl != NULL)
      {   
      echanger(locbiabl->CNDABL,oldnom,newnom);
      echanger(locbiabl->VALABL,oldnom,newnom);
      locbiabl = locbiabl->NEXT;
      }
    locbebus = locbebus->NEXT;
    }

  locbebux = tambefig->BEBUX;
  while (locbebux != NULL)
    {
    if(strcmp(oldnom,locbebux->NAME) == 0)
      { 
      locbebux->NAME = namealloc(newnom);
      if(searchPile(FIFO,newnom) == 1)
        {
        cutPile(FIFO,newnom);
        }
      addTH(tablesignauxtraiter,newnom);
      }
    locbiabl = locbebux->BIABL; 
    while (locbiabl != NULL)
      {   
      echanger(locbiabl->CNDABL,oldnom,newnom);
      echanger(locbiabl->VALABL,oldnom,newnom);
      locbiabl = locbiabl->NEXT;
      }
    locbebux = locbebux->NEXT;
    }
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : SansDollar()						*/
/*   Content  : get of the char '$' at the end of the chain if present  */
/*   Return   : pointer on the new chain				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

char *SansDollar(nom)
char *nom;
  {
  char buffer[200];
  char *dollar;
  char *nouv;

  strcpy(buffer,nom);
  dollar = strchr(buffer,'$');
  if(dollar != NULL)
    { 
    *dollar = '\0';
    nouv = namealloc(buffer);
    return(nouv);
    }
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : addliste()						*/
/*   Content  : add the partial list to the total list.			*/
/*   Return   : pointer on the total list.				*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct chain *addliste (listTT,listpart)
struct chain *listTT,*listpart;       
  {
  struct chain *loc, *obj;

  while(listpart != NULL)
   {
   obj = listpart;
   loc = listTT;
   listpart = listpart->NEXT;
   /* check if listpart is not yet recorded in the total list */
   while((loc != NULL) && (strcmp((char*)loc->DATA,(char *)obj->DATA) != 0))
     {
     loc = loc->NEXT;
     }
   if(loc == NULL)
     {
     /* listpart was not present */
     obj->NEXT = listTT;
     listTT = obj ;
     }
   }
  return(listTT);
  } 

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : echangerTampon()					*/
/*   Content  : substitute all the names of the connectors in the	*/
/*              given BEFIG.						*/
/*   Return   : 							*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

/*--------------              ALGORITHM :
  A list of all the names used in the model is built, for each name, search
  its equivalent in the given lofig, if this equivalent exist, substitute
  the names, if not create a new name and substitute.
---------------*/

void echangerTampon(tambefig,locbefig,ptlofig,loins_courant,newbefig,element)
struct befig *tambefig;
struct befig *locbefig;
struct lofig *ptlofig;
struct loins *loins_courant;
struct befig *newbefig;
t_elem *element;

  {
  struct beaux *locbeaux;
  struct beout *locbeout;
  struct bebus *locbebus;
  struct bebux *locbebux;
  struct bereg *locbereg;
  char *nomnouveau, *newnom, *nomtamp;
  struct biabl *locbiabl;
  struct chain *atom = NULL;
  struct chain *listAtom = NULL;
  struct chain *listtotale = NULL;

  locbeout = tambefig->BEOUT;
  locbebus = tambefig->BEBUS;
  locbereg = tambefig->BEREG;
  locbebux = tambefig->BEBUX;
  locbeaux = tambefig->BEAUX;

  element->name = namealloc(FIFO->head->name);
  element->next = NULL;
  element->signal=FIFO->head->signal;
  /* building the list of the ATOM used in the befig */
  /* Scan the beout */
  while(locbeout != NULL)
    {
    atom = createAtom(locbeout->NAME);
    listtotale = addliste (listtotale,atom); 
    listAtom = supportChain_listExpr(locbeout->ABL);
    listtotale = addliste (listtotale,listAtom);
    locbeout = locbeout->NEXT;
    }

  /* Scan the beaux */
  while(locbeaux != NULL)
    {
    atom = createAtom(locbeaux->NAME);
    listtotale = addliste(listtotale,atom); 
    listAtom = supportChain_listExpr(locbeaux->ABL);
    listtotale = addliste (listtotale,listAtom);
    locbeaux = locbeaux->NEXT;
    }

  /* Scan the bebus */
  while(locbebus != NULL)
    {
    atom = createAtom(locbebus->NAME);
    listtotale = addliste(listtotale,atom); 
    locbiabl = locbebus->BIABL;
    while(locbiabl != NULL)
      {
      listAtom = supportChain_listExpr(locbiabl->CNDABL);
      listtotale = addliste (listtotale,listAtom);
      listAtom = supportChain_listExpr(locbiabl->VALABL);
      listtotale = addliste (listtotale,listAtom);
      locbiabl = locbiabl->NEXT;
      }
    locbebus = locbebus->NEXT;
    }

  /* Scan the bebux */
  while(locbebux != NULL)
    {
    atom = createAtom(locbebux->NAME);
    listtotale = addliste(listtotale,atom); 
    locbiabl = locbebux->BIABL;
    while(locbiabl != NULL)
      {
      listAtom = supportChain_listExpr(locbiabl->CNDABL);
      listtotale = addliste(listtotale,listAtom);
      listAtom = supportChain_listExpr(locbiabl->VALABL);
      listtotale = addliste(listtotale,listAtom);
      locbiabl = locbiabl->NEXT;
      }
    locbebux = locbebux->NEXT;
    }

  /* scan the bereg */
  while (locbereg != NULL)
    {
    atom = createAtom(locbereg->NAME);
    listtotale = addliste(listtotale,atom); 
    locbiabl = locbereg->BIABL;
    while(locbiabl != NULL)
      {
      listAtom = supportChain_listExpr(locbiabl->CNDABL);
      listtotale = addliste(listtotale,listAtom);
      listAtom = supportChain_listExpr(locbiabl->VALABL);
      listtotale = addliste(listtotale,listAtom);
      locbiabl = locbiabl->NEXT;
      }
    locbereg = locbereg->NEXT;
    }

  /* Substituting the formal names by the local names */
  while (listtotale != NULL)
    {
    nomtamp = SansDollar((char *)listtotale->DATA);
    nomnouveau = namealloc(equival(nomtamp,loins_courant));
    /* The local name has not been found */
    if(nomnouveau == NULL)
      {
      if((strcmp((char *)listtotale->DATA,"'1'$")!= 0) &&
         (strcmp((char *)listtotale->DATA,"'0'$")!= 0))
        {
/*         newnom = inventeNom(SansDollar((char *) listtotale->DATA),
                            loins_courant,tambefig); */
        /* Create the path-name */
        newnom = concatname(loins_courant->INSNAME,
                            SansDollar(listtotale->DATA));
        echangerNom(tambefig,(char *)listtotale->DATA,newnom);
        }  
      else 
        {
        if(strcmp((char *) listtotale->DATA,"'1'$")== 0) 
          {
          echangerNom(tambefig,(char *)listtotale->DATA,"'1'");
          }
        else 
          {
          echangerNom(tambefig,(char *)listtotale->DATA,"'0'");
          }
        }
      }
    else 
      {
      rajouterPile(ptlofig,nomnouveau,locbefig,newbefig);
      echangerNom(tambefig,(char *)listtotale->DATA,nomnouveau);
      }
    listtotale = listtotale->NEXT;
    }
  }

/* ###--------------------------------------------------------------### */
/*                                                                      */
/*   Function : MAJBepor						*/
/*   Content  : update the type of the elements of the BEPOR		*/
/*   Return   : The befig pointer					*/ 
/*                                                                      */
/* ###--------------------------------------------------------------### */

struct befig *MAJBepor(locbefig)
struct befig *locbefig;
 
  {
  struct bepor *locbepor;
  struct berin *locberin;
  struct bebus *locbebus;
  struct beout *locbeout;
  char *locname;
  int drapeau;

  locbepor = locbefig->BEPOR;
  while (locbepor != NULL)
    {
    if(locbepor->DIRECTION == 'X')
      /* DIRECTION is UNKNOWN (LINKAGE) */
      /* If not in BEBUS nor in BEOUT then put in BERIN */
      {
      locname = locbepor->NAME;
      locbeout = locbefig->BEOUT;
      while((locbeout != NULL) && (strcmp(locbeout->NAME,locname) != 0))
        {
        locbeout = locbeout->NEXT;
        }
      if(locbeout == NULL)
        {
        locbebus = locbefig->BEBUS;
        while ((locbebus != NULL) && (strcmp(locbebus->NAME,locname) != 0))
          {
          locbebus = locbebus->NEXT;
          }
        if(locbebus == NULL) 
          {
          locbefig->BERIN = beh_addberin(locbefig->BERIN,locname);
          }
        }
      }
    locbepor = locbepor->NEXT;
    } 

  locbepor = locbefig->BEPOR;
  while (locbepor != NULL)
    {
    if(locbepor->DIRECTION == 'X')
     /* DIRECTION IS LINKAGE */
     /* Search the good direction of the signal */
     {
     drapeau = 0;
     locname = locbepor->NAME;
     locberin = locbefig->BERIN;
     while ((locberin != NULL) && (strcmp(locberin->NAME,locname) != 0))
       {
       locberin = locberin->NEXT;
       }
     if(locberin != NULL) 
       {
       drapeau = drapeau + 1;
       }
     locbeout = locbefig->BEOUT;
     while((locbeout != NULL) && (strcmp(locbeout->NAME,locname) != 0))
       {
       locbeout = locbeout->NEXT;
       }
     if(locbeout != NULL) 
       {
       drapeau = drapeau + 2;
       }
     locbebus = locbefig->BEBUS;
     while((locbebus != NULL) && (strcmp(locbebus->NAME,locname) != 0))
       {
       locbebus = locbebus->NEXT;
       }
     if(locbebus != NULL) 
       {
       drapeau = drapeau + 4;
       }
     /* 1 means BERIN */
     /* 2 means BEOUT */
     /* 4 means BEBUS */ 
     switch (drapeau)
       {
       case 1 : locbepor->DIRECTION = 'I'; 
                break;
       case 2 : locbepor->DIRECTION = 'O'; 
                break;
       case 3 : locbepor->DIRECTION = 'B'; 
                break;
       case 4 : locbepor->DIRECTION = 'Z'; 
                break;
       case 5 : locbepor->DIRECTION = 'T'; 
                break;
       default : locbepor->DIRECTION = 'X';
       }
     }

   locbebus = locbefig->BEBUS;
   locname = locbepor->NAME;
   while(locbebus != NULL)
     {
     if(strcmp (locname, locbebus->NAME) == 0)
       {
       locbepor->TYPE = 'M';
       }
     locbebus = locbebus->NEXT;
     }
   locbepor = locbepor->NEXT;
   }
  locbepor = locbefig->BEPOR;
  while (locbepor != NULL)
    {
    if(locbepor->DIRECTION == 'K')
     /* DIRECTION IS LINKAGE IN*/
     /* Search the good direction of the signal */
     {
     drapeau = 0;
     locname = locbepor->NAME;
     drapeau = drapeau + 1;
     locbeout = locbefig->BEOUT;
     while((locbeout != NULL) && (strcmp(locbeout->NAME,locname) != 0))
       {
       locbeout = locbeout->NEXT;
       }
     if(locbeout != NULL) 
       {
       drapeau = drapeau + 2;
       }
     locbebus = locbefig->BEBUS;
     while((locbebus != NULL) && (strcmp(locbebus->NAME,locname) != 0))
       {
       locbebus = locbebus->NEXT;
       }
     if(locbebus != NULL) 
       {
       drapeau = drapeau + 4;
       }
     /* 1 means BERIN */
     /* 2 means BEOUT */
     /* 4 means BEBUS */ 
     switch (drapeau)
       {
       case 1 : locbepor->DIRECTION = 'I'; 
                break;
       case 2 : locbepor->DIRECTION = 'O'; 
                break;
       case 3 : locbepor->DIRECTION = 'B'; 
                break;
       case 4 : locbepor->DIRECTION = 'Z'; 
                break;
       case 5 : locbepor->DIRECTION = 'T'; 
                break;
       default : locbepor->DIRECTION = 'X';
       }
     }

   locbebus = locbefig->BEBUS;
   locname = locbepor->NAME;
   while(locbebus != NULL)
     {
     if(strcmp (locname, locbebus->NAME) == 0)
       {
       locbepor->TYPE = 'M';
       }
     locbebus = locbebus->NEXT;
     }
   locbepor = locbepor->NEXT;
   }
 return(locbefig);
 }

/* ###--------------------------------------------------------------### */
/*								        */
/*   Function : flatten_beh1()						*/
/*   Content  : flatten a lofig of hierarchy one			*/
/*   Return   : the pointer on the befig resulted			*/
/*                                                                      */
/* ###--------------------------------------------------------------### */

/*--------              ALGORITHM
  -1- Create a befig with the NAME, BEPOR and BERIN filled.
        BEPOR is the copy of the locon list in the lofig, type is BIT.
        BERIN is filled with the locon of type IN or INOUT.

  -2- Take the locon of type OUT or INOUT and stack them in FIFO.
        If some of these locon are BUS, there will be the same amount of
        driver on this connector than the amount of this connector in the stack.
      
  -3- Until the stack is empty : 
        {
        a connector is popped and the loins is
        scanned until a path is finded which reach the connector.
        The pointer on the loins is stored.
        Duplicating the befig corresponding (LOINS->FIGNAME) and adding 
        a '$' char at the end of each name in the befig duplicated.
        Each variable of the ABL will be substituted by the corresponding
        variable of the figure.
        The input connectors of the instance will be pushed on the stack.
        Add the befig resulted to the befig total.
        }

  -4- Updating the BEPOR to put the correct kind.
      The BEAUX can be simplified following the flag of the function.

-----------*/
      
struct befig *flatten_beh1(ptbefig, ptlofig,flag)
struct befig *ptbefig;
struct lofig *ptlofig;
int flag;
  {
  struct befig *newbefig = NULL; /* The befig to fill */
  struct loins *loins_courant;
  struct befig *ptbef;
  struct befig *tamponbefig;
  t_elem *element;

  tablesignauxtraiter = createTH(NOMMAX);
  tableinstance = createTH(NOMMAX);
  /* Creating and initializing the befig */
  newbefig =  creer_befig(ptlofig,newbefig);

  (void)fprintf(stdout,"Treated figure : '%s'\n\n", newbefig->NAME);

  /* Creating FIFO */
  FIFO = createPile(FIFO);

  /* Read and Push the output locon of kind INOUT, OUT or BUS */
  lire_locon(ptlofig,ptbefig);

  while(isfreePile(FIFO) == FALSE)
    {
    ptbef = ptbefig;
    /* Searching the loins using the considered locon 		     */
    /* loins_courant->FIGNAME : the model using the considered locon */
    loins_courant = chercher_signal(FIFO->head->name,ptlofig->LOINS,ptbef);

    /* creating befig TAMPON to receive the model to duplicate */
    tamponbefig = beh_addbefig(NULL,"tampon");

    /* Searching and duplicating the befig */
    recopier_Befig(ptlofig,loins_courant,ptbefig,tamponbefig);

    /* substituting the real names in the model names in tamponbefig */
    element = (t_elem *)mbkalloc(sizeof(t_elem));
    echangerTampon(tamponbefig,ptbefig,ptlofig,loins_courant,newbefig,element);

    /* Add tamponbefig to newbefig */
    ajouterTampon(newbefig,tamponbefig,ptlofig);

    /* put the treated signal in the treated signals table */
    addTH(tablesignauxtraiter,namealloc(element->name),0);  
    beh_delbefig(tamponbefig,tamponbefig,'Y');  
    }
  /* Updating the BEPOR */
  newbefig = MAJBepor(newbefig);

  if(flag == 1)
    {
    /* Simplification of the BEFIG */
    simplifierBefig (newbefig);
    }                     
  destroyTH(tablesignauxtraiter);
  destroyTH(tableinstance);
  return(newbefig);
  }

/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : chercherCellule()					*/
/*  Content  : check if nomcellule is in the befig list			*/
/*  Return   : 1 if True, 0 if False					*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

int chercherCellule(nomcellule,ptbefig)
char *nomcellule;
struct befig *ptbefig;

  {
  struct befig  *locbefig;

  locbefig = ptbefig;
  while (locbefig != NULL)
    {
    if(strcmp(nomcellule,locbefig->NAME) == 0)
      {
      /* nomcellule is in the befig list */
      return(1);
      } 
    else
      {
      locbefig = locbefig->NEXT;
      }
    }
  /* nomcellule is NOT in the befig list */
  return(0);
  }

/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : chercherLofigPrimaire()					*/
/*  Content  : Check if the lofig is of the lowest level.		*/
/*  Return   : 1 if True, 0 if False					*/
/* 									*/
/*###----------------------------------------------------------------###*/

int chercherLofigPrimaire(loclofig,ptbefig)
struct lofig *loclofig;
struct befig *ptbefig;

  {
  struct chain *loccellule;

  loccellule = loclofig->MODELCHAIN;
  while(loccellule != NULL)
    {
    if(chercherCellule((char *)loccellule->DATA,ptbefig) == 1)
      {
      loccellule = loccellule->NEXT;
      }
    else 
      {
      /* One of the model is NOT in the befig list */
      return (0);
      }
    }
  return (1);
  }



/*###----------------------------------------------------------------###*/
/*                                                                      */
/*  Function : ajouterBefig()						*/
/*  Content  : insert locbefig at the head of the befig list ptbefig.	*/
/*  Return   :								*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

void ajouterBefig(locbefig,ptbefig)
struct befig *locbefig;
struct befig *ptbefig;
  {
  locbefig->NEXT = ptbefig;
  ptbefig = locbefig;
  }


/*###----------------------------------------------------------------###*/
/*                                                             		*/
/*   Function : flatten_beh()						*/
/*   Content  : extract a befig from the lofig, by flattening all the 	*/
/*              structural level until a befig is reached.		*/
/*   Return   : The pointer on the befig resulted			*/
/*                                                                      */
/*###----------------------------------------------------------------###*/

/*------                 ALGORITHM :
  The first pointer of the lofig list is the root, and the next are sons,
  little-sons and so on ... Each LOFIG contains a field MODELCHAIN with
  all the model instancied. If all the models are in the befig list, that
  means it is a lofig of the lowest level. It must be treated and the
  befig resulting is added in the befig list and the lofig is deleted
  of the lofig list. This algorithm is recursive until the lofig list
  contains only one lofig, the befig resulted of the flatten is the befig
  obtained from this lofig.

  BUGS : The lofig flattened is not deleted of the lofig list but put 
         in the "table lofig".
-------*/

struct befig *flatten_beh(ptbefig,ptlofig,flag)
struct befig *ptbefig;	/* The befig list of the model in the CATAL	*/
struct lofig *ptlofig;	/* The lofig list of the instances		*/
int           flag; 	/* The flag for the simplification, 1 is true	*/
  {
  struct lofig *loclofig;
  struct befig *locbefig;

  /* Positionning MBK environment */
  SEPAR = '_';
  /* Creating the globals hash table */
  tablelofig = createTH(NOMMAX);
  tablenom = createTH(NOMMAX);

  /* Initialization of the locals variables */
  loclofig = ptlofig;

  (void)fprintf(stdout,"Executing flatten_beh ... \n\n");

  while(loclofig != NULL)
    {
    if(chercherLofigPrimaire(loclofig,ptbefig) == 1)
      {
      /* It's a lofig of the lowest level            */
      /* Verifying this lofig has not be treated yet */
      if(searchTH(tablelofig,loclofig->NAME) != 0)
        {
        /* treating this lofig */
        locbefig = flatten_beh1(ptbefig,loclofig,flag);
        if(strcmp(locbefig->NAME, ptlofig->NAME) == 0)
          {
          /* Root file */
          /* affiche_resultat(locbefig); */
	  return(locbefig);
          }
        else
          {
          /* It's not the root file           */
          /* storing the lofig in table lofig */
	  addTH(tablelofig, loclofig->NAME);
          /* Add the befig resulted to the befig list */
	  ajouterBefig(locbefig, ptbefig);
          /* Beginning at the lofig list head */
	  loclofig = ptlofig;
          }
        }
      }
    else 
      {
      loclofig = loclofig -> NEXT;  
      }
    }
(void)fprintf(stdout,"######### End of flattenbeh ###############\n");
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    File        : pile.c                                            */
/*    Authors     : DE SMET bernard  &  GERAUD denis                  */
/*    Update      : VUONG Huu Nghia                                   */
/*    date        : 13/04/1992                                        */
/*                                                                    */
/*    description : contains seven functions :                        */
/*                    - addPile : to add a new argument at the queue  */
/*                    - delPile : to delete an argument at the head   */
/*                    - isfreePile : to know if the pile is free      */
/*                    - searchPile : searches an argument in the pile */
/*                                   return a boolean (1 if it exists)*/
/*                    - createPile : create a new Pile                */
/*                    - displayPile : display a Pile                  */
/*                    - cutPile : retire an element of a Pile         */
/* ###------------------------------------------------------------### */

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : addPile                                           */
/*    Description : add a new argument at the queue                   */
/*    The function returns the pointer on the FIFO                    */
/*                                                                    */
/* ###------------------------------------------------------------### */

t_pile  *addPile(pile,argu)
t_pile *pile;	/* pointer on the FIFO			*/
t_elem *argu;	/* pointer on the structure to add	*/
  { 
  if(pile->queue == NULL)
    { 
    pile->head = argu;
    pile->queue = argu;
    }
  else 
    { 
    pile->queue->next = argu;
    pile->queue = argu;
    }
  return (pile);
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : delPile                                           */
/*    Description : delete the head of the FIFO                       */
/*    The function returns the pointer on the FIFO                    */
/*                                                                    */
/* ###------------------------------------------------------------### */

t_pile *delPile (pile)
t_pile *pile;	/* pointer on the FIFO */
  { 
  t_elem *loc;
  if(pile->head == NULL)
    { 
    return(pile);
    }
  else 
    { 
    loc = pile->head;
    pile->head = pile->head->next;
    if(pile->queue == loc)
      {
      pile->queue = NULL;
      }
    mbkfree(loc);
    return(pile); 
    }
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : searchPile                                        */
/*    Description : searches an argument in the pile                  */
/*    The function returns a boolean which indicates if the argument  */
/*    is present                                                      */
/*                                                                    */
/* ###------------------------------------------------------------### */

int searchPile (pile,value)
t_pile *pile;	/* pointer on the FIFO			*/
char *value;	/* pointer on the searched string	*/
  { 
  t_elem *locpile;

  locpile = pile->head; 
  if (locpile == NULL)
    {
    return(FALSE);
    }
  while((locpile != NULL) && (strcmp(value,locpile->name) != 0))
    {
    locpile = locpile-> next ;
    }
  if(locpile == NULL)
    {
    return(FALSE);
    }
  else 
    {
    return(TRUE);
    }
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : isfreePile                                        */
/*    Description : test if the pile is free                          */
/*    The function returns a boolean which indicates if the pile is   */
/*    free.                                                           */
/*                                                                    */
/* ###------------------------------------------------------------### */

int isfreePile (pile)
t_pile *pile;	/* pointer on the FIFO */
  {  
  if(pile->head == NULL)
    { 
    return (TRUE);
    }
  else  
    {
    return(FALSE);
    }
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : displayPile                                       */
/*    Description : displays the pile.                                */
/*                                                                    */
/* ###------------------------------------------------------------### */

void displayPile (pile)
t_pile *pile;	/* pointer on the FIFO	*/
  { 
  t_elem *element; 

  element = pile->head; 
  if(element == NULL) 
    {
    printf("pile vide\n");
    }
  while (element  != NULL)
    { 
    (void)fprintf(stdout,"NOM  = %s , ",element->name);
    (void)fprintf(stdout,"TYPE = %d\n",element->signal);
    element = element->next;
    }
  }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : createPile                                        */
/*    Description : create a new free pile                            */
/*    The function returns a pointer on the new created structure     */
/*                                                                    */
/* ###------------------------------------------------------------### */

t_pile *createPile (pile)

t_pile *pile;	/* pointer on the FIFO	*/
   {

   pile = (t_pile *) mbkalloc (sizeof(t_pile));
   pile->head  = NULL;
   pile->queue = NULL;
   return (pile);
   }

/* ###------------------------------------------------------------### */
/*                                                                    */
/*    Function    : cutPile                                           */
/*    Description : delete an element of a pile                       */
/*                                                                    */
/* ###------------------------------------------------------------### */

void cutPile (FIFO,nom)

t_pile *FIFO;	/* pointer on the FIFO	*/
char *nom;	/* element to delete	*/

  {
  t_elem *el, *pred;

  if (isfreePile(FIFO) == FALSE)
    {
    if (FIFO->head->next == NULL)
      {	
      /* An unique element case */
      if( strcmp (FIFO->head->name,nom) == 0)
        {
        mbkfree (FIFO->head);
        FIFO->head  = NULL;
        FIFO->queue = NULL;
        }
      else 
        {
        ;
        }
      }
    else 
      {
      /* More than one element case */
      if(strcmp(FIFO->head->name,nom) == 0)
        {
        /* The first element is the good one */
        el = FIFO->head;
        FIFO->head = FIFO->head->next;
        free(el);
        }
      else 
        {
        el = FIFO->head->next;
        pred = FIFO->head;
        while((strcmp(el->name,nom) != 0) && (el != NULL))
          {
          el = el->next;
          pred = pred->next;
          }
        if(el != NULL)
          {
          if(el->next == NULL)
            {
            /* The last element is the good one */
            pred->next = NULL;
            FIFO->queue = pred;
            free(el);
            }
          else 
            {
            pred->next = el->next;
            free(el);
            }
          }
        }
      }
    }
  }
