1 /* -*- tab-width: 4 -*-
2  *
3  * Electric(tm) VLSI Design System
4  *
5  * File: sc1delete.c
6  * Modules for freeing data structures allocated by the QUISC Silicon Compiler
7  * Written by: Andrew R. Kostiuk, Queen's University
8  *
9  * Copyright (c) 2000 Static Free Software.
10  *
11  * Electric(tm) is free software; you can redistribute it and/or modify
12  * it under the terms of the GNU General Public License as published by
13  * the Free Software Foundation; either version 2 of the License, or
14  * (at your option) any later version.
15  *
16  * Electric(tm) is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19  * GNU General Public License for more details.
20  *
21  * You should have received a copy of the GNU General Public License
22  * along with Electric(tm); see the file COPYING.  If not, write to
23  * the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
24  * Boston, Mass 02111-1307, USA.
25  *
26  * Static Free Software
27  * 4119 Alpine Road
28  * Portola Valley, California 94028
29  * info@staticfreesoft.com
30  */
31 
32 #include "config.h"
33 #if SCTOOL
34 
35 #include	"global.h"
36 #include	"sc1.h"
37 
38 
39 /***********************************************************************
40 	External Variables
41 ------------------------------------------------------------------------
42 */
43 
44 extern SCCELL	*sc_cells, *sc_curcell;
45 
46 /* prototypes for local routines */
47 static int Sc_free_cell(SCCELL*);
48 static int Sc_free_string(CHAR*);
49 static int Sc_free_port(SCPORT*);
50 static int Sc_free_instance(SCNITREE*);
51 static int Sc_free_instance_port(SCNIPORT*);
52 static int Sc_free_extracted_node(SCEXTNODE*);
53 static int Sc_free_row(SCROWLIST*);
54 static int Sc_free_place(SCNBPLACE*);
55 static int Sc_free_route_channel(SCROUTECHANNEL*);
56 static int Sc_free_channel_node(SCROUTECHNODE*);
57 static int Sc_free_channel_track(SCROUTETRACK*);
58 static int Sc_free_route_row(SCROUTEROW*);
59 static int Sc_free_route_node(SCROUTENODE*);
60 
61 /***********************************************************************
62 Module:  Sc_delete
63 ------------------------------------------------------------------------
64 Description:
65 	Delete (free) the entire QUISC allocated database.
66 ------------------------------------------------------------------------
67 Calling Sequence:  err = Sc_delete();
68 
69 Name		Type		Description
70 ----		----		-----------
71 err			int			Returned error code, 0 = no error.
72 ------------------------------------------------------------------------
73 */
74 
Sc_delete(void)75 int Sc_delete(void)
76 {
77 	SCCELL	*cel, *nextcel;
78 	int		err;
79 
80 	/* free all cells */
81 	for (cel = sc_cells; cel; cel = nextcel)
82 	{
83 		nextcel = cel->next;
84 		err = Sc_free_cell(cel);
85 		if (err) return(err);
86 	}
87 
88 	sc_cells = NULL;
89 	sc_curcell = NULL;
90 	return(SC_NOERROR);
91 }
92 
93 /***********************************************************************
94 Module:  Sc_free_cell
95 ------------------------------------------------------------------------
96 Description:
97 	Free the memory consumed by the indicated cell and its components.
98 ------------------------------------------------------------------------
99 Calling Sequence:  err = Sc_free_cell(cell);
100 
101 Name		Type		Description
102 ----		----		-----------
103 cell		*SCCELL		Pointer to cell to free.
104 err			int			Returned error code, 0 = no error.
105 ------------------------------------------------------------------------
106 */
107 
Sc_free_cell(SCCELL * cell)108 int Sc_free_cell(SCCELL *cell)
109 {
110 	int			err;
111 	SCNITREE	*inst, *nextinst;
112 	SCSIM		*siminfo, *nextsiminfo;
113 	SCEXTNODE	*enode, *nextenode;
114 	SCPORT		*port, *nextport;
115 
116 	if (cell == NULL)
117 		return(SC_NOERROR);
118 
119 	/* free the name */
120 	err = Sc_free_string(cell->name);
121 	if (err) return(err);
122 
123 	/* free all instances */
124 	for (inst = cell->nilist; inst; inst = nextinst)
125 	{
126 		nextinst = inst->next;
127 		err = Sc_free_instance(inst);
128 		if (err) return(err);
129 	}
130 
131 	/* free any simulation information */
132 	for (siminfo = cell->siminfo; siminfo; siminfo = nextsiminfo)
133 	{
134 		nextsiminfo = siminfo->next;
135 		err = Sc_free_string(siminfo->model);
136 		/* is it a memory leak to NOT free siminfo here !!! */
137 		if (err) return(err);
138 	}
139 
140 	/* free extracted nodes */
141 	for (enode = cell->ex_nodes; enode; enode = nextenode)
142 	{
143 		nextenode = enode->next;
144 		err = Sc_free_extracted_node(enode);
145 		if (err) return(err);
146 	}
147 
148 	/* free power and ground */
149 	if ((err = Sc_free_extracted_node(cell->power)))
150 		return(err);
151 	if ((err = Sc_free_extracted_node(cell->ground)))
152 		return(err);
153 
154 	/* free ports */
155 	for (port = cell->ports; port; port = nextport)
156 	{
157 		nextport = port->next;
158 		err = Sc_free_port(port);
159 		if (err) return(err);
160 	}
161 
162 	/* free placement information */
163 	if ((err = Sc_free_placement(cell->placement)))
164 		return(err);
165 
166 	/* free routing information */
167 	if ((err = Sc_free_route(cell->route)))
168 		return(err);
169 
170 	efree((CHAR *)cell);
171 
172 	return(SC_NOERROR);
173 }
174 
175 /***********************************************************************
176 Module:  Sc_free_string
177 ------------------------------------------------------------------------
178 Description:
179 	Free the memory consumed by the indicated string.
180 ------------------------------------------------------------------------
181 Calling Sequence:  err = Sc_free_string(string);
182 
183 Name		Type		Description
184 ----		----		-----------
185 string		*char		Pointer to string.
186 err			int			Returned error code, 0 = no error.
187 ------------------------------------------------------------------------
188 */
189 
Sc_free_string(CHAR * string)190 int Sc_free_string(CHAR *string)
191 {
192 	if (string) efree(string);
193 	return(SC_NOERROR);
194 }
195 
196 /***********************************************************************
197 Module:  Sc_free_port
198 ------------------------------------------------------------------------
199 Description:
200 	Free the memory consumed by the indicated port and its components.
201 ------------------------------------------------------------------------
202 Calling Sequence:  err = Sc_free_port(port);
203 
204 Name		Type		Description
205 ----		----		-----------
206 port		*SCPORT		Port to be freed.
207 err			int			Returned error code, 0 = no error.
208 ------------------------------------------------------------------------
209 */
210 
Sc_free_port(SCPORT * port)211 int Sc_free_port(SCPORT *port)
212 {
213 	int		err;
214 
215 	if (port)
216 	{
217 		if ((err = Sc_free_string(port->name)))
218 			return(err);
219 		efree((CHAR *)port);
220 	}
221 	return(SC_NOERROR);
222 }
223 
224 /***********************************************************************
225 Module:  Sc_free_instance
226 ------------------------------------------------------------------------
227 Description:
228 	Free the memory consumed by the indicated instance and its components.
229 ------------------------------------------------------------------------
230 Calling Sequence:  err = Sc_free_instance(inst);
231 
232 Name		Type		Description
233 ----		----		-----------
234 inst		*SCNITREE	Instance to be freed.
235 err			int			Returned error code, 0 = no error.
236 ------------------------------------------------------------------------
237 */
238 
Sc_free_instance(SCNITREE * inst)239 int Sc_free_instance(SCNITREE *inst)
240 {
241 	int			err;
242 	SCCONLIST	*con, *nextcon;
243 	SCNIPORT	*nport, *nextnport;
244 
245 	if (inst)
246 	{
247 		if ((err = Sc_free_string(inst->name)))
248 			return(err);
249 		for (con = inst->connect; con; con = nextcon)
250 		{
251 			nextcon = con->next;
252 			efree((CHAR *)con);
253 		}
254 		for (nport = inst->ports; nport; nport = nextnport)
255 		{
256 			nextnport = nport->next;
257 			if ((err = Sc_free_instance_port(nport)))
258 				return(err);
259 		}
260 		if ((err = Sc_free_instance_port(inst->power)))
261 			return(err);
262 		if ((err = Sc_free_instance_port(inst->ground)))
263 			return(err);
264 		efree((CHAR *)inst);
265 	}
266 
267 	return(SC_NOERROR);
268 }
269 
270 /***********************************************************************
271 Module:  Sc_free_instance_port
272 ------------------------------------------------------------------------
273 Description:
274 	Free the memory consumed by the indicated instance port.
275 ------------------------------------------------------------------------
276 Calling Sequence:  err = Sc_free_instance_port(port);
277 
278 Name		Type		Description
279 ----		----		-----------
280 port		*SCNIPORT	Pointer to instance port.
281 err			int			Returned error code, 0 = no error.
282 ------------------------------------------------------------------------
283 */
284 
Sc_free_instance_port(SCNIPORT * port)285 int Sc_free_instance_port(SCNIPORT *port)
286 {
287 	if (port) efree((CHAR *)port);
288 	return(SC_NOERROR);
289 }
290 
291 /***********************************************************************
292 Module:  Sc_free_extracted_node
293 ------------------------------------------------------------------------
294 Description:
295 	Free the indicated extraced node and its contents.
296 ------------------------------------------------------------------------
297 Calling Sequence:  err = Sc_free_extracted_node(enode);
298 
299 Name		Type		Description
300 ----		----		-----------
301 enode		*SCEXTNODE	Pointer to extracted node.
302 err			int			Returned error code, 0 = no error.
303 ------------------------------------------------------------------------
304 */
305 
Sc_free_extracted_node(SCEXTNODE * enode)306 int Sc_free_extracted_node(SCEXTNODE *enode)
307 {
308 	int			err;
309 	SCEXTPORT	*eport, *nexteport;
310 
311 	if (enode)
312 	{
313 		if ((err = Sc_free_string(enode->name)))
314 			return(err);
315 		for (eport = enode->firstport; eport; eport = nexteport)
316 		{
317 			nexteport = eport->next;
318 			efree((CHAR *)eport);
319 		}
320 		efree((CHAR *)enode);
321 	}
322 
323 	return(SC_NOERROR);
324 }
325 
326 /***********************************************************************
327 Module:  Sc_free_placement
328 ------------------------------------------------------------------------
329 Description:
330 	Free the indicated placement structure and its contents.
331 ------------------------------------------------------------------------
332 Calling Sequence:  err = Sc_free_placement(placement);
333 
334 Name		Type		Description
335 ----		----		-----------
336 placement	*SCPLACE	Pointer to placement structure.
337 err			int			Returned error code, 0 = no error.
338 ------------------------------------------------------------------------
339 */
340 
Sc_free_placement(SCPLACE * placement)341 int Sc_free_placement(SCPLACE *placement)
342 {
343 	int			err;
344 	SCROWLIST	*row, *nextrow;
345 
346 	if (placement)
347 	{
348 		for (row = placement->rows; row; row = nextrow)
349 		{
350 			nextrow = row->next;
351 			if ((err = Sc_free_row(row)))
352 				return(err);
353 		}
354 		efree((CHAR *)placement);
355 	}
356 
357 	return(SC_NOERROR);
358 }
359 
360 /***********************************************************************
361 Module:  Sc_free_row
362 ------------------------------------------------------------------------
363 Description:
364 	Free the indicated row structure and its contents.
365 ------------------------------------------------------------------------
366 Calling Sequence:  err = Sc_free_row(row);
367 
368 Name		Type		Description
369 ----		----		-----------
370 row			*SCROWLIST	Pointer to row.
371 err			int			Returned error code, 0 = no error.
372 ------------------------------------------------------------------------
373 */
374 
Sc_free_row(SCROWLIST * row)375 int Sc_free_row(SCROWLIST *row)
376 {
377 	int			err;
378 	SCNBPLACE	*place, *nextplace;
379 
380 	if (row)
381 	{
382 		for (place = row->start; place; place = nextplace)
383 		{
384 			nextplace = place->next;
385 			if ((err = Sc_free_place(place)))
386 				return(err);
387 		}
388 		efree((CHAR *)row);
389 	}
390 
391 	return(SC_NOERROR);
392 }
393 
394 /***********************************************************************
395 Module:  Sc_free_place
396 ------------------------------------------------------------------------
397 Description:
398 	Free the indicated place structure and its contents.
399 ------------------------------------------------------------------------
400 Calling Sequence:  err = Sc_free_place(place);
401 
402 Name		Type		Description
403 ----		----		-----------
404 place		*SCNBPLACE	Pointer to place.
405 err			int			Returned error code, 0 = no error.
406 ------------------------------------------------------------------------
407 */
408 
Sc_free_place(SCNBPLACE * place)409 int Sc_free_place(SCNBPLACE *place)
410 {
411 	if (place) efree((CHAR *)place);
412 
413 	return(SC_NOERROR);
414 }
415 
416 /***********************************************************************
417 Module:  Sc_free_route
418 ------------------------------------------------------------------------
419 Description:
420 	Free the indicated route structure and its contents.
421 ------------------------------------------------------------------------
422 Calling Sequence:  err = Sc_free_route(route);
423 
424 Name		Type		Description
425 ----		----		-----------
426 route		*SCROUTE	Pointer to the route structure.
427 err			int			Returned error code, 0 = no error.
428 ------------------------------------------------------------------------
429 */
430 
Sc_free_route(SCROUTE * route)431 int Sc_free_route(SCROUTE *route)
432 {
433 	int				err;
434 	SCROUTECHANNEL	*chan, *nextchan;
435 	SCROUTEEXPORT	*xport, *nextxport;
436 	SCROUTEROW		*row, *nextrow;
437 
438 	if (route)
439 	{
440 		for (chan = route->channels; chan; chan = nextchan)
441 		{
442 			nextchan = chan->next;
443 			if ((err = Sc_free_route_channel(chan)))
444 				return(err);
445 		}
446 		for (xport = route->exports; xport; xport = nextxport)
447 		{
448 			nextxport = xport->next;
449 			efree((CHAR *)xport);
450 		}
451 		for (row = route->rows; row; row = nextrow)
452 		{
453 			nextrow = row->next;
454 			if ((err = Sc_free_route_row(row)))
455 				return(err);
456 		}
457 		efree((CHAR *)route);
458 	}
459 
460 	return(SC_NOERROR);
461 }
462 
463 /***********************************************************************
464 Module:  Sc_free_route_channel
465 ------------------------------------------------------------------------
466 Description:
467 	Free the indicated route channel structure and its contents.
468 ------------------------------------------------------------------------
469 Calling Sequence:  err = Sc_free_route_channel(chan);
470 
471 Name		Type			Description
472 ----		----			-----------
473 chan		*SCROUTECHANNEL	Route channel structure.
474 err			int				Returned error code, 0 = no error.
475 ------------------------------------------------------------------------
476 */
477 
Sc_free_route_channel(SCROUTECHANNEL * chan)478 int Sc_free_route_channel(SCROUTECHANNEL *chan)
479 {
480 	int				err;
481 	SCROUTECHNODE	*node, *nextnode;
482 	SCROUTETRACK	*track, *nexttrack;
483 
484 	if (chan)
485 	{
486 		for (node = chan->nodes; node; node = nextnode)
487 		{
488 			nextnode = node->next;
489 			if ((err = Sc_free_channel_node(node)))
490 				return(err);
491 		}
492 		for (track = chan->tracks; track; track = nexttrack)
493 		{
494 			nexttrack = track->next;
495 			if ((err = Sc_free_channel_track(track)))
496 				return(err);
497 		}
498 		efree((CHAR *)chan);
499 	}
500 
501 	return(SC_NOERROR);
502 }
503 
504 /***********************************************************************
505 Module:  Sc_free_channel_node
506 ------------------------------------------------------------------------
507 Description:
508 	Free the indicated route channel node structure and its contents.
509 ------------------------------------------------------------------------
510 Calling Sequence:  err = Sc_free_route_channel_node(node);
511 
512 Name		Type			Description
513 ----		----			-----------
514 node		*SCROUTECHNODE	Pointer to route channel node.
515 err			int				Returned error code, 0 = no error.
516 ------------------------------------------------------------------------
517 */
518 
Sc_free_channel_node(SCROUTECHNODE * node)519 int Sc_free_channel_node(SCROUTECHNODE *node)
520 {
521 	SCROUTECHPORT	*chport, *nextchport;
522 
523 	if (node)
524 	{
525 		for (chport = node->firstport; chport; chport = nextchport)
526 		{
527 			nextchport = chport->next;
528 			efree((CHAR *)chport);
529 		}
530 		efree((CHAR *)node);
531 	}
532 
533 	return(SC_NOERROR);
534 }
535 
536 /***********************************************************************
537 Module:  Sc_free_channel_track
538 ------------------------------------------------------------------------
539 Description:
540 	Free the indicated route channel track structure and its contents.
541 ------------------------------------------------------------------------
542 Calling Sequence:  err = Sc_free_route_channel_track(track);
543 
544 Name		Type			Description
545 ----		----			-----------
546 track		*SCROUTETRACK	Pointer to route channel track.
547 err			int				Returned error code, 0 = no error.
548 ------------------------------------------------------------------------
549 */
550 
Sc_free_channel_track(SCROUTETRACK * track)551 int Sc_free_channel_track(SCROUTETRACK *track)
552 {
553 	SCROUTETRACKMEM	*mem, *nextmem;
554 
555 	if (track)
556 	{
557 		for (mem = track->nodes; mem; mem = nextmem)
558 		{
559 			nextmem = mem->next;
560 			efree((CHAR *)mem);
561 		}
562 		efree((CHAR *)track);
563 	}
564 
565 	return(SC_NOERROR);
566 }
567 
568 /***********************************************************************
569 Module:  Sc_free_route_row
570 ------------------------------------------------------------------------
571 Description:
572 	Free the indicated route row structure and its contents.
573 ------------------------------------------------------------------------
574 Calling Sequence:  err = Sc_free_route_row(row);
575 
576 Name		Type		Description
577 ----		----		-----------
578 row			*SCROUTEROW	Pointer to route row.
579 err			int			Returned error code, 0 = no error.
580 ------------------------------------------------------------------------
581 */
582 
Sc_free_route_row(SCROUTEROW * row)583 int Sc_free_route_row(SCROUTEROW *row)
584 {
585 	int				err;
586 	SCROUTENODE		*node, *nextnode;
587 
588 	if (row)
589 	{
590 		for (node = row->nodes; node; node = nextnode)
591 		{
592 			nextnode = node->next;
593 			if ((err = Sc_free_route_node(node))) return(err);
594 		}
595 		efree((CHAR *)row);
596 	}
597 
598 	return(SC_NOERROR);
599 }
600 
601 /***********************************************************************
602 Module:  Sc_free_route_node
603 ------------------------------------------------------------------------
604 Description:
605 	Free the indicated route route node structure and its contents.
606 ------------------------------------------------------------------------
607 Calling Sequence:  err = Sc_free_route_route_node(node);
608 
609 Name		Type			Description
610 ----		----			-----------
611 node		*SCROUTENODE	Pointer to route node.
612 err			int				Returned error code, 0 = no error.
613 ------------------------------------------------------------------------
614 */
615 
Sc_free_route_node(SCROUTENODE * node)616 int Sc_free_route_node(SCROUTENODE *node)
617 {
618 	SCROUTEPORT		*port, *nextport;
619 
620 	if (node)
621 	{
622 		for (port = node->firstport; port; port = nextport)
623 		{
624 			nextport = port->next;
625 			efree((CHAR *)port);
626 		}
627 		efree((CHAR *)node);
628 	}
629 
630 	return(SC_NOERROR);
631 }
632 
633 #endif  /* SCTOOL - at top */
634