remove $Id$, it doesn't work with git anyway
[libfirm] / ir / debug / debugger.c
1 /*
2  * Copyright (C) 1995-2010 University of Karlsruhe.  All right reserved.
3  *
4  * This file is part of libFirm.
5  *
6  * This file may be distributed and/or modified under the terms of the
7  * GNU General Public License version 2 as published by the Free Software
8  * Foundation and appearing in the file LICENSE.GPL included in the
9  * packaging of this file.
10  *
11  * Licensees holding valid libFirm Professional Edition licenses may use
12  * this file in accordance with the libFirm Commercial License.
13  * Agreement provided with the Software.
14  *
15  * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
16  * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE.
18  */
19
20 /**
21  * @file
22  * @brief     Helper function for integrated debug support
23  * @author    Michael Beck
24  * @date      2005
25  */
26 #include "config.h"
27
28 #ifdef DEBUG_libfirm
29
30 #ifdef _WIN32
31 #define WIN32_LEAN_AND_MEAN
32 #include <windows.h>
33 #endif
34
35 #include "debugger.h"
36
37 #include <stdlib.h>
38 #include <stdio.h>
39 #include <signal.h>
40 #include <string.h>
41 #include <strings.h>
42
43 #include <ctype.h>
44
45 #include "set.h"
46 #include "ident.h"
47 #include "irhooks.h"
48 #include "irgraph_t.h"
49 #include "entity_t.h"
50 #include "irprintf.h"
51 #include "irdump.h"
52 #include "iredges_t.h"
53 #include "debug.h"
54 #include "error.h"
55
56 #ifdef _WIN32
57 /* Break into the debugger. The Win32 way. */
58 void firm_debug_break(void)
59 {
60         DebugBreak();
61 }
62 #elif defined(__GNUC__) && (defined(__i386__) || defined(__x86_64))
63 /* Break into the debugger. The ia32/x86_64 way under GCC. */
64 void firm_debug_break(void)
65 {
66         __asm__ __volatile__("int3");
67 }
68 #else
69 /* Break into the debugger. Poor Unix way. */
70 void firm_debug_break(void)
71 {
72         raise(SIGINT);
73 }
74 #endif /* _WIN32 */
75
76 /** supported breakpoint kinds */
77 typedef enum {
78         BP_NR    = 'n',   /**< break on node number. */
79         BP_IDENT = 'i'    /**< break on ident. */
80 } bp_kind;
81
82 /**
83  * Reasons for node number breakpoints.
84  */
85 typedef enum bp_reasons_t {
86         BP_ON_NEW_NODE,    /**< break if node with number is created */
87         BP_ON_REPLACE,     /**< break if node with number is replaced */
88         BP_ON_LOWER,       /**< break if node with number is lowered */
89         BP_ON_REMIRG,      /**< break if an IRG is removed */
90         BP_ON_NEW_ENT,     /**< break if a new entity is created */
91         BP_ON_NEW_TYPE,    /**< break if a new type is created */
92         BP_MAX_REASON
93 } bp_reasons_t;
94
95 /** A breakpoint. */
96 typedef struct breakpoint {
97         bp_kind      kind;        /**< the kind of this break point */
98         unsigned     bpnr;        /**< break point number */
99         int          active;      /**< non-zero, if this break point is active */
100         bp_reasons_t reason;      /**< reason for the breakpoint */
101         struct breakpoint *next; /**< link to the next one */
102 } breakpoint;
103
104 /** A number breakpoint. */
105 typedef struct {
106         breakpoint   bp;       /**< the breakpoint data */
107         long         nr;       /**< the node number */
108 } bp_nr_t;
109
110 /** Calculate the hash value for a node breakpoint. */
111 #define HASH_NR_BP(key) (((key).nr << 2) ^ (key).bp.reason)
112
113 /** An ident breakpoint. */
114 typedef struct {
115         breakpoint   bp;       /**< the breakpoint data */
116         ident        *id;      /**< the ident */
117 } bp_ident_t;
118
119 /** Calculate the hash value for an ident breakpoint. */
120 #define HASH_IDENT_BP(key) (HASH_PTR((key).id) ^ (key).bp.reason)
121
122 /** The set containing the breakpoints on node numbers. */
123 static set *bp_numbers;
124
125 /** The set containing the breakpoints on idents. */
126 static set *bp_idents;
127
128 /**< the list of all breakpoints */
129 static breakpoint *bp_list;
130
131 /** number of the current break point */
132 static unsigned bp_num = 0;
133
134 /** set if break on init command was issued. */
135 static int break_on_init = 0;
136
137 /** the hook entries for the Firm debugger module. */
138 static hook_entry_t debugger_hooks[hook_last];
139
140 /** number of active breakpoints to maintain hooks. */
141 static unsigned num_active_bp[BP_MAX_REASON];
142
143 /**
144  * The debug message buffer
145  */
146 static char firm_dbg_msg_buf[2048];
147
148 /**
149  * If set, the debug extension writes all output to the
150  * firm_dbg_msg_buf buffer
151  */
152 static int redir_output = 0;
153
154 /**
155  * Is set to one, if the debug extension is active
156  */
157 static int is_active = 0;
158
159 /** hook the hook h with function fkt. */
160 #define HOOK(h, fkt) \
161 do {                                      \
162         debugger_hooks[h].hook._##h = fkt;    \
163         register_hook(h, &debugger_hooks[h]); \
164 } while (0)
165
166 /** unhook the hook h */
167 #define UNHOOK(h) \
168 do {                                        \
169         unregister_hook(h, &debugger_hooks[h]); \
170         debugger_hooks[h].hook._##h = NULL;     \
171 } while (0)
172
173 /** returns non-zero if a entry hook h is used */
174 #define IS_HOOKED(h) (debugger_hooks[h].hook._##h != NULL)
175
176 /* some macros needed to create the info string */
177 #define _DBG_VERSION(major, minor)  #major "." #minor
178 #define DBG_VERSION(major, minor)   _DBG_VERSION(major, minor)
179 #define API_VERSION(major, minor)   "API:" DBG_VERSION(major, minor)
180
181 /* the API version: change if needed */
182 #define FIRM_DBG_MAJOR  1
183 #define FIRM_DBG_MINOR  0
184
185 /** for automatic detection of the debug extension */
186 static const char __attribute__((used)) firm_debug_info_string[] =
187         API_VERSION(FIRM_DBG_MAJOR, FIRM_DBG_MINOR);
188
189 int firm_debug_active(void)
190 {
191         return is_active;
192 }  /* firm_debug_active */
193
194 /**
195  * Reset the debug text buffer.
196  */
197 static void reset_dbg_buf(void)
198 {
199         firm_dbg_msg_buf[0] = '\0';
200 }  /* reset_dbg_buf */
201
202 static void add_to_dbg_buf(const char *buf)
203 {
204         strncat(firm_dbg_msg_buf, buf, sizeof(firm_dbg_msg_buf));
205 }  /* add_to_dbg_buf */
206
207 const char *firm_debug_text(void)
208 {
209         firm_dbg_msg_buf[sizeof(firm_dbg_msg_buf) - 1] = '\0';
210         return firm_dbg_msg_buf;
211 }  /* firm_debug_text */
212
213 /**
214  * debug output
215  */
216 static void dbg_printf(const char *fmt, ...)
217 {
218         char buf[1024];
219
220         va_list args;
221         va_start(args, fmt);
222
223         if (fmt[0] != '+')
224                 reset_dbg_buf();
225         else
226                 ++fmt;
227
228         ir_vsnprintf(buf, sizeof(buf), fmt, args);
229         va_end(args);
230
231         if (redir_output)
232                 add_to_dbg_buf(buf);
233         else
234                 puts(buf);
235 }  /* dbg_printf */
236
237 /**
238  * A new node is created.
239  *
240  * @param ctx   the hook context
241  * @param irg   the IR graph on which the node is created
242  * @param node  the new IR node that was created
243  */
244 static void dbg_new_node(void *ctx, ir_graph *irg, ir_node *node)
245 {
246         bp_nr_t key, *elem;
247         (void) ctx;
248         (void) irg;
249
250         key.nr        = get_irn_node_nr(node);
251         key.bp.reason = BP_ON_NEW_NODE;
252
253         elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
254         if (elem && elem->bp.active) {
255                 dbg_printf("Firm BP %u reached, %+F created\n", elem->bp.bpnr, node);
256                 firm_debug_break();
257         }
258 }  /* dbg_new_node */
259
260 /**
261  * A node is replaced.
262  *
263  * @param ctx   the hook context
264  * @param old   the IR node the is replaced
265  * @param nw    the new IR node that will replace old
266  */
267 static void dbg_replace(void *ctx, ir_node *old, ir_node *nw)
268 {
269         bp_nr_t key, *elem;
270         (void) ctx;
271
272         key.nr        = get_irn_node_nr(old);
273         key.bp.reason = BP_ON_REPLACE;
274
275         elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
276         if (elem && elem->bp.active) {
277                 dbg_printf("Firm BP %u reached, %+F will be replaced by %+F\n", elem->bp.bpnr, old, nw);
278                 firm_debug_break();
279         }
280 }  /* dbg_replace */
281
282 /**
283  * A new node is lowered.
284  *
285  * @param ctx   the hook context
286  * @param node  the new IR node that will be lowered
287  */
288 static void dbg_lower(void *ctx, ir_node *node)
289 {
290         bp_nr_t key, *elem;
291         (void) ctx;
292
293         key.nr        = get_irn_node_nr(node);
294         key.bp.reason = BP_ON_LOWER;
295
296         elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
297         if (elem && elem->bp.active) {
298                 dbg_printf("Firm BP %u reached, %+F will be lowered\n", elem->bp.bpnr, node);
299                 firm_debug_break();
300         }
301 }  /* dbg_lower */
302
303 /**
304  * A graph will be deleted.
305  *
306  * @param ctx   the hook context
307  * @param irg   the IR graph that will be deleted
308  */
309 static void dbg_free_graph(void *ctx, ir_graph *irg)
310 {
311         (void) ctx;
312         {
313                 bp_nr_t key, *elem;
314                 key.nr        = get_irg_graph_nr(irg);
315                 key.bp.reason = BP_ON_REMIRG;
316
317                 elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
318                 if (elem && elem->bp.active) {
319                         ir_printf("Firm BP %u reached, %+F will be deleted\n", elem->bp.bpnr, irg);
320                         firm_debug_break();
321                 }
322         }
323         {
324                 bp_ident_t key, *elem;
325                 ir_entity *ent = get_irg_entity(irg);
326
327                 if (! ent)
328                         return;
329
330                 key.id        = get_entity_ident(ent);
331                 key.bp.reason = BP_ON_REMIRG;
332
333                 elem = (bp_ident_t*)set_find(bp_idents, &key, sizeof(key), HASH_IDENT_BP(key));
334                 if (elem && elem->bp.active) {
335                         dbg_printf("Firm BP %u reached, %+F will be deleted\n", elem->bp.bpnr, ent);
336                         firm_debug_break();
337                 }
338         }
339 }  /* dbg_free_graph */
340
341 /**
342  * An entity was created.
343  *
344  * @param ctx   the hook context
345  * @param ent   the newly created entity
346  */
347 static void dbg_new_entity(void *ctx, ir_entity *ent)
348 {
349         (void) ctx;
350         {
351                 bp_ident_t key, *elem;
352
353                 key.id        = get_entity_ident(ent);
354                 key.bp.reason = BP_ON_NEW_ENT;
355
356                 elem = (bp_ident_t*)set_find(bp_idents, &key, sizeof(key), HASH_IDENT_BP(key));
357                 if (elem && elem->bp.active) {
358                         ir_printf("Firm BP %u reached, %+F was created\n", elem->bp.bpnr, ent);
359                         firm_debug_break();
360                 }
361         }
362         {
363                 bp_nr_t key, *elem;
364
365                 key.nr        = get_entity_nr(ent);
366                 key.bp.reason = BP_ON_NEW_ENT;
367
368                 elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
369                 if (elem && elem->bp.active) {
370                         dbg_printf("Firm BP %u reached, %+F was created\n", elem->bp.bpnr, ent);
371                         firm_debug_break();
372                 }
373         }
374 }  /* dbg_new_entity */
375
376 /**
377  * A type was created.
378  *
379  * @param ctx   the hook context
380  * @param tp    the newly created type
381  */
382 static void dbg_new_type(void *ctx, ir_type *tp)
383 {
384         (void) ctx;
385         {
386                 bp_nr_t key, *elem;
387
388                 key.nr        = get_type_nr(tp);
389                 key.bp.reason = BP_ON_NEW_TYPE;
390
391                 elem = (bp_nr_t*)set_find(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
392                 if (elem && elem->bp.active) {
393                         ir_printf("Firm BP %u reached, %+F was created\n", elem->bp.bpnr, tp);
394                         firm_debug_break();
395                 }
396         }
397 }  /* dbg_new_type */
398
399 /**
400  * Return the reason string.
401  */
402 static const char *reason_str(bp_reasons_t reason)
403 {
404         switch (reason) {
405         case BP_ON_NEW_NODE: return "node creation";
406         case BP_ON_REPLACE:  return "node replace";
407         case BP_ON_LOWER:    return "node lowering";
408         case BP_ON_REMIRG:   return "removing IRG";
409         case BP_ON_NEW_ENT:  return "entity creation";
410         case BP_ON_NEW_TYPE: return "type creation";
411         case BP_MAX_REASON:  break;
412         }
413         panic("unsupported reason");
414 }  /* reason_str */
415
416 /**
417  * Compare two number breakpoints.
418  */
419 static int cmp_nr_bp(const void *elt, const void *key, size_t size)
420 {
421         const bp_nr_t *e1 = (const bp_nr_t*)elt;
422         const bp_nr_t *e2 = (const bp_nr_t*)key;
423         (void) size;
424
425         return (e1->nr - e2->nr) | (e1->bp.reason - e2->bp.reason);
426 }  /* cmp_nr_bp */
427
428 /**
429  * Compare two ident breakpoints.
430  */
431 static int cmp_ident_bp(const void *elt, const void *key, size_t size)
432 {
433         const bp_ident_t *e1 = (const bp_ident_t*)elt;
434         const bp_ident_t *e2 = (const bp_ident_t*)key;
435         (void) size;
436
437         return (e1->id != e2->id) | (e1->bp.reason - e2->bp.reason);
438 }  /* cmp_ident_bp */
439
440 /**
441  * Update the hooks.
442  */
443 static void update_hooks(breakpoint *bp)
444 {
445 #define CASE_ON(a, b)  case a: if (! IS_HOOKED(hook_##b)) HOOK(hook_##b, dbg_##b); break
446 #define CASE_OFF(a, b) case a: if (IS_HOOKED(hook_##b)) UNHOOK(hook_##b); break
447
448         if (bp->active)
449                 ++num_active_bp[bp->reason];
450         else
451                 --num_active_bp[bp->reason];
452
453         if (num_active_bp[bp->reason] > 0) {
454                 /* register the hooks on demand */
455                 switch (bp->reason) {
456                 CASE_ON(BP_ON_NEW_NODE, new_node);
457                 CASE_ON(BP_ON_REPLACE, replace);
458                 CASE_ON(BP_ON_LOWER, lower);
459                 CASE_ON(BP_ON_REMIRG, free_graph);
460                 CASE_ON(BP_ON_NEW_ENT, new_entity);
461                 CASE_ON(BP_ON_NEW_TYPE, new_type);
462                 default:
463                         break;
464                 }
465         }
466         else {
467                 /* unregister the hook on demand */
468                 switch (bp->reason) {
469                 CASE_OFF(BP_ON_NEW_NODE, new_node);
470                 CASE_OFF(BP_ON_REPLACE, replace);
471                 CASE_OFF(BP_ON_LOWER, lower);
472                 CASE_OFF(BP_ON_REMIRG, free_graph);
473                 CASE_OFF(BP_ON_NEW_ENT, new_entity);
474                 CASE_OFF(BP_ON_NEW_TYPE, new_type);
475                 default:
476                         break;
477                 }
478         }
479 #undef CASE_ON
480 #undef CASE_OFF
481 }  /* update_hooks */
482
483 /**
484  * Break if nr is reached.
485  */
486 static void break_on_nr(long nr, bp_reasons_t reason)
487 {
488         bp_nr_t key, *elem;
489
490         key.bp.kind   = BP_NR;
491         key.bp.bpnr   = 0;
492         key.bp.active = 1;
493         key.bp.reason = reason;
494         key.nr        = nr;
495
496         elem = (bp_nr_t*)set_insert(bp_numbers, &key, sizeof(key), HASH_NR_BP(key));
497
498         if (elem->bp.bpnr == 0) {
499                 /* new break point */
500                 elem->bp.bpnr = ++bp_num;
501                 elem->bp.next = bp_list;
502                 bp_list = &elem->bp;
503
504                 dbg_printf("Firm BP %u: %s of Nr %ld\n", elem->bp.bpnr, reason_str(reason), nr);
505
506                 update_hooks(&elem->bp);
507         }
508 }  /* break_on_nr */
509
510 /**
511  * Break if ident name is reached.
512  */
513 static void break_on_ident(const char *name, bp_reasons_t reason)
514 {
515         bp_ident_t key, *elem;
516
517         key.bp.kind   = BP_IDENT;
518         key.bp.bpnr   = 0;
519         key.bp.active = 1;
520         key.bp.reason = reason;
521         key.id        = new_id_from_str(name);
522
523         elem = (bp_ident_t*)set_insert(bp_idents, &key, sizeof(key), HASH_IDENT_BP(key));
524
525         if (elem->bp.bpnr == 0) {
526                 /* new break point */
527                 elem->bp.bpnr = ++bp_num;
528                 elem->bp.next = bp_list;
529                 bp_list = &elem->bp;
530
531                 dbg_printf("Firm BP %u: %s of ident \"%s\"\n", elem->bp.bpnr, reason_str(reason), name);
532
533                 update_hooks(&elem->bp);
534         }
535 }  /* break_on_ident */
536
537 /**
538  * Sets/resets the active flag of breakpoint bp.
539  */
540 static void bp_activate(unsigned bp, int active)
541 {
542         breakpoint *p;
543
544         for (p = bp_list; p; p = p->next) {
545                 if (p->bpnr == bp) {
546                         if (p->active != active) {
547                                 p->active = active;
548                                 update_hooks(p);
549                         }
550
551                         dbg_printf("Firm BP %u is now %s\n", bp, active ? "enabled" : "disabled");
552                         return;
553                 }
554         }
555         dbg_printf("Error: Firm BP %u not exists.\n", bp);
556 }  /* bp_activate */
557
558
559 /**
560  * Show a list of supported commands
561  */
562 static void show_commands(void)
563 {
564         dbg_printf("Internal Firm debugger extension $Revision$ commands:\n"
565                 "init                  break after initialization\n"
566                 "create nr             break if node nr was created\n"
567                 "replace nr            break if node nr is replaced by another node\n"
568                 "lower nr              break before node nr is lowered\n"
569                 "remirg nr|name        break if the irg of nr or entity name is deleted\n"
570                 "newent nr|name        break if the entity nr or name was created\n"
571                 "newtype nr|name       break if the type nr or name was created\n"
572                 "bp                    show all breakpoints\n"
573                 "enable nr             enable breakpoint nr\n"
574                 "disable nr            disable breakpoint nr\n"
575                 "showtype nr|name      show content of the type nr or name\n"
576                 "showent nr|name       show content of the entity nr or name\n"
577                 "setmask name msk      sets the debug module name to mask msk\n"
578                 "setlvl  name lvl      sets the debug module name to level lvl\n"
579                 "setoutfile name file  redirects debug output of module name to file\n"
580                 "irgname name          prints address and graph number of a method given by its name\n"
581                 "irgldname ldname      prints address and graph number of a method given by its ldname\n"
582                 "help                  list all commands\n"
583                 );
584 }  /* show_commands */
585
586 /**
587  * Shows all Firm breakpoints.
588  */
589 static void show_bp(void)
590 {
591         breakpoint *p;
592         bp_nr_t  *node_p;
593         bp_ident_t *ident_p;
594         int have_one = 0;
595
596         dbg_printf("Firm Breakpoints:");
597         for (p = bp_list; p; p = p->next) {
598                 have_one = 1;
599                 dbg_printf("+\n  BP %u: ", p->bpnr);
600
601                 switch (p->kind) {
602                 case BP_NR:
603                         node_p = (bp_nr_t *)p;
604                         dbg_printf("%s of Nr %ld ", reason_str(p->reason), node_p->nr);
605                         break;
606
607                 case BP_IDENT:
608                         ident_p = (bp_ident_t *)p;
609                         dbg_printf("+%s of ident \"%s\" ", reason_str(p->reason), get_id_str(ident_p->id));
610                         break;
611                 }
612
613                 dbg_printf(p->active ? "+enabled" : "+disabled");
614         }
615         dbg_printf(have_one ? "+\n" : "+ NONE\n");
616 }  /* show_bp */
617
618 /**
619  * firm_dbg_register() expects that the name is stored persistent.
620  * So we need this little helper function
621  */
622 static firm_dbg_module_t *dbg_register(const char *name)
623 {
624         ident *id = new_id_from_str(name);
625
626         return firm_dbg_register(get_id_str(id));
627 }  /* dbg_register */
628
629 /**
630  * Sets the debug mask of module name to lvl
631  */
632 static void set_dbg_level(const char *name, unsigned lvl)
633 {
634         firm_dbg_module_t *module = dbg_register(name);
635
636         if (firm_dbg_get_mask(module) != lvl) {
637                 firm_dbg_set_mask(module, lvl);
638
639                 dbg_printf("Setting debug mask of module %s to %u\n", name, lvl);
640         }
641 }  /* set_dbg_level */
642
643 /**
644  * Redirects the debug output of module name to fname
645  */
646 static void set_dbg_outfile(const char *name, const char *fname)
647 {
648         firm_dbg_module_t *module = dbg_register(name);
649         FILE *f = fopen(fname, "w");
650
651         if (! f) {
652                 perror(fname);
653                 return;
654         }
655
656         firm_dbg_set_file(module, f);
657         dbg_printf("Redirecting debug output of module %s to file %s\n", name, fname);
658 }  /* set_dbg_outfile */
659
660 /**
661  * Show info about a firm thing.
662  */
663 static void show_firm_object(void *firm_thing)
664 {
665         FILE *f = stdout;
666
667         if (firm_thing == NULL) {
668                 fprintf(f, "<NULL>\n");
669                 return;
670         }
671         switch (get_kind(firm_thing)) {
672         case k_BAD:
673                 fprintf(f, "BAD: (%p)\n", firm_thing);
674                 break;
675         case k_entity:
676                 dump_entity_to_file(f, (ir_entity*)firm_thing);
677                 break;
678         case k_type:
679                 dump_type_to_file(f, (ir_type*)firm_thing);
680                 break;
681         case k_ir_graph:
682         case k_ir_node:
683         case k_ir_mode:
684         case k_ir_op:
685         case k_tarval:
686         case k_ir_loop:
687         case k_ir_compound_graph_path:
688         case k_ir_extblk:
689         case k_ir_prog:
690                 fprintf(f, "NIY\n");
691                 break;
692         default:
693                 fprintf(f, "Cannot identify thing at (%p).\n", firm_thing);
694         }
695 }  /* show_firm_object */
696
697 /**
698  * Find a firm type by its number.
699  */
700 static ir_type *find_type_nr(long nr)
701 {
702         int i, n = get_irp_n_types();
703         ir_type *tp;
704
705         for (i = 0; i < n; ++i) {
706                 tp = get_irp_type(i);
707                 if (get_type_nr(tp) == nr)
708                         return tp;
709         }
710         tp = get_glob_type();
711         if (get_type_nr(tp) == nr)
712                 return tp;
713         return NULL;
714 }  /* find_type_nr */
715
716 /**
717  * Find a firm type by its name.
718  */
719 static ir_type *find_type_name(const char *name)
720 {
721         int i, n = get_irp_n_types();
722         ir_type *tp;
723
724         for (i = 0; i < n; ++i) {
725                 tp = get_irp_type(i);
726                 if (!is_compound_type(tp))
727                         continue;
728
729                 if (strcmp(get_compound_name(tp), name) == 0)
730                         return tp;
731         }
732         tp = get_glob_type();
733         if (strcmp(get_compound_name(tp), name) == 0)
734                 return tp;
735         return NULL;
736 }  /* find_type_name */
737
738 /** The environment for the entity search functions. */
739 typedef struct find_env {
740         union {
741                 long        nr;   /**< the number that is searched for */
742                 const char *name; /**< the name that is searched for */
743         } u;
744         ir_entity *res;     /**< the result */
745 } find_env_t;
746
747 /**
748  * Type-walker: Find an entity with given number.
749  */
750 static void check_ent_nr(type_or_ent tore, void *ctx)
751 {
752         find_env_t *env = (find_env_t*)ctx;
753
754         if (is_entity(tore.ent)) {
755                 if (get_entity_nr(tore.ent) == env->u.nr) {
756                         env->res = tore.ent;
757                 }
758         }
759 }  /* check_ent_nr */
760
761 /**
762  * Type-walker: Find an entity with given name.
763  */
764 static void check_ent_name(type_or_ent tore, void *ctx)
765 {
766         find_env_t *env = (find_env_t*)ctx;
767
768         if (is_entity(tore.ent))
769                 if (strcmp(get_entity_name(tore.ent), env->u.name) == 0) {
770                         env->res = tore.ent;
771                 }
772 }  /* check_ent_name */
773
774 /**
775  * Find a firm entity by its number.
776  */
777 static ir_entity *find_entity_nr(long nr)
778 {
779         find_env_t env;
780
781         env.u.nr = nr;
782         env.res  = NULL;
783         type_walk(check_ent_nr, NULL, &env);
784         return env.res;
785 }  /* find_entity_nr */
786
787 /**
788  * Find a firm entity by its name.
789  */
790 static ir_entity *find_entity_name(const char *name)
791 {
792         find_env_t env;
793
794         env.u.name = name;
795         env.res    = NULL;
796         type_walk(check_ent_name, NULL, &env);
797         return env.res;
798 }  /* find_entity_name */
799
800 /**
801  * Search methods for a name.
802  */
803 static void show_by_name(type_or_ent tore, void *env)
804 {
805         ident *id = (ident *)env;
806
807         if (is_entity(tore.ent)) {
808                 ir_entity *ent = tore.ent;
809
810                 if (is_method_entity(ent)) {
811                         if (get_entity_ident(ent) == id) {
812                                 ir_type *owner = get_entity_owner(ent);
813                                 ir_graph *irg = get_entity_irg(ent);
814
815                                 if (owner != get_glob_type()) {
816                                         printf("%s::%s", get_compound_name(owner), get_id_str(id));
817                                 } else {
818                                         printf("%s", get_id_str(id));
819                                 }
820                                 if (irg)
821                                         printf("[%ld] (%p)\n", get_irg_graph_nr(irg), irg);
822                                 else
823                                         printf(" NULL\n");
824                         }
825                 }
826         }
827 }  /* show_by_name */
828
829 /**
830  * Search methods for a ldname.
831  */
832 static void show_by_ldname(type_or_ent tore, void *env)
833 {
834         ident *id = (ident *)env;
835
836         if (is_entity(tore.ent)) {
837                 ir_entity *ent = tore.ent;
838
839                 if (is_method_entity(ent)) {
840                         if (get_entity_ld_ident(ent) == id) {
841                                 ir_type *owner = get_entity_owner(ent);
842                                 ir_graph *irg = get_entity_irg(ent);
843
844                                 if (owner != get_glob_type()) {
845                                         printf("%s::%s", get_compound_name(owner), get_id_str(id));
846                                 } else {
847                                         printf("%s", get_id_str(id));
848                                 }
849                                 if (irg)
850                                         printf("[%ld] (%p)\n", get_irg_graph_nr(irg), irg);
851                                 else
852                                         printf(" NULL\n");
853                         }
854                 }
855         }
856 }  /* show_by_ldname */
857
858 /**
859  * prints the address and graph number of all irgs with given name
860  */
861 static void irg_name(const char *name)
862 {
863         ident *id = new_id_from_str(name);
864
865         type_walk(show_by_name, NULL, (void *)id);
866 }  /* irg_name */
867
868 /**
869  * prints the address and graph number of all irgs with given ld_name
870  */
871 static void irg_ld_name(const char *name)
872 {
873         ident *id = new_id_from_str(name);
874
875         type_walk(show_by_ldname, NULL, (void *)id);
876 }  /* irg_ld_name */
877
878 enum tokens {
879         tok_create = 256,
880         tok_replace,
881         tok_lower,
882         tok_remirg,
883         tok_newent,
884         tok_newtype,
885         tok_showtype,
886         tok_showent,
887         tok_init,
888         tok_bp,
889         tok_enable,
890         tok_disable,
891         tok_setmask,
892         tok_setlvl,
893         tok_setoutfile,
894         tok_irgname,
895         tok_irgldname,
896         tok_help,
897         tok_identifier,
898         tok_number,
899         tok_eof,
900         tok_error
901 };
902
903 static const char *reserved[] = {
904         "create",
905         "replace",
906         "lower",
907         "remirg",
908         "newent",
909         "newtype",
910         "showtype",
911         "showent",
912         "init",
913         "bp",
914         "enable",
915         "disable",
916         "setmask",
917         "setlvl",
918         "setoutfile",
919         "irgname",
920         "irgldname",
921         "help"
922 };
923
924 /**
925  * The Lexer data.
926  */
927 static struct lexer {
928         int has_token;        /**< set if a token is cached. */
929         unsigned cur_token;   /**< current token. */
930         unsigned number;      /**< current token attribute. */
931         const char *s;        /**< current token attribute. */
932         size_t len;           /**< current token attribute. */
933
934         const char *curr_pos;
935         const char *end_pos;
936         const char *tok_start;
937 } lexer;
938
939 /**
940  * Initialize the lexer.
941  */
942 static void init_lexer(const char *input)
943 {
944         lexer.has_token = 0;
945         lexer.curr_pos  = input;
946         lexer.end_pos   = input + strlen(input);
947 }  /* init_lexer */
948
949
950 /**
951  * Get the next char from the input.
952  */
953 static char next_char(void)
954 {
955         if (lexer.curr_pos >= lexer.end_pos)
956                 return '\0';
957         return *lexer.curr_pos++;
958 }  /* next_char */
959
960 #define unput()    if (lexer.curr_pos < lexer.end_pos) --lexer.curr_pos
961
962 #undef MIN
963 #define MIN(a, b) (a) < (b) ? (a) : (b)
964
965 /**
966  * The lexer.
967  */
968 static unsigned get_token(void)
969 {
970         char c;
971         int i;
972
973         /* skip white space */
974         do {
975                 c = next_char();
976         } while (c != '\0' && isspace((unsigned char)c));
977
978         lexer.tok_start = lexer.curr_pos - 1;
979         if (c == '.' || isalpha((unsigned char)c)) {
980                 /* command begins here */
981                 int         len = 0;
982                 const char* tok_start;
983
984                 do {
985                         c = next_char();
986                         ++len;
987                 } while (isgraph((unsigned char)c));
988                 unput();
989
990                 tok_start = lexer.tok_start;
991                 if (*tok_start == '.') {
992                         ++tok_start;
993                         --len;
994                 }
995                 for (i = sizeof(reserved)/sizeof(reserved[0]) - 1; i >= 0; --i) {
996                         if (strncasecmp(tok_start, reserved[i], len) == 0 && reserved[i][len] == '\0')
997                                 return 256 + i;
998                 }
999
1000                 /* identifier */
1001                 lexer.s   = lexer.tok_start;
1002                 lexer.len = lexer.curr_pos - lexer.s;
1003                 return tok_identifier;
1004         } else if (isdigit((unsigned char)c) || c == '-') {
1005                 unsigned number = 0;
1006                 unsigned sign   = 0;
1007
1008                 /* we support negative numbers as well, so one can easily set all bits with -1 */
1009                 if (c == '-') {
1010                         sign = 1;
1011                         c    = next_char();
1012                 }
1013
1014                 if (c == '0') {
1015                         c = next_char();
1016
1017                         if (c == 'x' || c == 'X') {
1018                                 for (;;) {
1019                                         c = next_char();
1020
1021                                         if (! isxdigit((unsigned char)c))
1022                                                 break;
1023                                         if (isdigit((unsigned char)c))
1024                                                 number = (number << 4) | (c - '0');
1025                                         else
1026                                                 number = (number << 4) | (toupper((unsigned char)c) - 'A' + 10);
1027                                 }
1028                                 unput();
1029                                 lexer.number = number;
1030                                 return tok_number;
1031                         }
1032                 }
1033                 for (;;) {
1034                         if (! isdigit((unsigned char)c))
1035                                 break;
1036                         number = number * 10 + (c - '0');
1037                         c = next_char();
1038                 }
1039                 unput();
1040                 lexer.number = sign ? 0 - number : number;
1041                 return tok_number;
1042         }
1043         else if (c == '\0')
1044                 return tok_eof;
1045         return c;
1046 }  /* get_token */
1047
1048 void firm_debug(const char *cmd)
1049 {
1050         char name[1024], fname[1024];
1051         size_t len;
1052
1053         init_lexer(cmd);
1054
1055         for (;;) {
1056                 unsigned token;
1057
1058                 token = get_token();
1059
1060                 switch (token) {
1061                 case tok_eof:
1062                         goto leave;
1063
1064                 case tok_create:
1065                         token = get_token();
1066                         if (token != tok_number)
1067                                 goto error;
1068                         break_on_nr(lexer.number, BP_ON_NEW_NODE);
1069                         break;
1070
1071                 case tok_replace:
1072                         token = get_token();
1073                         if (token != tok_number)
1074                                 goto error;
1075                         break_on_nr(lexer.number, BP_ON_REPLACE);
1076                         break;
1077
1078                 case tok_lower:
1079                         token = get_token();
1080                         if (token != tok_number)
1081                                 goto error;
1082                         break_on_nr(lexer.number, BP_ON_LOWER);
1083                         break;
1084
1085                 case tok_remirg:
1086                         token = get_token();
1087
1088                         if (token == tok_number)
1089                                 break_on_nr(lexer.number, BP_ON_REMIRG);
1090                         else if (token == tok_identifier) {
1091                                 len = MIN(lexer.len, 1023);
1092                                 strncpy(name, lexer.s, len);
1093                                 name[len] = '\0';
1094                                 break_on_ident(name, BP_ON_REMIRG);
1095                         } else
1096                                 goto error;
1097                         break;
1098
1099                 case tok_newent:
1100                         token = get_token();
1101
1102                         if (token == tok_number)
1103                                 break_on_nr(lexer.number, BP_ON_NEW_ENT);
1104                         else if (token == tok_identifier) {
1105                                 len = MIN(lexer.len, 1023);
1106                                 strncpy(name, lexer.s, len);
1107                                 name[len] = '\0';
1108                                 break_on_ident(name, BP_ON_NEW_ENT);
1109                         } else
1110                                 goto error;
1111                         break;
1112
1113                 case tok_newtype:
1114                         token = get_token();
1115
1116                         if (token == tok_number)
1117                                 break_on_nr(lexer.number, BP_ON_NEW_TYPE);
1118                         else if (token == tok_identifier) {
1119                                 len = MIN(lexer.len, 1023);
1120                                 strncpy(name, lexer.s, len);
1121                                 name[len] = '\0';
1122                                 break_on_ident(name, BP_ON_NEW_TYPE);
1123                         } else
1124                                 goto error;
1125                         break;
1126
1127                 case tok_showtype:
1128                         token = get_token();
1129
1130                         if (token == tok_number)
1131                                 show_firm_object(find_type_nr(lexer.number));
1132                         else if (token == tok_identifier) {
1133                                 len = MIN(lexer.len, 1023);
1134                                 strncpy(name, lexer.s, len);
1135                                 name[len] = '\0';
1136                                 show_firm_object(find_type_name(name));
1137                         } else
1138                                 goto error;
1139                         break;
1140
1141                 case tok_showent:
1142                         token = get_token();
1143
1144                         if (token == tok_number)
1145                                 show_firm_object(find_entity_nr(lexer.number));
1146                         else if (token == tok_identifier) {
1147                                 len = MIN(lexer.len, 1023);
1148                                 strncpy(name, lexer.s, len);
1149                                 name[len] = '\0';
1150                                 show_firm_object(find_entity_name(name));
1151                         } else
1152                                 goto error;
1153                         break;
1154
1155                 case tok_init:
1156                         break_on_init = 1;
1157                         break;
1158
1159                 case tok_bp:
1160                         show_bp();
1161                         break;
1162
1163                 case tok_enable:
1164                         token = get_token();
1165                         if (token != tok_number)
1166                                 goto error;
1167                         bp_activate(lexer.number, 1);
1168                         break;
1169
1170                 case tok_disable:
1171                         token = get_token();
1172                         if (token != tok_number)
1173                                 goto error;
1174                         bp_activate(lexer.number, 0);
1175                         break;
1176
1177                 case tok_setmask:
1178                         token = get_token();
1179                         if (token != tok_identifier)
1180                                 goto error;
1181                         len = MIN(lexer.len, 1023);
1182                         strncpy(name, lexer.s, len);
1183                         name[len] = '\0';
1184
1185                         token = get_token();
1186                         if (token != tok_number)
1187                                 goto error;
1188                         set_dbg_level(name, lexer.number);
1189                         break;
1190
1191                 case tok_setlvl:
1192                         token = get_token();
1193                         if (token != tok_identifier)
1194                                 goto error;
1195                         len = MIN(lexer.len, 1023);
1196                         strncpy(name, lexer.s, len);
1197                         name[len] = '\0';
1198
1199                         token = get_token();
1200                         if (token != tok_number)
1201                                 goto error;
1202                         set_dbg_level(name, (1 << lexer.number) - 1);
1203                         break;
1204
1205                 case tok_setoutfile:
1206                         token = get_token();
1207                         if (token != tok_identifier)
1208                                 goto error;
1209                         len = MIN(lexer.len, 1023);
1210                         strncpy(name, lexer.s, len);
1211                         name[len] = '\0';
1212
1213                         token = get_token();
1214                         if (token != tok_identifier)
1215                                 goto error;
1216                         len = MIN(lexer.len, 1023);
1217                         strncpy(fname, lexer.s, len);
1218                         fname[len] = '\0';
1219                         set_dbg_outfile(name, fname);
1220                         break;
1221
1222                 case tok_irgname:
1223                         token = get_token();
1224                         if (token != tok_identifier)
1225                                 goto error;
1226                         len = MIN(lexer.len, 1023);
1227                         strncpy(name, lexer.s, len);
1228                         name[len] = '\0';
1229                         irg_name(name);
1230                         break;
1231
1232                 case tok_irgldname:
1233                         token = get_token();
1234                         if (token != tok_identifier)
1235                                 goto error;
1236                         len = MIN(lexer.len, 1023);
1237                         strncpy(name, lexer.s, len);
1238                         name[len] = '\0';
1239                         irg_ld_name(name);
1240                         break;
1241
1242                 case tok_help:
1243                         show_commands();
1244                         break;
1245
1246                 case tok_error:
1247                 default:
1248 error:
1249                         printf("Error: before %s\n", lexer.tok_start);
1250                         show_commands();
1251                         goto leave;
1252                 }
1253
1254                 token = get_token();
1255                 if (token == tok_eof)
1256                         break;
1257                 if (token != ';')
1258                         goto error;
1259         }
1260 leave:
1261         ;
1262 }  /* firm_debug */
1263
1264 void firm_init_debugger(void)
1265 {
1266         char *env;
1267
1268         bp_numbers = new_set(cmp_nr_bp, 8);
1269         bp_idents  = new_set(cmp_ident_bp, 8);
1270
1271         env = getenv("FIRMDBG");
1272
1273         is_active = 1;
1274
1275         if (env)
1276                 firm_debug(env);
1277
1278         if (break_on_init)
1279                 firm_debug_break();
1280 }  /* firm_init_debugger */
1281
1282 /**
1283  * A gdb helper function to print firm objects.
1284  */
1285 const char *gdb_node_helper(void *firm_object)
1286 {
1287         static char buf[1024];
1288         ir_snprintf(buf, sizeof(buf), "%+F", firm_object);
1289         return buf;
1290 }
1291
1292 const char *gdb_tarval_helper(void *tv_object)
1293 {
1294         static char buf[1024];
1295         ir_snprintf(buf, sizeof(buf), "%+T", tv_object);
1296         return buf;
1297 }
1298
1299 const char *gdb_out_edge_helper(const ir_node *node)
1300 {
1301         static char buf[4*1024];
1302         char *b = buf;
1303         size_t l;
1304         size_t len = sizeof(buf);
1305         const ir_edge_t *edge;
1306         foreach_out_edge(node, edge) {
1307                 ir_node *n = get_edge_src_irn(edge);
1308
1309                 ir_snprintf(b, len, "%+F  ", n);
1310                 l = strlen(b);
1311                 len -= l;
1312                 b += l;
1313         }
1314
1315         return buf;
1316 }
1317
1318 #else
1319
1320 /* some picky compiler do not allow empty files */
1321 static int __attribute__((unused)) _firm_only_that_you_can_compile_with_NDEBUG_defined;
1322
1323 #endif /* NDEBUG */
1324
1325 /**
1326  * @page debugger   The Firm debugger extension
1327  *
1328  * Firm contains a debugger extension. This allows to set debugger breakpoints
1329  * an various events.
1330  * The extension uses a text interface which can be accessed from most debuggers.
1331  * More than one command can be given separated by ';'.
1332  *
1333  * @section sec_cmd Supported commands
1334  *
1335  * Historically all debugger commands start with a dot.  This isn't needed in newer
1336  * versions, but still supported, ie the commands ".init" and "init" are equal.
1337  * The following commands are currently supported:
1338  *
1339  * @b init
1340  *
1341  * Break immediately after the debugger extension was initialized.
1342  * Typically this command is used in the environment to stop the execution
1343  * of a Firm compiler right after the initialization, like this:
1344  *
1345  * $export FIRMDBG=".init"
1346  *
1347  * @b create nr
1348  *
1349  * Break if a new IR-node with node number nr was created.
1350  * Typically used to find the place where wrong nodes are created.
1351  *
1352  * @b replace nr
1353  *
1354  * Break before IR-node with node number nr is replaced by another node.
1355  *
1356  * @b lower nr
1357  *
1358  * Break before IR-node with node number nr is lowered.
1359  *
1360  * @b remirg nr
1361  *
1362  * Break if the irg with graph number nr is deleted.
1363  *
1364  * @b remirg name
1365  *
1366  * Break if the irg of entity name is deleted.
1367  *
1368  * @b newent nr
1369  *
1370  * Break if the entity with number nr was created.
1371  *
1372  * @b newent name
1373  *
1374  * Break if the entity name was created.
1375  *
1376  * @b newtype nr
1377  *
1378  * Break if the type with number nr was created.
1379  *
1380  * @b newtype name
1381  *
1382  * Break if the type name was created.
1383  *
1384  * @b bp
1385  *
1386  * Show all Firm internal breakpoints.
1387  *
1388  * @b enable nr
1389  *
1390  * Enables breakpoint nr.
1391  *
1392  * @b disable nr
1393  *
1394  * Disables breakpoint nr.
1395  *
1396  * @b showent nr
1397  *
1398  * Show the content of entity nr.
1399  *
1400  * @b showent name
1401  *
1402  * Show the content of entity name.
1403  *
1404  * @b showtype nr
1405  *
1406  * Show the content of type nr.
1407  *
1408  * @b showtype name
1409  *
1410  * Show the content of type name.
1411  *
1412  * @b setmask name msk
1413  *
1414  * Sets the debug module name to mask msk.
1415  *
1416  * @b setlvl name lvl
1417  *
1418  * Sets the debug module name to level lvl.
1419  *
1420  * @b setoutfile name file
1421  *
1422  * Redirects debug output of module name to file.
1423  *
1424  * @b irgname name
1425  *
1426  * Prints address and graph number of a method given by its name.
1427  *
1428  * @b irgldname name
1429  *
1430  * Prints address and graph number of a method given by its linker name.
1431  *
1432  * @b help
1433  *
1434  * List all commands.
1435  *
1436  *
1437  * The Firm debugger extension can be accessed using the function firm_debug().
1438  * The following example shows how to set a creation breakpoint in GDB when
1439  * node 2101 is created.
1440  *
1441  * -# set FIRMDBG="init"
1442  * -# start gdb with your compiler
1443  * -# after gdb breaks, issue
1444  *
1445  * call firm_debug("create 2101")
1446  *
1447  * On the console the following text should be issued:
1448  *
1449  * Firm BP 1: creation of Node 2101
1450  *
1451  *
1452  * @section gdb_macro GDB macro
1453  *
1454  * Add the following to your .gdbinit file:
1455  * @code
1456  #
1457  # define firm "cmd"  Firm debugger extension
1458  #
1459  define firm
1460  call firm_debug($arg0)
1461  end
1462  * @endcode
1463  *
1464  * Then, all Firm debugger extension commands can be accessed in the gdb
1465  * console using the firm prefix, eg.:
1466  *
1467  * firm "create 2101"
1468  *
1469  * firm "help"
1470  */