1 /*
2  * This file is part of the Alliance CAD System
3  * Copyright (C) Laboratoire LIP6 - D�partement ASIM
4  * Universite Pierre et Marie Curie
5  *
6  * Home page          : http://www-asim.lip6.fr/alliance/
7  * E-mail             : mailto:alliance-users@asim.lip6.fr
8  *
9  * This library is free software; you  can redistribute it and/or modify it
10  * under the terms  of the GNU Library General Public  License as published
11  * by the Free Software Foundation; either version 2 of the License, or (at
12  * your option) any later version.
13  *
14  * Alliance VLSI  CAD System  is distributed  in the hope  that it  will be
15  * useful, but WITHOUT  ANY WARRANTY; without even the  implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
17  * Public License for more details.
18  *
19  * You should have received a copy  of the GNU General Public License along
20  * with the GNU C Library; see the  file COPYING. If not, write to the Free
21  * Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
22  */
23 
24 /*----------------------------------------------------------------------------*/
25 /*                    @(#) MBK TO EDIF Driver                                 */
26 /*----------------------------------------------------------------------------*/
27 /*version 1.0 : Implemented by Fred Petrot                                    */
28 /*version 1.1 : Extended by Mokhtar Hirech (January, 92)                      */
29 /*version 1.2 : Extended by Olivier BEAURIN (September, 93)                   */
30 /*version 1.2 : Extended by Olivier BEAURIN (November, 93)                    */
31 /* $Log: driver.c,v $
32 /  Revision 1.5  2012/05/14 14:20:24  alliance
33 /  Updated GNU/FSF address (patch from Thibault North).
34 /
35 /  Revision 1.4  2002/09/30 16:20:54  czo
36 /  support/users
37 /
38 /  Revision 1.3  2002/04/25 14:16:44  ludo
39 /  correction petits bugs
40 /
41 /  Revision 1.2  2002/03/14 12:36:30  fred
42 /  Makes the correct substitutions in lex and yacc generated files.
43 /  Fixing includes in dot c files
44 /  ---------------------------------------------------------------------*/
45 
46 #include <stdio.h>
47 #include <stdlib.h>
48 #include <ctype.h>
49 #include <string.h>
50 #include <mut.h>
51 #include <mlo.h>
52 
53 /* defines */
54 #ifndef FALSE
55 #define FALSE 0
56 #endif
57 
58 #ifndef TRUE
59 #define TRUE 1
60 #endif
61 
62 #define SCHEMATIC "schematic"
63 #define SYMBOL    "symbol"
64 
65 #define MBK_EDIF_LIBNAME  "MBKEDIF_LIBNAME"
66 #define MBK_EDIF_SUFFIXES "MBKEDIF_SUFFIXES"
67 #define DEBUG_MBKEDIF     "DEBUG_MBKEDIF"
68 #define DEFAULT_SUFFIXES  "y=ScLib:dp=DpLib:fp=FpLib:sp=PadLib"
69 
70 /* External Functions */
71 
72 extern char *EdifTime();
73 
74 /* Global variables*/
75 
76 static int          edif_debug = FALSE;
77 static FILE        *edif_file;
78 static char        *EDIF_LIBNAME;
79 static char        *EDIF_SUFFIXES;
80 static int          nb_lib = 0;
81 static char       **suffixes = NULL;
82 static char       **libraries = NULL;
83 static chain_list **cellules = NULL;
84 static chain_list  *already_drived = NULL;
85 
86 /* Global Functions*/
87 
88 static void         port_ext         ( );
89 static void         edit_sig         ( );
90 static void         edit_ins         ( );
91 static void         edit_con         ( );
92 static void         connect          ( );
93 static void         view             ( );
94 static void         drive_cell       ( );
95 static void         r_drive_cell     ( );
96 static int          edif_busindex    ( );
97 static void         drive_basic_cells( );
98 static locon_list  *edif_found_array ( );
99 static void         check_fig_portref( );
100 static void         r_found_suffixed_cells( );
101 static void         save_libraries_cells( );
102 
103        char        *edif_busname     ( );
104 
105 /*---------------------------------------------------------\
106                      ParseSuffixes
107 \---------------------------------------------------------*/
ParseSuffixes(fill)108 int ParseSuffixes( fill )
109 int fill;
110 {
111     char *suf;
112     char *lib;
113     char *pt;
114     int   index;
115 
116     if( fill )
117     {
118         if( suffixes || libraries || cellules )
119         {
120             fprintf( stderr, "*** mbk error *** edifsavelofig : bugs in ParseSuffixes\n" );
121             exit( 1 );
122         }
123         suffixes  = mbkalloc( nb_lib * sizeof( char * ) );
124         libraries = mbkalloc( nb_lib * sizeof( char * ) );
125         cellules  = mbkalloc( nb_lib * sizeof( chain_list * ) );
126         index = 0;
127     }
128 
129     suf = EDIF_SUFFIXES;
130     do
131     {
132         lib = strchr( suf, '=' );
133         if( !lib )
134         {
135             return FALSE;
136         }
137         pt = strchr( lib, ':' );
138         if( pt && fill )
139         {
140             *pt = '\0';
141         }
142         if( fill )
143         {
144             *lib = '\0';
145         }
146         lib ++;
147 
148         if( !fill )
149         {
150             nb_lib++;
151         }
152         else
153         {
154             suffixes[ index ] = suf;
155             libraries[ index ] = lib;
156             cellules[ index ] = NULL;
157             index ++;
158         }
159 
160         if( pt )
161         {
162             suf = pt + 1;
163         }
164     } while( pt );
165 
166     if( fill && edif_debug )
167     {
168         fprintf( stdout, "\nMBKEDIF DEBUG : Libraries and suffixes used.\n\n");
169         for( index = 0; index < nb_lib; index ++)
170         {
171             fprintf( stdout, "\t%s\t=>\t%s\n",suffixes[index], libraries[index] );
172         }
173         fprintf( stdout, "\n");
174     }
175 
176     return TRUE;
177 } /* end of ParseSuffixes */
178 
179 /*---------------------------------------------------------\
180                      edifsavelofig
181 \---------------------------------------------------------*/
edifsavelofig(firstlofig)182 void edifsavelofig( firstlofig )
183 lofig_list *firstlofig;
184 {
185 	char        filename[ 255 ];
186 	char       *pc;
187     int         index;
188 
189     edif_debug = mbkgetenv( DEBUG_MBKEDIF ) != NULL;
190 
191 	EDIF_LIBNAME = mbkgetenv( MBK_EDIF_LIBNAME );
192 	if( !EDIF_LIBNAME )
193 		EDIF_LIBNAME = namealloc( "alliance" );
194 
195 	if( strcmp( EDIF_LIBNAME, "" ) == 0 )
196 		EDIF_LIBNAME = namealloc( "alliance" );
197 
198 
199 	for( pc = EDIF_LIBNAME; pc[0] != '\0'; pc ++ )
200     {
201 		if( ( pc[0] == '(' ) || ( pc[0] == ')' ) || ( pc[0] == ' ' ) )
202 		{
203 			fprintf( stderr, "*** mbk error *** edifloadlofig : environment variable 'MBK_EDIF_LIBNAME' invalid.\n" );
204 			exit( 1 );
205 		}
206     }
207 
208     if( nb_lib == 0 )
209     {
210         EDIF_SUFFIXES = mbkgetenv( MBK_EDIF_SUFFIXES );
211         if( !EDIF_SUFFIXES )
212         {
213             EDIF_SUFFIXES = mbkstrdup(DEFAULT_SUFFIXES);
214         }
215         if( !ParseSuffixes( FALSE ) )
216         {
217             fprintf(stderr, "*** mbk warning *** edifsavelofig : %s invalid, using default value.\n",
218                     MBK_EDIF_SUFFIXES );
219             EDIF_SUFFIXES = mbkstrdup(DEFAULT_SUFFIXES);
220             if( !ParseSuffixes( FALSE ) )
221             {
222                 fprintf( stderr, "*** mbk error *** edifsavelofig : Bugs with default %s value\n",
223                          MBK_EDIF_SUFFIXES);
224                 exit( 1 );
225             }
226         }
227         ParseSuffixes( TRUE );
228     }
229     else
230     {
231         for( index = 0; index < nb_lib; index ++)
232         {
233             cellules[index] = NULL;
234         }
235     }
236 
237 	if (firstlofig == NULL)
238 	{
239 		fprintf( stderr, "*** mbk error *** edifsavelofig : edif shall not drive a NULL figure\n");
240 		exit( 1 );
241 	}
242 
243     r_found_suffixed_cells( firstlofig );
244 
245 	sprintf( filename, "%s/%s.%s", WORK_LIB, firstlofig->NAME, OUT_LO );
246 
247 	if( ( edif_file = mbkfopen( firstlofig->NAME, OUT_LO, WRITE_TEXT ) ) == NULL )
248 	{
249 		fprintf( stderr, "*** mbk error *** edifsavelofig : the file %s cannot be opened\n", filename );
250 		exit( 1 );
251 	}
252 
253 	fprintf( edif_file, "(edif RobiN_EDIF\n"                                                    );
254 	fprintf( edif_file, " (edifversion 2 0 0)\n"                                                );
255 	fprintf( edif_file, " (ediflevel 0)\n"                                                      );
256 	fprintf( edif_file, " (keywordMap (keywordLevel 0))\n"                                      );
257 	fprintf( edif_file, " (status\n"                                                            );
258 	fprintf( edif_file, "  (written\n"                                                          );
259 	fprintf( edif_file, "   (timeStamp %s)\n",                               EdifTime( )        );
260 	fprintf( edif_file, "   (program \"Driver mbk2edif\")\n"                                    );
261 	fprintf( edif_file, "   (author \"FP & HM & OB for : %s\")\n", mbkgetenv( "USER" ) ? mbkgetenv( "USER" ) : "RobiN" );
262 	fprintf( edif_file, "   (dataOrigin \"VLSI-CAD : Masi Lab. UPMC\")))"                       );
263 
264     save_libraries_cells( );
265 
266     fprintf( edif_file, "\n (library %s\n", EDIF_LIBNAME );
267     fprintf( edif_file, "  (ediflevel 0)\n" );
268     fprintf( edif_file, "  (technology (numberDefinition))" );
269 
270 	r_drive_cell( firstlofig );
271 
272 	fprintf( edif_file, "))\n");
273 
274 	if( fclose( edif_file ) !=0 )
275 	{
276 		fprintf( stderr, "*** mbk error *** edifsavelofig : Cannot close file '%s'\n", filename );
277 		exit( 1 );
278 	}
279 
280 	freechain( already_drived );
281 	already_drived = (chain_list *)NULL;
282 
283 } /* end of edifsavelofig */
284 
285 /*---------------------------------------------------------\
286                      save_libraries_cells
287 \---------------------------------------------------------*/
save_libraries_cells()288 static void save_libraries_cells( )
289 {
290     chain_list *ptchain;
291     int         index;
292 
293     for( index = 0; index < nb_lib; index ++ )
294     {
295         if( !cellules[index] )
296         {
297             continue;
298         }
299 
300         fprintf( edif_file, "\n (library %s\n", libraries[index] );
301         fprintf( edif_file, "  (ediflevel 0)\n" );
302         fprintf( edif_file, "  (technology (numberDefinition))" );
303 
304         ptchain = cellules[ index ];
305 
306         while( ptchain )
307         {
308 	        drive_cell(ptchain->DATA, incatalog(ptchain->DATA) ? 'I' : 'C');
309             ptchain = ptchain->NEXT;
310         }
311 
312         fprintf( edif_file, ")");
313     }
314 } /* end of save_libraries_cells */
315 
316 /*---------------------------------------------------------\
317                      in_chain_list
318 \---------------------------------------------------------*/
in_chain_list(ptchain,cell_name)319 static char in_chain_list( ptchain, cell_name )
320 chain_list *ptchain;
321 char       *cell_name;
322 {
323 	chain_list *chainp;
324 
325 	for(chainp = ptchain; chainp; chainp = chainp->NEXT)
326 		if ((char *)chainp->DATA == cell_name)
327 			return 1;
328 
329 	return 0;
330 } /* end of in_chain_list */
331 
332 /*---------------------------------------------------------\
333                      found_suffixed_cell
334 \---------------------------------------------------------*/
found_suffixed_cell(name,insert)335 static char *found_suffixed_cell( name, insert )
336 char *name;
337 int   insert;
338 {
339     int index;
340     char *pt;
341 
342     pt = strrchr( name, '_' );
343     if( !pt )
344     {
345         return NULL;
346     }
347     pt++;
348 
349     for( index = 0; index < nb_lib; index ++ )
350     {
351         if( strcmp( pt, suffixes[index] ) == 0 )
352         {
353             if( (!insert) || ( in_chain_list( cellules[ index ], name ) ) )
354             {
355                 return libraries[ index ];
356             }
357             if( edif_debug )
358             {
359                 fprintf(stdout, "Cellule %s in library %s\n",name,libraries[index]);
360             }
361 
362             cellules[index] = addchain(cellules[index],name );
363             return NULL;
364         }
365     }
366     return NULL;
367 } /* end of found_suffixed_cell */
368 
369 /*---------------------------------------------------------\
370                      r_found_suffixed_cells
371 \---------------------------------------------------------*/
r_found_suffixed_cells(ptlofig)372 static void r_found_suffixed_cells( ptlofig )
373 lofig_list *ptlofig;
374 {
375 	chain_list *ptchain;
376 
377 	for (ptchain = ptlofig->MODELCHAIN; ptchain; ptchain = ptchain->NEXT)
378 	{
379 		found_suffixed_cell(ptchain->DATA, TRUE);
380 	}
381 	for (ptchain = ptlofig->MODELCHAIN; ptchain; ptchain = ptchain->NEXT)
382 	{
383 		if (!incatalog(ptchain->DATA))
384         {
385             r_found_suffixed_cells( getlofig( ptchain->DATA, 'A' ) );
386         }
387 	}
388 } /* end of r_found_suffixed_cells */
389 
390 /*---------------------------------------------------------\
391                      r_drive_cell
392 \---------------------------------------------------------*/
r_drive_cell(ptlofig)393 static void r_drive_cell(ptlofig)
394 lofig_list *ptlofig;
395 {
396 	chain_list *ptchain;
397 	lofig_list *ptlfig;
398 
399 	ptlofig->MODELCHAIN = (chain_list *)reverse((chain_list *)ptlofig->MODELCHAIN);
400 
401 	drive_basic_cells(ptlofig);
402 
403 	for (ptchain = ptlofig->MODELCHAIN; ptchain; ptchain = ptchain->NEXT)
404 	{
405 		if (!in_chain_list(already_drived, namealloc((char*)ptchain->DATA)))
406 		{
407 			ptlfig = getlofig((char *)ptchain->DATA, 'A');
408 			r_drive_cell(ptlfig);
409 		}
410 	}
411 
412 	ptlofig->MODELCHAIN = (chain_list *)reverse((chain_list *)ptlofig->MODELCHAIN);
413 	drive_cell(ptlofig->NAME, 'C');
414 } /* end of r_drive_cell */
415 
416 
417 /*---------------------------------------------------------\
418                      drive_basic_cells
419 \---------------------------------------------------------*/
drive_basic_cells(ptlofig)420 static void drive_basic_cells( ptlofig )
421 lofig_list *ptlofig;
422 {
423 	chain_list *ptchain;
424 	char       *cell_model_name;
425 
426 	for (ptchain = ptlofig->MODELCHAIN; ptchain; ptchain = ptchain->NEXT)
427 	{
428 		cell_model_name = namealloc((char *)ptchain->DATA);
429 		if (incatalog(cell_model_name))
430 			drive_cell(cell_model_name, 'I');
431 	}
432 } /* end of drive_basic_cells */
433 
434 /*---------------------------------------------------------\
435                      drive_cell
436 \---------------------------------------------------------*/
drive_cell(figname,c)437 static void drive_cell(figname, c)
438 char *figname;
439 char  c;
440 {
441 	if (in_chain_list(already_drived, figname))
442 		return;
443 
444 	already_drived = addchain(already_drived, figname);
445 
446 	if (c == 'C')
447     {
448 		view(figname, 'A');
449     }
450 
451     view(figname, 'I');
452 }
453 
454 /*---------------------------------------------------------\
455                      view
456 \---------------------------------------------------------*/
view(figname,viewtype)457 static void view(figname, viewtype)
458 char *figname;
459 char viewtype;
460 {
461 	lofig_list *ptlofig;
462 	char        view[20];
463 
464 	fprintf(edif_file, "\n   (cell %s (cellType GENERIC)", figname);
465 
466 	strcpy(&view[0], (viewtype == 'A') ? SCHEMATIC: SYMBOL );
467 
468 	fprintf(edif_file, "\n    (view %s (viewType NETLIST)", view);
469 	fprintf(edif_file, "\n     (interface");
470 
471 	ptlofig = getlofig(figname, 'P');
472 
473 	ptlofig->LOCON = (locon_list *)reverse((chain_list *)ptlofig->LOCON);
474 
475 	edit_con(ptlofig->LOCON);
476 
477 	fprintf(edif_file, ")");
478 
479 	if( viewtype == 'A' )
480 	{
481 		fprintf(edif_file, "\n     (contents");
482 
483 		ptlofig->LOINS = (loins_list *)reverse((chain_list *)ptlofig->LOINS);
484 		edit_ins( ptlofig->LOINS );
485 		ptlofig->LOINS = (loins_list *)reverse((chain_list *)ptlofig->LOINS);
486 
487 		ptlofig->LOSIG = (losig_list *)reverse((chain_list *)ptlofig->LOSIG);
488 		edit_sig( ptlofig );
489 		ptlofig->LOSIG = (losig_list *)reverse((chain_list *)ptlofig->LOSIG);
490 
491 		fprintf( edif_file, ")");
492 	}
493 
494 	fprintf(edif_file, "))");
495 
496 	ptlofig->LOCON = (locon_list *)reverse((chain_list *)ptlofig->LOCON);
497 
498 	return;
499 } /* end of view */
500 
501 /*---------------------------------------------------------\
502                      connect
503 \---------------------------------------------------------*/
connect(conn,index,instance)504 static void connect(conn, index, instance)
505 locon_list *conn;
506 int         index;
507 loins_list *instance;
508 {
509 	locon_list *ptcon;
510 	locon_list *ptcon2;
511 	losig_list *sig;
512 	char       *busname;
513     char       *name;
514 	char       *pt;
515 	int         begin;
516 	int         end;
517 	int         myindex;
518 
519 	ptcon = conn;
520 
521 	for( ; ptcon != (locon_list *) NULL; ptcon = ptcon -> NEXT)
522 	{
523 		sig = ptcon->SIG;
524 		if( sig->INDEX == index )
525 		{
526 			name = mbkalloc( strlen( ptcon->NAME ) + 1 );
527 			strcpy( name, ptcon->NAME );
528 			for( pt = name; *pt; pt++ )
529             {
530 				if( *pt == '/' )
531                 {
532 					*pt = '_';
533                 }
534             }
535 
536 			busname = edif_busname( name );
537 
538 			if( !busname )
539 				fprintf( edif_file,"\n        (portref %s ", name );
540 			else
541 			{
542 				myindex = edif_busindex( name );
543 				ptcon2 = conn;
544 				do
545 				{
546 					ptcon2 = edif_found_array( ptcon2, busname, &begin, &end );
547 				} while( ( ( begin <= end ) && ( ( myindex < begin ) || ( end < myindex ) ) )
548 				       ||( ( begin >  end ) && ( ( myindex > begin ) || ( end > myindex ) ) ) );
549 
550 				if( begin != end )
551 					fprintf( edif_file,"\n        (portref (member %s_60_%dTO%d_62 %d) ",
552 					         busname, begin, end,
553 					         ( begin <= end ) ? myindex - begin : begin - myindex );
554 				else
555 					fprintf( edif_file,"\n        (portref %s_%d_",
556 					         busname, begin );
557 			}
558 
559             mbkfree( name );
560 
561 			if( instance != (loins_list *) NULL )
562 			{
563 				name = mbkalloc( strlen( instance->INSNAME ) + 1 );
564 				strcpy( name, instance->INSNAME );
565 				for( pt = name; *pt; pt++ )
566 					if( *pt == '/' )
567 						*pt = '_';
568 
569 				fprintf( edif_file, "(instanceref %s )", name );
570 
571             	mbkfree( name );
572 			}
573 
574 			fprintf( edif_file, ")" );
575 
576 		}
577 	}
578 } /* end of connect */
579 
580 /*---------------------------------------------------------\
581                      edit_con
582 \---------------------------------------------------------*/
edit_con(ptcon)583 static void edit_con( ptcon )
584 locon_list *ptcon;
585 {
586 	char         direction[ 7 ];
587 	char         cadence_array_name[ 1000 ];
588 	char        *array_name;
589     char        *name;
590     char        *pt;
591 	int          begin;
592 	int          end;
593 
594 	while (ptcon != (locon_list *) NULL)
595 	{
596         if( isvdd( ptcon->NAME ) || isvss( ptcon->NAME ) )
597         {
598 			ptcon = ptcon -> NEXT;
599             continue;
600         }
601 		if( ptcon -> DIRECTION == IN )
602 			strcpy( direction, "INPUT" );
603 		else
604 			if( ( ptcon -> DIRECTION == OUT ) || ( ptcon->DIRECTION == 'Z' ) )
605 				strcpy(direction, "OUTPUT");
606 			else
607 				strcpy(direction, "INOUT");
608 
609 		name = mbkalloc( strlen( ptcon->NAME ) + 1 );
610 		strcpy( name, ptcon->NAME );
611 		for( pt = name; *pt; pt++ )
612 			if( *pt == '/' )
613 				*pt = '_';
614 
615 		if( !( array_name = edif_busname( name ) ) )
616 		{
617 			fprintf(edif_file, "\n      (port %s (direction %s))", name, direction);
618 			ptcon = ptcon -> NEXT;
619 		}
620 		else
621 		{
622 			ptcon = edif_found_array( ptcon, array_name, &begin, &end );
623 
624 			if( end != begin )
625 			{
626 				sprintf( cadence_array_name, "(rename %s_60_%dTO%d_62 \"%s<%d:%d>\")",
627 				         array_name, begin, end,
628 				         array_name, begin, end );
629 				fprintf(edif_file, "\n      (port (array %s %d)",
630 					               cadence_array_name, abs( end - begin ) + 1);
631 				fprintf(edif_file, "(direction %s))", direction );
632 			}
633 			else
634 				fprintf(edif_file, "\n      (port (rename %s_60_%d_62 \"%s<%d>\") (direction %s))",
635 					               array_name, begin, array_name, begin, direction);
636 
637 			if( ptcon == (locon_list *) NULL )
638 				break;
639 		}
640 
641         mbkfree( name );
642 	}
643 } /* end of edit_con */
644 
645 /*---------------------------------------------------------\
646                      edit_ins
647 \---------------------------------------------------------*/
edit_ins(ptins)648 static void edit_ins(ptins)
649 loins_list *ptins;
650 {
651 /*	char  cellref_type;*/
652 	char *name;
653 	char *pt;
654 
655 	while (ptins != (loins_list *) NULL)
656 	{
657 		name = mbkalloc( strlen( ptins->INSNAME ) + 1 );
658 		strcpy( name, ptins->INSNAME );
659 		for( pt = name; *pt; pt++ )
660         {
661 			if( *pt == '/' )
662             {
663 				*pt = '_';
664             }
665         }
666 
667 /*		cellref_type = (incatalog(ptins->FIGNAME) ? 'I' : 'A');*/
668 
669         pt = found_suffixed_cell( ptins->FIGNAME, FALSE );
670 
671 		fprintf(edif_file, "\n      (instance %s (viewref %s (cellref %s (libraryref %s) )))",
672 		                   name,
673 /* 		                   (cellref_type == 'I') ? SYMBOL : SCHEMATIC, */
674                            SYMBOL,
675 		                   ptins->FIGNAME,
676                            pt ? pt : EDIF_LIBNAME );
677 		ptins = ptins -> NEXT;
678 
679         mbkfree( name );
680 	}
681 } /* end of edit_ins */
682 
683 /*---------------------------------------------------------\
684                      edit_sig
685 \---------------------------------------------------------*/
edit_sig(ptlofig)686 static void edit_sig(ptlofig)
687 lofig_list *ptlofig;
688 {
689 	losig_list *ptsig;
690 	loins_list *sig_ins;
691 	int         idx = 0;
692 	long        sig_index;
693 	char       *array_name = (char *) NULL;
694 	char       *name = (char *) NULL;
695     char       *pt;
696 
697 	for (ptsig = ptlofig->LOSIG; ptsig != (losig_list *) NULL; ptsig = ptsig->NEXT)
698 		check_fig_portref( ptlofig->NAME, ptlofig->LOCON, ptsig->INDEX );
699 
700 	ptsig = ptlofig->LOSIG;
701 	while( ptsig != (losig_list *) NULL )
702 	{
703 		if( ptsig->TYPE != 'I' || ptlofig->LOINS )
704 		{
705 			sig_index = ptsig -> INDEX;
706 
707 			name = getsigname( ptsig );
708             if( isvdd( name ) || isvss( name ) )
709             {
710                 ptsig = ptsig->NEXT;
711                 continue;
712             }
713 			for( pt = name; *pt; pt++ )
714             {
715 				if( *pt == '/' )
716                 {
717 					*pt = '_';
718                 }
719             }
720 
721 			if( ( array_name = edif_busname( name ) ) && ( ( idx = edif_busindex( name ) ) != -1 ) )
722 			{
723 				fprintf( edif_file, "\n      (net (rename %s_60_%d_62 \"%s<%d>\") (joined ",
724 				         array_name, idx, array_name, idx );
725 			}
726 			else
727 			{
728 				if( !isdigit( name[0] ) )
729 					fprintf( edif_file, "\n      (net %s (joined ", name );
730 				else
731 					fprintf( edif_file, "\n      (net &_%s (joined ", name );
732 			}
733 
734 			if (ptsig->TYPE != 'I')
735 				port_ext( ptlofig->LOCON, sig_index );
736 
737 			for( sig_ins = ptlofig->LOINS; sig_ins != NULL; sig_ins = sig_ins->NEXT )
738             {
739                 sig_ins->LOCON = (locon_list *)reverse((chain_list *)sig_ins->LOCON);
740 				connect( sig_ins->LOCON, sig_index, sig_ins );
741                 sig_ins->LOCON = (locon_list *)reverse((chain_list *)sig_ins->LOCON);
742             }
743 
744 			fprintf(edif_file, "))");
745 		}
746 
747 		if( ptsig )
748         {
749 			ptsig = ptsig->NEXT;
750         }
751 	}
752 } /* end of edit_sig */
753 
754 /*---------------------------------------------------------\
755                      check_fig_portref
756 \---------------------------------------------------------*/
check_fig_portref(lofig_name,ptcon,sig_index)757 static void check_fig_portref( lofig_name, ptcon, sig_index )
758 char        *lofig_name;
759 locon_list  *ptcon;
760 int     sig_index;
761 {
762 	int nb = 0;
763 
764 	for (; (ptcon != (locon_list *) NULL) && (nb <= 1); ptcon = ptcon->NEXT)
765 		if (ptcon->SIG->INDEX == sig_index)
766 			nb++;
767 
768 	if (nb > 1)
769 	{
770 		fprintf( stderr, "*** mbk error *** edifsavelofig : Error in MBK Structure\n" );
771 		fprintf( stderr, "    multiple (portref ..) to lofig '%s' not\n", lofig_name );
772 		fprintf( stderr, "    allowed on signal of type 'E' (cadence)\n" );
773 		exit( 1 );
774 	}
775 
776 } /* end of check_fig_portref */
777 
778 /*---------------------------------------------------------\
779                      port_ext
780 \---------------------------------------------------------*/
port_ext(sig_con,sig_index)781 static void port_ext( sig_con, sig_index )
782 locon_list *sig_con;
783 int         sig_index;
784 {
785 	losig_list *sig_con_sig;
786 	locon_list *fig_con;
787 	char       *sig_con_name;
788 
789 	fig_con = sig_con;
790 	sig_con_name = (char *)NULL;
791 
792 	while (sig_con != (locon_list *)NULL)
793 	{
794 		sig_con_sig = sig_con -> SIG;
795 		if (sig_con_sig -> INDEX == sig_index)
796 		{
797 			sig_con_name = sig_con -> NAME;
798 			break;
799 		}
800 		sig_con = sig_con -> NEXT;
801 	}
802 
803 	if (sig_con_name == NULL)
804 	{
805 		fprintf( stderr, "***  mbk error *** edifsavelofig : Error in MBK Structure\n" );
806 		fprintf( stderr, "    No Connector on Signal of type 'E'\n" );
807 		exit( 1 );
808 	}
809 
810 	connect(fig_con, sig_index, (loins_list *)NULL);
811 
812 } /* end of port_ext */
813 
814 /*---------------------------------------------------------\
815                      edif_found_array
816 \---------------------------------------------------------*/
edif_found_array(ptcon,name,begin,end)817 static locon_list *edif_found_array( ptcon, name, begin, end )
818 locon_list *ptcon;
819 char       *name;
820 int        *begin;
821 int        *end;
822 {
823 	locon_list *ptcon_first_bus;
824 	char       *array_name;
825 
826 	*begin = 0;
827 	*end   = 0;
828 
829 	while( ( ptcon ) && (  ( array_name = edif_busname( ptcon->NAME ) ) != name ) )
830 		ptcon = ptcon->NEXT;
831 
832 	if( !ptcon )
833 		return NULL;
834 
835 	*begin = edif_busindex( ptcon -> NAME );
836 	*end   = *begin;
837 
838 	ptcon_first_bus = ptcon;
839 
840 	while( ( ptcon != (locon_list *) NULL ) && ( array_name == edif_busname( ptcon->NAME ) ) )
841 	{
842 		if (ptcon->DIRECTION != ptcon_first_bus->DIRECTION)
843 		{
844 			fprintf( stderr, "*** mbk error *** edifsavelofig : Error in MBK Structure\n" );
845 			fprintf( stderr, "    Connectors %s and %s of same bus must have same direction\n",
846 			                ptcon_first_bus->NAME, ptcon->NAME);
847 			exit( 1 );
848 		}
849 		*end = edif_busindex( ptcon->NAME );
850 		ptcon = ptcon->NEXT;
851 	}
852 
853 	return ptcon;
854 
855 } /* fin de edif_found_array */
856 
857 /*---------------------------------------------------------\
858                      edif_busindex
859 \---------------------------------------------------------*/
edif_busindex(s)860 static int edif_busindex(s)
861 char *s;
862 {
863 	char *t;
864 
865 	if( !( t = strchr( s, ' ' ) ) )
866 		return -1;
867 
868 	return atoi(t);
869 
870 } /* end of edif_busindex */
871 
872 /*---------------------------------------------------------\
873                      edif_busname
874 \---------------------------------------------------------*/
edif_busname(name)875 char *edif_busname( name )
876 char *name;
877 {
878 	char *s;
879 	char c[100];
880 
881 	if( !( s = strchr( name, ' ' ) ) )
882 		return (char *) NULL;
883 
884 	strncpy( c, name, (int)(s - name) );
885 	c[ s - name ] = '\0';
886 
887 	for (s++; *s != '\0'; s++)
888 		if( !isdigit( *s ) )
889 			return (char *) NULL;
890 
891 	return namealloc( c );
892 } /* end of edif_busname */
893 
894