OSDN Git Service

* dbxout.c (dbxout_type_methods): Only treat TYPE_METHODS as a
[pf3gnuchains/gcc-fork.git] / gcc / dbxout.c
1 /* Output dbx-format symbol table information from GNU compiler.
2    Copyright (C) 1987, 88, 92-96, 1997 Free Software Foundation, Inc.
3
4 This file is part of GNU CC.
5
6 GNU CC is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 GNU CC is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GNU CC; see the file COPYING.  If not, write to
18 the Free Software Foundation, 59 Temple Place - Suite 330,
19 Boston, MA 02111-1307, USA.  */
20
21
22 /* Output dbx-format symbol table data.
23    This consists of many symbol table entries, each of them
24    a .stabs assembler pseudo-op with four operands:
25    a "name" which is really a description of one symbol and its type,
26    a "code", which is a symbol defined in stab.h whose name starts with N_,
27    an unused operand always 0,
28    and a "value" which is an address or an offset.
29    The name is enclosed in doublequote characters.
30
31    Each function, variable, typedef, and structure tag
32    has a symbol table entry to define it.
33    The beginning and end of each level of name scoping within
34    a function are also marked by special symbol table entries.
35
36    The "name" consists of the symbol name, a colon, a kind-of-symbol letter,
37    and a data type number.  The data type number may be followed by
38    "=" and a type definition; normally this will happen the first time
39    the type number is mentioned.  The type definition may refer to
40    other types by number, and those type numbers may be followed
41    by "=" and nested definitions.
42
43    This can make the "name" quite long.
44    When a name is more than 80 characters, we split the .stabs pseudo-op
45    into two .stabs pseudo-ops, both sharing the same "code" and "value".
46    The first one is marked as continued with a double-backslash at the
47    end of its "name".
48
49    The kind-of-symbol letter distinguished function names from global
50    variables from file-scope variables from parameters from auto
51    variables in memory from typedef names from register variables.
52    See `dbxout_symbol'.
53
54    The "code" is mostly redundant with the kind-of-symbol letter
55    that goes in the "name", but not entirely: for symbols located
56    in static storage, the "code" says which segment the address is in,
57    which controls how it is relocated.
58
59    The "value" for a symbol in static storage
60    is the core address of the symbol (actually, the assembler
61    label for the symbol).  For a symbol located in a stack slot
62    it is the stack offset; for one in a register, the register number.
63    For a typedef symbol, it is zero.
64
65    If DEBUG_SYMS_TEXT is defined, all debugging symbols must be
66    output while in the text section.
67
68    For more on data type definitions, see `dbxout_type'.  */
69
70 #include "config.h"
71
72 #include <stdio.h>
73 #include <errno.h>
74
75 #ifdef HAVE_STRING_H
76 #include <string.h>
77 #else
78 #ifdef HAVE_STRINGS_H
79 #include <strings.h>
80 #endif
81 #endif
82
83 #include "tree.h"
84 #include "rtl.h"
85 #include "flags.h"
86 #include "regs.h"
87 #include "insn-config.h"
88 #include "reload.h"
89 #include "defaults.h"
90 #include "output.h" /* ASM_OUTPUT_SOURCE_LINE may refer to sdb functions.  */
91
92 #ifndef errno
93 extern int errno;
94 #endif
95
96 #ifdef XCOFF_DEBUGGING_INFO
97 #include "xcoffout.h"
98 #endif
99
100 #ifndef ASM_STABS_OP
101 #define ASM_STABS_OP ".stabs"
102 #endif
103
104 #ifndef ASM_STABN_OP
105 #define ASM_STABN_OP ".stabn"
106 #endif
107
108 #ifndef DBX_TYPE_DECL_STABS_CODE
109 #define DBX_TYPE_DECL_STABS_CODE N_LSYM
110 #endif
111
112 #ifndef DBX_STATIC_CONST_VAR_CODE
113 #define DBX_STATIC_CONST_VAR_CODE N_FUN
114 #endif
115
116 #ifndef DBX_REGPARM_STABS_CODE
117 #define DBX_REGPARM_STABS_CODE N_RSYM
118 #endif
119
120 #ifndef DBX_REGPARM_STABS_LETTER
121 #define DBX_REGPARM_STABS_LETTER 'P'
122 #endif
123
124 /* This is used for parameters passed by invisible reference in a register.  */
125 #ifndef GDB_INV_REF_REGPARM_STABS_LETTER
126 #define GDB_INV_REF_REGPARM_STABS_LETTER 'a'
127 #endif
128
129 #ifndef DBX_MEMPARM_STABS_LETTER
130 #define DBX_MEMPARM_STABS_LETTER 'p'
131 #endif
132
133 #ifndef FILE_NAME_JOINER
134 #define FILE_NAME_JOINER "/"
135 #endif
136
137 /* Nonzero means if the type has methods, only output debugging
138    information if methods are actually written to the asm file.  This
139    optimization only works if the debugger can detect the special C++
140    marker.  */
141
142 #define MINIMAL_DEBUG 1
143
144 #ifdef NO_DOLLAR_IN_LABEL
145 #ifdef NO_DOT_IN_LABEL
146 #undef MINIMAL_DEBUG
147 #define MINIMAL_DEBUG 0
148 #endif
149 #endif
150
151 static int flag_minimal_debug = MINIMAL_DEBUG;
152
153 /* Nonzero if we have actually used any of the GDB extensions
154    to the debugging format.  The idea is that we use them for the
155    first time only if there's a strong reason, but once we have done that,
156    we use them whenever convenient.  */
157
158 static int have_used_extensions = 0;
159
160 /* Number for the next N_SOL filename stabs label.  The number 0 is reserved
161    for the N_SO filename stabs label.  */
162
163 static int source_label_number = 1;
164
165 static int scope_labelno = 0;
166
167 char *getpwd ();
168
169 /* Typical USG systems don't have stab.h, and they also have
170    no use for DBX-format debugging info.  */
171
172 #if defined (DBX_DEBUGGING_INFO) || defined (XCOFF_DEBUGGING_INFO)
173
174 #ifdef DEBUG_SYMS_TEXT
175 #define FORCE_TEXT text_section ();
176 #else
177 #define FORCE_TEXT
178 #endif
179
180 #if defined (USG) || defined (NO_STAB_H) || defined (CROSS_COMPILE)
181 #include "gstab.h"  /* If doing DBX on sysV, use our own stab.h.  */
182 #else
183 #include <stab.h>  /* On BSD, use the system's stab.h.  */
184
185 /* This is a GNU extension we need to reference in this file.  */
186 #ifndef N_CATCH
187 #define N_CATCH 0x54
188 #endif
189 #endif /* not USG */
190
191 #ifdef __GNU_STAB__
192 #define STAB_CODE_TYPE enum __stab_debug_code
193 #else
194 #define STAB_CODE_TYPE int
195 #endif
196
197 /* 1 if PARM is passed to this function in memory.  */
198
199 #define PARM_PASSED_IN_MEMORY(PARM) \
200  (GET_CODE (DECL_INCOMING_RTL (PARM)) == MEM)
201
202 /* A C expression for the integer offset value of an automatic variable
203    (N_LSYM) having address X (an RTX).  */
204 #ifndef DEBUGGER_AUTO_OFFSET
205 #define DEBUGGER_AUTO_OFFSET(X) \
206   (GET_CODE (X) == PLUS ? INTVAL (XEXP (X, 1)) : 0)
207 #endif
208
209 /* A C expression for the integer offset value of an argument (N_PSYM)
210    having address X (an RTX).  The nominal offset is OFFSET.  */
211 #ifndef DEBUGGER_ARG_OFFSET
212 #define DEBUGGER_ARG_OFFSET(OFFSET, X) (OFFSET)
213 #endif
214
215 /* Stream for writing to assembler file.  */
216
217 static FILE *asmfile;
218
219 /* Last source file name mentioned in a NOTE insn.  */
220
221 static char *lastfile;
222
223 /* Current working directory.  */
224
225 static char *cwd;
226
227 enum typestatus {TYPE_UNSEEN, TYPE_XREF, TYPE_DEFINED};
228
229 /* Structure recording information about a C data type.
230    The status element says whether we have yet output
231    the definition of the type.  TYPE_XREF says we have
232    output it as a cross-reference only.
233    The file_number and type_number elements are used if DBX_USE_BINCL
234    is defined.  */
235
236 struct typeinfo
237 {
238   enum typestatus status;
239 #ifdef DBX_USE_BINCL
240   int file_number;
241   int type_number;
242 #endif
243 };
244
245 /* Vector recording information about C data types.
246    When we first notice a data type (a tree node),
247    we assign it a number using next_type_number.
248    That is its index in this vector.  */
249
250 struct typeinfo *typevec;
251
252 /* Number of elements of space allocated in `typevec'.  */
253
254 static int typevec_len;
255
256 /* In dbx output, each type gets a unique number.
257    This is the number for the next type output.
258    The number, once assigned, is in the TYPE_SYMTAB_ADDRESS field.  */
259
260 static int next_type_number;
261
262 #ifdef DBX_USE_BINCL
263
264 /* When using N_BINCL in dbx output, each type number is actually a
265    pair of the file number and the type number within the file.
266    This is a stack of input files.  */
267
268 struct dbx_file
269 {
270   struct dbx_file *next;
271   int file_number;
272   int next_type_number;
273 };
274
275 /* This is the top of the stack.  */
276
277 static struct dbx_file *current_file;
278
279 /* This is the next file number to use.  */
280
281 static int next_file_number;
282
283 #endif /* DBX_USE_BINCL */
284
285 /* In dbx output, we must assign symbol-blocks id numbers
286    in the order in which their beginnings are encountered.
287    We output debugging info that refers to the beginning and
288    end of the ranges of code in each block
289    with assembler labels LBBn and LBEn, where n is the block number.
290    The labels are generated in final, which assigns numbers to the
291    blocks in the same way.  */
292
293 static int next_block_number;
294
295 /* These variables are for dbxout_symbol to communicate to
296    dbxout_finish_symbol.
297    current_sym_code is the symbol-type-code, a symbol N_... define in stab.h.
298    current_sym_value and current_sym_addr are two ways to address the
299    value to store in the symtab entry.
300    current_sym_addr if nonzero represents the value as an rtx.
301    If that is zero, current_sym_value is used.  This is used
302    when the value is an offset (such as for auto variables,
303    register variables and parms).  */
304
305 static STAB_CODE_TYPE current_sym_code;
306 static int current_sym_value;
307 static rtx current_sym_addr;
308
309 /* Number of chars of symbol-description generated so far for the
310    current symbol.  Used by CHARS and CONTIN.  */
311
312 static int current_sym_nchars;
313
314 /* Report having output N chars of the current symbol-description.  */
315
316 #define CHARS(N) (current_sym_nchars += (N))
317
318 /* Break the current symbol-description, generating a continuation,
319    if it has become long.  */
320
321 #ifndef DBX_CONTIN_LENGTH
322 #define DBX_CONTIN_LENGTH 80
323 #endif
324
325 #if DBX_CONTIN_LENGTH > 0
326 #define CONTIN  \
327   do {if (current_sym_nchars > DBX_CONTIN_LENGTH) dbxout_continue ();} while (0)
328 #else
329 #define CONTIN
330 #endif
331
332 void dbxout_types ();
333 void dbxout_args ();
334 void dbxout_symbol ();
335
336 static void dbxout_function_end         PROTO((void));
337 static void dbxout_typedefs             PROTO((tree));
338 static void dbxout_type_index           PROTO((tree));
339 static void dbxout_continue             PROTO((void));
340 static void dbxout_type_fields          PROTO((tree));
341 static void dbxout_type_method_1        PROTO((tree, char *));
342 static void dbxout_type_methods         PROTO((tree));
343 static void dbxout_range_type           PROTO((tree));
344 static void dbxout_type                 PROTO((tree, int, int));
345 static void print_int_cst_octal         PROTO((tree));
346 static void print_octal                 PROTO((unsigned HOST_WIDE_INT, int));
347 static void dbxout_type_name            PROTO((tree));
348 static void dbxout_symbol_location      PROTO((tree, tree, char *, rtx));
349 static void dbxout_symbol_name          PROTO((tree, char *, int));
350 static void dbxout_prepare_symbol       PROTO((tree));
351 static void dbxout_finish_symbol        PROTO((tree));
352 static void dbxout_block                PROTO((tree, int, tree));
353 static void dbxout_really_begin_function PROTO((tree));
354 \f
355 static void
356 dbxout_function_end ()
357 {
358   char lscope_label_name[100];
359   /* Convert Ltext into the appropriate format for local labels in case
360      the system doesn't insert underscores in front of user generated
361      labels.  */
362   ASM_GENERATE_INTERNAL_LABEL (lscope_label_name, "Lscope", scope_labelno);
363   ASM_OUTPUT_INTERNAL_LABEL (asmfile, "Lscope", scope_labelno);
364   scope_labelno++;
365
366   /* By convention, GCC will mark the end of a function with an N_FUN
367      symbol and an empty string.  */
368   fprintf (asmfile, "%s \"\",%d,0,0,", ASM_STABS_OP, N_FUN);
369   assemble_name (asmfile, lscope_label_name);
370   fputc ('-', asmfile);
371   assemble_name (asmfile, XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0));
372   fprintf (asmfile, "\n");
373 }
374
375 /* At the beginning of compilation, start writing the symbol table.
376    Initialize `typevec' and output the standard data types of C.  */
377
378 void
379 dbxout_init (asm_file, input_file_name, syms)
380      FILE *asm_file;
381      char *input_file_name;
382      tree syms;
383 {
384   char ltext_label_name[100];
385
386   asmfile = asm_file;
387
388   typevec_len = 100;
389   typevec = (struct typeinfo *) xmalloc (typevec_len * sizeof typevec[0]);
390   bzero ((char *) typevec, typevec_len * sizeof typevec[0]);
391
392   /* Convert Ltext into the appropriate format for local labels in case
393      the system doesn't insert underscores in front of user generated
394      labels.  */
395   ASM_GENERATE_INTERNAL_LABEL (ltext_label_name, "Ltext", 0);
396
397   /* Put the current working directory in an N_SO symbol.  */
398 #ifndef DBX_WORKING_DIRECTORY /* Only some versions of DBX want this,
399                                  but GDB always does.  */
400   if (use_gnu_debug_info_extensions)
401 #endif
402     {
403       if (!cwd && (cwd = getpwd ()) && (!*cwd || cwd[strlen (cwd) - 1] != '/'))
404         {
405           char *wdslash = xmalloc (strlen (cwd) + sizeof (FILE_NAME_JOINER));
406           sprintf (wdslash, "%s%s", cwd, FILE_NAME_JOINER);
407           cwd = wdslash;
408         }
409       if (cwd)
410         {
411 #ifdef DBX_OUTPUT_MAIN_SOURCE_DIRECTORY
412           DBX_OUTPUT_MAIN_SOURCE_DIRECTORY (asmfile, cwd);
413 #else /* no DBX_OUTPUT_MAIN_SOURCE_DIRECTORY */
414           fprintf (asmfile, "%s ", ASM_STABS_OP);
415           output_quoted_string (asmfile, cwd);
416           fprintf (asmfile, ",%d,0,0,%s\n", N_SO, &ltext_label_name[1]);
417 #endif /* no DBX_OUTPUT_MAIN_SOURCE_DIRECTORY */
418         }
419     }
420
421 #ifdef DBX_OUTPUT_MAIN_SOURCE_FILENAME
422   /* This should NOT be DBX_OUTPUT_SOURCE_FILENAME. That
423      would give us an N_SOL, and we want an N_SO.  */
424   DBX_OUTPUT_MAIN_SOURCE_FILENAME (asmfile, input_file_name);
425 #else /* no DBX_OUTPUT_MAIN_SOURCE_FILENAME */
426   /* We include outputting `Ltext:' here,
427      because that gives you a way to override it.  */
428   /* Used to put `Ltext:' before the reference, but that loses on sun 4.  */
429   fprintf (asmfile, "%s ", ASM_STABS_OP);
430   output_quoted_string (asmfile, input_file_name);
431   fprintf (asmfile, ",%d,0,0,%s\n", 
432            N_SO, &ltext_label_name[1]);
433   text_section ();
434   ASM_OUTPUT_INTERNAL_LABEL (asmfile, "Ltext", 0);
435 #endif /* no DBX_OUTPUT_MAIN_SOURCE_FILENAME */
436
437   /* Possibly output something to inform GDB that this compilation was by
438      GCC.  It's easier for GDB to parse it when after the N_SO's.  This
439      is used in Solaris 2.  */
440 #ifdef ASM_IDENTIFY_GCC_AFTER_SOURCE
441   ASM_IDENTIFY_GCC_AFTER_SOURCE (asmfile);
442 #endif
443
444   lastfile = input_file_name;
445
446   next_type_number = 1;
447   next_block_number = 2;
448
449 #ifdef DBX_USE_BINCL
450   current_file = (struct dbx_file *) xmalloc (sizeof *current_file);
451   current_file->next = NULL;
452   current_file->file_number = 0;
453   current_file->next_type_number = 1;
454   next_file_number = 1;
455 #endif
456
457   /* Make sure that types `int' and `char' have numbers 1 and 2.
458      Definitions of other integer types will refer to those numbers.
459      (Actually it should no longer matter what their numbers are.
460      Also, if any types with tags have been defined, dbxout_symbol
461      will output them first, so the numbers won't be 1 and 2.  That
462      happens in C++.  So it's a good thing it should no longer matter).  */
463
464 #ifdef DBX_OUTPUT_STANDARD_TYPES
465   DBX_OUTPUT_STANDARD_TYPES (syms);
466 #else
467   dbxout_symbol (TYPE_NAME (integer_type_node), 0);
468   dbxout_symbol (TYPE_NAME (char_type_node), 0);
469 #endif
470
471   /* Get all permanent types that have typedef names,
472      and output them all, except for those already output.  */
473
474   dbxout_typedefs (syms);
475 }
476
477 /* Output any typedef names for types described by TYPE_DECLs in SYMS,
478    in the reverse order from that which is found in SYMS.  */
479
480 static void
481 dbxout_typedefs (syms)
482      tree syms;
483 {
484   if (syms)
485     {
486       dbxout_typedefs (TREE_CHAIN (syms));
487       if (TREE_CODE (syms) == TYPE_DECL)
488         {
489           tree type = TREE_TYPE (syms);
490           if (TYPE_NAME (type)
491               && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
492               && TYPE_SIZE (type) != NULL_TREE
493               && ! TREE_ASM_WRITTEN (TYPE_NAME (type)))
494             dbxout_symbol (TYPE_NAME (type), 0);
495         }
496     }
497 }
498
499 /* Change to reading from a new source file.  Generate a N_BINCL stab.  */
500
501 void
502 dbxout_start_new_source_file (filename)
503      char *filename;
504 {
505 #ifdef DBX_USE_BINCL
506   struct dbx_file *n = (struct dbx_file *) xmalloc (sizeof *n);
507
508   n->next = current_file;
509   n->file_number = next_file_number++;
510   n->next_type_number = 1;
511   current_file = n;
512   fprintf (asmfile, "%s ", ASM_STABS_OP);
513   output_quoted_string (asmfile, filename);
514   fprintf (asmfile, ",%d,0,0,0\n", N_BINCL);
515 #endif
516 }
517
518 /* Revert to reading a previous source file.  Generate a N_EINCL stab.  */
519
520 void
521 dbxout_resume_previous_source_file ()
522 {
523 #ifdef DBX_USE_BINCL
524   struct dbx_file *next;
525
526   fprintf (asmfile, "%s %d,0,0,0\n", ASM_STABN_OP, N_EINCL);
527   next = current_file->next;
528   free (current_file);
529   current_file = next;
530 #endif
531 }
532
533 /* Output debugging info to FILE to switch to sourcefile FILENAME.  */
534
535 void
536 dbxout_source_file (file, filename)
537      FILE *file;
538      char *filename;
539 {
540   char ltext_label_name[100];
541
542   if (filename && (lastfile == 0 || strcmp (filename, lastfile)))
543     {
544 #ifdef DBX_OUTPUT_SOURCE_FILENAME
545       DBX_OUTPUT_SOURCE_FILENAME (file, filename);
546 #else
547       ASM_GENERATE_INTERNAL_LABEL (ltext_label_name, "Ltext",
548                                    source_label_number);
549       fprintf (file, "%s ", ASM_STABS_OP);
550       output_quoted_string (file, filename);
551       fprintf (file, ",%d,0,0,%s\n", N_SOL, &ltext_label_name[1]);
552       if (current_function_decl != NULL_TREE
553           && DECL_SECTION_NAME (current_function_decl) != NULL_TREE)
554         ; /* Don't change section amid function.  */
555       else
556         text_section ();
557       ASM_OUTPUT_INTERNAL_LABEL (file, "Ltext", source_label_number);
558       source_label_number++;
559 #endif
560       lastfile = filename;
561     }
562 }
563
564 /* Output a line number symbol entry into output stream FILE, 
565    for source file FILENAME and line number LINENO.  */
566
567 void
568 dbxout_source_line (file, filename, lineno)
569      FILE *file;
570      char *filename;
571      int lineno;
572 {
573   dbxout_source_file (file, filename);
574
575 #ifdef ASM_OUTPUT_SOURCE_LINE
576   ASM_OUTPUT_SOURCE_LINE (file, lineno);
577 #else
578   fprintf (file, "\t%s %d,0,%d\n", ASM_STABD_OP, N_SLINE, lineno);
579 #endif
580 }
581
582 /* At the end of compilation, finish writing the symbol table.
583    Unless you define DBX_OUTPUT_MAIN_SOURCE_FILE_END, the default is
584    to do nothing.  */
585
586 void
587 dbxout_finish (file, filename)
588      FILE *file;
589      char *filename;
590 {
591 #ifdef DBX_OUTPUT_MAIN_SOURCE_FILE_END
592   DBX_OUTPUT_MAIN_SOURCE_FILE_END (file, filename);
593 #endif /* DBX_OUTPUT_MAIN_SOURCE_FILE_END */
594 }
595
596 /* Output the index of a type.  */
597
598 static void
599 dbxout_type_index (type)
600      tree type;
601 {
602 #ifndef DBX_USE_BINCL
603   fprintf (asmfile, "%d", TYPE_SYMTAB_ADDRESS (type));
604   CHARS (3);
605 #else
606   struct typeinfo *t = &typevec[TYPE_SYMTAB_ADDRESS (type)];
607   fprintf (asmfile, "(%d,%d)", t->file_number, t->type_number);
608   CHARS (7);
609 #endif
610 }
611
612 /* Continue a symbol-description that gets too big.
613    End one symbol table entry with a double-backslash
614    and start a new one, eventually producing something like
615    .stabs "start......\\",code,0,value
616    .stabs "...rest",code,0,value   */
617
618 static void
619 dbxout_continue ()
620 {
621 #ifdef DBX_CONTIN_CHAR
622   fprintf (asmfile, "%c", DBX_CONTIN_CHAR);
623 #else
624   fprintf (asmfile, "\\\\");
625 #endif
626   dbxout_finish_symbol (NULL_TREE);
627   fprintf (asmfile, "%s \"", ASM_STABS_OP);
628   current_sym_nchars = 0;
629 }
630 \f
631 /* Subroutine of `dbxout_type'.  Output the type fields of TYPE.
632    This must be a separate function because anonymous unions require
633    recursive calls.  */
634
635 static void
636 dbxout_type_fields (type)
637      tree type;
638 {
639   tree tem;
640   /* Output the name, type, position (in bits), size (in bits) of each
641      field.  */
642   for (tem = TYPE_FIELDS (type); tem; tem = TREE_CHAIN (tem))
643     {
644       /* Omit here local type decls until we know how to support them.  */
645       if (TREE_CODE (tem) == TYPE_DECL)
646         continue;
647       /* Omit fields whose position or size are variable.  */
648       else if (TREE_CODE (tem) == FIELD_DECL
649                && (TREE_CODE (DECL_FIELD_BITPOS (tem)) != INTEGER_CST
650                    || TREE_CODE (DECL_SIZE (tem)) != INTEGER_CST))
651         continue;
652       /* Omit here the nameless fields that are used to skip bits.  */
653       else if (DECL_IGNORED_P (tem))
654         continue;
655       else if (TREE_CODE (tem) != CONST_DECL)
656         {
657           /* Continue the line if necessary,
658              but not before the first field.  */
659           if (tem != TYPE_FIELDS (type))
660             CONTIN;
661
662           if (use_gnu_debug_info_extensions
663               && flag_minimal_debug
664               && TREE_CODE (tem) == FIELD_DECL
665               && DECL_VIRTUAL_P (tem)
666               && DECL_ASSEMBLER_NAME (tem))
667             {
668               have_used_extensions = 1;
669               CHARS (3 + IDENTIFIER_LENGTH (DECL_ASSEMBLER_NAME (tem)));
670               fputs (IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (tem)), asmfile);
671               dbxout_type (DECL_FCONTEXT (tem), 0, 0);
672               fprintf (asmfile, ":");
673               dbxout_type (TREE_TYPE (tem), 0, 0);
674               fprintf (asmfile, ",%d;",
675                        TREE_INT_CST_LOW (DECL_FIELD_BITPOS (tem)));
676               continue;
677             }
678
679           if (DECL_NAME (tem))
680             {
681               fprintf (asmfile, "%s:", IDENTIFIER_POINTER (DECL_NAME (tem)));
682               CHARS (2 + IDENTIFIER_LENGTH (DECL_NAME (tem)));
683             }
684           else
685             {
686               fprintf (asmfile, ":");
687               CHARS (2);
688             }
689
690           if (use_gnu_debug_info_extensions
691               && (TREE_PRIVATE (tem) || TREE_PROTECTED (tem)
692                   || TREE_CODE (tem) != FIELD_DECL))
693             {
694               have_used_extensions = 1;
695               putc ('/', asmfile);
696               putc ((TREE_PRIVATE (tem) ? '0'
697                      : TREE_PROTECTED (tem) ? '1' : '2'),
698                     asmfile);
699               CHARS (2);
700             }
701
702           dbxout_type ((TREE_CODE (tem) == FIELD_DECL
703                         && DECL_BIT_FIELD_TYPE (tem))
704                        ? DECL_BIT_FIELD_TYPE (tem)
705                        : TREE_TYPE (tem), 0, 0);
706
707           if (TREE_CODE (tem) == VAR_DECL)
708             {
709               if (TREE_STATIC (tem) && use_gnu_debug_info_extensions)
710                 {
711                   char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (tem));
712                   have_used_extensions = 1;
713                   fprintf (asmfile, ":%s;", name);
714                   CHARS (strlen (name));
715                 }
716               else
717                 {
718                   /* If TEM is non-static, GDB won't understand it.  */
719                   fprintf (asmfile, ",0,0;");
720                 }
721             }
722           else if (TREE_CODE (DECL_FIELD_BITPOS (tem)) == INTEGER_CST)
723             {
724               fprintf (asmfile, ",%d,%d;",
725                        TREE_INT_CST_LOW (DECL_FIELD_BITPOS (tem)),
726                        TREE_INT_CST_LOW (DECL_SIZE (tem)));
727             }
728           CHARS (23);
729         }
730     }
731 }
732 \f
733 /* Subroutine of `dbxout_type_methods'.  Output debug info about the
734    method described DECL.  DEBUG_NAME is an encoding of the method's
735    type signature.  ??? We may be able to do without DEBUG_NAME altogether
736    now.  */
737
738 static void
739 dbxout_type_method_1 (decl, debug_name)
740      tree decl;
741      char *debug_name;
742 {
743   char c1 = 'A', c2;
744
745   if (TREE_CODE (TREE_TYPE (decl)) == FUNCTION_TYPE)
746     c2 = '?';
747   else /* it's a METHOD_TYPE.  */
748     {
749       tree firstarg = TREE_VALUE (TYPE_ARG_TYPES (TREE_TYPE (decl)));
750       /* A for normal functions.
751          B for `const' member functions.
752          C for `volatile' member functions.
753          D for `const volatile' member functions.  */
754       if (TYPE_READONLY (TREE_TYPE (firstarg)))
755         c1 += 1;
756       if (TYPE_VOLATILE (TREE_TYPE (firstarg)))
757         c1 += 2;
758
759       if (DECL_VINDEX (decl))
760         c2 = '*';
761       else
762         c2 = '.';
763     }
764
765   fprintf (asmfile, ":%s;%c%c%c", debug_name,
766            TREE_PRIVATE (decl) ? '0' : TREE_PROTECTED (decl) ? '1' : '2', c1, c2);
767   CHARS (IDENTIFIER_LENGTH (DECL_ASSEMBLER_NAME (decl)) + 6
768          - (debug_name - IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl))));
769   if (DECL_VINDEX (decl))
770     {
771       fprintf (asmfile, "%d;",
772                TREE_INT_CST_LOW (DECL_VINDEX (decl)));
773       dbxout_type (DECL_CONTEXT (decl), 0, 0);
774       fprintf (asmfile, ";");
775       CHARS (8);
776     }
777 }
778 \f
779 /* Subroutine of `dbxout_type'.  Output debug info about the methods defined
780    in TYPE.  */
781
782 static void
783 dbxout_type_methods (type)
784      register tree type;
785 {
786   /* C++: put out the method names and their parameter lists */
787   tree methods = TYPE_METHODS (type);
788   tree type_encoding;
789   register tree fndecl;
790   register tree last;
791   char formatted_type_identifier_length[16];
792   register int type_identifier_length;
793
794   if (methods == NULL_TREE)
795     return;
796
797   type_encoding = DECL_NAME (TYPE_NAME (type));
798
799 #if 0
800   /* C++: Template classes break some assumptions made by this code about
801      the class names, constructor names, and encodings for assembler
802      label names.  For now, disable output of dbx info for them.  */
803   {
804     char *ptr = IDENTIFIER_POINTER (type_encoding);
805     /* This should use index.  (mrs) */
806     while (*ptr && *ptr != '<') ptr++;
807     if (*ptr != 0)
808       {
809         static int warned;
810         if (!warned)
811           {
812             warned = 1;
813 #ifdef HAVE_TEMPLATES
814             if (warn_template_debugging)
815               warning ("dbx info for template class methods not yet supported");
816 #endif
817           }
818         return;
819       }
820   }
821 #endif
822
823   type_identifier_length = IDENTIFIER_LENGTH (type_encoding);
824
825   sprintf(formatted_type_identifier_length, "%d", type_identifier_length);
826
827   if (TREE_CODE (methods) != TREE_VEC)
828     fndecl = methods;
829   else if (TREE_VEC_ELT (methods, 0) != NULL_TREE)
830     fndecl = TREE_VEC_ELT (methods, 0);
831   else
832     fndecl = TREE_VEC_ELT (methods, 1);
833
834   while (fndecl)
835     {
836       tree name = DECL_NAME (fndecl);
837       int need_prefix = 1;
838
839       /* Group together all the methods for the same operation.
840          These differ in the types of the arguments.  */
841       for (last = NULL_TREE;
842            fndecl && (last == NULL_TREE || DECL_NAME (fndecl) == DECL_NAME (last));
843            fndecl = TREE_CHAIN (fndecl))
844         /* Output the name of the field (after overloading), as
845            well as the name of the field before overloading, along
846            with its parameter list */
847         {
848           /* This is the "mangled" name of the method.
849              It encodes the argument types.  */
850           char *debug_name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (fndecl));
851           int show_arg_types = 0;
852
853           CONTIN;
854
855           last = fndecl;
856
857           if (DECL_IGNORED_P (fndecl))
858             continue;
859
860           if (flag_minimal_debug)
861             {
862               char marker;
863
864               /* We can't optimize a method which uses an anonymous
865                  class, because the debugger will not be able to
866                  associate the arbitrary class name with the actual
867                  class.  */
868 #ifndef NO_DOLLAR_IN_LABEL
869               marker = '$';
870 #else
871               marker = '.';
872 #endif
873               if (strchr (debug_name, marker))
874                 show_arg_types = 1;
875               /* Detect ordinary methods because their mangled names
876                  start with the operation name.  */
877               else if (!strncmp (IDENTIFIER_POINTER (name), debug_name,
878                                  IDENTIFIER_LENGTH (name)))
879                 {
880                   debug_name += IDENTIFIER_LENGTH (name);
881                   if (debug_name[0] == '_' && debug_name[1] == '_')
882                     {
883                       char *method_name = debug_name + 2;
884                       char *length_ptr = formatted_type_identifier_length;
885                       /* Get past const and volatile qualifiers.  */
886                       while (*method_name == 'C' || *method_name == 'V')
887                         method_name++;
888                       /* Skip digits for length of type_encoding.  */
889                       while (*method_name == *length_ptr && *length_ptr)
890                           length_ptr++, method_name++;
891                       if (! strncmp (method_name,
892                                      IDENTIFIER_POINTER (type_encoding),
893                                      type_identifier_length))
894                         method_name += type_identifier_length;
895                       debug_name = method_name;
896                     }
897                 }
898               /* Detect constructors by their style of name mangling.  */
899               else if (debug_name[0] == '_' && debug_name[1] == '_')
900                 {
901                   char *ctor_name = debug_name + 2;
902                   char *length_ptr = formatted_type_identifier_length;
903                   while (*ctor_name == 'C' || *ctor_name == 'V')
904                     ctor_name++;
905                   /* Skip digits for length of type_encoding.  */
906                   while (*ctor_name == *length_ptr && *length_ptr)
907                       length_ptr++, ctor_name++;
908                   if (!strncmp (IDENTIFIER_POINTER (type_encoding), ctor_name,
909                                 type_identifier_length))
910                     debug_name = ctor_name + type_identifier_length;
911                 }
912               /* The other alternative is a destructor.  */
913               else
914                 show_arg_types = 1;
915
916               /* Output the operation name just once, for the first method
917                  that we output.  */
918               if (need_prefix)
919                 {
920                   fprintf (asmfile, "%s::", IDENTIFIER_POINTER (name));
921                   CHARS (IDENTIFIER_LENGTH (name) + 2);
922                   need_prefix = 0;
923                 }
924             }
925
926           dbxout_type (TREE_TYPE (fndecl), 0, show_arg_types);
927
928           dbxout_type_method_1 (fndecl, debug_name);
929         }
930       if (!need_prefix)
931         {
932           putc (';', asmfile);
933           CHARS (1);
934         }
935     }
936 }
937
938 /* Emit a "range" type specification, which has the form:
939    "r<index type>;<lower bound>;<upper bound>;".
940    TYPE is an INTEGER_TYPE.  */
941
942 static void
943 dbxout_range_type (type)
944      tree type;
945 {
946   fprintf (asmfile, "r");
947   if (TREE_TYPE (type))
948     dbxout_type (TREE_TYPE (type), 0, 0);
949   else if (TREE_CODE (type) != INTEGER_TYPE)
950     dbxout_type (type, 0, 0); /* E.g. Pascal's ARRAY [BOOLEAN] of INTEGER */
951   else
952     {
953       /* Traditionally, we made sure 'int' was type 1, and builtin types
954          were defined to be sub-ranges of int.  Unfortunately, this
955          does not allow us to distinguish true sub-ranges from integer
956          types.  So, instead we define integer (non-sub-range) types as
957          sub-ranges of themselves.  */
958       dbxout_type_index (type);
959     }
960   if (TREE_CODE (TYPE_MIN_VALUE (type)) == INTEGER_CST)
961     fprintf (asmfile, ";%d", 
962              TREE_INT_CST_LOW (TYPE_MIN_VALUE (type)));
963   else
964     fprintf (asmfile, ";0");
965   if (TYPE_MAX_VALUE (type) 
966       && TREE_CODE (TYPE_MAX_VALUE (type)) == INTEGER_CST)
967     fprintf (asmfile, ";%d;", 
968              TREE_INT_CST_LOW (TYPE_MAX_VALUE (type)));
969   else
970     fprintf (asmfile, ";-1;");
971 }
972 \f
973 /* Output a reference to a type.  If the type has not yet been
974    described in the dbx output, output its definition now.
975    For a type already defined, just refer to its definition
976    using the type number.
977
978    If FULL is nonzero, and the type has been described only with
979    a forward-reference, output the definition now.
980    If FULL is zero in this case, just refer to the forward-reference
981    using the number previously allocated.
982
983    If SHOW_ARG_TYPES is nonzero, we output a description of the argument
984    types for a METHOD_TYPE.  */
985
986 static void
987 dbxout_type (type, full, show_arg_types)
988      tree type;
989      int full;
990      int show_arg_types;
991 {
992   register tree tem;
993   static int anonymous_type_number = 0;
994
995   /* If there was an input error and we don't really have a type,
996      avoid crashing and write something that is at least valid
997      by assuming `int'.  */
998   if (type == error_mark_node)
999     type = integer_type_node;
1000   else
1001     {
1002       /* Try to find the "main variant" with the same name but not const
1003          or volatile.  (Since stabs does not distinguish const and volatile,
1004          there is no need to make them separate types.  But types with
1005          different names are usefully distinguished.) */
1006          
1007       for (tem = TYPE_MAIN_VARIANT (type); tem; tem = TYPE_NEXT_VARIANT (tem))
1008         if (!TYPE_READONLY (tem) && !TYPE_VOLATILE (tem)
1009             && TYPE_NAME (tem) == TYPE_NAME (type))
1010           {
1011             type = tem;
1012             break;
1013           }
1014       if (TYPE_NAME (type)
1015           && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
1016           && TYPE_DECL_SUPPRESS_DEBUG (TYPE_NAME (type)))
1017         full = 0;
1018     }
1019
1020   if (TYPE_SYMTAB_ADDRESS (type) == 0)
1021     {
1022       /* Type has no dbx number assigned.  Assign next available number.  */
1023       TYPE_SYMTAB_ADDRESS (type) = next_type_number++;
1024
1025       /* Make sure type vector is long enough to record about this type.  */
1026
1027       if (next_type_number == typevec_len)
1028         {
1029           typevec
1030             = (struct typeinfo *) xrealloc (typevec,
1031                                             typevec_len * 2 * sizeof typevec[0]);
1032           bzero ((char *) (typevec + typevec_len),
1033                  typevec_len * sizeof typevec[0]);
1034           typevec_len *= 2;
1035         }
1036
1037 #ifdef DBX_USE_BINCL
1038       typevec[TYPE_SYMTAB_ADDRESS (type)].file_number
1039         = current_file->file_number;
1040       typevec[TYPE_SYMTAB_ADDRESS (type)].type_number
1041         = current_file->next_type_number++;
1042 #endif
1043     }
1044
1045   /* Output the number of this type, to refer to it.  */
1046   dbxout_type_index (type);
1047
1048 #ifdef DBX_TYPE_DEFINED
1049   if (DBX_TYPE_DEFINED (type))
1050     return;
1051 #endif
1052
1053   /* If this type's definition has been output or is now being output,
1054      that is all.  */
1055
1056   switch (typevec[TYPE_SYMTAB_ADDRESS (type)].status)
1057     {
1058     case TYPE_UNSEEN:
1059       break;
1060     case TYPE_XREF:
1061       /* If we have already had a cross reference,
1062          and either that's all we want or that's the best we could do,
1063          don't repeat the cross reference.
1064          Sun dbx crashes if we do.  */
1065       if (! full || TYPE_SIZE (type) == 0
1066           /* No way in DBX fmt to describe a variable size.  */
1067           || TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
1068         return;
1069       break;
1070     case TYPE_DEFINED:
1071       return;
1072     }
1073
1074 #ifdef DBX_NO_XREFS
1075   /* For systems where dbx output does not allow the `=xsNAME:' syntax,
1076      leave the type-number completely undefined rather than output
1077      a cross-reference.  If we have already used GNU debug info extensions,
1078      then it is OK to output a cross reference.  This is necessary to get
1079      proper C++ debug output.  */
1080   if ((TREE_CODE (type) == RECORD_TYPE || TREE_CODE (type) == UNION_TYPE
1081        || TREE_CODE (type) == QUAL_UNION_TYPE
1082        || TREE_CODE (type) == ENUMERAL_TYPE)
1083       && ! use_gnu_debug_info_extensions)
1084     /* We must use the same test here as we use twice below when deciding
1085        whether to emit a cross-reference.  */
1086     if ((TYPE_NAME (type) != 0
1087          && ! (TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
1088                && DECL_IGNORED_P (TYPE_NAME (type)))
1089          && !full)
1090         || TYPE_SIZE (type) == 0
1091         /* No way in DBX fmt to describe a variable size.  */
1092         || TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
1093       {
1094         typevec[TYPE_SYMTAB_ADDRESS (type)].status = TYPE_XREF;
1095         return;
1096       }
1097 #endif
1098
1099   /* Output a definition now.  */
1100
1101   fprintf (asmfile, "=");
1102   CHARS (1);
1103
1104   /* Mark it as defined, so that if it is self-referent
1105      we will not get into an infinite recursion of definitions.  */
1106
1107   typevec[TYPE_SYMTAB_ADDRESS (type)].status = TYPE_DEFINED;
1108
1109   if (TYPE_NAME (type) && TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
1110       && DECL_ORIGINAL_TYPE (TYPE_NAME (type)))
1111     { 
1112       dbxout_type (DECL_ORIGINAL_TYPE (TYPE_NAME (type)), 0, 0);
1113       return;
1114     }
1115
1116   switch (TREE_CODE (type))
1117     {
1118     case VOID_TYPE:
1119     case LANG_TYPE:
1120       /* For a void type, just define it as itself; ie, "5=5".
1121          This makes us consider it defined
1122          without saying what it is.  The debugger will make it
1123          a void type when the reference is seen, and nothing will
1124          ever override that default.  */
1125       dbxout_type_index (type);
1126       break;
1127
1128     case INTEGER_TYPE:
1129       if (type == char_type_node && ! TREE_UNSIGNED (type))
1130         {
1131           /* Output the type `char' as a subrange of itself!
1132              I don't understand this definition, just copied it
1133              from the output of pcc.
1134              This used to use `r2' explicitly and we used to
1135              take care to make sure that `char' was type number 2.  */
1136           fprintf (asmfile, "r");
1137           dbxout_type_index (type);
1138           fprintf (asmfile, ";0;127;");
1139         }
1140       else if (use_gnu_debug_info_extensions
1141                && (TYPE_PRECISION (type) > TYPE_PRECISION (integer_type_node)
1142                    || TYPE_PRECISION (type) > HOST_BITS_PER_WIDE_INT))
1143         {
1144           /* This used to say `r1' and we used to take care
1145              to make sure that `int' was type number 1.  */
1146           fprintf (asmfile, "r");
1147           dbxout_type_index (integer_type_node);
1148           fprintf (asmfile, ";");
1149           print_int_cst_octal (TYPE_MIN_VALUE (type));
1150           fprintf (asmfile, ";");
1151           print_int_cst_octal (TYPE_MAX_VALUE (type));
1152           fprintf (asmfile, ";");
1153         }
1154       else /* Output other integer types as subranges of `int'.  */
1155         dbxout_range_type (type);
1156       CHARS (22);
1157       break;
1158
1159     case REAL_TYPE:
1160       /* This used to say `r1' and we used to take care
1161          to make sure that `int' was type number 1.  */
1162       fprintf (asmfile, "r");
1163       dbxout_type_index (integer_type_node);
1164       fprintf (asmfile, ";%d;0;", int_size_in_bytes (type));
1165       CHARS (13);
1166       break;
1167
1168     case CHAR_TYPE:
1169       if (use_gnu_debug_info_extensions)
1170         fprintf (asmfile, "@s%d;-20;",
1171                  BITS_PER_UNIT * int_size_in_bytes (type));
1172       else
1173         {
1174           /* Output the type `char' as a subrange of itself.
1175              That is what pcc seems to do.  */
1176           fprintf (asmfile, "r");
1177           dbxout_type_index (char_type_node);
1178           fprintf (asmfile, ";0;%d;", TREE_UNSIGNED (type) ? 255 : 127);
1179         }
1180       CHARS (9);
1181       break;
1182
1183     case BOOLEAN_TYPE:
1184       if (use_gnu_debug_info_extensions)
1185         fprintf (asmfile, "@s%d;-16;",
1186                  BITS_PER_UNIT * int_size_in_bytes (type));
1187       else /* Define as enumeral type (False, True) */
1188         fprintf (asmfile, "eFalse:0,True:1,;");
1189       CHARS (17);
1190       break;
1191
1192     case FILE_TYPE:
1193       putc ('d', asmfile);
1194       CHARS (1);
1195       dbxout_type (TREE_TYPE (type), 0, 0);
1196       break;
1197
1198     case COMPLEX_TYPE:
1199       /* Differs from the REAL_TYPE by its new data type number */
1200
1201       if (TREE_CODE (TREE_TYPE (type)) == REAL_TYPE)
1202         {
1203           fprintf (asmfile, "r");
1204           dbxout_type_index (type);
1205           fprintf (asmfile, ";%d;0;",
1206                    int_size_in_bytes (TREE_TYPE (type)));
1207           CHARS (12);           /* The number is probably incorrect here.  */
1208         }
1209       else
1210         {
1211           /* Output a complex integer type as a structure,
1212              pending some other way to do it.  */
1213           fprintf (asmfile, "s%d", int_size_in_bytes (type));
1214
1215           fprintf (asmfile, "real:");
1216           CHARS (10);
1217           dbxout_type (TREE_TYPE (type), 0, 0);
1218           fprintf (asmfile, ",%d,%d;",
1219                    0, TYPE_PRECISION (TREE_TYPE (type)));
1220           CHARS (8);
1221           fprintf (asmfile, "imag:");
1222           CHARS (5);
1223           dbxout_type (TREE_TYPE (type), 0, 0);
1224           fprintf (asmfile, ",%d,%d;;",
1225                    TYPE_PRECISION (TREE_TYPE (type)),
1226                    TYPE_PRECISION (TREE_TYPE (type)));
1227           CHARS (9);
1228         }
1229       break;
1230
1231     case SET_TYPE:
1232       if (use_gnu_debug_info_extensions)
1233         {
1234           have_used_extensions = 1;
1235           fprintf (asmfile, "@s%d;",
1236                    BITS_PER_UNIT * int_size_in_bytes (type));
1237           /* Check if a bitstring type, which in Chill is
1238              different from a [power]set.  */
1239           if (TYPE_STRING_FLAG (type))
1240             fprintf (asmfile, "@S;");
1241         }
1242       putc ('S', asmfile);
1243       CHARS (1);
1244       dbxout_type (TYPE_DOMAIN (type), 0, 0);
1245       break;
1246
1247     case ARRAY_TYPE:
1248       /* Output "a" followed by a range type definition
1249          for the index type of the array
1250          followed by a reference to the target-type.
1251          ar1;0;N;M for a C array of type M and size N+1.  */
1252       /* Check if a character string type, which in Chill is
1253          different from an array of characters.  */
1254       if (TYPE_STRING_FLAG (type) && use_gnu_debug_info_extensions)
1255         {
1256           have_used_extensions = 1;
1257           fprintf (asmfile, "@S;");
1258         }
1259       tem = TYPE_DOMAIN (type);
1260       if (tem == NULL)
1261         {
1262           fprintf (asmfile, "ar");
1263           dbxout_type_index (integer_type_node);
1264           fprintf (asmfile, ";0;-1;");
1265         }
1266       else
1267         {
1268           fprintf (asmfile, "a");
1269           dbxout_range_type (tem);
1270         }
1271       CHARS (14);
1272       dbxout_type (TREE_TYPE (type), 0, 0);
1273       break;
1274
1275     case RECORD_TYPE:
1276     case UNION_TYPE:
1277     case QUAL_UNION_TYPE:
1278       {
1279         int i, n_baseclasses = 0;
1280
1281         if (TYPE_BINFO (type) != 0
1282             && TREE_CODE (TYPE_BINFO (type)) == TREE_VEC
1283             && TYPE_BINFO_BASETYPES (type) != 0)
1284           n_baseclasses = TREE_VEC_LENGTH (TYPE_BINFO_BASETYPES (type));
1285
1286         /* Output a structure type.  We must use the same test here as we
1287            use in the DBX_NO_XREFS case above.  */
1288         if ((TYPE_NAME (type) != 0
1289              && ! (TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
1290                    && DECL_IGNORED_P (TYPE_NAME (type)))
1291              && !full)
1292             || TYPE_SIZE (type) == 0
1293             /* No way in DBX fmt to describe a variable size.  */
1294             || TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST)
1295           {
1296             /* If the type is just a cross reference, output one
1297                and mark the type as partially described.
1298                If it later becomes defined, we will output
1299                its real definition.
1300                If the type has a name, don't nest its definition within
1301                another type's definition; instead, output an xref
1302                and let the definition come when the name is defined.  */
1303             fprintf (asmfile, (TREE_CODE (type) == RECORD_TYPE) ? "xs" : "xu");
1304             CHARS (3);
1305 #if 0 /* This assertion is legitimately false in C++.  */
1306             /* We shouldn't be outputting a reference to a type before its
1307                definition unless the type has a tag name.
1308                A typedef name without a tag name should be impossible.  */
1309             if (TREE_CODE (TYPE_NAME (type)) != IDENTIFIER_NODE)
1310               abort ();
1311 #endif
1312             if (TYPE_NAME (type) != 0)
1313               dbxout_type_name (type);
1314             else
1315               fprintf (asmfile, "$$%d", anonymous_type_number++);
1316             fprintf (asmfile, ":");
1317             typevec[TYPE_SYMTAB_ADDRESS (type)].status = TYPE_XREF;
1318             break;
1319           }
1320
1321         /* Identify record or union, and print its size.  */
1322         fprintf (asmfile, (TREE_CODE (type) == RECORD_TYPE) ? "s%d" : "u%d",
1323                  int_size_in_bytes (type));
1324
1325         if (use_gnu_debug_info_extensions)
1326           {
1327             if (n_baseclasses)
1328               {
1329                 have_used_extensions = 1;
1330                 fprintf (asmfile, "!%d,", n_baseclasses);
1331                 CHARS (8);
1332               }
1333           }
1334         for (i = 0; i < n_baseclasses; i++)
1335           {
1336             tree child = TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO (type)), i);
1337             if (use_gnu_debug_info_extensions)
1338               {
1339                 have_used_extensions = 1;
1340                 putc (TREE_VIA_VIRTUAL (child) ? '1'
1341                       : '0',
1342                       asmfile);
1343                 putc (TREE_VIA_PUBLIC (child) ? '2'
1344                       : '0',
1345                       asmfile);
1346                 fprintf (asmfile, "%d,",
1347                          TREE_INT_CST_LOW (BINFO_OFFSET (child)) * BITS_PER_UNIT);
1348                 CHARS (15);
1349                 dbxout_type (BINFO_TYPE (child), 0, 0);
1350                 putc (';', asmfile);
1351               }
1352             else
1353               {
1354                 /* Print out the base class information with fields
1355                    which have the same names at the types they hold.  */
1356                 dbxout_type_name (BINFO_TYPE (child));
1357                 putc (':', asmfile);
1358                 dbxout_type (BINFO_TYPE (child), full, 0);
1359                 fprintf (asmfile, ",%d,%d;",
1360                          TREE_INT_CST_LOW (BINFO_OFFSET (child)) * BITS_PER_UNIT,
1361                          TREE_INT_CST_LOW (DECL_SIZE (TYPE_NAME (BINFO_TYPE (child)))) * BITS_PER_UNIT);
1362                 CHARS (20);
1363               }
1364           }
1365       }
1366
1367       CHARS (11);
1368
1369       /* Write out the field declarations.  */
1370       dbxout_type_fields (type);
1371       if (use_gnu_debug_info_extensions && TYPE_METHODS (type) != NULL_TREE)
1372         {
1373           have_used_extensions = 1;
1374           dbxout_type_methods (type);
1375         }
1376       putc (';', asmfile);
1377
1378       if (use_gnu_debug_info_extensions && TREE_CODE (type) == RECORD_TYPE
1379           /* Avoid the ~ if we don't really need it--it confuses dbx.  */
1380           && TYPE_VFIELD (type))
1381         {
1382           have_used_extensions = 1;
1383
1384           /* Tell GDB+ that it may keep reading.  */
1385           putc ('~', asmfile);
1386
1387           /* We need to write out info about what field this class
1388              uses as its "main" vtable pointer field, because if this
1389              field is inherited from a base class, GDB cannot necessarily
1390              figure out which field it's using in time.  */
1391           if (TYPE_VFIELD (type))
1392             {
1393               putc ('%', asmfile);
1394               dbxout_type (DECL_FCONTEXT (TYPE_VFIELD (type)), 0, 0);
1395             }
1396           putc (';', asmfile);
1397           CHARS (3);
1398         }
1399       break;
1400
1401     case ENUMERAL_TYPE:
1402       /* We must use the same test here as we use in the DBX_NO_XREFS case
1403          above.  We simplify it a bit since an enum will never have a variable
1404          size.  */
1405       if ((TYPE_NAME (type) != 0
1406            && ! (TREE_CODE (TYPE_NAME (type)) == TYPE_DECL
1407                  && DECL_IGNORED_P (TYPE_NAME (type)))
1408            && !full)
1409           || TYPE_SIZE (type) == 0)
1410         {
1411           fprintf (asmfile, "xe");
1412           CHARS (3);
1413           dbxout_type_name (type);
1414           typevec[TYPE_SYMTAB_ADDRESS (type)].status = TYPE_XREF;
1415           fprintf (asmfile, ":");
1416           return;
1417         }
1418 #ifdef DBX_OUTPUT_ENUM
1419       DBX_OUTPUT_ENUM (asmfile, type);
1420 #else
1421       if (use_gnu_debug_info_extensions
1422           && TYPE_PRECISION (type) != TYPE_PRECISION (integer_type_node))
1423         fprintf (asmfile, "@s%d;", TYPE_PRECISION (type));
1424       putc ('e', asmfile);
1425       CHARS (1);
1426       for (tem = TYPE_VALUES (type); tem; tem = TREE_CHAIN (tem))
1427         {
1428           fprintf (asmfile, "%s:", IDENTIFIER_POINTER (TREE_PURPOSE (tem)));
1429           if (TREE_INT_CST_HIGH (TREE_VALUE (tem)) == 0)
1430             fprintf (asmfile, "%lu",
1431                      (unsigned long) TREE_INT_CST_LOW (TREE_VALUE (tem)));
1432           else if (TREE_INT_CST_HIGH (TREE_VALUE (tem)) == -1
1433                    && TREE_INT_CST_LOW (TREE_VALUE (tem)) < 0)
1434             fprintf (asmfile, "%ld",
1435                      (long) TREE_INT_CST_LOW (TREE_VALUE (tem)));
1436           else
1437             print_int_cst_octal (TREE_VALUE (tem));
1438           fprintf (asmfile, ",");
1439           CHARS (20 + IDENTIFIER_LENGTH (TREE_PURPOSE (tem)));
1440           if (TREE_CHAIN (tem) != 0)
1441             CONTIN;
1442         }
1443       putc (';', asmfile);
1444       CHARS (1);
1445 #endif
1446       break;
1447
1448     case POINTER_TYPE:
1449       putc ('*', asmfile);
1450       CHARS (1);
1451       dbxout_type (TREE_TYPE (type), 0, 0);
1452       break;
1453
1454     case METHOD_TYPE:
1455       if (use_gnu_debug_info_extensions)
1456         {
1457           have_used_extensions = 1;
1458           putc ('#', asmfile);
1459           CHARS (1);
1460           if (flag_minimal_debug && !show_arg_types)
1461             {
1462               /* Normally, just output the return type.
1463                  The argument types are encoded in the method name.  */
1464               putc ('#', asmfile);
1465               CHARS (1);
1466               dbxout_type (TREE_TYPE (type), 0, 0);
1467               putc (';', asmfile);
1468               CHARS (1);
1469             }
1470           else
1471             {
1472               /* When outputting destructors, we need to write
1473                  the argument types out longhand.  */
1474               dbxout_type (TYPE_METHOD_BASETYPE (type), 0, 0);
1475               putc (',', asmfile);
1476               CHARS (1);
1477               dbxout_type (TREE_TYPE (type), 0, 0);
1478               dbxout_args (TYPE_ARG_TYPES (type));
1479               putc (';', asmfile);
1480               CHARS (1);
1481             }
1482         }
1483       else
1484         {
1485           /* Treat it as a function type.  */
1486           dbxout_type (TREE_TYPE (type), 0, 0);
1487         }
1488       break;
1489
1490     case OFFSET_TYPE:
1491       if (use_gnu_debug_info_extensions)
1492         {
1493           have_used_extensions = 1;
1494           putc ('@', asmfile);
1495           CHARS (1);
1496           dbxout_type (TYPE_OFFSET_BASETYPE (type), 0, 0);
1497           putc (',', asmfile);
1498           CHARS (1);
1499           dbxout_type (TREE_TYPE (type), 0, 0);
1500         }
1501       else
1502         {
1503           /* Should print as an int, because it is really
1504              just an offset.  */
1505           dbxout_type (integer_type_node, 0, 0);
1506         }
1507       break;
1508
1509     case REFERENCE_TYPE:
1510       if (use_gnu_debug_info_extensions)
1511         have_used_extensions = 1;
1512       putc (use_gnu_debug_info_extensions ? '&' : '*', asmfile);
1513       CHARS (1);
1514       dbxout_type (TREE_TYPE (type), 0, 0);
1515       break;
1516
1517     case FUNCTION_TYPE:
1518       putc ('f', asmfile);
1519       CHARS (1);
1520       dbxout_type (TREE_TYPE (type), 0, 0);
1521       break;
1522
1523     default:
1524       abort ();
1525     }
1526 }
1527
1528 /* Print the value of integer constant C, in octal,
1529    handling double precision.  */
1530
1531 static void
1532 print_int_cst_octal (c)
1533      tree c;
1534 {
1535   unsigned HOST_WIDE_INT high = TREE_INT_CST_HIGH (c);
1536   unsigned HOST_WIDE_INT low = TREE_INT_CST_LOW (c);
1537   int excess = (3 - (HOST_BITS_PER_WIDE_INT % 3));
1538   int width = TYPE_PRECISION (TREE_TYPE (c));
1539
1540   /* GDB wants constants with no extra leading "1" bits, so
1541      we need to remove any sign-extension that might be
1542      present.  */
1543   if (width == HOST_BITS_PER_WIDE_INT * 2)
1544     ;
1545   else if (width > HOST_BITS_PER_WIDE_INT)
1546     high &= (((HOST_WIDE_INT) 1 << (width - HOST_BITS_PER_WIDE_INT)) - 1);
1547   else if (width == HOST_BITS_PER_WIDE_INT)
1548     high = 0;
1549   else
1550     high = 0, low &= (((HOST_WIDE_INT) 1 << width) - 1);
1551
1552   fprintf (asmfile, "0");
1553
1554   if (excess == 3)
1555     {
1556       print_octal (high, HOST_BITS_PER_WIDE_INT / 3);
1557       print_octal (low, HOST_BITS_PER_WIDE_INT / 3);
1558     }
1559   else
1560     {
1561       unsigned HOST_WIDE_INT beg = high >> excess;
1562       unsigned HOST_WIDE_INT middle
1563         = ((high & (((HOST_WIDE_INT) 1 << excess) - 1)) << (3 - excess)
1564            | (low >> (HOST_BITS_PER_WIDE_INT / 3 * 3)));
1565       unsigned HOST_WIDE_INT end
1566         = low & (((unsigned HOST_WIDE_INT) 1
1567                   << (HOST_BITS_PER_WIDE_INT / 3 * 3))
1568                  - 1);
1569
1570       fprintf (asmfile, "%o%01o", beg, middle);
1571       print_octal (end, HOST_BITS_PER_WIDE_INT / 3);
1572     }
1573 }
1574
1575 static void
1576 print_octal (value, digits)
1577      unsigned HOST_WIDE_INT value;
1578      int digits;
1579 {
1580   int i;
1581
1582   for (i = digits - 1; i >= 0; i--)
1583     fprintf (asmfile, "%01o", ((value >> (3 * i)) & 7));
1584 }
1585
1586 /* Output the name of type TYPE, with no punctuation.
1587    Such names can be set up either by typedef declarations
1588    or by struct, enum and union tags.  */
1589
1590 static void
1591 dbxout_type_name (type)
1592      register tree type;
1593 {
1594   tree t;
1595   if (TYPE_NAME (type) == 0)
1596     abort ();
1597   if (TREE_CODE (TYPE_NAME (type)) == IDENTIFIER_NODE)
1598     {
1599       t = TYPE_NAME (type);
1600     }
1601   else if (TREE_CODE (TYPE_NAME (type)) == TYPE_DECL)
1602     {
1603       t = DECL_NAME (TYPE_NAME (type));
1604     }
1605   else
1606     abort ();
1607
1608   fprintf (asmfile, "%s", IDENTIFIER_POINTER (t));
1609   CHARS (IDENTIFIER_LENGTH (t));
1610 }
1611 \f
1612 /* Output a .stabs for the symbol defined by DECL,
1613    which must be a ..._DECL node in the normal namespace.
1614    It may be a CONST_DECL, a FUNCTION_DECL, a PARM_DECL or a VAR_DECL.
1615    LOCAL is nonzero if the scope is less than the entire file.  */
1616
1617 void
1618 dbxout_symbol (decl, local)
1619      tree decl;
1620      int local;
1621 {
1622   tree type = TREE_TYPE (decl);
1623   tree context = NULL_TREE;
1624
1625   /* Cast avoids warning in old compilers.  */
1626   current_sym_code = (STAB_CODE_TYPE) 0;
1627   current_sym_value = 0;
1628   current_sym_addr = 0;
1629
1630   /* Ignore nameless syms, but don't ignore type tags.  */
1631
1632   if ((DECL_NAME (decl) == 0 && TREE_CODE (decl) != TYPE_DECL)
1633       || DECL_IGNORED_P (decl))
1634     return;
1635
1636   dbxout_prepare_symbol (decl);
1637
1638   /* The output will always start with the symbol name,
1639      so always count that in the length-output-so-far.  */
1640
1641   if (DECL_NAME (decl) != 0)
1642     current_sym_nchars = 2 + IDENTIFIER_LENGTH (DECL_NAME (decl));
1643
1644   switch (TREE_CODE (decl))
1645     {
1646     case CONST_DECL:
1647       /* Enum values are defined by defining the enum type.  */
1648       break;
1649
1650     case FUNCTION_DECL:
1651       if (DECL_RTL (decl) == 0)
1652         return;
1653       if (DECL_EXTERNAL (decl))
1654         break;
1655       /* Don't mention a nested function under its parent.  */
1656       context = decl_function_context (decl);
1657       if (context == current_function_decl)
1658         break;
1659       if (GET_CODE (DECL_RTL (decl)) != MEM
1660           || GET_CODE (XEXP (DECL_RTL (decl), 0)) != SYMBOL_REF)
1661         break;
1662       FORCE_TEXT;
1663
1664       fprintf (asmfile, "%s \"%s:%c", ASM_STABS_OP,
1665                IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)),
1666                TREE_PUBLIC (decl) ? 'F' : 'f');
1667
1668       current_sym_code = N_FUN;
1669       current_sym_addr = XEXP (DECL_RTL (decl), 0);
1670
1671       if (TREE_TYPE (type))
1672         dbxout_type (TREE_TYPE (type), 0, 0);
1673       else
1674         dbxout_type (void_type_node, 0, 0);
1675
1676       /* For a nested function, when that function is compiled,
1677          mention the containing function name
1678          as well as (since dbx wants it) our own assembler-name.  */
1679       if (context != 0)
1680         fprintf (asmfile, ",%s,%s",
1681                  IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl)),
1682                  IDENTIFIER_POINTER (DECL_NAME (context)));
1683
1684       dbxout_finish_symbol (decl);
1685       break;
1686
1687     case TYPE_DECL:
1688 #if 0
1689       /* This seems all wrong.  Outputting most kinds of types gives no name
1690          at all.  A true definition gives no name; a cross-ref for a
1691          structure can give the tag name, but not a type name.
1692          It seems that no typedef name is defined by outputting a type.  */
1693
1694       /* If this typedef name was defined by outputting the type,
1695          don't duplicate it.  */
1696       if (typevec[TYPE_SYMTAB_ADDRESS (type)].status == TYPE_DEFINED
1697           && TYPE_NAME (TREE_TYPE (decl)) == decl)
1698         return;
1699 #endif
1700       /* Don't output the same typedef twice.
1701          And don't output what language-specific stuff doesn't want output.  */
1702       if (TREE_ASM_WRITTEN (decl) || TYPE_DECL_SUPPRESS_DEBUG (decl))
1703         return;
1704
1705       FORCE_TEXT;
1706
1707       {
1708         int tag_needed = 1;
1709         int did_output = 0;
1710
1711         if (DECL_NAME (decl))
1712           {
1713             /* Nonzero means we must output a tag as well as a typedef.  */
1714             tag_needed = 0;
1715
1716             /* Handle the case of a C++ structure or union
1717                where the TYPE_NAME is a TYPE_DECL
1718                which gives both a typedef name and a tag.  */
1719             /* dbx requires the tag first and the typedef second.  */
1720             if ((TREE_CODE (type) == RECORD_TYPE
1721                  || TREE_CODE (type) == UNION_TYPE
1722                  || TREE_CODE (type) == QUAL_UNION_TYPE)
1723                 && TYPE_NAME (type) == decl
1724                 && !(use_gnu_debug_info_extensions && have_used_extensions)
1725                 && !TREE_ASM_WRITTEN (TYPE_NAME (type))
1726                 /* Distinguish the implicit typedefs of C++
1727                    from explicit ones that might be found in C.  */
1728                 && DECL_ARTIFICIAL (decl))
1729               {
1730                 tree name = TYPE_NAME (type);
1731                 if (TREE_CODE (name) == TYPE_DECL)
1732                   name = DECL_NAME (name);
1733
1734                 current_sym_code = DBX_TYPE_DECL_STABS_CODE;
1735                 current_sym_value = 0;
1736                 current_sym_addr = 0;
1737                 current_sym_nchars = 2 + IDENTIFIER_LENGTH (name);
1738
1739                 fprintf (asmfile, "%s \"%s:T", ASM_STABS_OP,
1740                          IDENTIFIER_POINTER (name));
1741                 dbxout_type (type, 1, 0);
1742                 dbxout_finish_symbol (NULL_TREE);
1743               }
1744
1745             /* Output typedef name.  */
1746             fprintf (asmfile, "%s \"%s:", ASM_STABS_OP,
1747                      IDENTIFIER_POINTER (DECL_NAME (decl)));
1748
1749             /* Short cut way to output a tag also.  */
1750             if ((TREE_CODE (type) == RECORD_TYPE
1751                  || TREE_CODE (type) == UNION_TYPE
1752                  || TREE_CODE (type) == QUAL_UNION_TYPE)
1753                 && TYPE_NAME (type) == decl
1754                 /* Distinguish the implicit typedefs of C++
1755                    from explicit ones that might be found in C.  */
1756                 && DECL_ARTIFICIAL (decl))
1757               {
1758                 if (use_gnu_debug_info_extensions && have_used_extensions)
1759                   {
1760                     putc ('T', asmfile);
1761                     TREE_ASM_WRITTEN (TYPE_NAME (type)) = 1;
1762                   }
1763 #if 0 /* Now we generate the tag for this case up above.  */
1764                 else
1765                   tag_needed = 1;
1766 #endif
1767               }
1768
1769             putc ('t', asmfile);
1770             current_sym_code = DBX_TYPE_DECL_STABS_CODE;
1771
1772             dbxout_type (type, 1, 0);
1773             dbxout_finish_symbol (decl);
1774             did_output = 1;
1775           }
1776
1777         /* Don't output a tag if this is an incomplete type (TYPE_SIZE is
1778            zero).  This prevents the sun4 Sun OS 4.x dbx from crashing.  */ 
1779
1780         if (tag_needed && TYPE_NAME (type) != 0
1781             && (TREE_CODE (TYPE_NAME (type)) == IDENTIFIER_NODE
1782                 || (DECL_NAME (TYPE_NAME (type)) != 0))
1783             && TYPE_SIZE (type) != 0
1784             && !TREE_ASM_WRITTEN (TYPE_NAME (type)))
1785           {
1786             /* For a TYPE_DECL with no name, but the type has a name,
1787                output a tag.
1788                This is what represents `struct foo' with no typedef.  */
1789             /* In C++, the name of a type is the corresponding typedef.
1790                In C, it is an IDENTIFIER_NODE.  */
1791             tree name = TYPE_NAME (type);
1792             if (TREE_CODE (name) == TYPE_DECL)
1793               name = DECL_NAME (name);
1794
1795             current_sym_code = DBX_TYPE_DECL_STABS_CODE;
1796             current_sym_value = 0;
1797             current_sym_addr = 0;
1798             current_sym_nchars = 2 + IDENTIFIER_LENGTH (name);
1799
1800             fprintf (asmfile, "%s \"%s:T", ASM_STABS_OP,
1801                      IDENTIFIER_POINTER (name));
1802             dbxout_type (type, 1, 0);
1803             dbxout_finish_symbol (NULL_TREE);
1804             did_output = 1;
1805           }
1806
1807         /* If an enum type has no name, it cannot be referred to,
1808            but we must output it anyway, since the enumeration constants
1809            can be referred to.  */
1810         if (!did_output && TREE_CODE (type) == ENUMERAL_TYPE)
1811           {
1812             current_sym_code = DBX_TYPE_DECL_STABS_CODE;
1813             current_sym_value = 0;
1814             current_sym_addr = 0;
1815             current_sym_nchars = 2;
1816
1817             /* Some debuggers fail when given NULL names, so give this a
1818                harmless name of ` '.  */
1819             fprintf (asmfile, "%s \" :T", ASM_STABS_OP);
1820             dbxout_type (type, 1, 0);
1821             dbxout_finish_symbol (NULL_TREE);
1822           }
1823
1824         /* Prevent duplicate output of a typedef.  */
1825         TREE_ASM_WRITTEN (decl) = 1;
1826         break;
1827       }
1828
1829     case PARM_DECL:
1830       /* Parm decls go in their own separate chains
1831          and are output by dbxout_reg_parms and dbxout_parms.  */
1832       abort ();
1833
1834     case RESULT_DECL:
1835       /* Named return value, treat like a VAR_DECL.  */
1836     case VAR_DECL:
1837       if (DECL_RTL (decl) == 0)
1838         return;
1839       /* Don't mention a variable that is external.
1840          Let the file that defines it describe it.  */
1841       if (DECL_EXTERNAL (decl))
1842         break;
1843
1844       /* If the variable is really a constant
1845          and not written in memory, inform the debugger.  */
1846       if (TREE_STATIC (decl) && TREE_READONLY (decl)
1847           && DECL_INITIAL (decl) != 0
1848           && ! TREE_ASM_WRITTEN (decl)
1849           && (DECL_FIELD_CONTEXT (decl) == NULL_TREE
1850               || TREE_CODE (DECL_FIELD_CONTEXT (decl)) == BLOCK))
1851         {
1852           if (TREE_PUBLIC (decl) == 0)
1853             {
1854               /* The sun4 assembler does not grok this.  */
1855               char *name = IDENTIFIER_POINTER (DECL_NAME (decl));
1856               if (TREE_CODE (TREE_TYPE (decl)) == INTEGER_TYPE
1857                   || TREE_CODE (TREE_TYPE (decl)) == ENUMERAL_TYPE)
1858                 {
1859                   HOST_WIDE_INT ival = TREE_INT_CST_LOW (DECL_INITIAL (decl));
1860 #ifdef DBX_OUTPUT_CONSTANT_SYMBOL
1861                   DBX_OUTPUT_CONSTANT_SYMBOL (asmfile, name, ival);
1862 #else
1863                   fprintf (asmfile, "%s \"%s:c=i%d\",0x%x,0,0,0\n",
1864                            ASM_STABS_OP, name, ival, N_LSYM);
1865 #endif
1866                   return;
1867                 }
1868               else if (TREE_CODE (TREE_TYPE (decl)) == REAL_TYPE)
1869                 {
1870                   /* don't know how to do this yet.  */
1871                 }
1872               break;
1873             }
1874           /* else it is something we handle like a normal variable.  */
1875         }
1876
1877       DECL_RTL (decl) = eliminate_regs (DECL_RTL (decl), 0, NULL_RTX);
1878 #ifdef LEAF_REG_REMAP
1879       if (leaf_function)
1880         leaf_renumber_regs_insn (DECL_RTL (decl));
1881 #endif
1882
1883       dbxout_symbol_location (decl, type, 0, DECL_RTL (decl));
1884       break;
1885       
1886     default:
1887       break;
1888     }
1889 }
1890 \f
1891 /* Output the stab for DECL, a VAR_DECL, RESULT_DECL or PARM_DECL.
1892    Add SUFFIX to its name, if SUFFIX is not 0.
1893    Describe the variable as residing in HOME
1894    (usually HOME is DECL_RTL (DECL), but not always).  */
1895
1896 static void
1897 dbxout_symbol_location (decl, type, suffix, home)
1898      tree decl, type;
1899      char *suffix;
1900      rtx home;
1901 {
1902   int letter = 0;
1903   int regno = -1;
1904
1905   /* Don't mention a variable at all
1906      if it was completely optimized into nothingness.
1907      
1908      If the decl was from an inline function, then it's rtl
1909      is not identically the rtl that was used in this
1910      particular compilation.  */
1911   if (GET_CODE (home) == REG)
1912     {
1913       regno = REGNO (home);
1914       if (regno >= FIRST_PSEUDO_REGISTER)
1915         return;
1916     }
1917   else if (GET_CODE (home) == SUBREG)
1918     {
1919       rtx value = home;
1920       int offset = 0;
1921       while (GET_CODE (value) == SUBREG)
1922         {
1923           offset += SUBREG_WORD (value);
1924           value = SUBREG_REG (value);
1925         }
1926       if (GET_CODE (value) == REG)
1927         {
1928           regno = REGNO (value);
1929           if (regno >= FIRST_PSEUDO_REGISTER)
1930             return;
1931           regno += offset;
1932         }
1933       alter_subreg (home);
1934     }
1935
1936   /* The kind-of-variable letter depends on where
1937      the variable is and on the scope of its name:
1938      G and N_GSYM for static storage and global scope,
1939      S for static storage and file scope,
1940      V for static storage and local scope,
1941      for those two, use N_LCSYM if data is in bss segment,
1942      N_STSYM if in data segment, N_FUN otherwise.
1943      (We used N_FUN originally, then changed to N_STSYM
1944      to please GDB.  However, it seems that confused ld.
1945      Now GDB has been fixed to like N_FUN, says Kingdon.)
1946      no letter at all, and N_LSYM, for auto variable,
1947      r and N_RSYM for register variable.  */
1948
1949   if (GET_CODE (home) == MEM
1950       && GET_CODE (XEXP (home, 0)) == SYMBOL_REF)
1951     {
1952       if (TREE_PUBLIC (decl))
1953         {
1954           letter = 'G';
1955           current_sym_code = N_GSYM;
1956         }
1957       else
1958         {
1959           current_sym_addr = XEXP (home, 0);
1960
1961           letter = decl_function_context (decl) ? 'V' : 'S';
1962
1963           /* This should be the same condition as in assemble_variable, but
1964              we don't have access to dont_output_data here.  So, instead,
1965              we rely on the fact that error_mark_node initializers always
1966              end up in bss for C++ and never end up in bss for C.  */
1967           if (DECL_INITIAL (decl) == 0
1968               || (!strcmp (lang_identify (), "cplusplus")
1969                   && DECL_INITIAL (decl) == error_mark_node))
1970             current_sym_code = N_LCSYM;
1971           else if (DECL_IN_TEXT_SECTION (decl))
1972             /* This is not quite right, but it's the closest
1973                of all the codes that Unix defines.  */
1974             current_sym_code = DBX_STATIC_CONST_VAR_CODE;
1975           else
1976             {
1977               /* Ultrix `as' seems to need this.  */
1978 #ifdef DBX_STATIC_STAB_DATA_SECTION
1979               data_section ();
1980 #endif
1981               current_sym_code = N_STSYM;
1982             }
1983         }
1984     }
1985   else if (regno >= 0)
1986     {
1987       letter = 'r';
1988       current_sym_code = N_RSYM;
1989       current_sym_value = DBX_REGISTER_NUMBER (regno);
1990     }
1991   else if (GET_CODE (home) == MEM
1992            && (GET_CODE (XEXP (home, 0)) == MEM
1993                || (GET_CODE (XEXP (home, 0)) == REG
1994                    && REGNO (XEXP (home, 0)) != HARD_FRAME_POINTER_REGNUM
1995                    && REGNO (XEXP (home, 0)) != STACK_POINTER_REGNUM
1996 #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM
1997                    && REGNO (XEXP (home, 0)) != ARG_POINTER_REGNUM
1998 #endif
1999                    )))
2000     /* If the value is indirect by memory or by a register
2001        that isn't the frame pointer
2002        then it means the object is variable-sized and address through
2003        that register or stack slot.  DBX has no way to represent this
2004        so all we can do is output the variable as a pointer.
2005        If it's not a parameter, ignore it.
2006        (VAR_DECLs like this can be made by integrate.c.)  */
2007     {
2008       if (GET_CODE (XEXP (home, 0)) == REG)
2009         {
2010           letter = 'r';
2011           current_sym_code = N_RSYM;
2012           current_sym_value = DBX_REGISTER_NUMBER (REGNO (XEXP (home, 0)));
2013         }
2014       else
2015         {
2016           current_sym_code = N_LSYM;
2017           /* RTL looks like (MEM (MEM (PLUS (REG...) (CONST_INT...)))).
2018              We want the value of that CONST_INT.  */
2019           current_sym_value
2020             = DEBUGGER_AUTO_OFFSET (XEXP (XEXP (home, 0), 0));
2021         }
2022
2023       /* Effectively do build_pointer_type, but don't cache this type,
2024          since it might be temporary whereas the type it points to
2025          might have been saved for inlining.  */
2026       /* Don't use REFERENCE_TYPE because dbx can't handle that.  */
2027       type = make_node (POINTER_TYPE);
2028       TREE_TYPE (type) = TREE_TYPE (decl);
2029     }
2030   else if (GET_CODE (home) == MEM
2031            && GET_CODE (XEXP (home, 0)) == REG)
2032     {
2033       current_sym_code = N_LSYM;
2034       current_sym_value = DEBUGGER_AUTO_OFFSET (XEXP (home, 0));
2035     }
2036   else if (GET_CODE (home) == MEM
2037            && GET_CODE (XEXP (home, 0)) == PLUS
2038            && GET_CODE (XEXP (XEXP (home, 0), 1)) == CONST_INT)
2039     {
2040       current_sym_code = N_LSYM;
2041       /* RTL looks like (MEM (PLUS (REG...) (CONST_INT...)))
2042          We want the value of that CONST_INT.  */
2043       current_sym_value = DEBUGGER_AUTO_OFFSET (XEXP (home, 0));
2044     }
2045   else if (GET_CODE (home) == MEM
2046            && GET_CODE (XEXP (home, 0)) == CONST)
2047     {
2048       /* Handle an obscure case which can arise when optimizing and
2049          when there are few available registers.  (This is *always*
2050          the case for i386/i486 targets).  The RTL looks like
2051          (MEM (CONST ...)) even though this variable is a local `auto'
2052          or a local `register' variable.  In effect, what has happened
2053          is that the reload pass has seen that all assignments and
2054          references for one such a local variable can be replaced by
2055          equivalent assignments and references to some static storage
2056          variable, thereby avoiding the need for a register.  In such
2057          cases we're forced to lie to debuggers and tell them that
2058          this variable was itself `static'.  */
2059       current_sym_code = N_LCSYM;
2060       letter = 'V';
2061       current_sym_addr = XEXP (XEXP (home, 0), 0);
2062     }
2063   else if (GET_CODE (home) == CONCAT)
2064     {
2065       tree subtype = TREE_TYPE (type);
2066
2067       /* If the variable's storage is in two parts,
2068          output each as a separate stab with a modified name.  */
2069       if (WORDS_BIG_ENDIAN)
2070         dbxout_symbol_location (decl, subtype, "$imag", XEXP (home, 0));
2071       else
2072         dbxout_symbol_location (decl, subtype, "$real", XEXP (home, 0));
2073
2074       /* Cast avoids warning in old compilers.  */
2075       current_sym_code = (STAB_CODE_TYPE) 0;
2076       current_sym_value = 0;
2077       current_sym_addr = 0;
2078       dbxout_prepare_symbol (decl);
2079
2080       if (WORDS_BIG_ENDIAN)
2081         dbxout_symbol_location (decl, subtype, "$real", XEXP (home, 1));
2082       else
2083         dbxout_symbol_location (decl, subtype, "$imag", XEXP (home, 1));
2084       return;
2085     }
2086   else
2087     /* Address might be a MEM, when DECL is a variable-sized object.
2088        Or it might be const0_rtx, meaning previous passes
2089        want us to ignore this variable.  */
2090     return;
2091
2092   /* Ok, start a symtab entry and output the variable name.  */
2093   FORCE_TEXT;
2094
2095 #ifdef DBX_STATIC_BLOCK_START
2096   DBX_STATIC_BLOCK_START (asmfile, current_sym_code);
2097 #endif
2098
2099   dbxout_symbol_name (decl, suffix, letter);
2100   dbxout_type (type, 0, 0);
2101   dbxout_finish_symbol (decl);
2102
2103 #ifdef DBX_STATIC_BLOCK_END
2104   DBX_STATIC_BLOCK_END (asmfile, current_sym_code);
2105 #endif
2106 }
2107 \f
2108 /* Output the symbol name of DECL for a stabs, with suffix SUFFIX.
2109    Then output LETTER to indicate the kind of location the symbol has.  */
2110
2111 static void
2112 dbxout_symbol_name (decl, suffix, letter)
2113      tree decl;
2114      char *suffix;
2115      int letter;
2116 {
2117   /* One slight hitch: if this is a VAR_DECL which is a static
2118      class member, we must put out the mangled name instead of the
2119      DECL_NAME.  Note also that static member (variable) names DO NOT begin
2120      with underscores in .stabs directives.  */
2121   char *name = IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (decl));
2122   if (name == 0)
2123     name = "(anon)";
2124   fprintf (asmfile, "%s \"%s%s:", ASM_STABS_OP, name,
2125            (suffix ? suffix : ""));
2126
2127   if (letter) putc (letter, asmfile);
2128 }
2129
2130 static void
2131 dbxout_prepare_symbol (decl)
2132      tree decl;
2133 {
2134 #ifdef WINNING_GDB
2135   char *filename = DECL_SOURCE_FILE (decl);
2136
2137   dbxout_source_file (asmfile, filename);
2138 #endif
2139 }
2140
2141 static void
2142 dbxout_finish_symbol (sym)
2143      tree sym;
2144 {
2145 #ifdef DBX_FINISH_SYMBOL
2146   DBX_FINISH_SYMBOL (sym);
2147 #else
2148   int line = 0;
2149   if (use_gnu_debug_info_extensions && sym != 0)
2150     line = DECL_SOURCE_LINE (sym);
2151
2152   fprintf (asmfile, "\",%d,0,%d,", current_sym_code, line);
2153   if (current_sym_addr)
2154     output_addr_const (asmfile, current_sym_addr);
2155   else
2156     fprintf (asmfile, "%d", current_sym_value);
2157   putc ('\n', asmfile);
2158 #endif
2159 }
2160
2161 /* Output definitions of all the decls in a chain.  */
2162
2163 void
2164 dbxout_syms (syms)
2165      tree syms;
2166 {
2167   while (syms)
2168     {
2169       dbxout_symbol (syms, 1);
2170       syms = TREE_CHAIN (syms);
2171     }
2172 }
2173 \f
2174 /* The following two functions output definitions of function parameters.
2175    Each parameter gets a definition locating it in the parameter list.
2176    Each parameter that is a register variable gets a second definition
2177    locating it in the register.
2178
2179    Printing or argument lists in gdb uses the definitions that
2180    locate in the parameter list.  But reference to the variable in
2181    expressions uses preferentially the definition as a register.  */
2182
2183 /* Output definitions, referring to storage in the parmlist,
2184    of all the parms in PARMS, which is a chain of PARM_DECL nodes.  */
2185
2186 void
2187 dbxout_parms (parms)
2188      tree parms;
2189 {
2190   for (; parms; parms = TREE_CHAIN (parms))
2191     if (DECL_NAME (parms) && TREE_TYPE (parms) != error_mark_node)
2192       {
2193         dbxout_prepare_symbol (parms);
2194
2195         /* Perform any necessary register eliminations on the parameter's rtl,
2196            so that the debugging output will be accurate.  */
2197         DECL_INCOMING_RTL (parms)
2198           = eliminate_regs (DECL_INCOMING_RTL (parms), 0, NULL_RTX);
2199         DECL_RTL (parms) = eliminate_regs (DECL_RTL (parms), 0, NULL_RTX);
2200 #ifdef LEAF_REG_REMAP
2201         if (leaf_function)
2202           {
2203             leaf_renumber_regs_insn (DECL_INCOMING_RTL (parms));
2204             leaf_renumber_regs_insn (DECL_RTL (parms));
2205           }
2206 #endif
2207
2208         if (PARM_PASSED_IN_MEMORY (parms))
2209           {
2210             rtx addr = XEXP (DECL_INCOMING_RTL (parms), 0);
2211
2212             /* ??? Here we assume that the parm address is indexed
2213                off the frame pointer or arg pointer.
2214                If that is not true, we produce meaningless results,
2215                but do not crash.  */
2216             if (GET_CODE (addr) == PLUS
2217                 && GET_CODE (XEXP (addr, 1)) == CONST_INT)
2218               current_sym_value = INTVAL (XEXP (addr, 1));
2219             else
2220               current_sym_value = 0;
2221
2222             current_sym_code = N_PSYM;
2223             current_sym_addr = 0;
2224
2225             FORCE_TEXT;
2226             if (DECL_NAME (parms))
2227               {
2228                 current_sym_nchars = 2 + IDENTIFIER_LENGTH (DECL_NAME (parms));
2229
2230                 fprintf (asmfile, "%s \"%s:%c", ASM_STABS_OP,
2231                          IDENTIFIER_POINTER (DECL_NAME (parms)),
2232                          DBX_MEMPARM_STABS_LETTER);
2233               }
2234             else
2235               {
2236                 current_sym_nchars = 8;
2237                 fprintf (asmfile, "%s \"(anon):%c", ASM_STABS_OP,
2238                          DBX_MEMPARM_STABS_LETTER);
2239               }
2240
2241             dbxout_type (DECL_ARG_TYPE (parms), 0, 0);
2242             current_sym_value = DEBUGGER_ARG_OFFSET (current_sym_value, addr);
2243             dbxout_finish_symbol (parms);
2244           }
2245         else if (GET_CODE (DECL_RTL (parms)) == REG)
2246           {
2247             rtx best_rtl;
2248             char regparm_letter;
2249             tree parm_type;
2250             /* Parm passed in registers and lives in registers or nowhere.  */
2251
2252             current_sym_code = DBX_REGPARM_STABS_CODE;
2253             regparm_letter = DBX_REGPARM_STABS_LETTER;
2254             current_sym_addr = 0;
2255
2256             /* If parm lives in a register, use that register;
2257                pretend the parm was passed there.  It would be more consistent
2258                to describe the register where the parm was passed,
2259                but in practice that register usually holds something else.
2260
2261                If we use DECL_RTL, then we must use the declared type of
2262                the variable, not the type that it arrived in.  */
2263             if (REGNO (DECL_RTL (parms)) >= 0
2264                 && REGNO (DECL_RTL (parms)) < FIRST_PSEUDO_REGISTER)
2265               {
2266                 best_rtl = DECL_RTL (parms);
2267                 parm_type = TREE_TYPE (parms);
2268               }
2269             /* If the parm lives nowhere, use the register where it was
2270                passed.  It is also better to use the declared type here.  */
2271             else
2272               {
2273                 best_rtl = DECL_INCOMING_RTL (parms);
2274                 parm_type = TREE_TYPE (parms);
2275               }
2276             current_sym_value = DBX_REGISTER_NUMBER (REGNO (best_rtl));
2277
2278             FORCE_TEXT;
2279             if (DECL_NAME (parms))
2280               {
2281                 current_sym_nchars = 2 + IDENTIFIER_LENGTH (DECL_NAME (parms));
2282                 fprintf (asmfile, "%s \"%s:%c", ASM_STABS_OP,
2283                          IDENTIFIER_POINTER (DECL_NAME (parms)),
2284                          regparm_letter);
2285               }
2286             else
2287               {
2288                 current_sym_nchars = 8;
2289                 fprintf (asmfile, "%s \"(anon):%c", ASM_STABS_OP,
2290                          regparm_letter);
2291               }
2292
2293             dbxout_type (parm_type, 0, 0);
2294             dbxout_finish_symbol (parms);
2295           }
2296         else if (GET_CODE (DECL_RTL (parms)) == MEM
2297                  && GET_CODE (XEXP (DECL_RTL (parms), 0)) == REG
2298                  && REGNO (XEXP (DECL_RTL (parms), 0)) != HARD_FRAME_POINTER_REGNUM
2299                  && REGNO (XEXP (DECL_RTL (parms), 0)) != STACK_POINTER_REGNUM
2300 #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM
2301                  && REGNO (XEXP (DECL_RTL (parms), 0)) != ARG_POINTER_REGNUM
2302 #endif
2303                  )
2304           {
2305             /* Parm was passed via invisible reference.
2306                That is, its address was passed in a register.
2307                Output it as if it lived in that register.
2308                The debugger will know from the type
2309                that it was actually passed by invisible reference.  */
2310
2311             char regparm_letter;
2312             /* Parm passed in registers and lives in registers or nowhere.  */
2313
2314             current_sym_code = DBX_REGPARM_STABS_CODE;
2315             if (use_gnu_debug_info_extensions)
2316               regparm_letter = GDB_INV_REF_REGPARM_STABS_LETTER;
2317             else
2318               regparm_letter = DBX_REGPARM_STABS_LETTER;
2319
2320             /* DECL_RTL looks like (MEM (REG...).  Get the register number.
2321                If it is an unallocated pseudo-reg, then use the register where
2322                it was passed instead.  */
2323             if (REGNO (XEXP (DECL_RTL (parms), 0)) >= 0
2324                 && REGNO (XEXP (DECL_RTL (parms), 0)) < FIRST_PSEUDO_REGISTER)
2325               current_sym_value = REGNO (XEXP (DECL_RTL (parms), 0));
2326             else
2327               current_sym_value = REGNO (DECL_INCOMING_RTL (parms));
2328
2329             current_sym_addr = 0;
2330
2331             FORCE_TEXT;
2332             if (DECL_NAME (parms))
2333               {
2334                 current_sym_nchars = 2 + strlen (IDENTIFIER_POINTER (DECL_NAME (parms)));
2335
2336                 fprintf (asmfile, "%s \"%s:%c", ASM_STABS_OP,
2337                          IDENTIFIER_POINTER (DECL_NAME (parms)),
2338                          regparm_letter);
2339               }
2340             else
2341               {
2342                 current_sym_nchars = 8;
2343                 fprintf (asmfile, "%s \"(anon):%c", ASM_STABS_OP,
2344                          regparm_letter);
2345               }
2346
2347             dbxout_type (TREE_TYPE (parms), 0, 0);
2348             dbxout_finish_symbol (parms);
2349           }
2350         else if (GET_CODE (DECL_RTL (parms)) == MEM
2351                  && XEXP (DECL_RTL (parms), 0) != const0_rtx
2352                  /* ??? A constant address for a parm can happen
2353                     when the reg it lives in is equiv to a constant in memory.
2354                     Should make this not happen, after 2.4.  */
2355                  && ! CONSTANT_P (XEXP (DECL_RTL (parms), 0)))
2356           {
2357             /* Parm was passed in registers but lives on the stack.  */
2358
2359             current_sym_code = N_PSYM;
2360             /* DECL_RTL looks like (MEM (PLUS (REG...) (CONST_INT...))),
2361                in which case we want the value of that CONST_INT,
2362                or (MEM (REG ...)) or (MEM (MEM ...)),
2363                in which case we use a value of zero.  */
2364             if (GET_CODE (XEXP (DECL_RTL (parms), 0)) == REG
2365                 || GET_CODE (XEXP (DECL_RTL (parms), 0)) == MEM)
2366               current_sym_value = 0;
2367             else
2368               current_sym_value = INTVAL (XEXP (XEXP (DECL_RTL (parms), 0), 1));
2369             current_sym_addr = 0;
2370
2371             FORCE_TEXT;
2372             if (DECL_NAME (parms))
2373               {
2374                 current_sym_nchars = 2 + strlen (IDENTIFIER_POINTER (DECL_NAME (parms)));
2375
2376                 fprintf (asmfile, "%s \"%s:%c", ASM_STABS_OP,
2377                          IDENTIFIER_POINTER (DECL_NAME (parms)),
2378                          DBX_MEMPARM_STABS_LETTER);
2379               }
2380             else
2381               {
2382                 current_sym_nchars = 8;
2383                 fprintf (asmfile, "%s \"(anon):%c", ASM_STABS_OP,
2384                 DBX_MEMPARM_STABS_LETTER);
2385               }
2386
2387             current_sym_value
2388               = DEBUGGER_ARG_OFFSET (current_sym_value,
2389                                      XEXP (DECL_RTL (parms), 0));
2390             dbxout_type (TREE_TYPE (parms), 0, 0);
2391             dbxout_finish_symbol (parms);
2392           }
2393       }
2394 }
2395
2396 /* Output definitions for the places where parms live during the function,
2397    when different from where they were passed, when the parms were passed
2398    in memory.
2399
2400    It is not useful to do this for parms passed in registers
2401    that live during the function in different registers, because it is
2402    impossible to look in the passed register for the passed value,
2403    so we use the within-the-function register to begin with.
2404
2405    PARMS is a chain of PARM_DECL nodes.  */
2406
2407 void
2408 dbxout_reg_parms (parms)
2409      tree parms;
2410 {
2411   for (; parms; parms = TREE_CHAIN (parms))
2412     if (DECL_NAME (parms) && PARM_PASSED_IN_MEMORY (parms))
2413       {
2414         dbxout_prepare_symbol (parms);
2415
2416         /* Report parms that live in registers during the function
2417            but were passed in memory.  */
2418         if (GET_CODE (DECL_RTL (parms)) == REG
2419             && REGNO (DECL_RTL (parms)) >= 0
2420             && REGNO (DECL_RTL (parms)) < FIRST_PSEUDO_REGISTER)
2421           dbxout_symbol_location (parms, TREE_TYPE (parms),
2422                                   0, DECL_RTL (parms));
2423         else if (GET_CODE (DECL_RTL (parms)) == CONCAT)
2424           dbxout_symbol_location (parms, TREE_TYPE (parms),
2425                                   0, DECL_RTL (parms));
2426         /* Report parms that live in memory but not where they were passed.  */
2427         else if (GET_CODE (DECL_RTL (parms)) == MEM
2428                  && ! rtx_equal_p (DECL_RTL (parms), DECL_INCOMING_RTL (parms)))
2429           dbxout_symbol_location (parms, TREE_TYPE (parms),
2430                                   0, DECL_RTL (parms));
2431       }
2432 }
2433 \f
2434 /* Given a chain of ..._TYPE nodes (as come in a parameter list),
2435    output definitions of those names, in raw form */
2436
2437 void
2438 dbxout_args (args)
2439      tree args;
2440 {
2441   while (args)
2442     {
2443       putc (',', asmfile);
2444       dbxout_type (TREE_VALUE (args), 0, 0);
2445       CHARS (1);
2446       args = TREE_CHAIN (args);
2447     }
2448 }
2449 \f
2450 /* Given a chain of ..._TYPE nodes,
2451    find those which have typedef names and output those names.
2452    This is to ensure those types get output.  */
2453
2454 void
2455 dbxout_types (types)
2456      register tree types;
2457 {
2458   while (types)
2459     {
2460       if (TYPE_NAME (types)
2461           && TREE_CODE (TYPE_NAME (types)) == TYPE_DECL
2462           && ! TREE_ASM_WRITTEN (TYPE_NAME (types)))
2463         dbxout_symbol (TYPE_NAME (types), 1);
2464       types = TREE_CHAIN (types);
2465     }
2466 }
2467 \f
2468 /* Output everything about a symbol block (a BLOCK node
2469    that represents a scope level),
2470    including recursive output of contained blocks.
2471
2472    BLOCK is the BLOCK node.
2473    DEPTH is its depth within containing symbol blocks.
2474    ARGS is usually zero; but for the outermost block of the
2475    body of a function, it is a chain of PARM_DECLs for the function parameters.
2476    We output definitions of all the register parms
2477    as if they were local variables of that block.
2478
2479    If -g1 was used, we count blocks just the same, but output nothing
2480    except for the outermost block.
2481
2482    Actually, BLOCK may be several blocks chained together.
2483    We handle them all in sequence.  */
2484
2485 static void
2486 dbxout_block (block, depth, args)
2487      register tree block;
2488      int depth;
2489      tree args;
2490 {
2491   int blocknum;
2492
2493   while (block)
2494     {
2495       /* Ignore blocks never expanded or otherwise marked as real.  */
2496       if (TREE_USED (block))
2497         {
2498 #ifndef DBX_LBRAC_FIRST
2499           /* In dbx format, the syms of a block come before the N_LBRAC.  */
2500           if (debug_info_level != DINFO_LEVEL_TERSE || depth == 0)
2501             dbxout_syms (BLOCK_VARS (block));
2502           if (args)
2503             dbxout_reg_parms (args);
2504 #endif
2505
2506           /* Now output an N_LBRAC symbol to represent the beginning of
2507              the block.  Use the block's tree-walk order to generate
2508              the assembler symbols LBBn and LBEn
2509              that final will define around the code in this block.  */
2510           if (depth > 0 && debug_info_level != DINFO_LEVEL_TERSE)
2511             {
2512               char buf[20];
2513               blocknum = next_block_number++;
2514               ASM_GENERATE_INTERNAL_LABEL (buf, "LBB", blocknum);
2515
2516               if (BLOCK_HANDLER_BLOCK (block))
2517                 {
2518                   /* A catch block.  Must precede N_LBRAC.  */
2519                   tree decl = BLOCK_VARS (block);
2520                   while (decl)
2521                     {
2522 #ifdef DBX_OUTPUT_CATCH
2523                       DBX_OUTPUT_CATCH (asmfile, decl, buf);
2524 #else
2525                       fprintf (asmfile, "%s \"%s:C1\",%d,0,0,", ASM_STABS_OP,
2526                                IDENTIFIER_POINTER (DECL_NAME (decl)), N_CATCH);
2527                       assemble_name (asmfile, buf);
2528                       fprintf (asmfile, "\n");
2529 #endif
2530                       decl = TREE_CHAIN (decl);
2531                     }
2532                 }
2533
2534 #ifdef DBX_OUTPUT_LBRAC
2535               DBX_OUTPUT_LBRAC (asmfile, buf);
2536 #else
2537               fprintf (asmfile, "%s %d,0,0,", ASM_STABN_OP, N_LBRAC);
2538               assemble_name (asmfile, buf);
2539 #if DBX_BLOCKS_FUNCTION_RELATIVE
2540               fputc ('-', asmfile);
2541               assemble_name (asmfile, XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0));
2542 #endif
2543               fprintf (asmfile, "\n");
2544 #endif
2545             }
2546           else if (depth > 0)
2547             /* Count blocks the same way regardless of debug_info_level.  */
2548             next_block_number++;
2549
2550 #ifdef DBX_LBRAC_FIRST
2551           /* On some weird machines, the syms of a block
2552              come after the N_LBRAC.  */
2553           if (debug_info_level != DINFO_LEVEL_TERSE || depth == 0)
2554             dbxout_syms (BLOCK_VARS (block));
2555           if (args)
2556             dbxout_reg_parms (args);
2557 #endif
2558
2559           /* Output the subblocks.  */
2560           dbxout_block (BLOCK_SUBBLOCKS (block), depth + 1, NULL_TREE);
2561
2562           /* Refer to the marker for the end of the block.  */
2563           if (depth > 0 && debug_info_level != DINFO_LEVEL_TERSE)
2564             {
2565               char buf[20];
2566               ASM_GENERATE_INTERNAL_LABEL (buf, "LBE", blocknum);
2567 #ifdef DBX_OUTPUT_RBRAC
2568               DBX_OUTPUT_RBRAC (asmfile, buf);
2569 #else
2570               fprintf (asmfile, "%s %d,0,0,", ASM_STABN_OP, N_RBRAC);
2571               assemble_name (asmfile, buf);
2572 #if DBX_BLOCKS_FUNCTION_RELATIVE
2573               fputc ('-', asmfile);
2574               assemble_name (asmfile, XSTR (XEXP (DECL_RTL (current_function_decl), 0), 0));
2575 #endif
2576               fprintf (asmfile, "\n");
2577 #endif
2578             }
2579         }
2580       block = BLOCK_CHAIN (block);
2581     }
2582 }
2583
2584 /* Output the information about a function and its arguments and result.
2585    Usually this follows the function's code,
2586    but on some systems, it comes before.  */
2587
2588 static void
2589 dbxout_really_begin_function (decl)
2590      tree decl;
2591 {
2592   dbxout_symbol (decl, 0);
2593   dbxout_parms (DECL_ARGUMENTS (decl));
2594   if (DECL_NAME (DECL_RESULT (decl)) != 0)
2595     dbxout_symbol (DECL_RESULT (decl), 1);
2596 }
2597
2598 /* Called at beginning of output of function definition.  */
2599
2600 void
2601 dbxout_begin_function (decl)
2602      tree decl;
2603 {
2604 #ifdef DBX_FUNCTION_FIRST
2605   dbxout_really_begin_function (decl);
2606 #endif
2607 }
2608
2609 /* Output dbx data for a function definition.
2610    This includes a definition of the function name itself (a symbol),
2611    definitions of the parameters (locating them in the parameter list)
2612    and then output the block that makes up the function's body
2613    (including all the auto variables of the function).  */
2614
2615 void
2616 dbxout_function (decl)
2617      tree decl;
2618 {
2619 #ifndef DBX_FUNCTION_FIRST
2620   dbxout_really_begin_function (decl);
2621 #endif
2622   dbxout_block (DECL_INITIAL (decl), 0, DECL_ARGUMENTS (decl));
2623 #ifdef DBX_OUTPUT_FUNCTION_END
2624   DBX_OUTPUT_FUNCTION_END (asmfile, decl);
2625 #endif
2626 #if defined(ASM_OUTPUT_SECTION_NAME)
2627   if (use_gnu_debug_info_extensions
2628 #if defined(NO_DBX_FUNCTION_END)
2629       && ! NO_DBX_FUNCTION_END
2630 #endif
2631       )
2632     dbxout_function_end ();
2633 #endif
2634 }
2635 #endif /* DBX_DEBUGGING_INFO */