xref: /openbsd/gnu/usr.bin/binutils/bfd/stabs.c (revision 3d8817e4)
1 /* Stabs in sections linking support.
2    Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004
3    Free Software Foundation, Inc.
4    Written by Ian Lance Taylor, Cygnus Support.
5 
6    This file is part of BFD, the Binary File Descriptor library.
7 
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 2 of the License, or
11    (at your option) any later version.
12 
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17 
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
21 
22 /* This file contains support for linking stabs in sections, as used
23    on COFF and ELF.  */
24 
25 #include "bfd.h"
26 #include "sysdep.h"
27 #include "libbfd.h"
28 #include "aout/stab_gnu.h"
29 #include "safe-ctype.h"
30 
31 /* Stabs entries use a 12 byte format:
32      4 byte string table index
33      1 byte stab type
34      1 byte stab other field
35      2 byte stab desc field
36      4 byte stab value
37    FIXME: This will have to change for a 64 bit object format.
38 
39    The stabs symbols are divided into compilation units.  For the
40    first entry in each unit, the type of 0, the value is the length of
41    the string table for this unit, and the desc field is the number of
42    stabs symbols for this unit.  */
43 
44 #define STRDXOFF (0)
45 #define TYPEOFF (4)
46 #define OTHEROFF (5)
47 #define DESCOFF (6)
48 #define VALOFF (8)
49 #define STABSIZE (12)
50 
51 /* A hash table used for header files with N_BINCL entries.  */
52 
53 struct stab_link_includes_table
54 {
55   struct bfd_hash_table root;
56 };
57 
58 /* A linked list of totals that we have found for a particular header
59    file.  A total is a unique identifier for a particular BINCL...EINCL
60    sequence of STABs that can be used to identify duplicate sequences.
61    It consists of three fields, 'sum_chars' which is the sum of all the
62    STABS characters; 'num_chars' which is the number of these charactes
63    and 'symb' which is a buffer of all the symbols in the sequence.  This
64    buffer is only checked as a last resort.  */
65 
66 struct stab_link_includes_totals
67 {
68   struct stab_link_includes_totals *next;
69   bfd_vma sum_chars;  /* Accumulated sum of STABS characters.  */
70   bfd_vma num_chars;  /* Number of STABS characters.  */
71   const char* symb;   /* The STABS characters themselves.  */
72 };
73 
74 /* An entry in the header file hash table.  */
75 
76 struct stab_link_includes_entry
77 {
78   struct bfd_hash_entry root;
79   /* List of totals we have found for this file.  */
80   struct stab_link_includes_totals *totals;
81 };
82 
83 /* Look up an entry in an the header file hash table.  */
84 
85 #define stab_link_includes_lookup(table, string, create, copy) \
86   ((struct stab_link_includes_entry *) \
87    bfd_hash_lookup (&(table)->root, (string), (create), (copy)))
88 
89 /* This structure is used to hold a list of N_BINCL symbols, some of
90    which might be converted into N_EXCL symbols.  */
91 
92 struct stab_excl_list
93 {
94   /* The next symbol to convert.  */
95   struct stab_excl_list *next;
96   /* The offset to this symbol in the section contents.  */
97   bfd_size_type offset;
98   /* The value to use for the symbol.  */
99   bfd_vma val;
100   /* The type of this symbol (N_BINCL or N_EXCL).  */
101   int type;
102 };
103 
104 /* This structure is stored with each .stab section.  */
105 
106 struct stab_section_info
107 {
108   /* This is a linked list of N_BINCL symbols which should be
109      converted into N_EXCL symbols.  */
110   struct stab_excl_list *excls;
111 
112   /* This is used to map input stab offsets within their sections
113      to output stab offsets, to take into account stabs that have
114      been deleted.  If it is NULL, the output offsets are the same
115      as the input offsets, because no stabs have been deleted from
116      this section.  Otherwise the i'th entry is the number of
117      bytes of stabs that have been deleted prior to the i'th
118      stab.  */
119   bfd_size_type *cumulative_skips;
120 
121   /* This is an array of string indices.  For each stab symbol, we
122      store the string index here.  If a stab symbol should not be
123      included in the final output, the string index is -1.  */
124   bfd_size_type stridxs[1];
125 };
126 
127 /* This structure is used to keep track of stabs in sections
128    information while linking.  */
129 
130 struct stab_info
131 {
132   /* A hash table used to hold stabs strings.  */
133   struct bfd_strtab_hash *strings;
134   /* The header file hash table.  */
135   struct stab_link_includes_table includes;
136   /* The first .stabstr section.  */
137   asection *stabstr;
138 };
139 
140 static struct bfd_hash_entry *stab_link_includes_newfunc
141   PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
142 
143 /* The function to create a new entry in the header file hash table.  */
144 
145 static struct bfd_hash_entry *
146 stab_link_includes_newfunc (entry, table, string)
147      struct bfd_hash_entry *entry;
148      struct bfd_hash_table *table;
149      const char *string;
150 {
151   struct stab_link_includes_entry *ret =
152     (struct stab_link_includes_entry *) entry;
153 
154   /* Allocate the structure if it has not already been allocated by a
155      subclass.  */
156   if (ret == (struct stab_link_includes_entry *) NULL)
157     ret = ((struct stab_link_includes_entry *)
158 	   bfd_hash_allocate (table,
159 			      sizeof (struct stab_link_includes_entry)));
160   if (ret == (struct stab_link_includes_entry *) NULL)
161     return (struct bfd_hash_entry *) ret;
162 
163   /* Call the allocation method of the superclass.  */
164   ret = ((struct stab_link_includes_entry *)
165 	 bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
166   if (ret)
167     {
168       /* Set local fields.  */
169       ret->totals = NULL;
170     }
171 
172   return (struct bfd_hash_entry *) ret;
173 }
174 
175 /* This function is called for each input file from the add_symbols
176    pass of the linker.  */
177 
178 bfd_boolean
179 _bfd_link_section_stabs (abfd, psinfo, stabsec, stabstrsec, psecinfo, pstring_offset)
180      bfd *abfd;
181      PTR *psinfo;
182      asection *stabsec;
183      asection *stabstrsec;
184      PTR *psecinfo;
185      bfd_size_type *pstring_offset;
186 {
187   bfd_boolean first;
188   struct stab_info *sinfo;
189   bfd_size_type count, amt;
190   struct stab_section_info *secinfo;
191   bfd_byte *stabbuf = NULL;
192   bfd_byte *stabstrbuf = NULL;
193   bfd_byte *sym, *symend;
194   bfd_size_type stroff, next_stroff, skip;
195   bfd_size_type *pstridx;
196 
197   if (stabsec->_raw_size == 0
198       || stabstrsec->_raw_size == 0)
199     {
200       /* This file does not contain stabs debugging information.  */
201       return TRUE;
202     }
203 
204   if (stabsec->_raw_size % STABSIZE != 0)
205     {
206       /* Something is wrong with the format of these stab symbols.
207 	 Don't try to optimize them.  */
208       return TRUE;
209     }
210 
211   if ((stabstrsec->flags & SEC_RELOC) != 0)
212     {
213       /* We shouldn't see relocations in the strings, and we aren't
214 	 prepared to handle them.  */
215       return TRUE;
216     }
217 
218   if ((stabsec->output_section != NULL
219        && bfd_is_abs_section (stabsec->output_section))
220       || (stabstrsec->output_section != NULL
221 	  && bfd_is_abs_section (stabstrsec->output_section)))
222     {
223       /* At least one of the sections is being discarded from the
224 	 link, so we should just ignore them.  */
225       return TRUE;
226     }
227 
228   first = FALSE;
229 
230   if (*psinfo == NULL)
231     {
232       /* Initialize the stabs information we need to keep track of.  */
233       first = TRUE;
234       amt = sizeof (struct stab_info);
235       *psinfo = (PTR) bfd_alloc (abfd, amt);
236       if (*psinfo == NULL)
237 	goto error_return;
238       sinfo = (struct stab_info *) *psinfo;
239       sinfo->strings = _bfd_stringtab_init ();
240       if (sinfo->strings == NULL)
241 	goto error_return;
242       /* Make sure the first byte is zero.  */
243       (void) _bfd_stringtab_add (sinfo->strings, "", TRUE, TRUE);
244       if (! bfd_hash_table_init_n (&sinfo->includes.root,
245 				   stab_link_includes_newfunc,
246 				   251))
247 	goto error_return;
248       sinfo->stabstr = bfd_make_section_anyway (abfd, ".stabstr");
249       sinfo->stabstr->flags |= SEC_HAS_CONTENTS | SEC_READONLY | SEC_DEBUGGING;
250     }
251 
252   sinfo = (struct stab_info *) *psinfo;
253 
254   /* Initialize the information we are going to store for this .stab
255      section.  */
256 
257   count = stabsec->_raw_size / STABSIZE;
258 
259   amt = sizeof (struct stab_section_info);
260   amt += (count - 1) * sizeof (bfd_size_type);
261   *psecinfo = bfd_alloc (abfd, amt);
262   if (*psecinfo == NULL)
263     goto error_return;
264 
265   secinfo = (struct stab_section_info *) *psecinfo;
266   secinfo->excls = NULL;
267   secinfo->cumulative_skips = NULL;
268   memset (secinfo->stridxs, 0, (size_t) count * sizeof (bfd_size_type));
269 
270   /* Read the stabs information from abfd.  */
271 
272   stabbuf = (bfd_byte *) bfd_malloc (stabsec->_raw_size);
273   stabstrbuf = (bfd_byte *) bfd_malloc (stabstrsec->_raw_size);
274   if (stabbuf == NULL || stabstrbuf == NULL)
275     goto error_return;
276 
277   if (! bfd_get_section_contents (abfd, stabsec, stabbuf, (bfd_vma) 0,
278 				  stabsec->_raw_size)
279       || ! bfd_get_section_contents (abfd, stabstrsec, stabstrbuf, (bfd_vma) 0,
280 				     stabstrsec->_raw_size))
281     goto error_return;
282 
283   /* Look through the stabs symbols, work out the new string indices,
284      and identify N_BINCL symbols which can be eliminated.  */
285 
286   stroff = 0;
287   /* The stabs sections can be split when
288      -split-by-reloc/-split-by-file is used.  We must keep track of
289      each stab section's place in the single concatenated string
290      table.  */
291   next_stroff = pstring_offset ? *pstring_offset : 0;
292   skip = 0;
293 
294   symend = stabbuf + stabsec->_raw_size;
295   for (sym = stabbuf, pstridx = secinfo->stridxs;
296        sym < symend;
297        sym += STABSIZE, ++pstridx)
298     {
299       bfd_size_type symstroff;
300       int type;
301       const char *string;
302 
303       if (*pstridx != 0)
304 	{
305 	  /* This symbol has already been handled by an N_BINCL pass.  */
306 	  continue;
307 	}
308 
309       type = sym[TYPEOFF];
310 
311       if (type == 0)
312 	{
313 	  /* Special type 0 stabs indicate the offset to the next
314 	     string table.  We only copy the very first one.  */
315 	  stroff = next_stroff;
316 	  next_stroff += bfd_get_32 (abfd, sym + 8);
317 	  if (pstring_offset)
318 	    *pstring_offset = next_stroff;
319 	  if (! first)
320 	    {
321 	      *pstridx = (bfd_size_type) -1;
322 	      ++skip;
323 	      continue;
324 	    }
325 	  first = FALSE;
326 	}
327 
328       /* Store the string in the hash table, and record the index.  */
329       symstroff = stroff + bfd_get_32 (abfd, sym + STRDXOFF);
330       if (symstroff >= stabstrsec->_raw_size)
331 	{
332 	  (*_bfd_error_handler)
333 	    (_("%s(%s+0x%lx): Stabs entry has invalid string index."),
334 	     bfd_archive_filename (abfd),
335 	     bfd_get_section_name (abfd, stabsec),
336 	     (long) (sym - stabbuf));
337 	  bfd_set_error (bfd_error_bad_value);
338 	  goto error_return;
339 	}
340       string = (char *) stabstrbuf + symstroff;
341       *pstridx = _bfd_stringtab_add (sinfo->strings, string, TRUE, TRUE);
342 
343       /* An N_BINCL symbol indicates the start of the stabs entries
344 	 for a header file.  We need to scan ahead to the next N_EINCL
345 	 symbol, ignoring nesting, adding up all the characters in the
346 	 symbol names, not including the file numbers in types (the
347 	 first number after an open parenthesis).  */
348       if (type == (int) N_BINCL)
349 	{
350 	  bfd_vma sum_chars;
351 	  bfd_vma num_chars;
352 	  bfd_vma buf_len = 0;
353 	  char * symb;
354 	  char * symb_rover;
355 	  int nest;
356 	  bfd_byte * incl_sym;
357 	  struct stab_link_includes_entry * incl_entry;
358 	  struct stab_link_includes_totals * t;
359 	  struct stab_excl_list * ne;
360 
361 	  symb = symb_rover = NULL;
362 	  sum_chars = num_chars = 0;
363 	  nest = 0;
364 
365 	  for (incl_sym = sym + STABSIZE;
366 	       incl_sym < symend;
367 	       incl_sym += STABSIZE)
368 	    {
369 	      int incl_type;
370 
371 	      incl_type = incl_sym[TYPEOFF];
372 	      if (incl_type == 0)
373 		break;
374 	      else if (incl_type == (int) N_EXCL)
375 		continue;
376 	      else if (incl_type == (int) N_EINCL)
377 		{
378 		  if (nest == 0)
379 		    break;
380 		  --nest;
381 		}
382 	      else if (incl_type == (int) N_BINCL)
383 		++nest;
384 	      else if (nest == 0)
385 		{
386 		  const char *str;
387 
388 		  str = ((char *) stabstrbuf
389 			 + stroff
390 			 + bfd_get_32 (abfd, incl_sym + STRDXOFF));
391 		  for (; *str != '\0'; str++)
392 		    {
393 		      if (num_chars >= buf_len)
394 			{
395 			  buf_len += 32 * 1024;
396 			  symb = bfd_realloc (symb, buf_len);
397 			  if (symb == NULL)
398 			    goto error_return;
399 			  symb_rover = symb + num_chars;
400 			}
401 		      * symb_rover ++ = * str;
402 		      sum_chars += *str;
403 		      num_chars ++;
404 		      if (*str == '(')
405 			{
406 			  /* Skip the file number.  */
407 			  ++str;
408 			  while (ISDIGIT (*str))
409 			    ++str;
410 			  --str;
411 			}
412 		    }
413 		}
414 	    }
415 
416 	  BFD_ASSERT (num_chars == (bfd_vma) (symb_rover - symb));
417 
418 	  /* If we have already included a header file with the same
419 	     value, then replaced this one with an N_EXCL symbol.  */
420 	  incl_entry = stab_link_includes_lookup (&sinfo->includes, string,
421 						  TRUE, TRUE);
422 	  if (incl_entry == NULL)
423 	    goto error_return;
424 
425 	  for (t = incl_entry->totals; t != NULL; t = t->next)
426 	    if (t->sum_chars == sum_chars
427 		&& t->num_chars == num_chars
428 		&& memcmp (t->symb, symb, num_chars) == 0)
429 	      break;
430 
431 	  /* Record this symbol, so that we can set the value
432 	     correctly.  */
433 	  amt = sizeof *ne;
434 	  ne = (struct stab_excl_list *) bfd_alloc (abfd, amt);
435 	  if (ne == NULL)
436 	    goto error_return;
437 	  ne->offset = sym - stabbuf;
438 	  ne->val = sum_chars;
439 	  ne->type = (int) N_BINCL;
440 	  ne->next = secinfo->excls;
441 	  secinfo->excls = ne;
442 
443 	  if (t == NULL)
444 	    {
445 	      /* This is the first time we have seen this header file
446 		 with this set of stabs strings.  */
447 	      t = ((struct stab_link_includes_totals *)
448 		   bfd_hash_allocate (&sinfo->includes.root, sizeof *t));
449 	      if (t == NULL)
450 		goto error_return;
451 	      t->sum_chars = sum_chars;
452 	      t->num_chars = num_chars;
453 	      t->symb = bfd_realloc (symb, num_chars); /* Trim data down.  */
454 	      t->next = incl_entry->totals;
455 	      incl_entry->totals = t;
456 	    }
457 	  else
458 	    {
459 	      bfd_size_type *incl_pstridx;
460 
461 	      /* We have seen this header file before.  Tell the final
462 		 pass to change the type to N_EXCL.  */
463 	      ne->type = (int) N_EXCL;
464 
465 	      /* Free off superfluous symbols.  */
466 	      free (symb);
467 
468 	      /* Mark the skipped symbols.  */
469 
470 	      nest = 0;
471 	      for (incl_sym = sym + STABSIZE, incl_pstridx = pstridx + 1;
472 		   incl_sym < symend;
473 		   incl_sym += STABSIZE, ++incl_pstridx)
474 		{
475 		  int incl_type;
476 
477 		  incl_type = incl_sym[TYPEOFF];
478 
479 		  if (incl_type == (int) N_EINCL)
480 		    {
481 		      if (nest == 0)
482 			{
483 			  *incl_pstridx = (bfd_size_type) -1;
484 			  ++skip;
485 			  break;
486 			}
487 		      --nest;
488 		    }
489 		  else if (incl_type == (int) N_BINCL)
490 		    ++nest;
491 		  else if (incl_type == (int) N_EXCL)
492 		    /* Keep existing exclusion marks.  */
493 		    continue;
494 		  else if (nest == 0)
495 		    {
496 		      *incl_pstridx = (bfd_size_type) -1;
497 		      ++skip;
498 		    }
499 		}
500 	    }
501 	}
502     }
503 
504   free (stabbuf);
505   stabbuf = NULL;
506   free (stabstrbuf);
507   stabstrbuf = NULL;
508 
509   /* We need to set the section sizes such that the linker will
510      compute the output section sizes correctly.  We set the .stab
511      size to not include the entries we don't want.  We set
512      SEC_EXCLUDE for the .stabstr section, so that it will be dropped
513      from the link.  We record the size of the strtab in the first
514      .stabstr section we saw, and make sure we don't set SEC_EXCLUDE
515      for that section.  */
516   stabsec->_cooked_size = (count - skip) * STABSIZE;
517   if (stabsec->_cooked_size == 0)
518     stabsec->flags |= SEC_EXCLUDE;
519   stabstrsec->flags |= SEC_EXCLUDE;
520   sinfo->stabstr->_cooked_size = _bfd_stringtab_size (sinfo->strings);
521 
522   /* Calculate the `cumulative_skips' array now that stabs have been
523      deleted for this section.  */
524 
525   if (skip != 0)
526     {
527       bfd_size_type i, offset;
528       bfd_size_type *pskips;
529 
530       amt = count * sizeof (bfd_size_type);
531       secinfo->cumulative_skips = (bfd_size_type *) bfd_alloc (abfd, amt);
532       if (secinfo->cumulative_skips == NULL)
533 	goto error_return;
534 
535       pskips = secinfo->cumulative_skips;
536       pstridx = secinfo->stridxs;
537       offset = 0;
538 
539       for (i = 0; i < count; i++, pskips++, pstridx++)
540 	{
541 	  *pskips = offset;
542 	  if (*pstridx == (bfd_size_type) -1)
543 	    offset += STABSIZE;
544 	}
545 
546       BFD_ASSERT (offset != 0);
547     }
548 
549   return TRUE;
550 
551  error_return:
552   if (stabbuf != NULL)
553     free (stabbuf);
554   if (stabstrbuf != NULL)
555     free (stabstrbuf);
556   return FALSE;
557 }
558 
559 
560 /* This function is called for each input file before the stab
561    section is relocated.  It discards stab entries for discarded
562    functions and variables.  The function returns TRUE iff
563    any entries have been deleted.
564 */
565 
566 bfd_boolean
567 _bfd_discard_section_stabs (abfd, stabsec, psecinfo,
568 			    reloc_symbol_deleted_p, cookie)
569      bfd *abfd;
570      asection *stabsec;
571      PTR psecinfo;
572      bfd_boolean (*reloc_symbol_deleted_p) PARAMS ((bfd_vma, PTR));
573      PTR cookie;
574 {
575   bfd_size_type count, amt;
576   struct stab_section_info *secinfo;
577   bfd_byte *stabbuf = NULL;
578   bfd_byte *sym, *symend;
579   bfd_size_type skip;
580   bfd_size_type *pstridx;
581   int deleting;
582 
583   if (stabsec->_raw_size == 0)
584     {
585       /* This file does not contain stabs debugging information.  */
586       return FALSE;
587     }
588 
589   if (stabsec->_raw_size % STABSIZE != 0)
590     {
591       /* Something is wrong with the format of these stab symbols.
592 	 Don't try to optimize them.  */
593       return FALSE;
594     }
595 
596   if ((stabsec->output_section != NULL
597        && bfd_is_abs_section (stabsec->output_section)))
598     {
599       /* At least one of the sections is being discarded from the
600 	 link, so we should just ignore them.  */
601       return FALSE;
602     }
603 
604   /* We should have initialized our data in _bfd_link_stab_sections.
605      If there was some bizarre error reading the string sections, though,
606      we might not have.  Bail rather than asserting.  */
607   if (psecinfo == NULL)
608     return FALSE;
609 
610   count = stabsec->_raw_size / STABSIZE;
611   secinfo = (struct stab_section_info *) psecinfo;
612 
613   /* Read the stabs information from abfd.  */
614 
615   stabbuf = (bfd_byte *) bfd_malloc (stabsec->_raw_size);
616   if (stabbuf == NULL)
617     goto error_return;
618 
619   if (! bfd_get_section_contents (abfd, stabsec, stabbuf, (bfd_vma) 0,
620 				  stabsec->_raw_size))
621     goto error_return;
622 
623   /* Look through the stabs symbols and discard any information for
624      discarded functions.  */
625 
626   skip = 0;
627   deleting = -1;
628 
629   symend = stabbuf + stabsec->_raw_size;
630   for (sym = stabbuf, pstridx = secinfo->stridxs;
631        sym < symend;
632        sym += STABSIZE, ++pstridx)
633     {
634       int type;
635 
636       if (*pstridx == (bfd_size_type) -1)
637 	{
638 	  /* This stab was deleted in a previous pass.  */
639 	  continue;
640 	}
641 
642       type = sym[TYPEOFF];
643 
644       if (type == (int) N_FUN)
645 	{
646 	  int strx = bfd_get_32 (abfd, sym + STRDXOFF);
647 
648 	  if (strx == 0)
649 	    {
650 	      if (deleting)
651 		{
652 		  skip++;
653 		  *pstridx = -1;
654 		}
655 	      deleting = -1;
656 	      continue;
657 	    }
658 	  deleting = 0;
659 	  if ((*reloc_symbol_deleted_p) (sym + VALOFF - stabbuf, cookie))
660 	    deleting = 1;
661 	}
662 
663       if (deleting == 1)
664 	{
665 	  *pstridx = -1;
666 	  skip++;
667 	}
668       else if (deleting == -1)
669 	{
670 	  /* Outside of a function.  Check for deleted variables.  */
671 	  if (type == (int) N_STSYM || type == (int) N_LCSYM)
672 	    if ((*reloc_symbol_deleted_p) (sym + VALOFF - stabbuf, cookie))
673 	      {
674 		*pstridx = -1;
675 		skip ++;
676 	      }
677 	  /* We should also check for N_GSYM entries which reference a
678 	     deleted global, but those are less harmful to debuggers
679 	     and would require parsing the stab strings.  */
680 	}
681     }
682 
683   free (stabbuf);
684   stabbuf = NULL;
685 
686   /* Shrink the stabsec as needed.  */
687   stabsec->_cooked_size -= skip * STABSIZE;
688   if (stabsec->_cooked_size == 0)
689     stabsec->flags |= SEC_EXCLUDE;
690 
691   /* Recalculate the `cumulative_skips' array now that stabs have been
692      deleted for this section.  */
693 
694   if (skip != 0)
695     {
696       bfd_size_type i, offset;
697       bfd_size_type *pskips;
698 
699       if (secinfo->cumulative_skips == NULL)
700 	{
701 	  amt = count * sizeof (bfd_size_type);
702 	  secinfo->cumulative_skips = (bfd_size_type *) bfd_alloc (abfd, amt);
703 	  if (secinfo->cumulative_skips == NULL)
704 	    goto error_return;
705 	}
706 
707       pskips = secinfo->cumulative_skips;
708       pstridx = secinfo->stridxs;
709       offset = 0;
710 
711       for (i = 0; i < count; i++, pskips++, pstridx++)
712 	{
713 	  *pskips = offset;
714 	  if (*pstridx == (bfd_size_type) -1)
715 	    offset += STABSIZE;
716 	}
717 
718       BFD_ASSERT (offset != 0);
719     }
720 
721   return skip > 0;
722 
723  error_return:
724   if (stabbuf != NULL)
725     free (stabbuf);
726   return FALSE;
727 }
728 
729 /* Write out the stab section.  This is called with the relocated
730    contents.  */
731 
732 bfd_boolean
733 _bfd_write_section_stabs (output_bfd, psinfo, stabsec, psecinfo, contents)
734      bfd *output_bfd;
735      PTR *psinfo;
736      asection *stabsec;
737      PTR *psecinfo;
738      bfd_byte *contents;
739 {
740   struct stab_info *sinfo;
741   struct stab_section_info *secinfo;
742   struct stab_excl_list *e;
743   bfd_byte *sym, *tosym, *symend;
744   bfd_size_type *pstridx;
745 
746   sinfo = (struct stab_info *) *psinfo;
747   secinfo = (struct stab_section_info *) *psecinfo;
748 
749   if (secinfo == NULL)
750     return bfd_set_section_contents (output_bfd, stabsec->output_section,
751 				     contents,
752 				     (file_ptr) stabsec->output_offset,
753 				     stabsec->_raw_size);
754 
755   /* Handle each N_BINCL entry.  */
756   for (e = secinfo->excls; e != NULL; e = e->next)
757     {
758       bfd_byte *excl_sym;
759 
760       BFD_ASSERT (e->offset < stabsec->_raw_size);
761       excl_sym = contents + e->offset;
762       bfd_put_32 (output_bfd, e->val, excl_sym + VALOFF);
763       excl_sym[TYPEOFF] = e->type;
764     }
765 
766   /* Copy over all the stabs symbols, omitting the ones we don't want,
767      and correcting the string indices for those we do want.  */
768   tosym = contents;
769   symend = contents + stabsec->_raw_size;
770   for (sym = contents, pstridx = secinfo->stridxs;
771        sym < symend;
772        sym += STABSIZE, ++pstridx)
773     {
774       if (*pstridx != (bfd_size_type) -1)
775 	{
776 	  if (tosym != sym)
777 	    memcpy (tosym, sym, STABSIZE);
778 	  bfd_put_32 (output_bfd, *pstridx, tosym + STRDXOFF);
779 
780 	  if (sym[TYPEOFF] == 0)
781 	    {
782 	      /* This is the header symbol for the stabs section.  We
783 		 don't really need one, since we have merged all the
784 		 input stabs sections into one, but we generate one
785 		 for the benefit of readers which expect to see one.  */
786 	      BFD_ASSERT (sym == contents);
787 	      bfd_put_32 (output_bfd, _bfd_stringtab_size (sinfo->strings),
788 			  tosym + VALOFF);
789 	      bfd_put_16 (output_bfd,
790 			  stabsec->output_section->_raw_size / STABSIZE - 1,
791 			  tosym + DESCOFF);
792 	    }
793 
794 	  tosym += STABSIZE;
795 	}
796     }
797 
798   BFD_ASSERT ((bfd_size_type) (tosym - contents) == stabsec->_cooked_size);
799 
800   return bfd_set_section_contents (output_bfd, stabsec->output_section,
801 				   contents, (file_ptr) stabsec->output_offset,
802 				   stabsec->_cooked_size);
803 }
804 
805 /* Write out the .stabstr section.  */
806 
807 bfd_boolean
808 _bfd_write_stab_strings (output_bfd, psinfo)
809      bfd *output_bfd;
810      PTR *psinfo;
811 {
812   struct stab_info *sinfo;
813 
814   sinfo = (struct stab_info *) *psinfo;
815 
816   if (sinfo == NULL)
817     return TRUE;
818 
819   if (bfd_is_abs_section (sinfo->stabstr->output_section))
820     {
821       /* The section was discarded from the link.  */
822       return TRUE;
823     }
824 
825   BFD_ASSERT ((sinfo->stabstr->output_offset
826 	       + _bfd_stringtab_size (sinfo->strings))
827 	      <= sinfo->stabstr->output_section->_raw_size);
828 
829   if (bfd_seek (output_bfd,
830 		(file_ptr) (sinfo->stabstr->output_section->filepos
831 			    + sinfo->stabstr->output_offset),
832 		SEEK_SET) != 0)
833     return FALSE;
834 
835   if (! _bfd_stringtab_emit (output_bfd, sinfo->strings))
836     return FALSE;
837 
838   /* We no longer need the stabs information.  */
839   _bfd_stringtab_free (sinfo->strings);
840   bfd_hash_table_free (&sinfo->includes.root);
841 
842   return TRUE;
843 }
844 
845 /* Adjust an address in the .stab section.  Given OFFSET within
846    STABSEC, this returns the new offset in the adjusted stab section,
847    or -1 if the address refers to a stab which has been removed.  */
848 
849 bfd_vma
850 _bfd_stab_section_offset (output_bfd, psinfo, stabsec, psecinfo, offset)
851      bfd *output_bfd ATTRIBUTE_UNUSED;
852      PTR *psinfo ATTRIBUTE_UNUSED;
853      asection *stabsec;
854      PTR *psecinfo;
855      bfd_vma offset;
856 {
857   struct stab_section_info *secinfo;
858 
859   secinfo = (struct stab_section_info *) *psecinfo;
860 
861   if (secinfo == NULL)
862     return offset;
863 
864   if (offset >= stabsec->_raw_size)
865     return offset - (stabsec->_cooked_size - stabsec->_raw_size);
866 
867   if (secinfo->cumulative_skips)
868     {
869       bfd_vma i;
870 
871       i = offset / STABSIZE;
872 
873       if (secinfo->stridxs [i] == (bfd_size_type) -1)
874 	return (bfd_vma) -1;
875 
876       return offset - secinfo->cumulative_skips [i];
877     }
878 
879   return offset;
880 }
881