OSDN Git Service

Fix sh-elf linker relaxation:
[pf3gnuchains/gcc-fork.git] / gcc / cfg.c
1 /* Control flow graph manipulation code for GNU compiler.
2    Copyright (C) 1987, 1988, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
3    1999, 2000, 2001, 2002 Free Software Foundation, Inc.
4
5 This file is part of GCC.
6
7 GCC is free software; you can redistribute it and/or modify it under
8 the terms of the GNU General Public License as published by the Free
9 Software Foundation; either version 2, or (at your option) any later
10 version.
11
12 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13 WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15 for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GCC; see the file COPYING.  If not, write to the Free
19 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20 02111-1307, USA.  */
21
22 /* This file contains low level functions to manipulate the CFG and
23    analyze it.  All other modules should not transform the datastructure
24    directly and use abstraction instead.  The file is supposed to be
25    ordered bottom-up and should not contain any code dependent on a
26    particular intermediate language (RTL or trees).
27
28    Available functionality:
29      - Initialization/deallocation
30          init_flow, clear_edges
31      - Low level basic block manipulation
32          alloc_block, expunge_block
33      - Edge manipulation
34          make_edge, make_single_succ_edge, cached_make_edge, remove_edge
35          - Low level edge redirection (without updating instruction chain)
36              redirect_edge_succ, redirect_edge_succ_nodup, redirect_edge_pred
37      - Dumping and debugging
38          dump_flow_info, debug_flow_info, dump_edge_info
39      - Allocation of AUX fields for basic blocks
40          alloc_aux_for_blocks, free_aux_for_blocks, alloc_aux_for_block
41      - clear_bb_flags
42  */
43 \f
44 #include "config.h"
45 #include "system.h"
46 #include "coretypes.h"
47 #include "tm.h"
48 #include "tree.h"
49 #include "rtl.h"
50 #include "hard-reg-set.h"
51 #include "basic-block.h"
52 #include "regs.h"
53 #include "flags.h"
54 #include "output.h"
55 #include "function.h"
56 #include "except.h"
57 #include "toplev.h"
58 #include "tm_p.h"
59 #include "obstack.h"
60 #include "alloc-pool.h"
61
62 /* The obstack on which the flow graph components are allocated.  */
63
64 struct obstack flow_obstack;
65 static char *flow_firstobj;
66
67 /* Basic block object pool.  */
68
69 static alloc_pool bb_pool;
70
71 /* Edge object pool.  */
72
73 static alloc_pool edge_pool;
74
75 /* Number of basic blocks in the current function.  */
76
77 int n_basic_blocks;
78
79 /* First free basic block number.  */
80
81 int last_basic_block;
82
83 /* Number of edges in the current function.  */
84
85 int n_edges;
86
87 /* The basic block array.  */
88
89 varray_type basic_block_info;
90
91 /* The special entry and exit blocks.  */
92
93 struct basic_block_def entry_exit_blocks[2]
94 = {{NULL,                       /* head */
95     NULL,                       /* end */
96     NULL,                       /* head_tree */
97     NULL,                       /* end_tree */
98     NULL,                       /* pred */
99     NULL,                       /* succ */
100     NULL,                       /* local_set */
101     NULL,                       /* cond_local_set */
102     NULL,                       /* global_live_at_start */
103     NULL,                       /* global_live_at_end */
104     NULL,                       /* aux */
105     ENTRY_BLOCK,                /* index */
106     NULL,                       /* prev_bb */
107     EXIT_BLOCK_PTR,             /* next_bb */
108     0,                          /* loop_depth */
109     NULL,                       /* loop_father */
110     0,                          /* count */
111     0,                          /* frequency */
112     0                           /* flags */
113   },
114   {
115     NULL,                       /* head */
116     NULL,                       /* end */
117     NULL,                       /* head_tree */
118     NULL,                       /* end_tree */
119     NULL,                       /* pred */
120     NULL,                       /* succ */
121     NULL,                       /* local_set */
122     NULL,                       /* cond_local_set */
123     NULL,                       /* global_live_at_start */
124     NULL,                       /* global_live_at_end */
125     NULL,                       /* aux */
126     EXIT_BLOCK,                 /* index */
127     ENTRY_BLOCK_PTR,            /* prev_bb */
128     NULL,                       /* next_bb */
129     0,                          /* loop_depth */
130     NULL,                       /* loop_father */
131     0,                          /* count */
132     0,                          /* frequency */
133     0                           /* flags */
134   }
135 };
136
137 void debug_flow_info                    PARAMS ((void));
138 static void free_edge                   PARAMS ((edge));
139 \f
140 /* Called once at initialization time.  */
141
142 void
143 init_flow ()
144 {
145   static int initialized;
146
147   n_edges = 0;
148
149   if (!initialized)
150     {
151       gcc_obstack_init (&flow_obstack);
152       flow_firstobj = (char *) obstack_alloc (&flow_obstack, 0);
153       initialized = 1;
154     }
155   else
156     {
157       free_alloc_pool (bb_pool);
158       free_alloc_pool (edge_pool);
159       obstack_free (&flow_obstack, flow_firstobj);
160       flow_firstobj = (char *) obstack_alloc (&flow_obstack, 0);
161     }
162   bb_pool = create_alloc_pool ("Basic block pool", 
163                                sizeof (struct basic_block_def), 100);
164   edge_pool = create_alloc_pool ("Edge pool",
165                                sizeof (struct edge_def), 100);
166 }
167 \f
168 /* Helper function for remove_edge and clear_edges.  Frees edge structure
169    without actually unlinking it from the pred/succ lists.  */
170
171 static void
172 free_edge (e)
173      edge e;
174 {
175   n_edges--;
176   pool_free (edge_pool, e);
177 }
178
179 /* Free the memory associated with the edge structures.  */
180
181 void
182 clear_edges ()
183 {
184   basic_block bb;
185   edge e;
186
187   FOR_EACH_BB (bb)
188     {
189       edge e = bb->succ;
190
191       while (e)
192         {
193           edge next = e->succ_next;
194
195           free_edge (e);
196           e = next;
197         }
198
199       bb->succ = NULL;
200       bb->pred = NULL;
201     }
202
203   e = ENTRY_BLOCK_PTR->succ;
204   while (e)
205     {
206       edge next = e->succ_next;
207
208       free_edge (e);
209       e = next;
210     }
211
212   EXIT_BLOCK_PTR->pred = NULL;
213   ENTRY_BLOCK_PTR->succ = NULL;
214
215   if (n_edges)
216     abort ();
217 }
218 \f
219 /* Allocate memory for basic_block.  */
220
221 basic_block
222 alloc_block ()
223 {
224   basic_block bb;
225   bb = pool_alloc (bb_pool);
226   memset (bb, 0, sizeof (*bb));
227   return bb;
228 }
229
230 /* Link block B to chain after AFTER.  */
231 void
232 link_block (b, after)
233      basic_block b, after;
234 {
235   b->next_bb = after->next_bb;
236   b->prev_bb = after;
237   after->next_bb = b;
238   b->next_bb->prev_bb = b;
239 }
240
241 /* Unlink block B from chain.  */
242 void
243 unlink_block (b)
244      basic_block b;
245 {
246   b->next_bb->prev_bb = b->prev_bb;
247   b->prev_bb->next_bb = b->next_bb;
248 }
249
250 /* Sequentially order blocks and compact the arrays.  */
251 void
252 compact_blocks ()
253 {
254   int i;
255   basic_block bb;
256  
257   i = 0;
258   FOR_EACH_BB (bb)
259     {
260       BASIC_BLOCK (i) = bb;
261       bb->index = i;
262       i++;
263     }
264
265   if (i != n_basic_blocks)
266     abort ();
267
268   last_basic_block = n_basic_blocks;
269 }
270
271 /* Remove block B from the basic block array.  */
272
273 void
274 expunge_block (b)
275      basic_block b;
276 {
277   unlink_block (b);
278   BASIC_BLOCK (b->index) = NULL;
279   n_basic_blocks--;
280   pool_free (bb_pool, b);
281 }
282 \f
283 /* Create an edge connecting SRC and DST with FLAGS optionally using
284    edge cache CACHE.  Return the new edge, NULL if already exist.  */
285
286 edge
287 cached_make_edge (edge_cache, src, dst, flags)
288      sbitmap *edge_cache;
289      basic_block src, dst;
290      int flags;
291 {
292   int use_edge_cache;
293   edge e;
294
295   /* Don't bother with edge cache for ENTRY or EXIT, if there aren't that
296      many edges to them, or we didn't allocate memory for it.  */
297   use_edge_cache = (edge_cache
298                     && src != ENTRY_BLOCK_PTR && dst != EXIT_BLOCK_PTR);
299
300   /* Make sure we don't add duplicate edges.  */
301   switch (use_edge_cache)
302     {
303     default:
304       /* Quick test for non-existence of the edge.  */
305       if (! TEST_BIT (edge_cache[src->index], dst->index))
306         break;
307
308       /* The edge exists; early exit if no work to do.  */
309       if (flags == 0)
310         return NULL;
311
312       /* FALLTHRU */
313     case 0:
314       for (e = src->succ; e; e = e->succ_next)
315         if (e->dest == dst)
316           {
317             e->flags |= flags;
318             return NULL;
319           }
320       break;
321     }
322   
323   
324   e = pool_alloc (edge_pool);
325   memset (e, 0, sizeof (*e));
326   n_edges++;
327
328   e->succ_next = src->succ;
329   e->pred_next = dst->pred;
330   e->src = src;
331   e->dest = dst;
332   e->flags = flags;
333
334   src->succ = e;
335   dst->pred = e;
336
337   if (use_edge_cache)
338     SET_BIT (edge_cache[src->index], dst->index);
339
340   return e;
341 }
342
343 /* Create an edge connecting SRC and DEST with flags FLAGS.  Return newly
344    created edge or NULL if already exist.  */
345
346 edge
347 make_edge (src, dest, flags)
348      basic_block src, dest;
349      int flags;
350 {
351   return cached_make_edge (NULL, src, dest, flags);
352 }
353
354 /* Create an edge connecting SRC to DEST and set probability by knowing
355    that it is the single edge leaving SRC.  */
356
357 edge
358 make_single_succ_edge (src, dest, flags)
359      basic_block src, dest;
360      int flags;
361 {
362   edge e = make_edge (src, dest, flags);
363
364   e->probability = REG_BR_PROB_BASE;
365   e->count = src->count;
366   return e;
367 }
368
369 /* This function will remove an edge from the flow graph.  */
370
371 void
372 remove_edge (e)
373      edge e;
374 {
375   edge last_pred = NULL;
376   edge last_succ = NULL;
377   edge tmp;
378   basic_block src, dest;
379
380   src = e->src;
381   dest = e->dest;
382   for (tmp = src->succ; tmp && tmp != e; tmp = tmp->succ_next)
383     last_succ = tmp;
384
385   if (!tmp)
386     abort ();
387   if (last_succ)
388     last_succ->succ_next = e->succ_next;
389   else
390     src->succ = e->succ_next;
391
392   for (tmp = dest->pred; tmp && tmp != e; tmp = tmp->pred_next)
393     last_pred = tmp;
394
395   if (!tmp)
396     abort ();
397   if (last_pred)
398     last_pred->pred_next = e->pred_next;
399   else
400     dest->pred = e->pred_next;
401
402   free_edge (e);
403 }
404
405 /* Redirect an edge's successor from one block to another.  */
406
407 void
408 redirect_edge_succ (e, new_succ)
409      edge e;
410      basic_block new_succ;
411 {
412   edge *pe;
413
414   /* Disconnect the edge from the old successor block.  */
415   for (pe = &e->dest->pred; *pe != e; pe = &(*pe)->pred_next)
416     continue;
417   *pe = (*pe)->pred_next;
418
419   /* Reconnect the edge to the new successor block.  */
420   e->pred_next = new_succ->pred;
421   new_succ->pred = e;
422   e->dest = new_succ;
423 }
424
425 /* Like previous but avoid possible duplicate edge.  */
426
427 edge
428 redirect_edge_succ_nodup (e, new_succ)
429      edge e;
430      basic_block new_succ;
431 {
432   edge s;
433
434   /* Check whether the edge is already present.  */
435   for (s = e->src->succ; s; s = s->succ_next)
436     if (s->dest == new_succ && s != e)
437       break;
438
439   if (s)
440     {
441       s->flags |= e->flags;
442       s->probability += e->probability;
443       if (s->probability > REG_BR_PROB_BASE)
444         s->probability = REG_BR_PROB_BASE;
445       s->count += e->count;
446       remove_edge (e);
447       e = s;
448     }
449   else
450     redirect_edge_succ (e, new_succ);
451
452   return e;
453 }
454
455 /* Redirect an edge's predecessor from one block to another.  */
456
457 void
458 redirect_edge_pred (e, new_pred)
459      edge e;
460      basic_block new_pred;
461 {
462   edge *pe;
463
464   /* Disconnect the edge from the old predecessor block.  */
465   for (pe = &e->src->succ; *pe != e; pe = &(*pe)->succ_next)
466     continue;
467
468   *pe = (*pe)->succ_next;
469
470   /* Reconnect the edge to the new predecessor block.  */
471   e->succ_next = new_pred->succ;
472   new_pred->succ = e;
473   e->src = new_pred;
474 }
475
476 void
477 clear_bb_flags ()
478 {
479   basic_block bb;
480
481   FOR_BB_BETWEEN (bb, ENTRY_BLOCK_PTR, NULL, next_bb)
482     bb->flags = 0;
483 }
484 \f
485 void
486 dump_flow_info (file)
487      FILE *file;
488 {
489   int i;
490   int max_regno = max_reg_num ();
491   basic_block bb;
492   static const char * const reg_class_names[] = REG_CLASS_NAMES;
493
494   fprintf (file, "%d registers.\n", max_regno);
495   for (i = FIRST_PSEUDO_REGISTER; i < max_regno; i++)
496     if (REG_N_REFS (i))
497       {
498         enum reg_class class, altclass;
499
500         fprintf (file, "\nRegister %d used %d times across %d insns",
501                  i, REG_N_REFS (i), REG_LIVE_LENGTH (i));
502         if (REG_BASIC_BLOCK (i) >= 0)
503           fprintf (file, " in block %d", REG_BASIC_BLOCK (i));
504         if (REG_N_SETS (i))
505           fprintf (file, "; set %d time%s", REG_N_SETS (i),
506                    (REG_N_SETS (i) == 1) ? "" : "s");
507         if (regno_reg_rtx[i] != NULL && REG_USERVAR_P (regno_reg_rtx[i]))
508           fprintf (file, "; user var");
509         if (REG_N_DEATHS (i) != 1)
510           fprintf (file, "; dies in %d places", REG_N_DEATHS (i));
511         if (REG_N_CALLS_CROSSED (i) == 1)
512           fprintf (file, "; crosses 1 call");
513         else if (REG_N_CALLS_CROSSED (i))
514           fprintf (file, "; crosses %d calls", REG_N_CALLS_CROSSED (i));
515         if (regno_reg_rtx[i] != NULL
516             && PSEUDO_REGNO_BYTES (i) != UNITS_PER_WORD)
517           fprintf (file, "; %d bytes", PSEUDO_REGNO_BYTES (i));
518
519         class = reg_preferred_class (i);
520         altclass = reg_alternate_class (i);
521         if (class != GENERAL_REGS || altclass != ALL_REGS)
522           {
523             if (altclass == ALL_REGS || class == ALL_REGS)
524               fprintf (file, "; pref %s", reg_class_names[(int) class]);
525             else if (altclass == NO_REGS)
526               fprintf (file, "; %s or none", reg_class_names[(int) class]);
527             else
528               fprintf (file, "; pref %s, else %s",
529                        reg_class_names[(int) class],
530                        reg_class_names[(int) altclass]);
531           }
532
533         if (regno_reg_rtx[i] != NULL && REG_POINTER (regno_reg_rtx[i]))
534           fprintf (file, "; pointer");
535         fprintf (file, ".\n");
536       }
537
538   fprintf (file, "\n%d basic blocks, %d edges.\n", n_basic_blocks, n_edges);
539   FOR_EACH_BB (bb)
540     {
541       edge e;
542       int sum;
543       gcov_type lsum;
544
545       fprintf (file, "\nBasic block %d: first insn %d, last %d, ",
546                bb->index, INSN_UID (bb->head), INSN_UID (bb->end));
547       fprintf (file, "prev %d, next %d, ",
548                bb->prev_bb->index, bb->next_bb->index);
549       fprintf (file, "loop_depth %d, count ", bb->loop_depth);
550       fprintf (file, HOST_WIDEST_INT_PRINT_DEC, bb->count);
551       fprintf (file, ", freq %i", bb->frequency);
552       if (maybe_hot_bb_p (bb))
553         fprintf (file, ", maybe hot");
554       if (probably_never_executed_bb_p (bb))
555         fprintf (file, ", probably never executed");
556       fprintf (file, ".\n");
557
558       fprintf (file, "Predecessors: ");
559       for (e = bb->pred; e; e = e->pred_next)
560         dump_edge_info (file, e, 0);
561
562       fprintf (file, "\nSuccessors: ");
563       for (e = bb->succ; e; e = e->succ_next)
564         dump_edge_info (file, e, 1);
565
566       fprintf (file, "\nRegisters live at start:");
567       dump_regset (bb->global_live_at_start, file);
568
569       fprintf (file, "\nRegisters live at end:");
570       dump_regset (bb->global_live_at_end, file);
571
572       putc ('\n', file);
573
574       /* Check the consistency of profile information.  We can't do that
575          in verify_flow_info, as the counts may get invalid for incompletely
576          solved graphs, later eliminating of conditionals or roundoff errors.
577          It is still practical to have them reported for debugging of simple
578          testcases.  */
579       sum = 0;
580       for (e = bb->succ; e; e = e->succ_next)
581         sum += e->probability;
582       if (bb->succ && abs (sum - REG_BR_PROB_BASE) > 100)
583         fprintf (file, "Invalid sum of outgoing probabilities %.1f%%\n",
584                  sum * 100.0 / REG_BR_PROB_BASE);
585       sum = 0;
586       for (e = bb->pred; e; e = e->pred_next)
587         sum += EDGE_FREQUENCY (e);
588       if (abs (sum - bb->frequency) > 100)
589         fprintf (file,
590                  "Invalid sum of incomming frequencies %i, should be %i\n",
591                  sum, bb->frequency);
592       lsum = 0;
593       for (e = bb->pred; e; e = e->pred_next)
594         lsum += e->count;
595       if (lsum - bb->count > 100 || lsum - bb->count < -100)
596         fprintf (file, "Invalid sum of incomming counts %i, should be %i\n",
597                  (int)lsum, (int)bb->count);
598       lsum = 0;
599       for (e = bb->succ; e; e = e->succ_next)
600         lsum += e->count;
601       if (bb->succ && (lsum - bb->count > 100 || lsum - bb->count < -100))
602         fprintf (file, "Invalid sum of incomming counts %i, should be %i\n",
603                  (int)lsum, (int)bb->count);
604     }
605
606   putc ('\n', file);
607 }
608
609 void
610 debug_flow_info ()
611 {
612   dump_flow_info (stderr);
613 }
614
615 void
616 dump_edge_info (file, e, do_succ)
617      FILE *file;
618      edge e;
619      int do_succ;
620 {
621   basic_block side = (do_succ ? e->dest : e->src);
622
623   if (side == ENTRY_BLOCK_PTR)
624     fputs (" ENTRY", file);
625   else if (side == EXIT_BLOCK_PTR)
626     fputs (" EXIT", file);
627   else
628     fprintf (file, " %d", side->index);
629
630   if (e->probability)
631     fprintf (file, " [%.1f%%] ", e->probability * 100.0 / REG_BR_PROB_BASE);
632
633   if (e->count)
634     {
635       fprintf (file, " count:");
636       fprintf (file, HOST_WIDEST_INT_PRINT_DEC, e->count);
637     }
638
639   if (e->flags)
640     {
641       static const char * const bitnames[]
642         = {"fallthru", "ab", "abcall", "eh", "fake", "dfs_back", "can_fallthru"};
643       int comma = 0;
644       int i, flags = e->flags;
645
646       fputs (" (", file);
647       for (i = 0; flags; i++)
648         if (flags & (1 << i))
649           {
650             flags &= ~(1 << i);
651
652             if (comma)
653               fputc (',', file);
654             if (i < (int) ARRAY_SIZE (bitnames))
655               fputs (bitnames[i], file);
656             else
657               fprintf (file, "%d", i);
658             comma = 1;
659           }
660
661       fputc (')', file);
662     }
663 }
664 \f
665 /* Simple routines to easily allocate AUX fields of basic blocks.  */
666
667 static struct obstack block_aux_obstack;
668 static void *first_block_aux_obj = 0;
669 static struct obstack edge_aux_obstack;
670 static void *first_edge_aux_obj = 0;
671
672 /* Allocate a memory block of SIZE as BB->aux.  The obstack must
673    be first initialized by alloc_aux_for_blocks.  */
674
675 inline void
676 alloc_aux_for_block (bb, size)
677      basic_block bb;
678      int size;
679 {
680   /* Verify that aux field is clear.  */
681   if (bb->aux || !first_block_aux_obj)
682     abort ();
683   bb->aux = obstack_alloc (&block_aux_obstack, size);
684   memset (bb->aux, 0, size);
685 }
686
687 /* Initialize the block_aux_obstack and if SIZE is nonzero, call
688    alloc_aux_for_block for each basic block.  */
689
690 void
691 alloc_aux_for_blocks (size)
692      int size;
693 {
694   static int initialized;
695
696   if (!initialized)
697     {
698       gcc_obstack_init (&block_aux_obstack);
699       initialized = 1;
700     }
701
702   /* Check whether AUX data are still allocated.  */
703   else if (first_block_aux_obj)
704     abort ();
705   first_block_aux_obj = (char *) obstack_alloc (&block_aux_obstack, 0);
706   if (size)
707     {
708       basic_block bb;
709
710       FOR_BB_BETWEEN (bb, ENTRY_BLOCK_PTR, NULL, next_bb)
711         alloc_aux_for_block (bb, size);
712     }
713 }
714
715 /* Clear AUX pointers of all blocks.  */
716
717 void
718 clear_aux_for_blocks ()
719 {
720   basic_block bb;
721
722   FOR_BB_BETWEEN (bb, ENTRY_BLOCK_PTR, NULL, next_bb)
723     bb->aux = NULL;
724 }
725
726 /* Free data allocated in block_aux_obstack and clear AUX pointers
727    of all blocks.  */
728
729 void
730 free_aux_for_blocks ()
731 {
732   if (!first_block_aux_obj)
733     abort ();
734   obstack_free (&block_aux_obstack, first_block_aux_obj);
735   first_block_aux_obj = NULL;
736
737   clear_aux_for_blocks ();
738 }
739
740 /* Allocate a memory edge of SIZE as BB->aux.  The obstack must
741    be first initialized by alloc_aux_for_edges.  */
742
743 inline void
744 alloc_aux_for_edge (e, size)
745      edge e;
746      int size;
747 {
748   /* Verify that aux field is clear.  */
749   if (e->aux || !first_edge_aux_obj)
750     abort ();
751   e->aux = obstack_alloc (&edge_aux_obstack, size);
752   memset (e->aux, 0, size);
753 }
754
755 /* Initialize the edge_aux_obstack and if SIZE is nonzero, call
756    alloc_aux_for_edge for each basic edge.  */
757
758 void
759 alloc_aux_for_edges (size)
760      int size;
761 {
762   static int initialized;
763
764   if (!initialized)
765     {
766       gcc_obstack_init (&edge_aux_obstack);
767       initialized = 1;
768     }
769
770   /* Check whether AUX data are still allocated.  */
771   else if (first_edge_aux_obj)
772     abort ();
773
774   first_edge_aux_obj = (char *) obstack_alloc (&edge_aux_obstack, 0);
775   if (size)
776     {
777       basic_block bb;
778
779       FOR_BB_BETWEEN (bb, ENTRY_BLOCK_PTR, EXIT_BLOCK_PTR, next_bb)
780         {
781           edge e;
782
783           for (e = bb->succ; e; e = e->succ_next)
784             alloc_aux_for_edge (e, size);
785         }
786     }
787 }
788
789 /* Clear AUX pointers of all edges.  */
790
791 void
792 clear_aux_for_edges ()
793 {
794   basic_block bb;
795   edge e;
796
797   FOR_BB_BETWEEN (bb, ENTRY_BLOCK_PTR, EXIT_BLOCK_PTR, next_bb)
798     {
799       for (e = bb->succ; e; e = e->succ_next)
800         e->aux = NULL;
801     }
802 }
803
804 /* Free data allocated in edge_aux_obstack and clear AUX pointers
805    of all edges.  */
806
807 void
808 free_aux_for_edges ()
809 {
810   if (!first_edge_aux_obj)
811     abort ();
812   obstack_free (&edge_aux_obstack, first_edge_aux_obj);
813   first_edge_aux_obj = NULL;
814
815   clear_aux_for_edges ();
816 }