1 /* Generic stabs parsing for gas.
2 Copyright (C) 1989-2023 Free Software Foundation, Inc.
4 This file is part of GAS, the GNU Assembler.
6 GAS is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as
8 published by the Free Software Foundation; either version 3,
9 or (at your option) any later version.
11 GAS is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
14 the GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with GAS; see the file COPYING. If not, write to the Free
18 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
22 #include "filenames.h"
27 /* We need this, despite the apparent object format dependency, since
28 it defines stab types, which all object formats can use now. */
30 #include "aout/stab_gnu.h"
32 /* Holds whether the assembler is generating stabs line debugging
33 information or not. Potentially used by md_cleanup function. */
35 int outputting_stabs_line_debug
= 0;
37 static void generate_asm_file (int, const char *);
39 /* Allow backends to override the names used for the stab sections. */
40 #ifndef STAB_SECTION_NAME
41 #define STAB_SECTION_NAME ".stab"
44 #ifndef STAB_STRING_SECTION_NAME
45 #define STAB_STRING_SECTION_NAME ".stabstr"
48 /* Label at start of current function if we're in the middle of a
49 .func function, in which case stabs_generate_asm_lineno emits
50 function relative line number stabs. Otherwise it emits line
51 number stabs with absolute addresses. Note that both cases only
52 apply to assembler code assembled with -gstabs. */
53 static const char *current_function_label
;
55 /* Current stab section when SEPARATE_STAB_SECTIONS. */
56 static segT cached_sec
;
58 /* State used by generate_asm_file. */
59 static char *last_asm_file
;
60 static int file_label_count
;
62 /* State used by stabs_generate_asm_lineno. */
63 static int line_label_count
;
64 static unsigned int prev_lineno
;
65 static char *prev_line_file
;
67 /* State used by stabs_generate_asm_func. */
68 static bool void_emitted_p
;
70 /* State used by stabs_generate_asm_endfunc. */
71 static int endfunc_label_count
;
74 * Handle .stabX directives, which used to be open-coded.
75 * So much creeping featurism overloaded the semantics that we decided
76 * to put all .stabX thinking in one place. Here.
78 * We try to make any .stabX directive legal. Other people's AS will often
79 * do assembly-time consistency checks: eg assigning meaning to n_type bits
80 * and "protecting" you from setting them to certain values. (They also zero
81 * certain bits before emitting symbols. Tut tut.)
83 * If an expression is not absolute we either gripe or use the relocation
84 * information. Other people's assemblers silently forget information they
85 * don't need and invent information they need that you didn't supply.
89 * Build a string dictionary entry for a .stabX symbol.
90 * The symbol is added to the .<secname>str section.
93 #ifndef SEPARATE_STAB_SECTIONS
94 #define SEPARATE_STAB_SECTIONS 0
98 get_stab_string_offset (const char *string
, const char *stabstr_secname
,
99 bool free_stabstr_secname
)
108 if (! SEPARATE_STAB_SECTIONS
)
111 length
= strlen (string
);
114 save_subseg
= now_subseg
;
116 /* Create the stab string section, if it doesn't already exist. */
117 seg
= subseg_new (stabstr_secname
, 0);
118 if (free_stabstr_secname
&& seg
->name
!= stabstr_secname
)
119 free ((char *) stabstr_secname
);
121 retval
= seg_info (seg
)->stabu
.stab_string_size
;
124 /* Make sure the first string is empty. */
127 retval
= seg_info (seg
)->stabu
.stab_string_size
= 1;
128 bfd_set_section_flags (seg
, SEC_READONLY
| SEC_DEBUGGING
);
132 { /* Ordinary case. */
133 p
= frag_more (length
+ 1);
136 seg_info (seg
)->stabu
.stab_string_size
+= length
+ 1;
141 subseg_set (save_seg
, save_subseg
);
147 #ifndef OBJ_PROCESS_STAB
148 #define OBJ_PROCESS_STAB(SEG,W,S,T,O,D) aout_process_stab(W,S,T,O,D)
151 /* Here instead of obj-aout.c because other formats use it too. */
153 aout_process_stab (int what
, const char *string
, int type
, int other
, int desc
)
155 /* Put the stab information in the symbol table. */
158 /* Create the symbol now, but only insert it into the symbol chain
159 after any symbols mentioned in the value expression get into the
160 symbol chain. This is to avoid "continuation symbols" (where one
161 ends in "\" and the debug info is continued in the next .stabs
162 directive) from being separated by other random symbols. */
163 symbol
= symbol_create (string
, undefined_section
, &zero_address_frag
, 0);
164 if (what
== 's' || what
== 'n')
166 /* Pick up the value from the input line. */
171 /* .stabd sets the name to NULL. Why? */
172 S_SET_NAME (symbol
, NULL
);
173 symbol_set_frag (symbol
, frag_now
);
174 S_SET_VALUE (symbol
, (valueT
) frag_now_fix ());
177 symbol_append (symbol
, symbol_lastP
, &symbol_rootP
, &symbol_lastP
);
179 symbol_get_bfdsym (symbol
)->flags
|= BSF_DEBUGGING
;
181 S_SET_TYPE (symbol
, type
);
182 S_SET_OTHER (symbol
, other
);
183 S_SET_DESC (symbol
, desc
);
187 /* This can handle different kinds of stabs (s,n,d) and different
188 kinds of stab sections. If STAB_SECNAME_OBSTACK_END is non-NULL,
189 then STAB_SECNAME and STABSTR_SECNAME will be freed if possible
190 before this function returns (the former by obstack_free). */
193 s_stab_generic (int what
,
194 const char *stab_secname
,
195 const char *stabstr_secname
,
196 const char *stab_secname_obstack_end
)
200 char *saved_string_obstack_end
;
205 /* The general format is:
206 .stabs "STRING",TYPE,OTHER,DESC,VALUE
207 .stabn TYPE,OTHER,DESC,VALUE
208 .stabd TYPE,OTHER,DESC
209 At this point input_line_pointer points after the pseudo-op and
210 any trailing whitespace. The argument what is one of 's', 'n' or
211 'd' indicating which type of .stab this is. */
216 saved_string_obstack_end
= 0;
222 string
= demand_copy_C_string (&length
);
225 as_warn (_(".stab%c: missing string"), what
);
226 ignore_rest_of_line ();
229 /* FIXME: We should probably find some other temporary storage
230 for string, rather than leaking memory if someone else
231 happens to use the notes obstack. */
232 saved_string_obstack_end
= obstack_next_free (¬es
);
234 if (*input_line_pointer
== ',')
235 input_line_pointer
++;
238 as_warn (_(".stab%c: missing comma"), what
);
239 ignore_rest_of_line ();
244 if (get_absolute_expression_and_terminator (&longint
) != ',')
246 as_warn (_(".stab%c: missing comma"), what
);
247 ignore_rest_of_line ();
252 if (get_absolute_expression_and_terminator (&longint
) != ',')
254 as_warn (_(".stab%c: missing comma"), what
);
255 ignore_rest_of_line ();
260 desc
= get_absolute_expression ();
262 if ((desc
> 0xffff) || (desc
< -0x8000))
263 /* This could happen for example with a source file with a huge
264 number of lines. The only cure is to use a different debug
265 format, probably DWARF. */
266 as_warn (_(".stab%c: description field '%x' too big, try a different debug format"),
269 if (what
== 's' || what
== 'n')
271 if (*input_line_pointer
!= ',')
273 as_warn (_(".stab%c: missing comma"), what
);
274 ignore_rest_of_line ();
277 input_line_pointer
++;
283 /* Solaris on PowerPC has decided that .stabd can take 4 arguments, so if we were
284 given 4 arguments, make it a .stabn */
285 else if (what
== 'd')
287 char *save_location
= input_line_pointer
;
290 if (*input_line_pointer
== ',')
292 input_line_pointer
++;
296 input_line_pointer
= save_location
;
307 listing_source_line ((unsigned int) desc
);
311 listing_source_file (string
);
315 #endif /* ! NO_LISTING */
317 /* We have now gathered the type, other, and desc information. For
318 .stabs or .stabn, input_line_pointer is now pointing at the
321 if (SEPARATE_STAB_SECTIONS
)
322 /* Output the stab information in a separate section. This is used
323 at least for COFF and ELF. */
325 segT saved_seg
= now_seg
;
326 subsegT saved_subseg
= now_subseg
;
327 fragS
*saved_frag
= frag_now
;
333 dot
= frag_now_fix ();
335 #ifdef md_flush_pending_output
336 md_flush_pending_output ();
339 if (cached_sec
&& strcmp (cached_sec
->name
, stab_secname
) == 0)
346 seg
= subseg_new (stab_secname
, 0);
350 if (! seg_info (seg
)->hadone
)
352 bfd_set_section_flags (seg
,
353 SEC_READONLY
| SEC_RELOC
| SEC_DEBUGGING
);
354 #ifdef INIT_STAB_SECTION
355 INIT_STAB_SECTION (seg
);
357 seg_info (seg
)->hadone
= 1;
360 stroff
= get_stab_string_offset (string
, stabstr_secname
,
361 stab_secname_obstack_end
!= NULL
);
363 /* Release the string, if nobody else has used the obstack. */
364 if (saved_string_obstack_end
!= NULL
365 && saved_string_obstack_end
== obstack_next_free (¬es
))
366 obstack_free (¬es
, string
);
367 /* Similarly for the section name. This must be done before
368 creating symbols below, which uses the notes obstack. */
369 if (seg
->name
!= stab_secname
370 && stab_secname_obstack_end
!= NULL
371 && stab_secname_obstack_end
== obstack_next_free (¬es
))
372 obstack_free (¬es
, stab_secname
);
374 /* At least for now, stabs in a special stab section are always
375 output as 12 byte blocks of information. */
377 md_number_to_chars (p
, (valueT
) stroff
, 4);
378 md_number_to_chars (p
+ 4, (valueT
) type
, 1);
379 md_number_to_chars (p
+ 5, (valueT
) other
, 1);
380 md_number_to_chars (p
+ 6, (valueT
) desc
, 2);
382 if (what
== 's' || what
== 'n')
384 /* Pick up the value from the input line. */
386 input_line_pointer
--;
393 /* Arrange for a value representing the current location. */
394 symbol
= symbol_temp_new (saved_seg
, saved_frag
, dot
);
397 exp
.X_add_symbol
= symbol
;
398 exp
.X_add_number
= 0;
403 #ifdef OBJ_PROCESS_STAB
404 OBJ_PROCESS_STAB (seg
, what
, string
, type
, other
, desc
);
407 subseg_set (saved_seg
, saved_subseg
);
411 if (stab_secname_obstack_end
!= NULL
)
413 free ((char *) stabstr_secname
);
414 if (stab_secname_obstack_end
== obstack_next_free (¬es
))
415 obstack_free (¬es
, stab_secname
);
417 #ifdef OBJ_PROCESS_STAB
418 OBJ_PROCESS_STAB (0, what
, string
, type
, other
, desc
);
424 demand_empty_rest_of_line ();
427 /* Regular stab directive. */
432 s_stab_generic (what
, STAB_SECTION_NAME
, STAB_STRING_SECTION_NAME
, NULL
);
435 /* "Extended stabs", used in Solaris only now. */
441 char *stab_secname
, *stabstr_secname
, *stab_secname_obstack_end
;
443 stab_secname
= demand_copy_C_string (&length
);
444 stab_secname_obstack_end
= obstack_next_free (¬es
);
446 if (*input_line_pointer
== ',')
447 input_line_pointer
++;
450 as_bad (_("comma missing in .xstabs"));
451 ignore_rest_of_line ();
455 /* To get the name of the stab string section, simply add "str" to
456 the stab section name. */
457 stabstr_secname
= concat (stab_secname
, "str", (char *) NULL
);
458 s_stab_generic (what
, stab_secname
, stabstr_secname
,
459 stab_secname_obstack_end
);
464 /* Frob invented at RMS' request. Set the n_desc of a symbol. */
467 s_desc (int ignore ATTRIBUTE_UNUSED
)
475 c
= get_symbol_name (&name
);
476 p
= input_line_pointer
;
478 SKIP_WHITESPACE_AFTER_NAME ();
479 if (*input_line_pointer
!= ',')
482 as_bad (_("expected comma after \"%s\""), name
);
484 ignore_rest_of_line ();
488 input_line_pointer
++;
489 temp
= get_absolute_expression ();
491 symbolP
= symbol_find_or_make (name
);
493 S_SET_DESC (symbolP
, temp
);
495 demand_empty_rest_of_line ();
498 #endif /* defined (S_SET_DESC) */
500 /* Generate stabs debugging information to denote the main source file. */
503 stabs_generate_asm_file (void)
508 file
= as_where (&lineno
);
509 if (use_gnu_debug_info_extensions
)
514 dir
= remap_debug_filename (getpwd ());
515 dir2
= concat (dir
, "/", NULL
);
516 generate_asm_file (N_SO
, dir2
);
520 generate_asm_file (N_SO
, file
);
523 /* Generate stabs debugging information to denote the source file.
524 TYPE is one of N_SO, N_SOL. */
527 generate_asm_file (int type
, const char *file
)
531 const char *tmp
= file
;
532 const char *file_endp
= file
+ strlen (file
);
535 if (last_asm_file
!= NULL
536 && filename_cmp (last_asm_file
, file
) == 0)
539 /* Rather than try to do this in some efficient fashion, we just
540 generate a string and then parse it again. That lets us use the
541 existing stabs hook, which expect to see a string, rather than
542 inventing new ones. */
543 sprintf (sym
, "%sF%d", FAKE_LABEL_NAME
, file_label_count
);
546 /* Allocate enough space for the file name (possibly extended with
547 doubled up backslashes), the symbol name, and the other characters
548 that make up a stabs file directive. */
549 bufp
= buf
= XNEWVEC (char, 2 * strlen (file
) + strlen (sym
) + 12);
553 while (tmp
< file_endp
)
555 const char *bslash
= strchr (tmp
, '\\');
556 size_t len
= bslash
!= NULL
? bslash
- tmp
+ 1 : file_endp
- tmp
;
558 /* Double all backslashes, since demand_copy_C_string (used by
559 s_stab to extract the part in quotes) will try to replace them as
560 escape sequences. backslash may appear in a filespec. */
561 memcpy (bufp
, tmp
, len
);
570 sprintf (bufp
, "\",%d,0,0,%s\n", type
, sym
);
578 free (last_asm_file
);
579 last_asm_file
= xstrdup (file
);
584 /* Generate stabs debugging information for the current line. This is
585 used to produce debugging information for an assembler file. */
588 stabs_generate_asm_lineno (void)
595 /* Rather than try to do this in some efficient fashion, we just
596 generate a string and then parse it again. That lets us use the
597 existing stabs hook, which expect to see a string, rather than
598 inventing new ones. */
600 file
= as_where (&lineno
);
602 /* Don't emit sequences of stabs for the same line. */
603 if (prev_line_file
!= NULL
604 && filename_cmp (file
, prev_line_file
) == 0)
606 if (lineno
== prev_lineno
)
607 /* Same file/line as last time. */
612 /* Remember file/line for next time. */
613 free (prev_line_file
);
614 prev_line_file
= xstrdup (file
);
617 prev_lineno
= lineno
;
619 /* Let the world know that we are in the middle of generating a
620 piece of stabs line debugging information. */
621 outputting_stabs_line_debug
= 1;
623 generate_asm_file (N_SOL
, file
);
625 sprintf (sym
, "%sL%d", FAKE_LABEL_NAME
, line_label_count
);
628 if (current_function_label
)
630 buf
= XNEWVEC (char, 100 + strlen (current_function_label
));
631 sprintf (buf
, "%d,0,%d,%s-%s\n", N_SLINE
, lineno
,
632 sym
, current_function_label
);
636 buf
= XNEWVEC (char, 100);
637 sprintf (buf
, "%d,0,%d,%s\n", N_SLINE
, lineno
, sym
);
646 outputting_stabs_line_debug
= 0;
650 /* Emit a function stab.
651 All assembler functions are assumed to have return type `void'. */
654 stabs_generate_asm_func (const char *funcname
, const char *startlabname
)
659 if (! void_emitted_p
)
661 temp_ilp ((char *) "\"void:t1=1\",128,0,0,0");
664 void_emitted_p
= true;
668 if (asprintf (&buf
, "\"%s:F1\",%d,0,%d,%s",
669 funcname
, N_FUN
, lineno
+ 1, startlabname
) == -1)
670 as_fatal ("%s", xstrerror (errno
));
677 free ((char *) current_function_label
);
678 current_function_label
= xstrdup (startlabname
);
681 /* Emit a stab to record the end of a function. */
684 stabs_generate_asm_endfunc (const char *funcname ATTRIBUTE_UNUSED
,
685 const char *startlabname
)
690 sprintf (sym
, "%sendfunc%d", FAKE_LABEL_NAME
, endfunc_label_count
);
691 ++endfunc_label_count
;
694 if (asprintf (&buf
, "\"\",%d,0,0,%s-%s", N_FUN
, sym
, startlabname
) == -1)
695 as_fatal ("%s", xstrerror (errno
));
702 free ((char *) current_function_label
);
703 current_function_label
= NULL
;
709 current_function_label
= NULL
;
711 last_asm_file
= NULL
;
712 file_label_count
= 0;
713 line_label_count
= 0;
715 prev_line_file
= NULL
;
716 void_emitted_p
= false;
717 endfunc_label_count
= 0;
723 free ((char *) current_function_label
);
724 free (last_asm_file
);
725 free (prev_line_file
);