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