* bcache.c, bcache.h: New files to implement a byte cache.
[external/binutils.git] / gdb / symmisc.c
1 /* Do various things to symbol tables (other than lookup), for GDB.
2    Copyright 1986, 1987, 1989, 1991, 1992, 1993, 1994, 1995, 1996
3    Free Software Foundation, Inc.
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
20
21 #include "defs.h"
22 #include "symtab.h"
23 #include "gdbtypes.h"
24 #include "bfd.h"
25 #include "symfile.h"
26 #include "objfiles.h"
27 #include "breakpoint.h"
28 #include "command.h"
29 #include "obstack.h"
30 #include "language.h"
31
32 #include "gdb_string.h"
33
34 #ifndef DEV_TTY
35 #define DEV_TTY "/dev/tty"
36 #endif
37
38 /* Unfortunately for debugging, stderr is usually a macro.  This is painful
39    when calling functions that take FILE *'s from the debugger.
40    So we make a variable which has the same value and which is accessible when
41    debugging GDB with itself.  Because stdin et al need not be constants,
42    we initialize them in the _initialize_symmisc function at the bottom
43    of the file.  */
44 FILE *std_in;
45 FILE *std_out;
46 FILE *std_err;
47
48 /* Prototypes for local functions */
49
50 static void 
51 dump_symtab PARAMS ((struct objfile *, struct symtab *, GDB_FILE *));
52
53 static void 
54 dump_psymtab PARAMS ((struct objfile *, struct partial_symtab *, GDB_FILE *));
55
56 static void 
57 dump_msymbols PARAMS ((struct objfile *, GDB_FILE *));
58
59 static void 
60 dump_objfile PARAMS ((struct objfile *));
61
62 static int
63 block_depth PARAMS ((struct block *));
64
65 static void
66 print_partial_symbols PARAMS ((struct partial_symbol **, int, char *, GDB_FILE *));
67
68 struct print_symbol_args {
69   struct symbol *symbol;
70   int depth;
71   GDB_FILE *outfile;
72 };
73
74 static int print_symbol PARAMS ((char *));
75
76 static void
77 free_symtab_block PARAMS ((struct objfile *, struct block *));
78
79 \f
80 /* Free a struct block <- B and all the symbols defined in that block.  */
81
82 static void
83 free_symtab_block (objfile, b)
84      struct objfile *objfile;
85      struct block *b;
86 {
87   register int i, n;
88   n = BLOCK_NSYMS (b);
89   for (i = 0; i < n; i++)
90     {
91       mfree (objfile -> md, SYMBOL_NAME (BLOCK_SYM (b, i)));
92       mfree (objfile -> md, (PTR) BLOCK_SYM (b, i));
93     }
94   mfree (objfile -> md, (PTR) b);
95 }
96
97 /* Free all the storage associated with the struct symtab <- S.
98    Note that some symtabs have contents malloc'ed structure by structure,
99    while some have contents that all live inside one big block of memory,
100    and some share the contents of another symbol table and so you should
101    not free the contents on their behalf (except sometimes the linetable,
102    which maybe per symtab even when the rest is not).
103    It is s->free_code that says which alternative to use.  */
104
105 void
106 free_symtab (s)
107      register struct symtab *s;
108 {
109   register int i, n;
110   register struct blockvector *bv;
111
112   switch (s->free_code)
113     {
114     case free_nothing:
115       /* All the contents are part of a big block of memory (an obstack),
116          and some other symtab is in charge of freeing that block.
117          Therefore, do nothing.  */
118       break;
119
120     case free_contents:
121       /* Here all the contents were malloc'ed structure by structure
122          and must be freed that way.  */
123       /* First free the blocks (and their symbols.  */
124       bv = BLOCKVECTOR (s);
125       n = BLOCKVECTOR_NBLOCKS (bv);
126       for (i = 0; i < n; i++)
127         free_symtab_block (s -> objfile, BLOCKVECTOR_BLOCK (bv, i));
128       /* Free the blockvector itself.  */
129       mfree (s -> objfile -> md, (PTR) bv);
130       /* Also free the linetable.  */
131       
132     case free_linetable:
133       /* Everything will be freed either by our `free_ptr'
134          or by some other symtab, except for our linetable.
135          Free that now.  */
136       if (LINETABLE (s))
137         mfree (s -> objfile -> md, (PTR) LINETABLE (s));
138       break;
139     }
140
141   /* If there is a single block of memory to free, free it.  */
142   if (s -> free_ptr != NULL)
143     mfree (s -> objfile -> md, s -> free_ptr);
144
145   /* Free source-related stuff */
146   if (s -> line_charpos != NULL)
147     mfree (s -> objfile -> md, (PTR) s -> line_charpos);
148   if (s -> fullname != NULL)
149     mfree (s -> objfile -> md, s -> fullname);
150   mfree (s -> objfile -> md, (PTR) s);
151 }
152
153 #if MAINTENANCE_CMDS
154
155 void
156 print_symbol_bcache_statistics ()
157 {
158   struct objfile *objfile;
159
160   immediate_quit++;
161   ALL_OBJFILES (objfile)
162     {
163       printf_filtered ("Cached obstack statistics for '%s':\n", objfile -> name);
164       print_bcache_statistics (&objfile -> psymbol_cache, "partial symbol obstack");
165     }
166   immediate_quit--;
167 }
168
169 void
170 print_objfile_statistics ()
171 {
172   struct objfile *objfile;
173
174   immediate_quit++;
175   ALL_OBJFILES (objfile)
176     {
177       printf_filtered ("Statistics for '%s':\n", objfile -> name);
178       if (OBJSTAT (objfile, n_stabs) > 0)
179         printf_filtered ("  Number of \"stab\" symbols read: %d\n",
180                          OBJSTAT (objfile, n_stabs));
181       if (OBJSTAT (objfile, n_minsyms) > 0)
182         printf_filtered ("  Number of \"minimal symbols read: %d\n",
183                          OBJSTAT (objfile, n_minsyms));
184       if (OBJSTAT (objfile, n_psyms) > 0)
185         printf_filtered ("  Number of \"partial symbols read: %d\n",
186                          OBJSTAT (objfile, n_psyms));
187       if (OBJSTAT (objfile, n_syms) > 0)
188         printf_filtered ("  Number of \"full symbols read: %d\n",
189                          OBJSTAT (objfile, n_syms));
190       if (OBJSTAT (objfile, n_types) > 0)
191         printf_filtered ("  Number of \"types defined: %d\n",
192                          OBJSTAT (objfile, n_types));
193       if (OBJSTAT (objfile, sz_strtab) > 0)
194         printf_filtered ("  Space used by a.out string tables: %d\n",
195                          OBJSTAT (objfile, sz_strtab));
196       printf_filtered ("  Total memory used for psymbol obstack: %d\n",
197                        obstack_memory_used (&objfile -> psymbol_obstack));
198       printf_filtered ("  Total memory used for symbol obstack: %d\n",
199                        obstack_memory_used (&objfile -> symbol_obstack));
200       printf_filtered ("  Total memory used for type obstack: %d\n",
201                        obstack_memory_used (&objfile -> type_obstack));
202     }
203   immediate_quit--;
204 }
205
206 static void 
207 dump_objfile (objfile)
208      struct objfile *objfile;
209 {
210   struct symtab *symtab;
211   struct partial_symtab *psymtab;
212
213   printf_filtered ("\nObject file %s:  ", objfile -> name);
214   printf_filtered ("Objfile at ");
215   gdb_print_address (objfile, gdb_stdout);
216   printf_filtered (", bfd at ");
217   gdb_print_address (objfile->obfd, gdb_stdout);
218   printf_filtered (", %d minsyms\n\n",
219                    objfile->minimal_symbol_count);
220
221   if (objfile -> psymtabs)
222     {
223       printf_filtered ("Psymtabs:\n");
224       for (psymtab = objfile -> psymtabs;
225            psymtab != NULL;
226            psymtab = psymtab -> next)
227         {
228           printf_filtered ("%s at ",
229                            psymtab -> filename);
230           gdb_print_address (psymtab, gdb_stdout);
231           printf_filtered (", ");
232           if (psymtab -> objfile != objfile)
233             {
234               printf_filtered ("NOT ON CHAIN!  ");
235             }
236           wrap_here ("  ");
237         }
238       printf_filtered ("\n\n");
239     }
240
241   if (objfile -> symtabs)
242     {
243       printf_filtered ("Symtabs:\n");
244       for (symtab = objfile -> symtabs;
245            symtab != NULL;
246            symtab = symtab->next)
247         {
248           printf_filtered ("%s at ", symtab -> filename);
249           gdb_print_address (symtab, gdb_stdout);
250           printf_filtered (", ");
251           if (symtab -> objfile != objfile)
252             {
253               printf_filtered ("NOT ON CHAIN!  ");
254             }
255           wrap_here ("  ");
256         }
257       printf_filtered ("\n\n");
258     }
259 }
260
261 /* Print minimal symbols from this objfile.  */
262  
263 static void 
264 dump_msymbols (objfile, outfile)
265      struct objfile *objfile;
266      GDB_FILE *outfile;
267 {
268   struct minimal_symbol *msymbol;
269   int index;
270   char ms_type;
271   
272   fprintf_filtered (outfile, "\nObject file %s:\n\n", objfile -> name);
273   if (objfile -> minimal_symbol_count == 0)
274     {
275       fprintf_filtered (outfile, "No minimal symbols found.\n");
276       return;
277     }
278   for (index = 0, msymbol = objfile -> msymbols;
279        SYMBOL_NAME (msymbol) != NULL; msymbol++, index++)
280     {
281       switch (msymbol -> type)
282         {
283           case mst_unknown:
284             ms_type = 'u';
285             break;
286           case mst_text:
287             ms_type = 'T';
288             break;
289           case mst_solib_trampoline:
290             ms_type = 'S';
291             break;
292           case mst_data:
293             ms_type = 'D';
294             break;
295           case mst_bss:
296             ms_type = 'B';
297             break;
298           case mst_abs:
299             ms_type = 'A';
300             break;
301           case mst_file_text:
302             ms_type = 't';
303             break;
304           case mst_file_data:
305             ms_type = 'd';
306             break;
307           case mst_file_bss:
308             ms_type = 'b';
309             break;
310           default:
311             ms_type = '?';
312             break;
313         }
314       fprintf_filtered (outfile, "[%2d] %c %#10lx %s", index, ms_type,
315                         SYMBOL_VALUE_ADDRESS (msymbol), SYMBOL_NAME (msymbol));
316       if (SYMBOL_DEMANGLED_NAME (msymbol) != NULL)
317         {
318           fprintf_filtered (outfile, "  %s", SYMBOL_DEMANGLED_NAME (msymbol));
319         }
320 #ifdef SOFUN_ADDRESS_MAYBE_MISSING
321       if (msymbol->filename)
322         fprintf_filtered (outfile, "  %s", msymbol->filename);
323 #endif
324       fputs_filtered ("\n", outfile);
325     }
326   if (objfile -> minimal_symbol_count != index)
327     {
328       warning ("internal error:  minimal symbol count %d != %d",
329                objfile -> minimal_symbol_count, index);
330     }
331   fprintf_filtered (outfile, "\n");
332 }
333
334 static void
335 dump_psymtab (objfile, psymtab, outfile)
336      struct objfile *objfile;
337      struct partial_symtab *psymtab;
338      GDB_FILE *outfile;
339 {
340   int i;
341
342   fprintf_filtered (outfile, "\nPartial symtab for source file %s ",
343                     psymtab -> filename);
344   fprintf_filtered (outfile, "(object ");
345   gdb_print_address (psymtab, outfile);
346   fprintf_filtered (outfile, ")\n\n");
347   fprintf_unfiltered (outfile, "  Read from object file %s (",
348                       objfile -> name);
349   gdb_print_address (objfile, outfile);
350   fprintf_unfiltered (outfile, ")\n");
351
352   if (psymtab -> readin)
353     {
354       fprintf_filtered (outfile,
355                 "  Full symtab was read (at ");
356       gdb_print_address (psymtab->symtab, outfile);
357       fprintf_filtered (outfile, " by function at ");
358       gdb_print_address ((PTR)psymtab->read_symtab, outfile);
359       fprintf_filtered (outfile, ")\n");
360     }
361
362   fprintf_filtered (outfile, "  Relocate symbols by ");
363   for (i = 0; i < psymtab->objfile->num_sections; ++i)
364     {
365       if (i != 0)
366         fprintf_filtered (outfile, ", ");
367       wrap_here ("    ");
368       print_address_numeric (ANOFFSET (psymtab->section_offsets, i),
369                              1,
370                              outfile);
371     }
372   fprintf_filtered (outfile, "\n");
373
374   fprintf_filtered (outfile, "  Symbols cover text addresses ");
375   print_address_numeric (psymtab->textlow, 1, outfile);
376   fprintf_filtered (outfile, "-");
377   print_address_numeric (psymtab->texthigh, 1, outfile);
378   fprintf_filtered (outfile, "\n");
379   fprintf_filtered (outfile, "  Depends on %d other partial symtabs.\n",
380                     psymtab -> number_of_dependencies);
381   for (i = 0; i < psymtab -> number_of_dependencies; i++)
382     {
383       fprintf_filtered (outfile, "    %d ", i);
384       gdb_print_address (psymtab -> dependencies[i], outfile);
385       fprintf_filtered (outfile, " %s\n",
386                         psymtab -> dependencies[i] -> filename);
387     }
388   if (psymtab -> n_global_syms > 0)
389     {
390       print_partial_symbols (objfile -> global_psymbols.list
391                             + psymtab -> globals_offset,
392                             psymtab -> n_global_syms, "Global", outfile);
393     }
394   if (psymtab -> n_static_syms > 0)
395     {
396       print_partial_symbols (objfile -> static_psymbols.list
397                             + psymtab -> statics_offset,
398                             psymtab -> n_static_syms, "Static", outfile);
399     }
400   fprintf_filtered (outfile, "\n");
401 }
402
403 static void 
404 dump_symtab (objfile, symtab, outfile)
405      struct objfile *objfile;
406      struct symtab *symtab;
407      GDB_FILE *outfile;
408 {
409   register int i, j;
410   int len, blen;
411   register struct linetable *l;
412   struct blockvector *bv;
413   register struct block *b;
414   int depth;
415
416   fprintf_filtered (outfile, "\nSymtab for file %s\n", symtab->filename);
417   fprintf_filtered (outfile, "Read from object file %s (", objfile->name);
418   gdb_print_address (objfile, outfile);
419   fprintf_filtered (outfile, ")\n");
420   fprintf_filtered (outfile, "Language: %s\n", language_str (symtab -> language));
421
422   /* First print the line table.  */
423   l = LINETABLE (symtab);
424   if (l)
425     {
426       fprintf_filtered (outfile, "\nLine table:\n\n");
427       len = l->nitems;
428       for (i = 0; i < len; i++)
429         {
430           fprintf_filtered (outfile, " line %d at ", l->item[i].line);
431           print_address_numeric (l->item[i].pc, 1, outfile);
432           fprintf_filtered (outfile, "\n");
433         }
434     }
435   /* Now print the block info.  */
436   fprintf_filtered (outfile, "\nBlockvector:\n\n");
437   bv = BLOCKVECTOR (symtab);
438   len = BLOCKVECTOR_NBLOCKS (bv);
439   for (i = 0; i < len; i++)
440     {
441       b = BLOCKVECTOR_BLOCK (bv, i);
442       depth = block_depth (b) * 2;
443       print_spaces (depth, outfile);
444       fprintf_filtered (outfile, "block #%03d (object ", i);
445       gdb_print_address (b, outfile);
446       fprintf_filtered (outfile, ") ");
447       fprintf_filtered (outfile, "[");
448       print_address_numeric (BLOCK_START (b), 1, outfile);
449       fprintf_filtered (outfile, "..");
450       print_address_numeric (BLOCK_END (b), 1, outfile);
451       fprintf_filtered (outfile, "]");
452       if (BLOCK_SUPERBLOCK (b))
453         {
454           fprintf_filtered (outfile, " (under ");
455           gdb_print_address (BLOCK_SUPERBLOCK (b), outfile);
456           fprintf_filtered (outfile, ")");
457         }
458       if (BLOCK_FUNCTION (b))
459         {
460           fprintf_filtered (outfile, " %s", SYMBOL_NAME (BLOCK_FUNCTION (b)));
461           if (SYMBOL_DEMANGLED_NAME (BLOCK_FUNCTION (b)) != NULL)
462             {
463               fprintf_filtered (outfile, " %s",
464                        SYMBOL_DEMANGLED_NAME (BLOCK_FUNCTION (b)));
465             }
466         }
467       if (BLOCK_GCC_COMPILED(b))
468         fprintf_filtered (outfile, " gcc%d compiled", BLOCK_GCC_COMPILED(b));
469       fprintf_filtered (outfile, "\n");
470       blen = BLOCK_NSYMS (b);
471       for (j = 0; j < blen; j++)
472         {
473           struct print_symbol_args s;
474           s.symbol = BLOCK_SYM (b, j);
475           s.depth = depth + 1;
476           s.outfile = outfile;
477           catch_errors (print_symbol, &s, "Error printing symbol:\n",
478                         RETURN_MASK_ALL);
479         }
480     }
481   fprintf_filtered (outfile, "\n");
482 }
483
484 void
485 maintenance_print_symbols (args, from_tty)
486      char *args;
487      int from_tty;
488 {
489   char **argv;
490   GDB_FILE *outfile;
491   struct cleanup *cleanups;
492   char *symname = NULL;
493   char *filename = DEV_TTY;
494   struct objfile *objfile;
495   struct symtab *s;
496
497   dont_repeat ();
498
499   if (args == NULL)
500     {
501       error ("\
502 Arguments missing: an output file name and an optional symbol file name");
503     }
504   else if ((argv = buildargv (args)) == NULL)
505     {
506       nomem (0);
507     }
508   cleanups = make_cleanup (freeargv, (char *) argv);
509
510   if (argv[0] != NULL)
511     {
512       filename = argv[0];
513       /* If a second arg is supplied, it is a source file name to match on */
514       if (argv[1] != NULL)
515         {
516           symname = argv[1];
517         }
518     }
519
520   filename = tilde_expand (filename);
521   make_cleanup (free, filename);
522   
523   outfile = gdb_fopen (filename, FOPEN_WT);
524   if (outfile == 0)
525     perror_with_name (filename);
526   make_cleanup (fclose, (char *) outfile);
527
528   immediate_quit++;
529   ALL_SYMTABS (objfile, s)
530     if (symname == NULL || (STREQ (symname, s -> filename)))
531       dump_symtab (objfile, s, outfile);
532   immediate_quit--;
533   do_cleanups (cleanups);
534 }
535
536 /* Print symbol ARGS->SYMBOL on ARGS->OUTFILE.  ARGS->DEPTH says how
537    far to indent.  ARGS is really a struct print_symbol_args *, but is
538    declared as char * to get it past catch_errors.  Returns 0 for error,
539    1 for success.  */
540
541 static int
542 print_symbol (args)
543      char *args;
544 {
545   struct symbol *symbol = ((struct print_symbol_args *)args)->symbol;
546   int depth = ((struct print_symbol_args *)args)->depth;
547   GDB_FILE *outfile = ((struct print_symbol_args *)args)->outfile;
548
549   print_spaces (depth, outfile);
550   if (SYMBOL_NAMESPACE (symbol) == LABEL_NAMESPACE)
551     {
552       fprintf_filtered (outfile, "label %s at ", SYMBOL_SOURCE_NAME (symbol));
553       print_address_numeric (SYMBOL_VALUE_ADDRESS (symbol), 1, outfile);
554       fprintf_filtered (outfile, "\n");
555       return 1;
556     }
557   if (SYMBOL_NAMESPACE (symbol) == STRUCT_NAMESPACE)
558     {
559       if (TYPE_TAG_NAME (SYMBOL_TYPE (symbol)))
560         {
561           LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
562         }
563       else
564         {
565           fprintf_filtered (outfile, "%s %s = ",
566                (TYPE_CODE (SYMBOL_TYPE (symbol)) == TYPE_CODE_ENUM
567                 ? "enum"
568                 : (TYPE_CODE (SYMBOL_TYPE (symbol)) == TYPE_CODE_STRUCT
569                    ? "struct" : "union")),
570                SYMBOL_NAME (symbol));
571           LA_PRINT_TYPE (SYMBOL_TYPE (symbol), "", outfile, 1, depth);
572         }
573       fprintf_filtered (outfile, ";\n");
574     }
575   else
576     {
577       if (SYMBOL_CLASS (symbol) == LOC_TYPEDEF)
578         fprintf_filtered (outfile, "typedef ");
579       if (SYMBOL_TYPE (symbol))
580         {
581           /* Print details of types, except for enums where it's clutter.  */
582           LA_PRINT_TYPE (SYMBOL_TYPE (symbol), SYMBOL_SOURCE_NAME (symbol),
583                          outfile,
584                          TYPE_CODE (SYMBOL_TYPE (symbol)) != TYPE_CODE_ENUM,
585                          depth);
586           fprintf_filtered (outfile, "; ");
587         }
588       else
589         fprintf_filtered (outfile, "%s ", SYMBOL_SOURCE_NAME (symbol));
590
591       switch (SYMBOL_CLASS (symbol))
592         {
593         case LOC_CONST:
594           fprintf_filtered (outfile, "const %ld (0x%lx),",
595                             SYMBOL_VALUE (symbol),
596                             SYMBOL_VALUE (symbol));
597           break;
598
599         case LOC_CONST_BYTES:
600           {
601             unsigned i;
602             struct type *type = check_typedef (SYMBOL_TYPE (symbol));
603             fprintf_filtered (outfile, "const %u hex bytes:",
604                               TYPE_LENGTH (type));
605             for (i = 0; i < TYPE_LENGTH (type); i++)
606               fprintf_filtered (outfile, " %02x",
607                                 (unsigned)SYMBOL_VALUE_BYTES (symbol) [i]);
608             fprintf_filtered (outfile, ",");
609           }
610           break;
611
612         case LOC_STATIC:
613           fprintf_filtered (outfile, "static at ");
614           print_address_numeric (SYMBOL_VALUE_ADDRESS (symbol), 1,outfile);
615           fprintf_filtered (outfile, ",");
616           break;
617
618         case LOC_REGISTER:
619           fprintf_filtered (outfile, "register %ld,", SYMBOL_VALUE (symbol));
620           break;
621
622         case LOC_ARG:
623           fprintf_filtered (outfile, "arg at offset 0x%lx,",
624                             SYMBOL_VALUE (symbol));
625           break;
626
627         case LOC_LOCAL_ARG:
628           fprintf_filtered (outfile, "arg at offset 0x%lx from fp,",
629                    SYMBOL_VALUE (symbol));
630           break;
631
632         case LOC_REF_ARG:
633           fprintf_filtered (outfile, "reference arg at 0x%lx,", SYMBOL_VALUE (symbol));
634           break;
635
636         case LOC_REGPARM:
637           fprintf_filtered (outfile, "parameter register %ld,", SYMBOL_VALUE (symbol));
638           break;
639
640         case LOC_REGPARM_ADDR:
641           fprintf_filtered (outfile, "address parameter register %ld,", SYMBOL_VALUE (symbol));
642           break;
643
644         case LOC_LOCAL:
645           fprintf_filtered (outfile, "local at offset 0x%lx,",
646                             SYMBOL_VALUE (symbol));
647           break;
648
649         case LOC_BASEREG:
650           fprintf_filtered (outfile, "local at 0x%lx from register %d",
651                    SYMBOL_VALUE (symbol), SYMBOL_BASEREG (symbol));
652           break;
653
654         case LOC_BASEREG_ARG:
655           fprintf_filtered (outfile, "arg at 0x%lx from register %d,",
656                    SYMBOL_VALUE (symbol), SYMBOL_BASEREG (symbol));
657           break;
658
659         case LOC_TYPEDEF:
660           break;
661
662         case LOC_LABEL:
663           fprintf_filtered (outfile, "label at ");
664           print_address_numeric (SYMBOL_VALUE_ADDRESS (symbol), 1, outfile);
665           break;
666
667         case LOC_BLOCK:
668           fprintf_filtered (outfile, "block (object ");
669           gdb_print_address (SYMBOL_BLOCK_VALUE (symbol), outfile);
670           fprintf_filtered (outfile, ") starting at ");
671           print_address_numeric (BLOCK_START (SYMBOL_BLOCK_VALUE (symbol)),
672                                  1,
673                                  outfile);
674           fprintf_filtered (outfile, ",");
675           break;
676
677         case LOC_UNRESOLVED:
678           fprintf_filtered (outfile, "unresolved");
679           break;
680
681         case LOC_OPTIMIZED_OUT:
682           fprintf_filtered (outfile, "optimized out");
683           break;
684
685         default:
686           fprintf_filtered (outfile, "botched symbol class %x",
687                             SYMBOL_CLASS (symbol));
688           break;
689         }
690     }
691   fprintf_filtered (outfile, "\n");
692   return 1;
693 }
694
695 void
696 maintenance_print_psymbols (args, from_tty)
697      char *args;
698      int from_tty;
699 {
700   char **argv;
701   GDB_FILE *outfile;
702   struct cleanup *cleanups;
703   char *symname = NULL;
704   char *filename = DEV_TTY;
705   struct objfile *objfile;
706   struct partial_symtab *ps;
707
708   dont_repeat ();
709
710   if (args == NULL)
711     {
712       error ("print-psymbols takes an output file name and optional symbol file name");
713     }
714   else if ((argv = buildargv (args)) == NULL)
715     {
716       nomem (0);
717     }
718   cleanups = make_cleanup (freeargv, (char *) argv);
719
720   if (argv[0] != NULL)
721     {
722       filename = argv[0];
723       /* If a second arg is supplied, it is a source file name to match on */
724       if (argv[1] != NULL)
725         {
726           symname = argv[1];
727         }
728     }
729
730   filename = tilde_expand (filename);
731   make_cleanup (free, filename);
732   
733   outfile = gdb_fopen (filename, FOPEN_WT);
734   if (outfile == 0)
735     perror_with_name (filename);
736   make_cleanup (fclose, outfile);
737
738   immediate_quit++;
739   ALL_PSYMTABS (objfile, ps)
740     if (symname == NULL || (STREQ (symname, ps -> filename)))
741       dump_psymtab (objfile, ps, outfile);
742   immediate_quit--;
743   do_cleanups (cleanups);
744 }
745
746 static void
747 print_partial_symbols (p, count, what, outfile)
748      struct partial_symbol **p;
749      int count;
750      char *what;
751      GDB_FILE *outfile;
752 {
753   fprintf_filtered (outfile, "  %s partial symbols:\n", what);
754   while (count-- > 0)
755     {
756       fprintf_filtered (outfile, "    `%s'", SYMBOL_NAME(*p));
757       if (SYMBOL_DEMANGLED_NAME (*p) != NULL)
758         {
759           fprintf_filtered (outfile, "  `%s'", SYMBOL_DEMANGLED_NAME (*p));
760         }
761       fputs_filtered (", ", outfile);
762       switch (SYMBOL_NAMESPACE (*p))
763         {
764         case UNDEF_NAMESPACE:
765           fputs_filtered ("undefined namespace, ", outfile);
766           break;
767         case VAR_NAMESPACE:
768           /* This is the usual thing -- don't print it */
769           break;
770         case STRUCT_NAMESPACE:
771           fputs_filtered ("struct namespace, ", outfile);
772           break;
773         case LABEL_NAMESPACE:
774           fputs_filtered ("label namespace, ", outfile);
775           break;
776         default:
777           fputs_filtered ("<invalid namespace>, ", outfile);
778           break;
779         }
780       switch (SYMBOL_CLASS (*p))
781         {
782         case LOC_UNDEF:
783           fputs_filtered ("undefined", outfile);
784           break;
785         case LOC_CONST:
786           fputs_filtered ("constant int", outfile);
787           break;
788         case LOC_STATIC:
789           fputs_filtered ("static", outfile);
790           break;
791         case LOC_REGISTER:
792           fputs_filtered ("register", outfile);
793           break;
794         case LOC_ARG:
795           fputs_filtered ("pass by value", outfile);
796           break;
797         case LOC_REF_ARG:
798           fputs_filtered ("pass by reference", outfile);
799           break;
800         case LOC_REGPARM:
801           fputs_filtered ("register parameter", outfile);
802           break;
803         case LOC_REGPARM_ADDR:
804           fputs_filtered ("register address parameter", outfile);
805           break;
806         case LOC_LOCAL:
807           fputs_filtered ("stack parameter", outfile);
808           break;
809         case LOC_TYPEDEF:
810           fputs_filtered ("type", outfile);
811           break;
812         case LOC_LABEL:
813           fputs_filtered ("label", outfile);
814           break;
815         case LOC_BLOCK:
816           fputs_filtered ("function", outfile);
817           break;
818         case LOC_CONST_BYTES:
819           fputs_filtered ("constant bytes", outfile);
820           break;
821         case LOC_LOCAL_ARG:
822           fputs_filtered ("shuffled arg", outfile);
823           break;
824         case LOC_UNRESOLVED:
825           fputs_filtered ("unresolved", outfile);
826           break;
827         case LOC_OPTIMIZED_OUT:
828           fputs_filtered ("optimized out", outfile);
829           break;
830         default:
831           fputs_filtered ("<invalid location>", outfile);
832           break;
833         }
834       fputs_filtered (", ", outfile);
835       /* FIXME-32x64: Need to use SYMBOL_VALUE_ADDRESS, etc.; this
836          could be 32 bits when some of the other fields in the union
837          are 64.  */
838       fprintf_filtered (outfile, "0x%lx\n", SYMBOL_VALUE (*p));
839       p++;
840     }
841 }
842
843 void
844 maintenance_print_msymbols (args, from_tty)
845      char *args;
846      int from_tty;
847 {
848   char **argv;
849   GDB_FILE *outfile;
850   struct cleanup *cleanups;
851   char *filename = DEV_TTY;
852   char *symname = NULL;
853   struct objfile *objfile;
854
855   dont_repeat ();
856
857   if (args == NULL)
858     {
859       error ("print-msymbols takes an output file name and optional symbol file name");
860     }
861   else if ((argv = buildargv (args)) == NULL)
862     {
863       nomem (0);
864     }
865   cleanups = make_cleanup (freeargv, argv);
866
867   if (argv[0] != NULL)
868     {
869       filename = argv[0];
870       /* If a second arg is supplied, it is a source file name to match on */
871       if (argv[1] != NULL)
872         {
873           symname = argv[1];
874         }
875     }
876
877   filename = tilde_expand (filename);
878   make_cleanup (free, filename);
879   
880   outfile = gdb_fopen (filename, FOPEN_WT);
881   if (outfile == 0)
882     perror_with_name (filename);
883   make_cleanup (fclose, outfile);
884
885   immediate_quit++;
886   ALL_OBJFILES (objfile)
887     if (symname == NULL || (STREQ (symname, objfile -> name)))
888       dump_msymbols (objfile, outfile);
889   immediate_quit--;
890   fprintf_filtered (outfile, "\n\n");
891   do_cleanups (cleanups);
892 }
893
894 void
895 maintenance_print_objfiles (ignore, from_tty)
896      char *ignore;
897      int from_tty;
898 {
899   struct objfile *objfile;
900
901   dont_repeat ();
902
903   immediate_quit++;
904   ALL_OBJFILES (objfile)
905     dump_objfile (objfile);
906   immediate_quit--;
907 }
908
909 /* Check consistency of psymtabs and symtabs.  */
910
911 void
912 maintenance_check_symtabs (ignore, from_tty)
913      char *ignore;
914      int from_tty;
915 {
916   register struct symbol *sym;
917   register struct partial_symbol **psym;
918   register struct symtab *s = NULL;
919   register struct partial_symtab *ps;
920   struct blockvector *bv;
921   register struct objfile *objfile;
922   register struct block *b;
923   int length;
924
925   ALL_PSYMTABS (objfile, ps)
926     {
927       s = PSYMTAB_TO_SYMTAB(ps);
928       if (s == NULL)
929         continue;
930       bv = BLOCKVECTOR (s);
931       b = BLOCKVECTOR_BLOCK (bv, STATIC_BLOCK);
932       psym = ps->objfile->static_psymbols.list + ps->statics_offset;
933       length = ps->n_static_syms;
934       while (length--)
935         {
936           sym = lookup_block_symbol (b, SYMBOL_NAME (*psym),
937                                      SYMBOL_NAMESPACE (*psym));
938           if (!sym)
939             {
940               printf_filtered ("Static symbol `");
941               puts_filtered (SYMBOL_NAME (*psym));
942               printf_filtered ("' only found in ");
943               puts_filtered (ps->filename);
944               printf_filtered (" psymtab\n");
945             }
946           psym++;
947         }
948       b = BLOCKVECTOR_BLOCK (bv, GLOBAL_BLOCK);
949       psym = ps->objfile->global_psymbols.list + ps->globals_offset;
950       length = ps->n_global_syms;
951       while (length--)
952         {
953           sym = lookup_block_symbol (b, SYMBOL_NAME (*psym),
954                                      SYMBOL_NAMESPACE (*psym));
955           if (!sym)
956             {
957               printf_filtered ("Global symbol `");
958               puts_filtered (SYMBOL_NAME (*psym));
959               printf_filtered ("' only found in ");
960               puts_filtered (ps->filename);
961               printf_filtered (" psymtab\n");
962             }
963           psym++;
964         }
965       if (ps->texthigh < ps->textlow)
966         {
967           printf_filtered ("Psymtab ");
968           puts_filtered (ps->filename);
969           printf_filtered (" covers bad range ");
970           print_address_numeric (ps->textlow, 1, stdout);
971           printf_filtered (" - ");
972           print_address_numeric (ps->texthigh, 1, stdout);
973           printf_filtered ("\n");
974           continue;
975         }
976       if (ps->texthigh == 0)
977         continue;
978       if (ps->textlow < BLOCK_START (b) || ps->texthigh > BLOCK_END (b))
979         {
980           printf_filtered ("Psymtab ");
981           puts_filtered (ps->filename);
982           printf_filtered (" covers ");
983           print_address_numeric (ps->textlow, 1, stdout);
984           printf_filtered (" - ");
985           print_address_numeric (ps->texthigh, 1, stdout);
986           printf_filtered (" but symtab covers only ");
987           print_address_numeric (BLOCK_START (b), 1, stdout);
988           printf_filtered (" - ");
989           print_address_numeric (BLOCK_END (b), 1, stdout);
990           printf_filtered ("\n");
991         }
992     }
993 }
994
995 \f
996 /* Return the nexting depth of a block within other blocks in its symtab.  */
997
998 static int
999 block_depth (block)
1000      struct block *block;
1001 {
1002   register int i = 0;
1003   while ((block = BLOCK_SUPERBLOCK (block)) != NULL) 
1004     {
1005       i++;
1006     }
1007   return i;
1008 }
1009
1010 #endif  /* MAINTENANCE_CMDS */
1011
1012 \f
1013 /* Increase the space allocated for LISTP, which is probably
1014    global_psymbols or static_psymbols. This space will eventually
1015    be freed in free_objfile().  */
1016
1017 void
1018 extend_psymbol_list (listp, objfile)
1019      register struct psymbol_allocation_list *listp;
1020      struct objfile *objfile;
1021 {
1022   int new_size;
1023   if (listp->size == 0)
1024     {
1025       new_size = 255;
1026       listp->list = (struct partial_symbol **)
1027         xmmalloc (objfile -> md, new_size * sizeof (struct partial_symbol *));
1028     }
1029   else
1030     {
1031       new_size = listp->size * 2;
1032       listp->list = (struct partial_symbol **)
1033         xmrealloc (objfile -> md, (char *) listp->list,
1034                    new_size * sizeof (struct partial_symbol *));
1035     }
1036   /* Next assumes we only went one over.  Should be good if
1037      program works correctly */
1038   listp->next = listp->list + listp->size;
1039   listp->size = new_size;
1040 }
1041
1042
1043 /* Do early runtime initializations. */
1044 void
1045 _initialize_symmisc ()
1046 {
1047   std_in  = stdin;
1048   std_out = stdout;
1049   std_err = stderr;
1050 }