]> git.ipfire.org Git - thirdparty/gcc.git/blame - gcc/cgraph.c
MAINTAINERS: Move myself from 'Write After Approval' to 'CPU Port Maintainers' sectio...
[thirdparty/gcc.git] / gcc / cgraph.c
CommitLineData
e72fcfe8 1/* Callgraph handling code.
b684a3df 2 Copyright (C) 2003, 2004 Free Software Foundation, Inc.
e72fcfe8
JH
3 Contributed by Jan Hubicka
4
5This file is part of GCC.
6
7GCC is free software; you can redistribute it and/or modify it under
8the terms of the GNU General Public License as published by the Free
9Software Foundation; either version 2, or (at your option) any later
10version.
11
12GCC is distributed in the hope that it will be useful, but WITHOUT ANY
13WARRANTY; without even the implied warranty of MERCHANTABILITY or
14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
15for more details.
16
17You should have received a copy of the GNU General Public License
18along with GCC; see the file COPYING. If not, write to the Free
19Software Foundation, 59 Temple Place - Suite 330, Boston, MA
2002111-1307, USA. */
21
22#include "config.h"
23#include "system.h"
24#include "coretypes.h"
25#include "tm.h"
26#include "tree.h"
e72fcfe8
JH
27#include "langhooks.h"
28#include "hashtab.h"
29#include "toplev.h"
30#include "flags.h"
31#include "ggc.h"
32#include "debug.h"
33#include "target.h"
1c4a429a 34#include "cgraph.h"
988d1653 35#include "varray.h"
e69529cd 36#include "output.h"
988d1653 37
e72fcfe8
JH
38
39/* Hash table used to convert declarations into nodes. */
ed2df68b 40static GTY((param_is (struct cgraph_node))) htab_t cgraph_hash;
e72fcfe8
JH
41
42/* The linked list of cgraph nodes. */
1c4a429a 43struct cgraph_node *cgraph_nodes;
e72fcfe8 44
1668aabc
JH
45/* Queue of cgraph nodes scheduled to be lowered. */
46struct cgraph_node *cgraph_nodes_queue;
47
e72fcfe8 48/* Number of nodes in existence. */
1c4a429a 49int cgraph_n_nodes;
e72fcfe8 50
b58b1157
JH
51/* Maximal uid used in cgraph nodes. */
52int cgraph_max_uid;
53
dafc5b82
JH
54/* Set when whole unit has been analyzed so we can access global info. */
55bool cgraph_global_info_ready = false;
56
e69529cd 57/* Hash table used to convert declarations into nodes. */
ed2df68b 58static GTY((param_is (struct cgraph_varpool_node))) htab_t cgraph_varpool_hash;
e69529cd
JH
59
60/* Queue of cgraph nodes scheduled to be lowered and output. */
61struct cgraph_varpool_node *cgraph_varpool_nodes_queue;
62
63/* Number of nodes in existence. */
64int cgraph_varpool_n_nodes;
65
ed2df68b
JH
66/* The linked list of cgraph varpool nodes. */
67static GTY(()) struct cgraph_varpool_node *cgraph_varpool_nodes;
68
439f7bc3
AJ
69static struct cgraph_edge *create_edge (struct cgraph_node *,
70 struct cgraph_node *);
439f7bc3
AJ
71static hashval_t hash_node (const void *);
72static int eq_node (const void *, const void *);
e72fcfe8
JH
73
74/* Returns a hash code for P. */
75
76static hashval_t
439f7bc3 77hash_node (const void *p)
e72fcfe8 78{
ed2df68b
JH
79 return ((hashval_t)
80 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME
81 (((struct cgraph_node *) p)->decl)));
e72fcfe8
JH
82}
83
6356f892 84/* Returns nonzero if P1 and P2 are equal. */
e72fcfe8
JH
85
86static int
439f7bc3 87eq_node (const void *p1, const void *p2)
e72fcfe8
JH
88{
89 return ((DECL_ASSEMBLER_NAME (((struct cgraph_node *) p1)->decl)) ==
1668aabc 90 (tree) p2);
e72fcfe8
JH
91}
92
93/* Return cgraph node assigned to DECL. Create new one when needed. */
1c4a429a 94struct cgraph_node *
439f7bc3 95cgraph_node (tree decl)
e72fcfe8
JH
96{
97 struct cgraph_node *node;
98 struct cgraph_node **slot;
99
988d1653
JH
100 if (TREE_CODE (decl) != FUNCTION_DECL)
101 abort ();
102
e72fcfe8 103 if (!cgraph_hash)
ed2df68b 104 cgraph_hash = htab_create_ggc (10, hash_node, eq_node, NULL);
e72fcfe8 105
ed2df68b
JH
106 slot = (struct cgraph_node **)
107 htab_find_slot_with_hash (cgraph_hash, DECL_ASSEMBLER_NAME (decl),
108 IDENTIFIER_HASH_VALUE
b97e92ed 109 (DECL_ASSEMBLER_NAME (decl)), INSERT);
e72fcfe8
JH
110 if (*slot)
111 return *slot;
ed2df68b 112 node = ggc_alloc_cleared (sizeof (*node));
e72fcfe8
JH
113 node->decl = decl;
114 node->next = cgraph_nodes;
b58b1157 115 node->uid = cgraph_max_uid++;
18d13f34
JH
116 if (cgraph_nodes)
117 cgraph_nodes->previous = node;
118 node->previous = NULL;
e72fcfe8
JH
119 cgraph_nodes = node;
120 cgraph_n_nodes++;
121 *slot = node;
5c2e00ee 122 if (DECL_CONTEXT (decl) && TREE_CODE (DECL_CONTEXT (decl)) == FUNCTION_DECL)
e72fcfe8
JH
123 {
124 node->origin = cgraph_node (DECL_CONTEXT (decl));
125 node->next_nested = node->origin->nested;
126 node->origin->nested = node;
127 }
128 return node;
129}
130
1668aabc
JH
131/* Try to find existing function for identifier ID. */
132struct cgraph_node *
439f7bc3 133cgraph_node_for_identifier (tree id)
1668aabc
JH
134{
135 struct cgraph_node **slot;
136
137 if (TREE_CODE (id) != IDENTIFIER_NODE)
138 abort ();
139
140 if (!cgraph_hash)
e69529cd 141 return NULL;
1668aabc 142
ed2df68b
JH
143 slot = (struct cgraph_node **)
144 htab_find_slot_with_hash (cgraph_hash, id,
b97e92ed 145 IDENTIFIER_HASH_VALUE (id), NO_INSERT);
1668aabc
JH
146 if (!slot)
147 return NULL;
148 return *slot;
149}
150
e72fcfe8
JH
151/* Create edge from CALLER to CALLEE in the cgraph. */
152
153static struct cgraph_edge *
439f7bc3 154create_edge (struct cgraph_node *caller, struct cgraph_node *callee)
e72fcfe8 155{
ed2df68b 156 struct cgraph_edge *edge = ggc_alloc (sizeof (struct cgraph_edge));
b58b1157
JH
157 struct cgraph_edge *edge2;
158
159 edge->inline_call = false;
160 /* At the moment we don't associate calls with specific CALL_EXPRs
161 as we probably ought to, so we must preserve inline_call flags to
162 be the same in all copies of the same edge. */
163 if (cgraph_global_info_ready)
fdacb904 164 for (edge2 = caller->callees; edge2; edge2 = edge2->next_callee)
b58b1157
JH
165 if (edge2->callee == callee)
166 {
167 edge->inline_call = edge2->inline_call;
168 break;
169 }
e72fcfe8
JH
170
171 edge->caller = caller;
172 edge->callee = callee;
173 edge->next_caller = callee->callers;
174 edge->next_callee = caller->callees;
175 caller->callees = edge;
176 callee->callers = edge;
177 return edge;
178}
179
180/* Remove the edge from CALLER to CALLEE in the cgraph. */
181
cb967da5 182void
439f7bc3 183cgraph_remove_edge (struct cgraph_node *caller, struct cgraph_node *callee)
e72fcfe8
JH
184{
185 struct cgraph_edge **edge, **edge2;
186
187 for (edge = &callee->callers; *edge && (*edge)->caller != caller;
188 edge = &((*edge)->next_caller))
189 continue;
190 if (!*edge)
191 abort ();
192 *edge = (*edge)->next_caller;
193 for (edge2 = &caller->callees; *edge2 && (*edge2)->callee != callee;
194 edge2 = &(*edge2)->next_callee)
195 continue;
196 if (!*edge2)
197 abort ();
198 *edge2 = (*edge2)->next_callee;
199}
200
18d13f34
JH
201/* Remove the node from cgraph. */
202
203void
439f7bc3 204cgraph_remove_node (struct cgraph_node *node)
18d13f34 205{
2ee1067b 206 void **slot;
18d13f34
JH
207 while (node->callers)
208 cgraph_remove_edge (node->callers->caller, node);
209 while (node->callees)
210 cgraph_remove_edge (node, node->callees->callee);
211 while (node->nested)
212 cgraph_remove_node (node->nested);
213 if (node->origin)
214 {
215 struct cgraph_node **node2 = &node->origin->nested;
216
217 while (*node2 != node)
218 node2 = &(*node2)->next_nested;
219 *node2 = node->next_nested;
220 }
221 if (node->previous)
222 node->previous->next = node->next;
223 else
224 cgraph_nodes = node;
225 if (node->next)
226 node->next->previous = node->previous;
227 DECL_SAVED_TREE (node->decl) = NULL;
2ee1067b
JH
228 slot =
229 htab_find_slot_with_hash (cgraph_hash, DECL_ASSEMBLER_NAME (node->decl),
230 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME
b97e92ed 231 (node->decl)), NO_INSERT);
2ee1067b 232 htab_clear_slot (cgraph_hash, slot);
18d13f34
JH
233 /* Do not free the structure itself so the walk over chain can continue. */
234}
235
8dafba3c
RH
236/* Notify finalize_compilation_unit that given node is reachable. */
237
1668aabc 238void
8dafba3c 239cgraph_mark_reachable_node (struct cgraph_node *node)
1668aabc 240{
ba245151 241 if (!node->reachable && node->local.finalized)
1668aabc 242 {
ba245151 243 notice_global_symbol (node->decl);
1668aabc 244 node->reachable = 1;
e767b5be
JH
245
246 node->next_needed = cgraph_nodes_queue;
247 cgraph_nodes_queue = node;
248
249 /* At the moment frontend automatically emits all nested functions. */
250 if (node->nested)
1668aabc 251 {
e767b5be
JH
252 struct cgraph_node *node2;
253
254 for (node2 = node->nested; node2; node2 = node2->next_nested)
255 if (!node2->reachable)
8dafba3c 256 cgraph_mark_reachable_node (node2);
e767b5be 257 }
1668aabc
JH
258 }
259}
260
8dafba3c
RH
261/* Likewise indicate that a node is needed, i.e. reachable via some
262 external means. */
263
264void
265cgraph_mark_needed_node (struct cgraph_node *node)
266{
267 node->needed = 1;
268 cgraph_mark_reachable_node (node);
269}
18d13f34 270
6614fd40 271/* Record call from CALLER to CALLEE. */
e72fcfe8 272
1c4a429a 273struct cgraph_edge *
439f7bc3 274cgraph_record_call (tree caller, tree callee)
e72fcfe8
JH
275{
276 return create_edge (cgraph_node (caller), cgraph_node (callee));
277}
278
279void
439f7bc3 280cgraph_remove_call (tree caller, tree callee)
e72fcfe8 281{
18d13f34 282 cgraph_remove_edge (cgraph_node (caller), cgraph_node (callee));
e72fcfe8
JH
283}
284
285/* Return true when CALLER_DECL calls CALLEE_DECL. */
286
287bool
439f7bc3 288cgraph_calls_p (tree caller_decl, tree callee_decl)
e72fcfe8
JH
289{
290 struct cgraph_node *caller = cgraph_node (caller_decl);
291 struct cgraph_node *callee = cgraph_node (callee_decl);
292 struct cgraph_edge *edge;
293
294 for (edge = callee->callers; edge && (edge)->caller != caller;
295 edge = (edge->next_caller))
296 continue;
297 return edge != NULL;
298}
299
dafc5b82
JH
300/* Return local info for the compiled function. */
301
302struct cgraph_local_info *
439f7bc3 303cgraph_local_info (tree decl)
dafc5b82
JH
304{
305 struct cgraph_node *node;
306 if (TREE_CODE (decl) != FUNCTION_DECL)
307 abort ();
308 node = cgraph_node (decl);
309 return &node->local;
310}
311
312/* Return local info for the compiled function. */
313
314struct cgraph_global_info *
439f7bc3 315cgraph_global_info (tree decl)
dafc5b82
JH
316{
317 struct cgraph_node *node;
318 if (TREE_CODE (decl) != FUNCTION_DECL || !cgraph_global_info_ready)
319 abort ();
320 node = cgraph_node (decl);
321 return &node->global;
322}
323
b255a036
JH
324/* Return local info for the compiled function. */
325
326struct cgraph_rtl_info *
439f7bc3 327cgraph_rtl_info (tree decl)
b255a036
JH
328{
329 struct cgraph_node *node;
330 if (TREE_CODE (decl) != FUNCTION_DECL)
331 abort ();
332 node = cgraph_node (decl);
333 if (decl != current_function_decl
334 && !TREE_ASM_WRITTEN (node->decl))
335 return NULL;
336 return &node->rtl;
337}
338
a194aa56
JH
339/* Return name of the node used in debug output. */
340const char *
439f7bc3 341cgraph_node_name (struct cgraph_node *node)
a194aa56
JH
342{
343 return (*lang_hooks.decl_printable_name) (node->decl, 2);
344}
dafc5b82 345
e72fcfe8
JH
346/* Dump the callgraph. */
347
348void
439f7bc3 349dump_cgraph (FILE *f)
e72fcfe8
JH
350{
351 struct cgraph_node *node;
352
7d82fe7c 353 fprintf (f, "callgraph:\n\n");
e72fcfe8
JH
354 for (node = cgraph_nodes; node; node = node->next)
355 {
356 struct cgraph_edge *edge;
7d82fe7c 357 fprintf (f, "%s:", cgraph_node_name (node));
b58b1157
JH
358 if (node->local.self_insns)
359 fprintf (f, " %i insns", node->local.self_insns);
7d82fe7c
KC
360 if (node->global.insns && node->global.insns != node->local.self_insns)
361 fprintf (f, " (%i after inlining)", node->global.insns);
e72fcfe8 362 if (node->origin)
a194aa56 363 fprintf (f, " nested in: %s", cgraph_node_name (node->origin));
e72fcfe8
JH
364 if (node->needed)
365 fprintf (f, " needed");
366 else if (node->reachable)
367 fprintf (f, " reachable");
368 if (DECL_SAVED_TREE (node->decl))
369 fprintf (f, " tree");
370
7d82fe7c
KC
371 if (node->local.local)
372 fprintf (f, " local");
b3c3af2f 373 if (node->local.disregard_inline_limits)
b58b1157
JH
374 fprintf (f, " always_inline");
375 else if (node->local.inlinable)
376 fprintf (f, " inlinable");
b58b1157
JH
377 if (node->global.cloned_times > 1)
378 fprintf (f, " cloned %ix", node->global.cloned_times);
b58b1157 379
7dd87381 380 fprintf (f, "\n called by: ");
e72fcfe8 381 for (edge = node->callers; edge; edge = edge->next_caller)
b58b1157
JH
382 {
383 fprintf (f, "%s ", cgraph_node_name (edge->caller));
384 if (edge->inline_call)
385 fprintf(f, "(inlined) ");
386 }
e72fcfe8
JH
387
388 fprintf (f, "\n calls: ");
389 for (edge = node->callees; edge; edge = edge->next_callee)
b58b1157
JH
390 {
391 fprintf (f, "%s ", cgraph_node_name (edge->callee));
392 if (edge->inline_call)
393 fprintf(f, "(inlined) ");
394 }
e72fcfe8
JH
395 fprintf (f, "\n");
396 }
397}
988d1653 398
e69529cd
JH
399/* Returns a hash code for P. */
400
401static hashval_t
439f7bc3 402cgraph_varpool_hash_node (const void *p)
e69529cd 403{
ed2df68b
JH
404 return ((hashval_t)
405 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME
406 (((struct cgraph_varpool_node *) p)->decl)));
e69529cd
JH
407}
408
f1ba665b 409/* Returns nonzero if P1 and P2 are equal. */
e69529cd
JH
410
411static int
439f7bc3 412eq_cgraph_varpool_node (const void *p1, const void *p2)
e69529cd
JH
413{
414 return ((DECL_ASSEMBLER_NAME (((struct cgraph_varpool_node *) p1)->decl)) ==
415 (tree) p2);
416}
417
418/* Return cgraph_varpool node assigned to DECL. Create new one when needed. */
419struct cgraph_varpool_node *
420cgraph_varpool_node (tree decl)
421{
422 struct cgraph_varpool_node *node;
423 struct cgraph_varpool_node **slot;
424
425 if (!DECL_P (decl) || TREE_CODE (decl) == FUNCTION_DECL)
426 abort ();
427
428 if (!cgraph_varpool_hash)
ed2df68b
JH
429 cgraph_varpool_hash = htab_create_ggc (10, cgraph_varpool_hash_node,
430 eq_cgraph_varpool_node, NULL);
ed2df68b
JH
431 slot = (struct cgraph_varpool_node **)
432 htab_find_slot_with_hash (cgraph_varpool_hash, DECL_ASSEMBLER_NAME (decl),
433 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME (decl)),
b97e92ed 434 INSERT);
e69529cd
JH
435 if (*slot)
436 return *slot;
ed2df68b 437 node = ggc_alloc_cleared (sizeof (*node));
e69529cd
JH
438 node->decl = decl;
439 cgraph_varpool_n_nodes++;
ed2df68b 440 cgraph_varpool_nodes = node;
e69529cd 441 *slot = node;
e69529cd
JH
442 return node;
443}
444
fccc4eb2
JH
445/* Set the DECL_ASSEMBLER_NAME and update cgraph hashtables. */
446void
447change_decl_assembler_name (tree decl, tree name)
448{
449 struct cgraph_node *node = NULL;
450 struct cgraph_varpool_node *vnode = NULL;
451 void **slot;
452
453 if (!DECL_ASSEMBLER_NAME_SET_P (decl))
454 {
455 SET_DECL_ASSEMBLER_NAME (decl, name);
456 return;
457 }
458 if (name == DECL_ASSEMBLER_NAME (decl))
459 return;
460
df964a18
JH
461 if (TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl))
462 && DECL_RTL_SET_P (decl))
fccc4eb2
JH
463 warning ("%D renamed after being referenced in assembly", decl);
464
465 if (TREE_CODE (decl) == FUNCTION_DECL && cgraph_hash)
466 {
467 /* Take a look whether declaration is in the cgraph structure. */
468 slot =
469 htab_find_slot_with_hash (cgraph_hash, DECL_ASSEMBLER_NAME (decl),
470 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME
471 (decl)), NO_INSERT);
472 if (slot)
473 node = *slot;
474
475 /* It is, verify that we are the canonical node for this decl. */
476 if (node && node->decl == decl)
477 {
478 node = *slot;
479 htab_clear_slot (cgraph_hash, slot);
480 }
481 else
482 node = NULL;
483 }
484 if (TREE_CODE (decl) == VAR_DECL && TREE_STATIC (decl) && cgraph_varpool_hash)
485 {
486 /* Take a look whether declaration is in the cgraph structure. */
487 slot =
488 htab_find_slot_with_hash (cgraph_varpool_hash, DECL_ASSEMBLER_NAME (decl),
489 IDENTIFIER_HASH_VALUE (DECL_ASSEMBLER_NAME
490 (decl)), NO_INSERT);
491 if (slot)
492 vnode = *slot;
493
494 /* It is, verify that we are the canonical vnode for this decl. */
495 if (vnode && vnode->decl == decl)
496 {
497 vnode = *slot;
498 htab_clear_slot (cgraph_varpool_hash, slot);
499 }
500 else
501 vnode = NULL;
502 }
503 SET_DECL_ASSEMBLER_NAME (decl, name);
504 if (node)
505 {
506 slot =
507 htab_find_slot_with_hash (cgraph_hash, name,
508 IDENTIFIER_HASH_VALUE (name), INSERT);
509 if (*slot)
510 abort ();
511 *slot = node;
512 }
513 if (vnode)
514 {
515 slot =
516 htab_find_slot_with_hash (cgraph_varpool_hash, name,
517 IDENTIFIER_HASH_VALUE (name), INSERT);
518 if (*slot)
519 abort ();
520 *slot = vnode;
521 }
522}
523
e69529cd
JH
524/* Try to find existing function for identifier ID. */
525struct cgraph_varpool_node *
526cgraph_varpool_node_for_identifier (tree id)
527{
528 struct cgraph_varpool_node **slot;
529
530 if (TREE_CODE (id) != IDENTIFIER_NODE)
531 abort ();
532
533 if (!cgraph_varpool_hash)
534 return NULL;
535
ed2df68b
JH
536 slot = (struct cgraph_varpool_node **)
537 htab_find_slot_with_hash (cgraph_varpool_hash, id,
b97e92ed 538 IDENTIFIER_HASH_VALUE (id), NO_INSERT);
e69529cd
JH
539 if (!slot)
540 return NULL;
541 return *slot;
542}
543
544/* Notify finalize_compilation_unit that given node is reachable
545 or needed. */
546void
547cgraph_varpool_mark_needed_node (struct cgraph_varpool_node *node)
548{
549 if (!node->needed && node->finalized)
550 {
8bd87c4e 551 node->next_needed = cgraph_varpool_nodes_queue;
e69529cd 552 cgraph_varpool_nodes_queue = node;
810db579 553 notice_global_symbol (node->decl);
e69529cd
JH
554 }
555 node->needed = 1;
556}
557
558void
559cgraph_varpool_finalize_decl (tree decl)
560{
561 struct cgraph_varpool_node *node = cgraph_varpool_node (decl);
d853a20e
JH
562
563 /* The first declaration of a variable that comes through this function
564 decides whether it is global (in C, has external linkage)
565 or local (in C, has internal linkage). So do nothing more
566 if this function has already run. */
567 if (node->finalized)
568 return;
569 if (node->needed)
e69529cd 570 {
8bd87c4e 571 node->next_needed = cgraph_varpool_nodes_queue;
e69529cd 572 cgraph_varpool_nodes_queue = node;
ba245151 573 notice_global_symbol (decl);
e69529cd
JH
574 }
575 node->finalized = true;
576
577 if (/* Externally visible variables must be output. The exception are
578 COMDAT functions that must be output only when they are needed. */
579 (TREE_PUBLIC (decl) && !DECL_COMDAT (decl))
580 /* Function whose name is output to the assembler file must be produced.
581 It is possible to assemble the name later after finalizing the function
582 and the fact is noticed in assemble_name then. */
583 || (DECL_ASSEMBLER_NAME_SET_P (decl)
584 && TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl))))
585 {
586 cgraph_varpool_mark_needed_node (node);
587 }
588}
589
590bool
439f7bc3 591cgraph_varpool_assemble_pending_decls (void)
e69529cd
JH
592{
593 bool changed = false;
594
595 while (cgraph_varpool_nodes_queue)
596 {
597 tree decl = cgraph_varpool_nodes_queue->decl;
598 struct cgraph_varpool_node *node = cgraph_varpool_nodes_queue;
599
8bd87c4e 600 cgraph_varpool_nodes_queue = cgraph_varpool_nodes_queue->next_needed;
e69529cd
JH
601 if (!TREE_ASM_WRITTEN (decl))
602 {
603 assemble_variable (decl, 0, 1, 0);
604 changed = true;
605 }
8bd87c4e 606 node->next_needed = NULL;
e69529cd
JH
607 }
608 return changed;
609}
610
1bb17c21
JH
611/* Return true when the DECL can possibly be inlined. */
612bool
613cgraph_function_possibly_inlined_p (tree decl)
614{
1bb17c21 615 if (!cgraph_global_info_ready)
b684a3df
JH
616 return (DECL_INLINE (decl)
617 && (!flag_really_no_inline
618 || (*lang_hooks.tree_inlining.disregard_inline_limits) (decl)));
1bb17c21
JH
619 return cgraph_node (decl)->global.inlined;
620}
e69529cd 621
988d1653 622#include "gt-cgraph.h"