Merge branch 'vendor/GCC44'
[dragonfly.git] / contrib / binutils-2.17 / gas / config / obj-elf.c
1 /* ELF object file format
2    Copyright 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3    2001, 2002, 2003, 2004, 2005 Free Software Foundation, Inc.
4
5    This file is part of GAS, the GNU Assembler.
6
7    GAS is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as
9    published by the Free Software Foundation; either version 2,
10    or (at your option) any later version.
11
12    GAS is distributed in the hope that it will be useful, but
13    WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See
15    the GNU General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with GAS; see the file COPYING.  If not, write to the Free
19    Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
20    02110-1301, USA.  */
21
22 #define OBJ_HEADER "obj-elf.h"
23 #include "as.h"
24 #include "safe-ctype.h"
25 #include "subsegs.h"
26 #include "obstack.h"
27 #include "struc-symbol.h"
28 #include "dwarf2dbg.h"
29
30 #ifndef ECOFF_DEBUGGING
31 #define ECOFF_DEBUGGING 0
32 #else
33 #define NEED_ECOFF_DEBUG
34 #endif
35
36 #ifdef NEED_ECOFF_DEBUG
37 #include "ecoff.h"
38 #endif
39
40 #ifdef TC_ALPHA
41 #include "elf/alpha.h"
42 #endif
43
44 #ifdef TC_MIPS
45 #include "elf/mips.h"
46 #endif
47
48 #ifdef TC_PPC
49 #include "elf/ppc.h"
50 #endif
51
52 #ifdef TC_I370
53 #include "elf/i370.h"
54 #endif
55
56 #ifdef TC_I386
57 #include "elf/x86-64.h"
58 #endif
59
60 static void obj_elf_line (int);
61 static void obj_elf_size (int);
62 static void obj_elf_type (int);
63 static void obj_elf_ident (int);
64 static void obj_elf_weak (int);
65 static void obj_elf_local (int);
66 static void obj_elf_visibility (int);
67 static void obj_elf_symver (int);
68 static void obj_elf_subsection (int);
69 static void obj_elf_popsection (int);
70 static void obj_elf_tls_common (int);
71 static void obj_elf_lcomm (int);
72 static void obj_elf_struct (int);
73
74 static const pseudo_typeS elf_pseudo_table[] =
75 {
76   {"comm", obj_elf_common, 0},
77   {"common", obj_elf_common, 1},
78   {"ident", obj_elf_ident, 0},
79   {"lcomm", obj_elf_lcomm, 0},
80   {"local", obj_elf_local, 0},
81   {"previous", obj_elf_previous, 0},
82   {"section", obj_elf_section, 0},
83   {"section.s", obj_elf_section, 0},
84   {"sect", obj_elf_section, 0},
85   {"sect.s", obj_elf_section, 0},
86   {"pushsection", obj_elf_section, 1},
87   {"popsection", obj_elf_popsection, 0},
88   {"size", obj_elf_size, 0},
89   {"type", obj_elf_type, 0},
90   {"version", obj_elf_version, 0},
91   {"weak", obj_elf_weak, 0},
92
93   /* These define symbol visibility.  */
94   {"internal", obj_elf_visibility, STV_INTERNAL},
95   {"hidden", obj_elf_visibility, STV_HIDDEN},
96   {"protected", obj_elf_visibility, STV_PROTECTED},
97
98   /* These are used for stabs-in-elf configurations.  */
99   {"line", obj_elf_line, 0},
100
101   /* This is a GNU extension to handle symbol versions.  */
102   {"symver", obj_elf_symver, 0},
103
104   /* A GNU extension to change subsection only.  */
105   {"subsection", obj_elf_subsection, 0},
106
107   /* These are GNU extensions to aid in garbage collecting C++ vtables.  */
108   {"vtable_inherit", (void (*) (int)) &obj_elf_vtable_inherit, 0},
109   {"vtable_entry", (void (*) (int)) &obj_elf_vtable_entry, 0},
110
111   /* These are used for dwarf.  */
112   {"2byte", cons, 2},
113   {"4byte", cons, 4},
114   {"8byte", cons, 8},
115   /* These are used for dwarf2.  */
116   { "file", (void (*) (int)) dwarf2_directive_file, 0 },
117   { "loc",  dwarf2_directive_loc,  0 },
118   { "loc_mark_labels", dwarf2_directive_loc_mark_labels, 0 },
119
120   /* We need to trap the section changing calls to handle .previous.  */
121   {"data", obj_elf_data, 0},
122   {"offset", obj_elf_struct, 0},
123   {"struct", obj_elf_struct, 0},
124   {"text", obj_elf_text, 0},
125
126   {"tls_common", obj_elf_tls_common, 0},
127
128   /* End sentinel.  */
129   {NULL, NULL, 0},
130 };
131
132 static const pseudo_typeS ecoff_debug_pseudo_table[] =
133 {
134 #ifdef NEED_ECOFF_DEBUG
135   /* COFF style debugging information for ECOFF. .ln is not used; .loc
136      is used instead.  */
137   { "def",      ecoff_directive_def,    0 },
138   { "dim",      ecoff_directive_dim,    0 },
139   { "endef",    ecoff_directive_endef,  0 },
140   { "file",     ecoff_directive_file,   0 },
141   { "scl",      ecoff_directive_scl,    0 },
142   { "tag",      ecoff_directive_tag,    0 },
143   { "val",      ecoff_directive_val,    0 },
144
145   /* COFF debugging requires pseudo-ops .size and .type, but ELF
146      already has meanings for those.  We use .esize and .etype
147      instead.  These are only generated by gcc anyhow.  */
148   { "esize",    ecoff_directive_size,   0 },
149   { "etype",    ecoff_directive_type,   0 },
150
151   /* ECOFF specific debugging information.  */
152   { "begin",    ecoff_directive_begin,  0 },
153   { "bend",     ecoff_directive_bend,   0 },
154   { "end",      ecoff_directive_end,    0 },
155   { "ent",      ecoff_directive_ent,    0 },
156   { "fmask",    ecoff_directive_fmask,  0 },
157   { "frame",    ecoff_directive_frame,  0 },
158   { "loc",      ecoff_directive_loc,    0 },
159   { "mask",     ecoff_directive_mask,   0 },
160
161   /* Other ECOFF directives.  */
162   { "extern",   ecoff_directive_extern, 0 },
163
164   /* These are used on Irix.  I don't know how to implement them.  */
165   { "alias",    s_ignore,               0 },
166   { "bgnb",     s_ignore,               0 },
167   { "endb",     s_ignore,               0 },
168   { "lab",      s_ignore,               0 },
169   { "noalias",  s_ignore,               0 },
170   { "verstamp", s_ignore,               0 },
171   { "vreg",     s_ignore,               0 },
172 #endif
173
174   {NULL, NULL, 0}                       /* end sentinel */
175 };
176
177 #undef NO_RELOC
178 #include "aout/aout64.h"
179
180 /* This is called when the assembler starts.  */
181
182 asection *elf_com_section_ptr;
183
184 void
185 elf_begin (void)
186 {
187   asection *s;
188
189   /* Add symbols for the known sections to the symbol table.  */
190   s = bfd_get_section_by_name (stdoutput, TEXT_SECTION_NAME);
191   symbol_table_insert (section_symbol (s));
192   s = bfd_get_section_by_name (stdoutput, DATA_SECTION_NAME);
193   symbol_table_insert (section_symbol (s));
194   s = bfd_get_section_by_name (stdoutput, BSS_SECTION_NAME);
195   symbol_table_insert (section_symbol (s));
196   elf_com_section_ptr = bfd_com_section_ptr;
197 }
198
199 void
200 elf_pop_insert (void)
201 {
202   pop_insert (elf_pseudo_table);
203   if (ECOFF_DEBUGGING)
204     pop_insert (ecoff_debug_pseudo_table);
205 }
206
207 static bfd_vma
208 elf_s_get_size (symbolS *sym)
209 {
210   return S_GET_SIZE (sym);
211 }
212
213 static void
214 elf_s_set_size (symbolS *sym, bfd_vma sz)
215 {
216   S_SET_SIZE (sym, sz);
217 }
218
219 static bfd_vma
220 elf_s_get_align (symbolS *sym)
221 {
222   return S_GET_ALIGN (sym);
223 }
224
225 static void
226 elf_s_set_align (symbolS *sym, bfd_vma align)
227 {
228   S_SET_ALIGN (sym, align);
229 }
230
231 int
232 elf_s_get_other (symbolS *sym)
233 {
234   return elf_symbol (symbol_get_bfdsym (sym))->internal_elf_sym.st_other;
235 }
236
237 static void
238 elf_s_set_other (symbolS *sym, int other)
239 {
240   S_SET_OTHER (sym, other);
241 }
242
243 static int
244 elf_sec_sym_ok_for_reloc (asection *sec)
245 {
246   return obj_sec_sym_ok_for_reloc (sec);
247 }
248
249 void
250 elf_file_symbol (const char *s, int appfile)
251 {
252   if (!appfile
253       || symbol_rootP == NULL
254       || symbol_rootP->bsym == NULL
255       || (symbol_rootP->bsym->flags & BSF_FILE) == 0)
256     {
257       symbolS *sym;
258
259       sym = symbol_new (s, absolute_section, 0, NULL);
260       symbol_set_frag (sym, &zero_address_frag);
261       symbol_get_bfdsym (sym)->flags |= BSF_FILE;
262
263       if (symbol_rootP != sym)
264         {
265           symbol_remove (sym, &symbol_rootP, &symbol_lastP);
266           symbol_insert (sym, symbol_rootP, &symbol_rootP, &symbol_lastP);
267 #ifdef DEBUG
268           verify_symbol_chain (symbol_rootP, symbol_lastP);
269 #endif
270         }
271     }
272
273 #ifdef NEED_ECOFF_DEBUG
274   ecoff_new_file (s, appfile);
275 #endif
276 }
277
278 /* Called from read.c:s_comm after we've parsed .comm symbol, size.
279    Parse a possible alignment value.  */
280
281 symbolS *
282 elf_common_parse (int ignore ATTRIBUTE_UNUSED, symbolS *symbolP, addressT size)
283 {
284   addressT align = 0;
285   int is_local = symbol_get_obj (symbolP)->local;
286
287   if (*input_line_pointer == ',')
288     {
289       char *save = input_line_pointer;
290
291       input_line_pointer++;
292       SKIP_WHITESPACE ();
293
294       if (*input_line_pointer == '"')
295         {
296           /* For sparc.  Accept .common symbol, length, "bss"  */
297           input_line_pointer++;
298           /* Some use the dot, some don't.  */
299           if (*input_line_pointer == '.')
300             input_line_pointer++;
301           /* Some say data, some say bss.  */
302           if (strncmp (input_line_pointer, "bss\"", 4) == 0)
303             input_line_pointer += 4;
304           else if (strncmp (input_line_pointer, "data\"", 5) == 0)
305             input_line_pointer += 5;
306           else
307             {
308               char *p = input_line_pointer;
309               char c;
310
311               while (*--p != '"')
312                 ;
313               while (!is_end_of_line[(unsigned char) *input_line_pointer])
314                 if (*input_line_pointer++ == '"')
315                   break;
316               c = *input_line_pointer;
317               *input_line_pointer = '\0';
318               as_bad (_("bad .common segment %s"), p);
319               *input_line_pointer = c;
320               ignore_rest_of_line ();
321               return NULL;
322             }
323           /* ??? Don't ask me why these are always global.  */
324           is_local = 0;
325         }
326       else
327         {
328           input_line_pointer = save;
329           align = parse_align (is_local);
330           if (align == (addressT) -1)
331             return NULL;
332         }
333     }
334
335   if (is_local)
336     {
337       bss_alloc (symbolP, size, align);
338       S_CLEAR_EXTERNAL (symbolP);
339     }
340   else
341     {
342       S_SET_VALUE (symbolP, size);
343       S_SET_ALIGN (symbolP, align);
344       S_SET_EXTERNAL (symbolP);
345       S_SET_SEGMENT (symbolP, elf_com_section_ptr);
346     }
347
348   symbol_get_bfdsym (symbolP)->flags |= BSF_OBJECT;
349
350   return symbolP;
351 }
352
353 void
354 obj_elf_common (int is_common)
355 {
356   if (flag_mri && is_common)
357     s_mri_common (0);
358   else
359     s_comm_internal (0, elf_common_parse);
360 }
361
362 static void
363 obj_elf_tls_common (int ignore ATTRIBUTE_UNUSED)
364 {
365   symbolS *symbolP = s_comm_internal (0, elf_common_parse);
366
367   if (symbolP)
368     symbol_get_bfdsym (symbolP)->flags |= BSF_THREAD_LOCAL;
369 }
370
371 static void
372 obj_elf_lcomm (int ignore ATTRIBUTE_UNUSED)
373 {
374   symbolS *symbolP = s_comm_internal (0, s_lcomm_internal);
375
376   if (symbolP)
377     symbol_get_bfdsym (symbolP)->flags |= BSF_OBJECT;
378 }
379
380 static void
381 obj_elf_local (int ignore ATTRIBUTE_UNUSED)
382 {
383   char *name;
384   int c;
385   symbolS *symbolP;
386
387   do
388     {
389       name = input_line_pointer;
390       c = get_symbol_end ();
391       symbolP = symbol_find_or_make (name);
392       *input_line_pointer = c;
393       SKIP_WHITESPACE ();
394       S_CLEAR_EXTERNAL (symbolP);
395       symbol_get_obj (symbolP)->local = 1;
396       if (c == ',')
397         {
398           input_line_pointer++;
399           SKIP_WHITESPACE ();
400           if (*input_line_pointer == '\n')
401             c = '\n';
402         }
403     }
404   while (c == ',');
405   demand_empty_rest_of_line ();
406 }
407
408 static void
409 obj_elf_weak (int ignore ATTRIBUTE_UNUSED)
410 {
411   char *name;
412   int c;
413   symbolS *symbolP;
414
415   do
416     {
417       name = input_line_pointer;
418       c = get_symbol_end ();
419       symbolP = symbol_find_or_make (name);
420       *input_line_pointer = c;
421       SKIP_WHITESPACE ();
422       S_SET_WEAK (symbolP);
423       symbol_get_obj (symbolP)->local = 1;
424       if (c == ',')
425         {
426           input_line_pointer++;
427           SKIP_WHITESPACE ();
428           if (*input_line_pointer == '\n')
429             c = '\n';
430         }
431     }
432   while (c == ',');
433   demand_empty_rest_of_line ();
434 }
435
436 static void
437 obj_elf_visibility (int visibility)
438 {
439   char *name;
440   int c;
441   symbolS *symbolP;
442   asymbol *bfdsym;
443   elf_symbol_type *elfsym;
444
445   do
446     {
447       name = input_line_pointer;
448       c = get_symbol_end ();
449       symbolP = symbol_find_or_make (name);
450       *input_line_pointer = c;
451
452       SKIP_WHITESPACE ();
453
454       bfdsym = symbol_get_bfdsym (symbolP);
455       elfsym = elf_symbol_from (bfd_asymbol_bfd (bfdsym), bfdsym);
456
457       assert (elfsym);
458
459       elfsym->internal_elf_sym.st_other &= ~3;
460       elfsym->internal_elf_sym.st_other |= visibility;
461
462       if (c == ',')
463         {
464           input_line_pointer ++;
465
466           SKIP_WHITESPACE ();
467
468           if (*input_line_pointer == '\n')
469             c = '\n';
470         }
471     }
472   while (c == ',');
473
474   demand_empty_rest_of_line ();
475 }
476
477 static segT previous_section;
478 static int previous_subsection;
479
480 struct section_stack
481 {
482   struct section_stack *next;
483   segT seg, prev_seg;
484   int subseg, prev_subseg;
485 };
486
487 static struct section_stack *section_stack;
488
489 static bfd_boolean
490 get_section (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, void *inf)
491 {
492   const char *gname = inf;
493   const char *group_name = elf_group_name (sec);
494   
495   return (group_name == gname
496           || (group_name != NULL
497               && gname != NULL
498               && strcmp (group_name, gname) == 0));
499 }
500
501 /* Handle the .section pseudo-op.  This code supports two different
502    syntaxes.
503
504    The first is found on Solaris, and looks like
505        .section ".sec1",#alloc,#execinstr,#write
506    Here the names after '#' are the SHF_* flags to turn on for the
507    section.  I'm not sure how it determines the SHT_* type (BFD
508    doesn't really give us control over the type, anyhow).
509
510    The second format is found on UnixWare, and probably most SVR4
511    machines, and looks like
512        .section .sec1,"a",@progbits
513    The quoted string may contain any combination of a, w, x, and
514    represents the SHF_* flags to turn on for the section.  The string
515    beginning with '@' can be progbits or nobits.  There should be
516    other possibilities, but I don't know what they are.  In any case,
517    BFD doesn't really let us set the section type.  */
518
519 void
520 obj_elf_change_section (const char *name,
521                         int type,
522                         int attr,
523                         int entsize,
524                         const char *group_name,
525                         int linkonce,
526                         int push)
527 {
528   asection *old_sec;
529   segT sec;
530   flagword flags;
531   const struct elf_backend_data *bed;
532   const struct bfd_elf_special_section *ssect;
533
534 #ifdef md_flush_pending_output
535   md_flush_pending_output ();
536 #endif
537
538   /* Switch to the section, creating it if necessary.  */
539   if (push)
540     {
541       struct section_stack *elt;
542       elt = xmalloc (sizeof (struct section_stack));
543       elt->next = section_stack;
544       elt->seg = now_seg;
545       elt->prev_seg = previous_section;
546       elt->subseg = now_subseg;
547       elt->prev_subseg = previous_subsection;
548       section_stack = elt;
549     }
550   previous_section = now_seg;
551   previous_subsection = now_subseg;
552
553   old_sec = bfd_get_section_by_name_if (stdoutput, name, get_section,
554                                         (void *) group_name);
555   if (old_sec)
556     {
557       sec = old_sec;
558       subseg_set (sec, 0);
559     }
560   else
561     sec = subseg_force_new (name, 0);
562
563   bed = get_elf_backend_data (stdoutput);
564   ssect = (*bed->get_sec_type_attr) (stdoutput, sec);
565
566   if (ssect != NULL)
567     {
568       bfd_boolean override = FALSE;
569
570       if (type == SHT_NULL)
571         type = ssect->type;
572       else if (type != ssect->type)
573         {
574           if (old_sec == NULL
575               /* FIXME: gcc, as of 2002-10-22, will emit
576
577                  .section .init_array,"aw",@progbits
578
579                  for __attribute__ ((section (".init_array"))).
580                  "@progbits" is incorrect.  Also for x86-64 large bss
581                  sections, gcc, as of 2005-07-06, will emit
582
583                  .section .lbss,"aw",@progbits
584
585                  "@progbits" is incorrect.  */
586 #ifdef TC_I386
587               && (bed->s->arch_size != 64
588                   || !(ssect->attr & SHF_X86_64_LARGE))
589 #endif
590               && ssect->type != SHT_INIT_ARRAY
591               && ssect->type != SHT_FINI_ARRAY
592               && ssect->type != SHT_PREINIT_ARRAY)
593             {
594               /* We allow to specify any type for a .note section.  */
595               if (ssect->type != SHT_NOTE)
596                 as_warn (_("setting incorrect section type for %s"),
597                          name);
598             }
599           else
600             {
601               as_warn (_("ignoring incorrect section type for %s"),
602                        name);
603               type = ssect->type;
604             }
605         }
606
607       if (old_sec == NULL && (attr & ~ssect->attr) != 0)
608         {
609           /* As a GNU extension, we permit a .note section to be
610              allocatable.  If the linker sees an allocatable .note
611              section, it will create a PT_NOTE segment in the output
612              file.  We also allow "x" for .note.GNU-stack.  */
613           if (ssect->type == SHT_NOTE
614               && (attr == SHF_ALLOC || attr == SHF_EXECINSTR))
615             ;
616           /* Allow different SHF_MERGE and SHF_STRINGS if we have
617              something like .rodata.str.  */
618           else if (ssect->suffix_length == -2
619                    && name[ssect->prefix_length] == '.'
620                    && (attr
621                        & ~ssect->attr
622                        & ~SHF_MERGE
623                        & ~SHF_STRINGS) == 0)
624             ;
625           /* .interp, .strtab and .symtab can have SHF_ALLOC.  */
626           else if (attr == SHF_ALLOC
627                    && (strcmp (name, ".interp") == 0
628                        || strcmp (name, ".strtab") == 0
629                        || strcmp (name, ".symtab") == 0))
630             override = TRUE;
631           /* .note.GNU-stack can have SHF_EXECINSTR.  */
632           else if (attr == SHF_EXECINSTR
633                    && strcmp (name, ".note.GNU-stack") == 0)
634             override = TRUE;
635           else
636             {
637               if (group_name == NULL)
638                 as_warn (_("setting incorrect section attributes for %s"),
639                          name);
640               override = TRUE;
641             }
642         }
643       if (!override && old_sec == NULL)
644         attr |= ssect->attr;
645     }
646
647   /* Convert ELF type and flags to BFD flags.  */
648   flags = (SEC_RELOC
649            | ((attr & SHF_WRITE) ? 0 : SEC_READONLY)
650            | ((attr & SHF_ALLOC) ? SEC_ALLOC : 0)
651            | (((attr & SHF_ALLOC) && type != SHT_NOBITS) ? SEC_LOAD : 0)
652            | ((attr & SHF_EXECINSTR) ? SEC_CODE : 0)
653            | ((attr & SHF_MERGE) ? SEC_MERGE : 0)
654            | ((attr & SHF_STRINGS) ? SEC_STRINGS : 0)
655            | ((attr & SHF_TLS) ? SEC_THREAD_LOCAL : 0));
656 #ifdef md_elf_section_flags
657   flags = md_elf_section_flags (flags, attr, type);
658 #endif
659
660   if (linkonce)
661     flags |= SEC_LINK_ONCE | SEC_LINK_DUPLICATES_DISCARD;
662
663   if (old_sec == NULL)
664     {
665       symbolS *secsym;
666
667       elf_section_type (sec) = type;
668       elf_section_flags (sec) = attr;
669
670       /* Prevent SEC_HAS_CONTENTS from being inadvertently set.  */
671       if (type == SHT_NOBITS)
672         seg_info (sec)->bss = 1;
673
674       bfd_set_section_flags (stdoutput, sec, flags);
675       if (flags & SEC_MERGE)
676         sec->entsize = entsize;
677       elf_group_name (sec) = group_name;
678
679       /* Add a symbol for this section to the symbol table.  */
680       secsym = symbol_find (name);
681       if (secsym != NULL)
682         symbol_set_bfdsym (secsym, sec->symbol);
683       else
684         symbol_table_insert (section_symbol (sec));
685     }
686   else
687     {
688       if (type != SHT_NULL
689           && (unsigned) type != elf_section_type (old_sec))
690         as_warn (_("ignoring changed section type for %s"), name);
691
692       if (attr != 0)
693         {
694           /* If section attributes are specified the second time we see a
695              particular section, then check that they are the same as we
696              saw the first time.  */
697           if (((old_sec->flags ^ flags)
698                & (SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE
699                   | SEC_EXCLUDE | SEC_SORT_ENTRIES | SEC_MERGE | SEC_STRINGS
700                   | SEC_LINK_ONCE | SEC_LINK_DUPLICATES_DISCARD
701                   | SEC_THREAD_LOCAL)))
702             as_warn (_("ignoring changed section attributes for %s"), name);
703           if ((flags & SEC_MERGE) && old_sec->entsize != (unsigned) entsize)
704             as_warn (_("ignoring changed section entity size for %s"), name);
705         }
706     }
707
708 #ifdef md_elf_section_change_hook
709   md_elf_section_change_hook ();
710 #endif
711 }
712
713 static int
714 obj_elf_parse_section_letters (char *str, size_t len)
715 {
716   int attr = 0;
717
718   while (len > 0)
719     {
720       switch (*str)
721         {
722         case 'a':
723           attr |= SHF_ALLOC;
724           break;
725         case 'w':
726           attr |= SHF_WRITE;
727           break;
728         case 'x':
729           attr |= SHF_EXECINSTR;
730           break;
731         case 'M':
732           attr |= SHF_MERGE;
733           break;
734         case 'S':
735           attr |= SHF_STRINGS;
736           break;
737         case 'G':
738           attr |= SHF_GROUP;
739           break;
740         case 'T':
741           attr |= SHF_TLS;
742           break;
743         /* Compatibility.  */
744         case 'm':
745           if (*(str - 1) == 'a')
746             {
747               attr |= SHF_MERGE;
748               if (len > 1 && str[1] == 's')
749                 {
750                   attr |= SHF_STRINGS;
751                   str++, len--;
752                 }
753               break;
754             }
755         default:
756           {
757             char *bad_msg = _("unrecognized .section attribute: want a,w,x,M,S,G,T");
758 #ifdef md_elf_section_letter
759             int md_attr = md_elf_section_letter (*str, &bad_msg);
760             if (md_attr >= 0)
761               attr |= md_attr;
762             else
763 #endif
764               as_fatal ("%s", bad_msg);
765           }
766           break;
767         }
768       str++, len--;
769     }
770
771   return attr;
772 }
773
774 static int
775 obj_elf_section_word (char *str, size_t len)
776 {
777   if (len == 5 && strncmp (str, "write", 5) == 0)
778     return SHF_WRITE;
779   if (len == 5 && strncmp (str, "alloc", 5) == 0)
780     return SHF_ALLOC;
781   if (len == 9 && strncmp (str, "execinstr", 9) == 0)
782     return SHF_EXECINSTR;
783   if (len == 3 && strncmp (str, "tls", 3) == 0)
784     return SHF_TLS;
785
786 #ifdef md_elf_section_word
787   {
788     int md_attr = md_elf_section_word (str, len);
789     if (md_attr >= 0)
790       return md_attr;
791   }
792 #endif
793
794   as_warn (_("unrecognized section attribute"));
795   return 0;
796 }
797
798 static int
799 obj_elf_section_type (char *str, size_t len)
800 {
801   if (len == 8 && strncmp (str, "progbits", 8) == 0)
802     return SHT_PROGBITS;
803   if (len == 6 && strncmp (str, "nobits", 6) == 0)
804     return SHT_NOBITS;
805   if (len == 4 && strncmp (str, "note", 4) == 0)
806     return SHT_NOTE;
807   if (len == 10 && strncmp (str, "init_array", 10) == 0)
808     return SHT_INIT_ARRAY;
809   if (len == 10 && strncmp (str, "fini_array", 10) == 0)
810     return SHT_FINI_ARRAY;
811   if (len == 13 && strncmp (str, "preinit_array", 13) == 0)
812     return SHT_PREINIT_ARRAY;
813
814 #ifdef md_elf_section_type
815   {
816     int md_type = md_elf_section_type (str, len);
817     if (md_type >= 0)
818       return md_type;
819   }
820 #endif
821
822   as_warn (_("unrecognized section type"));
823   return 0;
824 }
825
826 /* Get name of section.  */
827 static char *
828 obj_elf_section_name (void)
829 {
830   char *name;
831
832   SKIP_WHITESPACE ();
833   if (*input_line_pointer == '"')
834     {
835       int dummy;
836
837       name = demand_copy_C_string (&dummy);
838       if (name == NULL)
839         {
840           ignore_rest_of_line ();
841           return NULL;
842         }
843     }
844   else
845     {
846       char *end = input_line_pointer;
847
848       while (0 == strchr ("\n\t,; ", *end))
849         end++;
850       if (end == input_line_pointer)
851         {
852           as_bad (_("missing name"));
853           ignore_rest_of_line ();
854           return NULL;
855         }
856
857       name = xmalloc (end - input_line_pointer + 1);
858       memcpy (name, input_line_pointer, end - input_line_pointer);
859       name[end - input_line_pointer] = '\0';
860 #ifdef tc_canonicalize_section_name
861       name = tc_canonicalize_section_name (name);
862 #endif
863       input_line_pointer = end;
864     }
865   SKIP_WHITESPACE ();
866   return name;
867 }
868
869 void
870 obj_elf_section (int push)
871 {
872   char *name, *group_name, *beg;
873   int type, attr, dummy;
874   int entsize;
875   int linkonce;
876
877 #ifndef TC_I370
878   if (flag_mri)
879     {
880       char mri_type;
881
882 #ifdef md_flush_pending_output
883       md_flush_pending_output ();
884 #endif
885
886       previous_section = now_seg;
887       previous_subsection = now_subseg;
888
889       s_mri_sect (&mri_type);
890
891 #ifdef md_elf_section_change_hook
892       md_elf_section_change_hook ();
893 #endif
894
895       return;
896     }
897 #endif /* ! defined (TC_I370) */
898
899   name = obj_elf_section_name ();
900   if (name == NULL)
901     return;
902   type = SHT_NULL;
903   attr = 0;
904   group_name = NULL;
905   entsize = 0;
906   linkonce = 0;
907
908   if (*input_line_pointer == ',')
909     {
910       /* Skip the comma.  */
911       ++input_line_pointer;
912       SKIP_WHITESPACE ();
913
914       if (*input_line_pointer == '"')
915         {
916           beg = demand_copy_C_string (&dummy);
917           if (beg == NULL)
918             {
919               ignore_rest_of_line ();
920               return;
921             }
922           attr |= obj_elf_parse_section_letters (beg, strlen (beg));
923
924           SKIP_WHITESPACE ();
925           if (*input_line_pointer == ',')
926             {
927               char c;
928               char *save = input_line_pointer;
929
930               ++input_line_pointer;
931               SKIP_WHITESPACE ();
932               c = *input_line_pointer;
933               if (c == '"')
934                 {
935                   beg = demand_copy_C_string (&dummy);
936                   if (beg == NULL)
937                     {
938                       ignore_rest_of_line ();
939                       return;
940                     }
941                   type = obj_elf_section_type (beg, strlen (beg));
942                 }
943               else if (c == '@' || c == '%')
944                 {
945                   beg = ++input_line_pointer;
946                   c = get_symbol_end ();
947                   *input_line_pointer = c;
948                   type = obj_elf_section_type (beg, input_line_pointer - beg);
949                 }
950               else
951                 input_line_pointer = save;
952             }
953
954           SKIP_WHITESPACE ();
955           if ((attr & SHF_MERGE) != 0 && *input_line_pointer == ',')
956             {
957               ++input_line_pointer;
958               SKIP_WHITESPACE ();
959               entsize = get_absolute_expression ();
960               SKIP_WHITESPACE ();
961               if (entsize < 0)
962                 {
963                   as_warn (_("invalid merge entity size"));
964                   attr &= ~SHF_MERGE;
965                   entsize = 0;
966                 }
967             }
968           else if ((attr & SHF_MERGE) != 0)
969             {
970               as_warn (_("entity size for SHF_MERGE not specified"));
971               attr &= ~SHF_MERGE;
972             }
973
974           if ((attr & SHF_GROUP) != 0 && *input_line_pointer == ',')
975             {
976               ++input_line_pointer;
977               group_name = obj_elf_section_name ();
978               if (group_name == NULL)
979                 attr &= ~SHF_GROUP;
980               else if (strncmp (input_line_pointer, ",comdat", 7) == 0)
981                 {
982                   input_line_pointer += 7;
983                   linkonce = 1;
984                 }
985               else if (strncmp (name, ".gnu.linkonce", 13) == 0)
986                 linkonce = 1;
987             }
988           else if ((attr & SHF_GROUP) != 0)
989             {
990               as_warn (_("group name for SHF_GROUP not specified"));
991               attr &= ~SHF_GROUP;
992             }
993         }
994       else
995         {
996           do
997             {
998               char c;
999
1000               SKIP_WHITESPACE ();
1001               if (*input_line_pointer != '#')
1002                 {
1003                   as_bad (_("character following name is not '#'"));
1004                   ignore_rest_of_line ();
1005                   return;
1006                 }
1007               beg = ++input_line_pointer;
1008               c = get_symbol_end ();
1009               *input_line_pointer = c;
1010
1011               attr |= obj_elf_section_word (beg, input_line_pointer - beg);
1012
1013               SKIP_WHITESPACE ();
1014             }
1015           while (*input_line_pointer++ == ',');
1016           --input_line_pointer;
1017         }
1018     }
1019
1020   demand_empty_rest_of_line ();
1021
1022   obj_elf_change_section (name, type, attr, entsize, group_name, linkonce, push);
1023 }
1024
1025 /* Change to the .data section.  */
1026
1027 void
1028 obj_elf_data (int i)
1029 {
1030 #ifdef md_flush_pending_output
1031   md_flush_pending_output ();
1032 #endif
1033
1034   previous_section = now_seg;
1035   previous_subsection = now_subseg;
1036   s_data (i);
1037
1038 #ifdef md_elf_section_change_hook
1039   md_elf_section_change_hook ();
1040 #endif
1041 }
1042
1043 /* Change to the .text section.  */
1044
1045 void
1046 obj_elf_text (int i)
1047 {
1048 #ifdef md_flush_pending_output
1049   md_flush_pending_output ();
1050 #endif
1051
1052   previous_section = now_seg;
1053   previous_subsection = now_subseg;
1054   s_text (i);
1055
1056 #ifdef md_elf_section_change_hook
1057   md_elf_section_change_hook ();
1058 #endif
1059 }
1060
1061 /* Change to the *ABS* section.  */
1062
1063 void
1064 obj_elf_struct (int i)
1065 {
1066 #ifdef md_flush_pending_output
1067   md_flush_pending_output ();
1068 #endif
1069
1070   previous_section = now_seg;
1071   previous_subsection = now_subseg;
1072   s_struct (i);
1073
1074 #ifdef md_elf_section_change_hook
1075   md_elf_section_change_hook ();
1076 #endif
1077 }
1078
1079 static void
1080 obj_elf_subsection (int ignore ATTRIBUTE_UNUSED)
1081 {
1082   register int temp;
1083
1084 #ifdef md_flush_pending_output
1085   md_flush_pending_output ();
1086 #endif
1087
1088   previous_section = now_seg;
1089   previous_subsection = now_subseg;
1090
1091   temp = get_absolute_expression ();
1092   subseg_set (now_seg, (subsegT) temp);
1093   demand_empty_rest_of_line ();
1094
1095 #ifdef md_elf_section_change_hook
1096   md_elf_section_change_hook ();
1097 #endif
1098 }
1099
1100 /* This can be called from the processor backends if they change
1101    sections.  */
1102
1103 void
1104 obj_elf_section_change_hook (void)
1105 {
1106   previous_section = now_seg;
1107   previous_subsection = now_subseg;
1108 }
1109
1110 void
1111 obj_elf_previous (int ignore ATTRIBUTE_UNUSED)
1112 {
1113   segT new_section;
1114   int new_subsection;
1115
1116   if (previous_section == 0)
1117     {
1118       as_warn (_(".previous without corresponding .section; ignored"));
1119       return;
1120     }
1121
1122 #ifdef md_flush_pending_output
1123   md_flush_pending_output ();
1124 #endif
1125
1126   new_section = previous_section;
1127   new_subsection = previous_subsection;
1128   previous_section = now_seg;
1129   previous_subsection = now_subseg;
1130   subseg_set (new_section, new_subsection);
1131
1132 #ifdef md_elf_section_change_hook
1133   md_elf_section_change_hook ();
1134 #endif
1135 }
1136
1137 static void
1138 obj_elf_popsection (int xxx ATTRIBUTE_UNUSED)
1139 {
1140   struct section_stack *top = section_stack;
1141
1142   if (top == NULL)
1143     {
1144       as_warn (_(".popsection without corresponding .pushsection; ignored"));
1145       return;
1146     }
1147
1148 #ifdef md_flush_pending_output
1149   md_flush_pending_output ();
1150 #endif
1151
1152   section_stack = top->next;
1153   previous_section = top->prev_seg;
1154   previous_subsection = top->prev_subseg;
1155   subseg_set (top->seg, top->subseg);
1156   free (top);
1157
1158 #ifdef md_elf_section_change_hook
1159   md_elf_section_change_hook ();
1160 #endif
1161 }
1162
1163 static void
1164 obj_elf_line (int ignore ATTRIBUTE_UNUSED)
1165 {
1166   /* Assume delimiter is part of expression.  BSD4.2 as fails with
1167      delightful bug, so we are not being incompatible here.  */
1168   new_logical_line (NULL, get_absolute_expression ());
1169   demand_empty_rest_of_line ();
1170 }
1171
1172 /* This handles the .symver pseudo-op, which is used to specify a
1173    symbol version.  The syntax is ``.symver NAME,SYMVERNAME''.
1174    SYMVERNAME may contain ELF_VER_CHR ('@') characters.  This
1175    pseudo-op causes the assembler to emit a symbol named SYMVERNAME
1176    with the same value as the symbol NAME.  */
1177
1178 static void
1179 obj_elf_symver (int ignore ATTRIBUTE_UNUSED)
1180 {
1181   char *name;
1182   char c;
1183   char old_lexat;
1184   symbolS *sym;
1185
1186   name = input_line_pointer;
1187   c = get_symbol_end ();
1188
1189   sym = symbol_find_or_make (name);
1190
1191   *input_line_pointer = c;
1192
1193   SKIP_WHITESPACE ();
1194   if (*input_line_pointer != ',')
1195     {
1196       as_bad (_("expected comma after name in .symver"));
1197       ignore_rest_of_line ();
1198       return;
1199     }
1200
1201   ++input_line_pointer;
1202   SKIP_WHITESPACE ();
1203   name = input_line_pointer;
1204
1205   /* Temporarily include '@' in symbol names.  */
1206   old_lexat = lex_type[(unsigned char) '@'];
1207   lex_type[(unsigned char) '@'] |= LEX_NAME;
1208   c = get_symbol_end ();
1209   lex_type[(unsigned char) '@'] = old_lexat;
1210
1211   if (symbol_get_obj (sym)->versioned_name == NULL)
1212     {
1213       symbol_get_obj (sym)->versioned_name = xstrdup (name);
1214
1215       *input_line_pointer = c;
1216
1217       if (strchr (symbol_get_obj (sym)->versioned_name,
1218                   ELF_VER_CHR) == NULL)
1219         {
1220           as_bad (_("missing version name in `%s' for symbol `%s'"),
1221                   symbol_get_obj (sym)->versioned_name,
1222                   S_GET_NAME (sym));
1223           ignore_rest_of_line ();
1224           return;
1225         }
1226     }
1227   else
1228     {
1229       if (strcmp (symbol_get_obj (sym)->versioned_name, name))
1230         {
1231           as_bad (_("multiple versions [`%s'|`%s'] for symbol `%s'"),
1232                   name, symbol_get_obj (sym)->versioned_name,
1233                   S_GET_NAME (sym));
1234           ignore_rest_of_line ();
1235           return;
1236         }
1237
1238       *input_line_pointer = c;
1239     }
1240
1241   demand_empty_rest_of_line ();
1242 }
1243
1244 /* This handles the .vtable_inherit pseudo-op, which is used to indicate
1245    to the linker the hierarchy in which a particular table resides.  The
1246    syntax is ".vtable_inherit CHILDNAME, PARENTNAME".  */
1247
1248 struct fix *
1249 obj_elf_vtable_inherit (int ignore ATTRIBUTE_UNUSED)
1250 {
1251   char *cname, *pname;
1252   symbolS *csym, *psym;
1253   char c, bad = 0;
1254
1255   if (*input_line_pointer == '#')
1256     ++input_line_pointer;
1257
1258   cname = input_line_pointer;
1259   c = get_symbol_end ();
1260   csym = symbol_find (cname);
1261
1262   /* GCFIXME: should check that we don't have two .vtable_inherits for
1263      the same child symbol.  Also, we can currently only do this if the
1264      child symbol is already exists and is placed in a fragment.  */
1265
1266   if (csym == NULL || symbol_get_frag (csym) == NULL)
1267     {
1268       as_bad ("expected `%s' to have already been set for .vtable_inherit",
1269               cname);
1270       bad = 1;
1271     }
1272
1273   *input_line_pointer = c;
1274
1275   SKIP_WHITESPACE ();
1276   if (*input_line_pointer != ',')
1277     {
1278       as_bad ("expected comma after name in .vtable_inherit");
1279       ignore_rest_of_line ();
1280       return NULL;
1281     }
1282
1283   ++input_line_pointer;
1284   SKIP_WHITESPACE ();
1285
1286   if (*input_line_pointer == '#')
1287     ++input_line_pointer;
1288
1289   if (input_line_pointer[0] == '0'
1290       && (input_line_pointer[1] == '\0'
1291           || ISSPACE (input_line_pointer[1])))
1292     {
1293       psym = section_symbol (absolute_section);
1294       ++input_line_pointer;
1295     }
1296   else
1297     {
1298       pname = input_line_pointer;
1299       c = get_symbol_end ();
1300       psym = symbol_find_or_make (pname);
1301       *input_line_pointer = c;
1302     }
1303
1304   demand_empty_rest_of_line ();
1305
1306   if (bad)
1307     return NULL;
1308
1309   assert (symbol_get_value_expression (csym)->X_op == O_constant);
1310   return fix_new (symbol_get_frag (csym),
1311                   symbol_get_value_expression (csym)->X_add_number,
1312                   0, psym, 0, 0, BFD_RELOC_VTABLE_INHERIT);
1313 }
1314
1315 /* This handles the .vtable_entry pseudo-op, which is used to indicate
1316    to the linker that a vtable slot was used.  The syntax is
1317    ".vtable_entry tablename, offset".  */
1318
1319 struct fix *
1320 obj_elf_vtable_entry (int ignore ATTRIBUTE_UNUSED)
1321 {
1322   char *name;
1323   symbolS *sym;
1324   offsetT offset;
1325   char c;
1326
1327   if (*input_line_pointer == '#')
1328     ++input_line_pointer;
1329
1330   name = input_line_pointer;
1331   c = get_symbol_end ();
1332   sym = symbol_find_or_make (name);
1333   *input_line_pointer = c;
1334
1335   SKIP_WHITESPACE ();
1336   if (*input_line_pointer != ',')
1337     {
1338       as_bad ("expected comma after name in .vtable_entry");
1339       ignore_rest_of_line ();
1340       return NULL;
1341     }
1342
1343   ++input_line_pointer;
1344   if (*input_line_pointer == '#')
1345     ++input_line_pointer;
1346
1347   offset = get_absolute_expression ();
1348
1349   demand_empty_rest_of_line ();
1350
1351   return fix_new (frag_now, frag_now_fix (), 0, sym, offset, 0,
1352                   BFD_RELOC_VTABLE_ENTRY);
1353 }
1354
1355 void
1356 elf_obj_read_begin_hook (void)
1357 {
1358 #ifdef NEED_ECOFF_DEBUG
1359   if (ECOFF_DEBUGGING)
1360     ecoff_read_begin_hook ();
1361 #endif
1362 }
1363
1364 void
1365 elf_obj_symbol_new_hook (symbolS *symbolP)
1366 {
1367   struct elf_obj_sy *sy_obj;
1368
1369   sy_obj = symbol_get_obj (symbolP);
1370   sy_obj->size = NULL;
1371   sy_obj->versioned_name = NULL;
1372
1373 #ifdef NEED_ECOFF_DEBUG
1374   if (ECOFF_DEBUGGING)
1375     ecoff_symbol_new_hook (symbolP);
1376 #endif
1377 }
1378
1379 /* When setting one symbol equal to another, by default we probably
1380    want them to have the same "size", whatever it means in the current
1381    context.  */
1382
1383 void
1384 elf_copy_symbol_attributes (symbolS *dest, symbolS *src)
1385 {
1386   struct elf_obj_sy *srcelf = symbol_get_obj (src);
1387   struct elf_obj_sy *destelf = symbol_get_obj (dest);
1388   if (srcelf->size)
1389     {
1390       if (destelf->size == NULL)
1391         destelf->size = xmalloc (sizeof (expressionS));
1392       *destelf->size = *srcelf->size;
1393     }
1394   else
1395     {
1396       if (destelf->size != NULL)
1397         free (destelf->size);
1398       destelf->size = NULL;
1399     }
1400   S_SET_SIZE (dest, S_GET_SIZE (src));
1401   /* Don't copy visibility.  */
1402   S_SET_OTHER (dest, (ELF_ST_VISIBILITY (S_GET_OTHER (dest))
1403                       | (S_GET_OTHER (src) & ~ELF_ST_VISIBILITY (-1))));
1404 }
1405
1406 void
1407 obj_elf_version (int ignore ATTRIBUTE_UNUSED)
1408 {
1409   char *name;
1410   unsigned int c;
1411   char *p;
1412   asection *seg = now_seg;
1413   subsegT subseg = now_subseg;
1414   Elf_Internal_Note i_note;
1415   Elf_External_Note e_note;
1416   asection *note_secp = NULL;
1417   int len;
1418
1419   SKIP_WHITESPACE ();
1420   if (*input_line_pointer == '\"')
1421     {
1422       ++input_line_pointer;     /* -> 1st char of string.  */
1423       name = input_line_pointer;
1424
1425       while (is_a_char (c = next_char_of_string ()))
1426         ;
1427       c = *input_line_pointer;
1428       *input_line_pointer = '\0';
1429       *(input_line_pointer - 1) = '\0';
1430       *input_line_pointer = c;
1431
1432       /* create the .note section */
1433
1434       note_secp = subseg_new (".note", 0);
1435       bfd_set_section_flags (stdoutput,
1436                              note_secp,
1437                              SEC_HAS_CONTENTS | SEC_READONLY);
1438
1439       /* process the version string */
1440
1441       len = strlen (name);
1442
1443       i_note.namesz = ((len + 1) + 3) & ~3; /* round this to word boundary */
1444       i_note.descsz = 0;        /* no description */
1445       i_note.type = NT_VERSION;
1446       p = frag_more (sizeof (e_note.namesz));
1447       md_number_to_chars (p, i_note.namesz, sizeof (e_note.namesz));
1448       p = frag_more (sizeof (e_note.descsz));
1449       md_number_to_chars (p, i_note.descsz, sizeof (e_note.descsz));
1450       p = frag_more (sizeof (e_note.type));
1451       md_number_to_chars (p, i_note.type, sizeof (e_note.type));
1452       p = frag_more (len + 1);
1453       strcpy (p, name);
1454
1455       frag_align (2, 0, 0);
1456
1457       subseg_set (seg, subseg);
1458     }
1459   else
1460     {
1461       as_bad (_("expected quoted string"));
1462     }
1463   demand_empty_rest_of_line ();
1464 }
1465
1466 static void
1467 obj_elf_size (int ignore ATTRIBUTE_UNUSED)
1468 {
1469   char *name = input_line_pointer;
1470   char c = get_symbol_end ();
1471   char *p;
1472   expressionS exp;
1473   symbolS *sym;
1474
1475   p = input_line_pointer;
1476   *p = c;
1477   SKIP_WHITESPACE ();
1478   if (*input_line_pointer != ',')
1479     {
1480       *p = 0;
1481       as_bad (_("expected comma after name `%s' in .size directive"), name);
1482       *p = c;
1483       ignore_rest_of_line ();
1484       return;
1485     }
1486   input_line_pointer++;
1487   expression (&exp);
1488   if (exp.X_op == O_absent)
1489     {
1490       as_bad (_("missing expression in .size directive"));
1491       exp.X_op = O_constant;
1492       exp.X_add_number = 0;
1493     }
1494   *p = 0;
1495   sym = symbol_find_or_make (name);
1496   *p = c;
1497   if (exp.X_op == O_constant)
1498     {
1499       S_SET_SIZE (sym, exp.X_add_number);
1500       if (symbol_get_obj (sym)->size)
1501         {
1502           xfree (symbol_get_obj (sym)->size);
1503           symbol_get_obj (sym)->size = NULL;
1504         }
1505     }
1506   else
1507     {
1508       symbol_get_obj (sym)->size = xmalloc (sizeof (expressionS));
1509       *symbol_get_obj (sym)->size = exp;
1510     }
1511   demand_empty_rest_of_line ();
1512 }
1513
1514 /* Handle the ELF .type pseudo-op.  This sets the type of a symbol.
1515    There are five syntaxes:
1516
1517    The first (used on Solaris) is
1518        .type SYM,#function
1519    The second (used on UnixWare) is
1520        .type SYM,@function
1521    The third (reportedly to be used on Irix 6.0) is
1522        .type SYM STT_FUNC
1523    The fourth (used on NetBSD/Arm and Linux/ARM) is
1524        .type SYM,%function
1525    The fifth (used on SVR4/860) is
1526        .type SYM,"function"
1527    */
1528
1529 static void
1530 obj_elf_type (int ignore ATTRIBUTE_UNUSED)
1531 {
1532   char *name;
1533   char c;
1534   int type;
1535   const char *typename;
1536   symbolS *sym;
1537   elf_symbol_type *elfsym;
1538
1539   name = input_line_pointer;
1540   c = get_symbol_end ();
1541   sym = symbol_find_or_make (name);
1542   elfsym = (elf_symbol_type *) symbol_get_bfdsym (sym);
1543   *input_line_pointer = c;
1544
1545   SKIP_WHITESPACE ();
1546   if (*input_line_pointer == ',')
1547     ++input_line_pointer;
1548
1549   SKIP_WHITESPACE ();
1550   if (   *input_line_pointer == '#'
1551       || *input_line_pointer == '@'
1552       || *input_line_pointer == '"'
1553       || *input_line_pointer == '%')
1554     ++input_line_pointer;
1555
1556   typename = input_line_pointer;
1557   c = get_symbol_end ();
1558
1559   type = 0;
1560   if (strcmp (typename, "function") == 0
1561       || strcmp (typename, "STT_FUNC") == 0)
1562     type = BSF_FUNCTION;
1563   else if (strcmp (typename, "object") == 0
1564            || strcmp (typename, "STT_OBJECT") == 0)
1565     type = BSF_OBJECT;
1566   else if (strcmp (typename, "tls_object") == 0
1567            || strcmp (typename, "STT_TLS") == 0)
1568     type = BSF_OBJECT | BSF_THREAD_LOCAL;
1569   else if (strcmp (typename, "notype") == 0
1570            || strcmp (typename, "STT_NOTYPE") == 0)
1571     ;
1572 #ifdef md_elf_symbol_type
1573   else if ((type = md_elf_symbol_type (typename, sym, elfsym)) != -1)
1574     ;
1575 #endif
1576   else
1577     as_bad (_("unrecognized symbol type \"%s\""), typename);
1578
1579   *input_line_pointer = c;
1580
1581   if (*input_line_pointer == '"')
1582     ++input_line_pointer;
1583
1584   elfsym->symbol.flags |= type;
1585
1586   demand_empty_rest_of_line ();
1587 }
1588
1589 static void
1590 obj_elf_ident (int ignore ATTRIBUTE_UNUSED)
1591 {
1592   static segT comment_section;
1593   segT old_section = now_seg;
1594   int old_subsection = now_subseg;
1595
1596 #ifdef md_flush_pending_output
1597   md_flush_pending_output ();
1598 #endif
1599
1600   if (!comment_section)
1601     {
1602       char *p;
1603       comment_section = subseg_new (".comment", 0);
1604       bfd_set_section_flags (stdoutput, comment_section,
1605                              SEC_READONLY | SEC_HAS_CONTENTS);
1606       p = frag_more (1);
1607       *p = 0;
1608     }
1609   else
1610     subseg_set (comment_section, 0);
1611   stringer (1);
1612   subseg_set (old_section, old_subsection);
1613 }
1614
1615 #ifdef INIT_STAB_SECTION
1616
1617 /* The first entry in a .stabs section is special.  */
1618
1619 void
1620 obj_elf_init_stab_section (segT seg)
1621 {
1622   char *file;
1623   char *p;
1624   char *stabstr_name;
1625   unsigned int stroff;
1626
1627   /* Force the section to align to a longword boundary.  Without this,
1628      UnixWare ar crashes.  */
1629   bfd_set_section_alignment (stdoutput, seg, 2);
1630
1631   /* Make space for this first symbol.  */
1632   p = frag_more (12);
1633   /* Zero it out.  */
1634   memset (p, 0, 12);
1635   as_where (&file, NULL);
1636   stabstr_name = xmalloc (strlen (segment_name (seg)) + 4);
1637   strcpy (stabstr_name, segment_name (seg));
1638   strcat (stabstr_name, "str");
1639   stroff = get_stab_string_offset (file, stabstr_name);
1640   know (stroff == 1);
1641   md_number_to_chars (p, stroff, 4);
1642   seg_info (seg)->stabu.p = p;
1643 }
1644
1645 #endif
1646
1647 /* Fill in the counts in the first entry in a .stabs section.  */
1648
1649 static void
1650 adjust_stab_sections (bfd *abfd, asection *sec, void *xxx ATTRIBUTE_UNUSED)
1651 {
1652   char *name;
1653   asection *strsec;
1654   char *p;
1655   int strsz, nsyms;
1656
1657   if (strncmp (".stab", sec->name, 5))
1658     return;
1659   if (!strcmp ("str", sec->name + strlen (sec->name) - 3))
1660     return;
1661
1662   name = alloca (strlen (sec->name) + 4);
1663   strcpy (name, sec->name);
1664   strcat (name, "str");
1665   strsec = bfd_get_section_by_name (abfd, name);
1666   if (strsec)
1667     strsz = bfd_section_size (abfd, strsec);
1668   else
1669     strsz = 0;
1670   nsyms = bfd_section_size (abfd, sec) / 12 - 1;
1671
1672   p = seg_info (sec)->stabu.p;
1673   assert (p != 0);
1674
1675   bfd_h_put_16 (abfd, nsyms, p + 6);
1676   bfd_h_put_32 (abfd, strsz, p + 8);
1677 }
1678
1679 #ifdef NEED_ECOFF_DEBUG
1680
1681 /* This function is called by the ECOFF code.  It is supposed to
1682    record the external symbol information so that the backend can
1683    write it out correctly.  The ELF backend doesn't actually handle
1684    this at the moment, so we do it ourselves.  We save the information
1685    in the symbol.  */
1686
1687 void
1688 elf_ecoff_set_ext (symbolS *sym, struct ecoff_extr *ext)
1689 {
1690   symbol_get_bfdsym (sym)->udata.p = ext;
1691 }
1692
1693 /* This function is called by bfd_ecoff_debug_externals.  It is
1694    supposed to *EXT to the external symbol information, and return
1695    whether the symbol should be used at all.  */
1696
1697 static bfd_boolean
1698 elf_get_extr (asymbol *sym, EXTR *ext)
1699 {
1700   if (sym->udata.p == NULL)
1701     return FALSE;
1702   *ext = *(EXTR *) sym->udata.p;
1703   return TRUE;
1704 }
1705
1706 /* This function is called by bfd_ecoff_debug_externals.  It has
1707    nothing to do for ELF.  */
1708
1709 static void
1710 elf_set_index (asymbol *sym ATTRIBUTE_UNUSED,
1711                bfd_size_type indx ATTRIBUTE_UNUSED)
1712 {
1713 }
1714
1715 #endif /* NEED_ECOFF_DEBUG */
1716
1717 void
1718 elf_frob_symbol (symbolS *symp, int *puntp)
1719 {
1720   struct elf_obj_sy *sy_obj;
1721
1722 #ifdef NEED_ECOFF_DEBUG
1723   if (ECOFF_DEBUGGING)
1724     ecoff_frob_symbol (symp);
1725 #endif
1726
1727   sy_obj = symbol_get_obj (symp);
1728
1729   if (sy_obj->size != NULL)
1730     {
1731       switch (sy_obj->size->X_op)
1732         {
1733         case O_subtract:
1734           S_SET_SIZE (symp,
1735                       (S_GET_VALUE (sy_obj->size->X_add_symbol)
1736                        + sy_obj->size->X_add_number
1737                        - S_GET_VALUE (sy_obj->size->X_op_symbol)));
1738           break;
1739         case O_constant:
1740           S_SET_SIZE (symp,
1741                       (S_GET_VALUE (sy_obj->size->X_add_symbol)
1742                        + sy_obj->size->X_add_number));
1743           break;
1744         default:
1745           as_bad (_(".size expression too complicated to fix up"));
1746           break;
1747         }
1748       free (sy_obj->size);
1749       sy_obj->size = NULL;
1750     }
1751
1752   if (sy_obj->versioned_name != NULL)
1753     {
1754       char *p;
1755
1756       p = strchr (sy_obj->versioned_name, ELF_VER_CHR);
1757       know (p != NULL);
1758
1759       /* This symbol was given a new name with the .symver directive.
1760
1761          If this is an external reference, just rename the symbol to
1762          include the version string.  This will make the relocs be
1763          against the correct versioned symbol.
1764
1765          If this is a definition, add an alias.  FIXME: Using an alias
1766          will permit the debugging information to refer to the right
1767          symbol.  However, it's not clear whether it is the best
1768          approach.  */
1769
1770       if (! S_IS_DEFINED (symp))
1771         {
1772           /* Verify that the name isn't using the @@ syntax--this is
1773              reserved for definitions of the default version to link
1774              against.  */
1775           if (p[1] == ELF_VER_CHR)
1776             {
1777               as_bad (_("invalid attempt to declare external version name as default in symbol `%s'"),
1778                       sy_obj->versioned_name);
1779               *puntp = TRUE;
1780             }
1781           S_SET_NAME (symp, sy_obj->versioned_name);
1782         }
1783       else
1784         {
1785           if (p[1] == ELF_VER_CHR && p[2] == ELF_VER_CHR)
1786             {
1787               size_t l;
1788
1789               /* The @@@ syntax is a special case. It renames the
1790                  symbol name to versioned_name with one `@' removed.  */
1791               l = strlen (&p[3]) + 1;
1792               memmove (&p[2], &p[3], l);
1793               S_SET_NAME (symp, sy_obj->versioned_name);
1794             }
1795           else
1796             {
1797               symbolS *symp2;
1798
1799               /* FIXME: Creating a new symbol here is risky.  We're
1800                  in the final loop over the symbol table.  We can
1801                  get away with it only because the symbol goes to
1802                  the end of the list, where the loop will still see
1803                  it.  It would probably be better to do this in
1804                  obj_frob_file_before_adjust.  */
1805
1806               symp2 = symbol_find_or_make (sy_obj->versioned_name);
1807
1808               /* Now we act as though we saw symp2 = sym.  */
1809
1810               S_SET_SEGMENT (symp2, S_GET_SEGMENT (symp));
1811
1812               /* Subtracting out the frag address here is a hack
1813                  because we are in the middle of the final loop.  */
1814               S_SET_VALUE (symp2,
1815                            (S_GET_VALUE (symp)
1816                             - symbol_get_frag (symp)->fr_address));
1817
1818               symbol_set_frag (symp2, symbol_get_frag (symp));
1819
1820               /* This will copy over the size information.  */
1821               copy_symbol_attributes (symp2, symp);
1822
1823               S_SET_OTHER (symp2, S_GET_OTHER (symp));
1824
1825               if (S_IS_WEAK (symp))
1826                 S_SET_WEAK (symp2);
1827
1828               if (S_IS_EXTERNAL (symp))
1829                 S_SET_EXTERNAL (symp2);
1830             }
1831         }
1832     }
1833
1834   /* Double check weak symbols.  */
1835   if (S_IS_WEAK (symp))
1836     {
1837       if (S_IS_COMMON (symp))
1838         as_bad (_("symbol `%s' can not be both weak and common"),
1839                 S_GET_NAME (symp));
1840     }
1841
1842 #ifdef TC_MIPS
1843   /* The Irix 5 and 6 assemblers set the type of any common symbol and
1844      any undefined non-function symbol to STT_OBJECT.  We try to be
1845      compatible, since newer Irix 5 and 6 linkers care.  However, we
1846      only set undefined symbols to be STT_OBJECT if we are on Irix,
1847      because that is the only time gcc will generate the necessary
1848      .global directives to mark functions.  */
1849
1850   if (S_IS_COMMON (symp))
1851     symbol_get_bfdsym (symp)->flags |= BSF_OBJECT;
1852
1853   if (strstr (TARGET_OS, "irix") != NULL
1854       && ! S_IS_DEFINED (symp)
1855       && (symbol_get_bfdsym (symp)->flags & BSF_FUNCTION) == 0)
1856     symbol_get_bfdsym (symp)->flags |= BSF_OBJECT;
1857 #endif
1858 }
1859
1860 struct group_list
1861 {
1862   asection **head;              /* Section lists.  */
1863   unsigned int *elt_count;      /* Number of sections in each list.  */
1864   unsigned int num_group;       /* Number of lists.  */
1865 };
1866
1867 /* Called via bfd_map_over_sections.  If SEC is a member of a group,
1868    add it to a list of sections belonging to the group.  INF is a
1869    pointer to a struct group_list, which is where we store the head of
1870    each list.  */
1871
1872 static void
1873 build_group_lists (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, void *inf)
1874 {
1875   struct group_list *list = inf;
1876   const char *group_name = elf_group_name (sec);
1877   unsigned int i;
1878
1879   if (group_name == NULL)
1880     return;
1881
1882   /* If this group already has a list, add the section to the head of
1883      the list.  */
1884   for (i = 0; i < list->num_group; i++)
1885     {
1886       if (strcmp (group_name, elf_group_name (list->head[i])) == 0)
1887         {
1888           elf_next_in_group (sec) = list->head[i];
1889           list->head[i] = sec;
1890           list->elt_count[i] += 1;
1891           return;
1892         }
1893     }
1894
1895   /* New group.  Make the arrays bigger in chunks to minimize calls to
1896      realloc.  */
1897   i = list->num_group;
1898   if ((i & 127) == 0)
1899     {
1900       unsigned int newsize = i + 128;
1901       list->head = xrealloc (list->head, newsize * sizeof (*list->head));
1902       list->elt_count = xrealloc (list->elt_count,
1903                                   newsize * sizeof (*list->elt_count));
1904     }
1905   list->head[i] = sec;
1906   list->elt_count[i] = 1;
1907   list->num_group += 1;
1908 }
1909
1910 void
1911 elf_frob_file (void)
1912 {
1913   struct group_list list;
1914   unsigned int i;
1915
1916   bfd_map_over_sections (stdoutput, adjust_stab_sections, NULL);
1917
1918   /* Go find section groups.  */
1919   list.num_group = 0;
1920   list.head = NULL;
1921   list.elt_count = NULL;
1922   bfd_map_over_sections (stdoutput, build_group_lists, &list);
1923
1924   /* Make the SHT_GROUP sections that describe each section group.  We
1925      can't set up the section contents here yet, because elf section
1926      indices have yet to be calculated.  elf.c:set_group_contents does
1927      the rest of the work.  */
1928   for (i = 0; i < list.num_group; i++)
1929     {
1930       const char *group_name = elf_group_name (list.head[i]);
1931       const char *sec_name;
1932       asection *s;
1933       flagword flags;
1934       struct symbol *sy;
1935       int has_sym;
1936       bfd_size_type size;
1937
1938       flags = SEC_READONLY | SEC_HAS_CONTENTS | SEC_IN_MEMORY | SEC_GROUP;
1939       for (s = list.head[i]; s != NULL; s = elf_next_in_group (s))
1940         if ((s->flags ^ flags) & SEC_LINK_ONCE)
1941           {
1942             flags |= SEC_LINK_ONCE | SEC_LINK_DUPLICATES_DISCARD;
1943             if (s != list.head[i])
1944               {
1945                 as_warn (_("assuming all members of group `%s' are COMDAT"),
1946                          group_name);
1947                 break;
1948               }
1949           }
1950
1951       sec_name = group_name;
1952       sy = symbol_find_exact (group_name);
1953       has_sym = 0;
1954       if (sy != NULL
1955           && (sy == symbol_lastP
1956               || (sy->sy_next != NULL
1957                   && sy->sy_next->sy_previous == sy)))
1958         {
1959           has_sym = 1;
1960           sec_name = ".group";
1961         }
1962       s = subseg_force_new (sec_name, 0);
1963       if (s == NULL
1964           || !bfd_set_section_flags (stdoutput, s, flags)
1965           || !bfd_set_section_alignment (stdoutput, s, 2))
1966         {
1967           as_fatal (_("can't create group: %s"),
1968                     bfd_errmsg (bfd_get_error ()));
1969         }
1970       elf_section_type (s) = SHT_GROUP;
1971
1972       /* Pass a pointer to the first section in this group.  */
1973       elf_next_in_group (s) = list.head[i];
1974       if (has_sym)
1975         elf_group_id (s) = sy->bsym;
1976
1977       size = 4 * (list.elt_count[i] + 1);
1978       bfd_set_section_size (stdoutput, s, size);
1979       s->contents = (unsigned char *) frag_more (size);
1980       frag_now->fr_fix = frag_now_fix_octets ();
1981     }
1982
1983 #ifdef elf_tc_final_processing
1984   elf_tc_final_processing ();
1985 #endif
1986 }
1987
1988 /* It removes any unneeded versioned symbols from the symbol table.  */
1989
1990 void
1991 elf_frob_file_before_adjust (void)
1992 {
1993   if (symbol_rootP)
1994     {
1995       symbolS *symp;
1996
1997       for (symp = symbol_rootP; symp; symp = symbol_next (symp))
1998         if (!S_IS_DEFINED (symp))
1999           {
2000             if (symbol_get_obj (symp)->versioned_name)
2001               {
2002                 char *p;
2003
2004                 /* The @@@ syntax is a special case. If the symbol is
2005                    not defined, 2 `@'s will be removed from the
2006                    versioned_name.  */
2007
2008                 p = strchr (symbol_get_obj (symp)->versioned_name,
2009                             ELF_VER_CHR);
2010                 know (p != NULL);
2011                 if (p[1] == ELF_VER_CHR && p[2] == ELF_VER_CHR)
2012                   {
2013                     size_t l = strlen (&p[3]) + 1;
2014                     memmove (&p[1], &p[3], l);
2015                   }
2016                 if (symbol_used_p (symp) == 0
2017                     && symbol_used_in_reloc_p (symp) == 0)
2018                   symbol_remove (symp, &symbol_rootP, &symbol_lastP);
2019               }
2020
2021             /* If there was .weak foo, but foo was neither defined nor
2022                used anywhere, remove it.  */
2023
2024             else if (S_IS_WEAK (symp)
2025                      && symbol_used_p (symp) == 0
2026                      && symbol_used_in_reloc_p (symp) == 0)
2027               symbol_remove (symp, &symbol_rootP, &symbol_lastP);
2028           }
2029     }
2030 }
2031
2032 /* It is required that we let write_relocs have the opportunity to
2033    optimize away fixups before output has begun, since it is possible
2034    to eliminate all fixups for a section and thus we never should
2035    have generated the relocation section.  */
2036
2037 void
2038 elf_frob_file_after_relocs (void)
2039 {
2040 #ifdef NEED_ECOFF_DEBUG
2041   if (ECOFF_DEBUGGING)
2042     /* Generate the ECOFF debugging information.  */
2043     {
2044       const struct ecoff_debug_swap *debug_swap;
2045       struct ecoff_debug_info debug;
2046       char *buf;
2047       asection *sec;
2048
2049       debug_swap
2050         = get_elf_backend_data (stdoutput)->elf_backend_ecoff_debug_swap;
2051       know (debug_swap != NULL);
2052       ecoff_build_debug (&debug.symbolic_header, &buf, debug_swap);
2053
2054       /* Set up the pointers in debug.  */
2055 #define SET(ptr, offset, type) \
2056     debug.ptr = (type) (buf + debug.symbolic_header.offset)
2057
2058       SET (line, cbLineOffset, unsigned char *);
2059       SET (external_dnr, cbDnOffset, void *);
2060       SET (external_pdr, cbPdOffset, void *);
2061       SET (external_sym, cbSymOffset, void *);
2062       SET (external_opt, cbOptOffset, void *);
2063       SET (external_aux, cbAuxOffset, union aux_ext *);
2064       SET (ss, cbSsOffset, char *);
2065       SET (external_fdr, cbFdOffset, void *);
2066       SET (external_rfd, cbRfdOffset, void *);
2067       /* ssext and external_ext are set up just below.  */
2068
2069 #undef SET
2070
2071       /* Set up the external symbols.  */
2072       debug.ssext = debug.ssext_end = NULL;
2073       debug.external_ext = debug.external_ext_end = NULL;
2074       if (! bfd_ecoff_debug_externals (stdoutput, &debug, debug_swap, TRUE,
2075                                        elf_get_extr, elf_set_index))
2076         as_fatal (_("failed to set up debugging information: %s"),
2077                   bfd_errmsg (bfd_get_error ()));
2078
2079       sec = bfd_get_section_by_name (stdoutput, ".mdebug");
2080       assert (sec != NULL);
2081
2082       know (!stdoutput->output_has_begun);
2083
2084       /* We set the size of the section, call bfd_set_section_contents
2085          to force the ELF backend to allocate a file position, and then
2086          write out the data.  FIXME: Is this really the best way to do
2087          this?  */
2088       bfd_set_section_size
2089         (stdoutput, sec, bfd_ecoff_debug_size (stdoutput, &debug, debug_swap));
2090
2091       /* Pass BUF to bfd_set_section_contents because this will
2092          eventually become a call to fwrite, and ISO C prohibits
2093          passing a NULL pointer to a stdio function even if the
2094          pointer will not be used.  */
2095       if (! bfd_set_section_contents (stdoutput, sec, buf, 0, 0))
2096         as_fatal (_("can't start writing .mdebug section: %s"),
2097                   bfd_errmsg (bfd_get_error ()));
2098
2099       know (stdoutput->output_has_begun);
2100       know (sec->filepos != 0);
2101
2102       if (! bfd_ecoff_write_debug (stdoutput, &debug, debug_swap,
2103                                    sec->filepos))
2104         as_fatal (_("could not write .mdebug section: %s"),
2105                   bfd_errmsg (bfd_get_error ()));
2106     }
2107 #endif /* NEED_ECOFF_DEBUG */
2108 }
2109
2110 #ifdef SCO_ELF
2111
2112 /* Heavily plagiarized from obj_elf_version.  The idea is to emit the
2113    SCO specific identifier in the .notes section to satisfy the SCO
2114    linker.
2115
2116    This looks more complicated than it really is.  As opposed to the
2117    "obvious" solution, this should handle the cross dev cases
2118    correctly.  (i.e, hosting on a 64 bit big endian processor, but
2119    generating SCO Elf code) Efficiency isn't a concern, as there
2120    should be exactly one of these sections per object module.
2121
2122    SCO OpenServer 5 identifies it's ELF modules with a standard ELF
2123    .note section.
2124
2125    int_32 namesz  = 4 ;  Name size
2126    int_32 descsz  = 12 ; Descriptive information
2127    int_32 type    = 1 ;
2128    char   name[4] = "SCO" ; Originator name ALWAYS SCO + NULL
2129    int_32 version = (major ver # << 16)  | version of tools ;
2130    int_32 source  = (tool_id << 16 ) | 1 ;
2131    int_32 info    = 0 ;    These are set by the SCO tools, but we
2132                            don't know enough about the source
2133                            environment to set them.  SCO ld currently
2134                            ignores them, and recommends we set them
2135                            to zero.  */
2136
2137 #define SCO_MAJOR_VERSION 0x1
2138 #define SCO_MINOR_VERSION 0x1
2139
2140 void
2141 sco_id (void)
2142 {
2143
2144   char *name;
2145   unsigned int c;
2146   char ch;
2147   char *p;
2148   asection *seg = now_seg;
2149   subsegT subseg = now_subseg;
2150   Elf_Internal_Note i_note;
2151   Elf_External_Note e_note;
2152   asection *note_secp = NULL;
2153   int i, len;
2154
2155   /* create the .note section */
2156
2157   note_secp = subseg_new (".note", 0);
2158   bfd_set_section_flags (stdoutput,
2159                          note_secp,
2160                          SEC_HAS_CONTENTS | SEC_READONLY);
2161
2162   /* process the version string */
2163
2164   i_note.namesz = 4;
2165   i_note.descsz = 12;           /* 12 descriptive bytes */
2166   i_note.type = NT_VERSION;     /* Contains a version string */
2167
2168   p = frag_more (sizeof (i_note.namesz));
2169   md_number_to_chars (p, i_note.namesz, 4);
2170
2171   p = frag_more (sizeof (i_note.descsz));
2172   md_number_to_chars (p, i_note.descsz, 4);
2173
2174   p = frag_more (sizeof (i_note.type));
2175   md_number_to_chars (p, i_note.type, 4);
2176
2177   p = frag_more (4);
2178   strcpy (p, "SCO");
2179
2180   /* Note: this is the version number of the ELF we're representing */
2181   p = frag_more (4);
2182   md_number_to_chars (p, (SCO_MAJOR_VERSION << 16) | (SCO_MINOR_VERSION), 4);
2183
2184   /* Here, we pick a magic number for ourselves (yes, I "registered"
2185      it with SCO.  The bottom bit shows that we are compat with the
2186      SCO ABI.  */
2187   p = frag_more (4);
2188   md_number_to_chars (p, 0x4c520000 | 0x0001, 4);
2189
2190   /* If we knew (or cared) what the source language options were, we'd
2191      fill them in here.  SCO has given us permission to ignore these
2192      and just set them to zero.  */
2193   p = frag_more (4);
2194   md_number_to_chars (p, 0x0000, 4);
2195
2196   frag_align (2, 0, 0);
2197
2198   /* We probably can't restore the current segment, for there likely
2199      isn't one yet...  */
2200   if (seg && subseg)
2201     subseg_set (seg, subseg);
2202
2203 }
2204
2205 #endif /* SCO_ELF */
2206
2207 static int
2208 elf_separate_stab_sections (void)
2209 {
2210 #ifdef NEED_ECOFF_DEBUG
2211   return (!ECOFF_DEBUGGING);
2212 #else
2213   return 1;
2214 #endif
2215 }
2216
2217 static void
2218 elf_init_stab_section (segT seg)
2219 {
2220 #ifdef NEED_ECOFF_DEBUG
2221   if (!ECOFF_DEBUGGING)
2222 #endif
2223     obj_elf_init_stab_section (seg);
2224 }
2225
2226 const struct format_ops elf_format_ops =
2227 {
2228   bfd_target_elf_flavour,
2229   0,    /* dfl_leading_underscore */
2230   1,    /* emit_section_symbols */
2231   elf_begin,
2232   elf_file_symbol,
2233   elf_frob_symbol,
2234   elf_frob_file,
2235   elf_frob_file_before_adjust,
2236   0,    /* obj_frob_file_before_fix */
2237   elf_frob_file_after_relocs,
2238   elf_s_get_size, elf_s_set_size,
2239   elf_s_get_align, elf_s_set_align,
2240   elf_s_get_other,
2241   elf_s_set_other,
2242   0,    /* s_get_desc */
2243   0,    /* s_set_desc */
2244   0,    /* s_get_type */
2245   0,    /* s_set_type */
2246   elf_copy_symbol_attributes,
2247 #ifdef NEED_ECOFF_DEBUG
2248   ecoff_generate_asm_lineno,
2249   ecoff_stab,
2250 #else
2251   0,    /* generate_asm_lineno */
2252   0,    /* process_stab */
2253 #endif
2254   elf_separate_stab_sections,
2255   elf_init_stab_section,
2256   elf_sec_sym_ok_for_reloc,
2257   elf_pop_insert,
2258 #ifdef NEED_ECOFF_DEBUG
2259   elf_ecoff_set_ext,
2260 #else
2261   0,    /* ecoff_set_ext */
2262 #endif
2263   elf_obj_read_begin_hook,
2264   elf_obj_symbol_new_hook
2265 };