obj-elf.c revision 33965
1/* ELF object file format 2 Copyright (C) 1992, 93, 94, 95, 96, 1997 Free Software Foundation, Inc. 3 4 This file is part of GAS, the GNU Assembler. 5 6 GAS is free software; you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as 8 published by the Free Software Foundation; either version 2, 9 or (at your option) any later version. 10 11 GAS is distributed in the hope that it will be useful, but 12 WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See 14 the GNU General Public License for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with GAS; see the file COPYING. If not, write to the Free 18 Software Foundation, 59 Temple Place - Suite 330, Boston, MA 19 02111-1307, USA. */ 20 21#define OBJ_HEADER "obj-elf.h" 22#include "as.h" 23#include "subsegs.h" 24#include "obstack.h" 25 26#ifndef ECOFF_DEBUGGING 27#define ECOFF_DEBUGGING 0 28#else 29#define NEED_ECOFF_DEBUG 30#endif 31 32#ifdef NEED_ECOFF_DEBUG 33#include "ecoff.h" 34#endif 35 36#ifdef TC_MIPS 37#include "elf/mips.h" 38#endif 39 40#ifdef TC_PPC 41#include "elf/ppc.h" 42#endif 43 44static bfd_vma elf_s_get_size PARAMS ((symbolS *)); 45static void elf_s_set_size PARAMS ((symbolS *, bfd_vma)); 46static bfd_vma elf_s_get_align PARAMS ((symbolS *)); 47static void elf_s_set_align PARAMS ((symbolS *, bfd_vma)); 48static void elf_copy_symbol_attributes PARAMS ((symbolS *, symbolS *)); 49static int elf_sec_sym_ok_for_reloc PARAMS ((asection *)); 50static void adjust_stab_sections PARAMS ((bfd *, asection *, PTR)); 51 52#ifdef NEED_ECOFF_DEBUG 53static boolean elf_get_extr PARAMS ((asymbol *, EXTR *)); 54static void elf_set_index PARAMS ((asymbol *, bfd_size_type)); 55#endif 56 57static void obj_elf_line PARAMS ((int)); 58void obj_elf_version PARAMS ((int)); 59static void obj_elf_size PARAMS ((int)); 60static void obj_elf_type PARAMS ((int)); 61static void obj_elf_ident PARAMS ((int)); 62static void obj_elf_weak PARAMS ((int)); 63static void obj_elf_local PARAMS ((int)); 64static void obj_elf_common PARAMS ((int)); 65static void obj_elf_symver PARAMS ((int)); 66static void obj_elf_data PARAMS ((int)); 67static void obj_elf_text PARAMS ((int)); 68 69static const pseudo_typeS elf_pseudo_table[] = 70{ 71 {"comm", obj_elf_common, 0}, 72 {"ident", obj_elf_ident, 0}, 73 {"local", obj_elf_local, 0}, 74 {"previous", obj_elf_previous, 0}, 75 {"section", obj_elf_section, 0}, 76 {"section.s", obj_elf_section, 0}, 77 {"sect", obj_elf_section, 0}, 78 {"sect.s", obj_elf_section, 0}, 79 {"size", obj_elf_size, 0}, 80 {"type", obj_elf_type, 0}, 81 {"version", obj_elf_version, 0}, 82 {"weak", obj_elf_weak, 0}, 83 84 /* These are used for stabs-in-elf configurations. */ 85 {"line", obj_elf_line, 0}, 86 87 /* This is a GNU extension to handle symbol versions. */ 88 {"symver", obj_elf_symver, 0}, 89 90 /* These are used for dwarf. */ 91 {"2byte", cons, 2}, 92 {"4byte", cons, 4}, 93 {"8byte", cons, 8}, 94 95 /* We need to trap the section changing calls to handle .previous. */ 96 {"data", obj_elf_data, 0}, 97 {"text", obj_elf_text, 0}, 98 99 /* End sentinel. */ 100 {NULL}, 101}; 102 103static const pseudo_typeS ecoff_debug_pseudo_table[] = 104{ 105#ifdef NEED_ECOFF_DEBUG 106 /* COFF style debugging information for ECOFF. .ln is not used; .loc 107 is used instead. */ 108 { "def", ecoff_directive_def, 0 }, 109 { "dim", ecoff_directive_dim, 0 }, 110 { "endef", ecoff_directive_endef, 0 }, 111 { "file", ecoff_directive_file, 0 }, 112 { "scl", ecoff_directive_scl, 0 }, 113 { "tag", ecoff_directive_tag, 0 }, 114 { "val", ecoff_directive_val, 0 }, 115 116 /* COFF debugging requires pseudo-ops .size and .type, but ELF 117 already has meanings for those. We use .esize and .etype 118 instead. These are only generated by gcc anyhow. */ 119 { "esize", ecoff_directive_size, 0 }, 120 { "etype", ecoff_directive_type, 0 }, 121 122 /* ECOFF specific debugging information. */ 123 { "begin", ecoff_directive_begin, 0 }, 124 { "bend", ecoff_directive_bend, 0 }, 125 { "end", ecoff_directive_end, 0 }, 126 { "ent", ecoff_directive_ent, 0 }, 127 { "fmask", ecoff_directive_fmask, 0 }, 128 { "frame", ecoff_directive_frame, 0 }, 129 { "loc", ecoff_directive_loc, 0 }, 130 { "mask", ecoff_directive_mask, 0 }, 131 132 /* Other ECOFF directives. */ 133 { "extern", ecoff_directive_extern, 0 }, 134 135 /* These are used on Irix. I don't know how to implement them. */ 136 { "alias", s_ignore, 0 }, 137 { "bgnb", s_ignore, 0 }, 138 { "endb", s_ignore, 0 }, 139 { "lab", s_ignore, 0 }, 140 { "noalias", s_ignore, 0 }, 141 { "verstamp", s_ignore, 0 }, 142 { "vreg", s_ignore, 0 }, 143#endif 144 145 {NULL} /* end sentinel */ 146}; 147 148#undef NO_RELOC 149#include "aout/aout64.h" 150 151/* This is called when the assembler starts. */ 152 153void 154elf_begin () 155{ 156 /* Add symbols for the known sections to the symbol table. */ 157 symbol_table_insert (section_symbol (bfd_get_section_by_name (stdoutput, 158 ".text"))); 159 symbol_table_insert (section_symbol (bfd_get_section_by_name (stdoutput, 160 ".data"))); 161 symbol_table_insert (section_symbol (bfd_get_section_by_name (stdoutput, 162 ".bss"))); 163} 164 165void 166elf_pop_insert () 167{ 168 pop_insert (elf_pseudo_table); 169 if (ECOFF_DEBUGGING) 170 pop_insert (ecoff_debug_pseudo_table); 171} 172 173static bfd_vma 174elf_s_get_size (sym) 175 symbolS *sym; 176{ 177 return S_GET_SIZE (sym); 178} 179 180static void 181elf_s_set_size (sym, sz) 182 symbolS *sym; 183 bfd_vma sz; 184{ 185 S_SET_SIZE (sym, sz); 186} 187 188static bfd_vma 189elf_s_get_align (sym) 190 symbolS *sym; 191{ 192 return S_GET_ALIGN (sym); 193} 194 195static void 196elf_s_set_align (sym, align) 197 symbolS *sym; 198 bfd_vma align; 199{ 200 S_SET_ALIGN (sym, align); 201} 202 203static void 204elf_copy_symbol_attributes (dest, src) 205 symbolS *dest, *src; 206{ 207 OBJ_COPY_SYMBOL_ATTRIBUTES (dest, src); 208} 209 210static int 211elf_sec_sym_ok_for_reloc (sec) 212 asection *sec; 213{ 214 return obj_sec_sym_ok_for_reloc (sec); 215} 216 217void 218elf_file_symbol (s) 219 char *s; 220{ 221 symbolS *sym; 222 223 sym = symbol_new (s, absolute_section, (valueT) 0, (struct frag *) 0); 224 sym->sy_frag = &zero_address_frag; 225 sym->bsym->flags |= BSF_FILE; 226 227 if (symbol_rootP != sym) 228 { 229 symbol_remove (sym, &symbol_rootP, &symbol_lastP); 230 symbol_insert (sym, symbol_rootP, &symbol_rootP, &symbol_lastP); 231#ifdef DEBUG 232 verify_symbol_chain (symbol_rootP, symbol_lastP); 233#endif 234 } 235 236#ifdef NEED_ECOFF_DEBUG 237 ecoff_new_file (s); 238#endif 239} 240 241static void 242obj_elf_common (ignore) 243 int ignore; 244{ 245 char *name; 246 char c; 247 char *p; 248 int temp, size; 249 symbolS *symbolP; 250 int have_align; 251 252 name = input_line_pointer; 253 c = get_symbol_end (); 254 /* just after name is now '\0' */ 255 p = input_line_pointer; 256 *p = c; 257 SKIP_WHITESPACE (); 258 if (*input_line_pointer != ',') 259 { 260 as_bad ("Expected comma after symbol-name"); 261 ignore_rest_of_line (); 262 return; 263 } 264 input_line_pointer++; /* skip ',' */ 265 if ((temp = get_absolute_expression ()) < 0) 266 { 267 as_bad (".COMMon length (%d.) <0! Ignored.", temp); 268 ignore_rest_of_line (); 269 return; 270 } 271 size = temp; 272 *p = 0; 273 symbolP = symbol_find_or_make (name); 274 *p = c; 275 if (S_IS_DEFINED (symbolP) && ! S_IS_COMMON (symbolP)) 276 { 277 as_bad ("Ignoring attempt to re-define symbol"); 278 ignore_rest_of_line (); 279 return; 280 } 281 if (S_GET_VALUE (symbolP) != 0) 282 { 283 if (S_GET_VALUE (symbolP) != size) 284 { 285 as_warn ("Length of .comm \"%s\" is already %ld. Not changed to %d.", 286 S_GET_NAME (symbolP), (long) S_GET_VALUE (symbolP), size); 287 } 288 } 289 know (symbolP->sy_frag == &zero_address_frag); 290 if (*input_line_pointer != ',') 291 have_align = 0; 292 else 293 { 294 have_align = 1; 295 input_line_pointer++; 296 SKIP_WHITESPACE (); 297 } 298 if (! have_align || *input_line_pointer != '"') 299 { 300 if (! have_align) 301 temp = 0; 302 else 303 { 304 temp = get_absolute_expression (); 305 if (temp < 0) 306 { 307 temp = 0; 308 as_warn ("Common alignment negative; 0 assumed"); 309 } 310 } 311 if (symbolP->local) 312 { 313 segT old_sec; 314 int old_subsec; 315 char *pfrag; 316 int align; 317 318 /* allocate_bss: */ 319 old_sec = now_seg; 320 old_subsec = now_subseg; 321 if (temp) 322 { 323 /* convert to a power of 2 alignment */ 324 for (align = 0; (temp & 1) == 0; temp >>= 1, ++align); 325 if (temp != 1) 326 { 327 as_bad ("Common alignment not a power of 2"); 328 ignore_rest_of_line (); 329 return; 330 } 331 } 332 else 333 align = 0; 334 record_alignment (bss_section, align); 335 subseg_set (bss_section, 0); 336 if (align) 337 frag_align (align, 0, 0); 338 if (S_GET_SEGMENT (symbolP) == bss_section) 339 symbolP->sy_frag->fr_symbol = 0; 340 symbolP->sy_frag = frag_now; 341 pfrag = frag_var (rs_org, 1, 1, (relax_substateT) 0, symbolP, 342 (offsetT) size, (char *) 0); 343 *pfrag = 0; 344 S_SET_SIZE (symbolP, size); 345 S_SET_SEGMENT (symbolP, bss_section); 346 S_CLEAR_EXTERNAL (symbolP); 347 subseg_set (old_sec, old_subsec); 348 } 349 else 350 { 351 allocate_common: 352 S_SET_VALUE (symbolP, (valueT) size); 353 S_SET_ALIGN (symbolP, temp); 354 S_SET_EXTERNAL (symbolP); 355 S_SET_SEGMENT (symbolP, bfd_com_section_ptr); 356 } 357 } 358 else 359 { 360 input_line_pointer++; 361 /* @@ Some use the dot, some don't. Can we get some consistency?? */ 362 if (*input_line_pointer == '.') 363 input_line_pointer++; 364 /* @@ Some say data, some say bss. */ 365 if (strncmp (input_line_pointer, "bss\"", 4) 366 && strncmp (input_line_pointer, "data\"", 5)) 367 { 368 while (*--input_line_pointer != '"') 369 ; 370 input_line_pointer--; 371 goto bad_common_segment; 372 } 373 while (*input_line_pointer++ != '"') 374 ; 375 goto allocate_common; 376 } 377 378 symbolP->bsym->flags |= BSF_OBJECT; 379 380 demand_empty_rest_of_line (); 381 return; 382 383 { 384 bad_common_segment: 385 p = input_line_pointer; 386 while (*p && *p != '\n') 387 p++; 388 c = *p; 389 *p = '\0'; 390 as_bad ("bad .common segment %s", input_line_pointer + 1); 391 *p = c; 392 input_line_pointer = p; 393 ignore_rest_of_line (); 394 return; 395 } 396} 397 398static void 399obj_elf_local (ignore) 400 int ignore; 401{ 402 char *name; 403 int c; 404 symbolS *symbolP; 405 406 do 407 { 408 name = input_line_pointer; 409 c = get_symbol_end (); 410 symbolP = symbol_find_or_make (name); 411 *input_line_pointer = c; 412 SKIP_WHITESPACE (); 413 S_CLEAR_EXTERNAL (symbolP); 414 symbolP->local = 1; 415 if (c == ',') 416 { 417 input_line_pointer++; 418 SKIP_WHITESPACE (); 419 if (*input_line_pointer == '\n') 420 c = '\n'; 421 } 422 } 423 while (c == ','); 424 demand_empty_rest_of_line (); 425} 426 427static void 428obj_elf_weak (ignore) 429 int ignore; 430{ 431 char *name; 432 int c; 433 symbolS *symbolP; 434 435 do 436 { 437 name = input_line_pointer; 438 c = get_symbol_end (); 439 symbolP = symbol_find_or_make (name); 440 *input_line_pointer = c; 441 SKIP_WHITESPACE (); 442 S_SET_WEAK (symbolP); 443 symbolP->local = 1; 444 if (c == ',') 445 { 446 input_line_pointer++; 447 SKIP_WHITESPACE (); 448 if (*input_line_pointer == '\n') 449 c = '\n'; 450 } 451 } 452 while (c == ','); 453 demand_empty_rest_of_line (); 454} 455 456static segT previous_section; 457static int previous_subsection; 458 459/* Handle the .section pseudo-op. This code supports two different 460 syntaxes. 461 462 The first is found on Solaris, and looks like 463 .section ".sec1",#alloc,#execinstr,#write 464 Here the names after '#' are the SHF_* flags to turn on for the 465 section. I'm not sure how it determines the SHT_* type (BFD 466 doesn't really give us control over the type, anyhow). 467 468 The second format is found on UnixWare, and probably most SVR4 469 machines, and looks like 470 .section .sec1,"a",@progbits 471 The quoted string may contain any combination of a, w, x, and 472 represents the SHF_* flags to turn on for the section. The string 473 beginning with '@' can be progbits or nobits. There should be 474 other possibilities, but I don't know what they are. In any case, 475 BFD doesn't really let us set the section type. */ 476 477/* Certain named sections have particular defined types, listed on p. 478 4-19 of the ABI. */ 479struct special_section 480{ 481 const char *name; 482 int type; 483 int attributes; 484}; 485 486static struct special_section special_sections[] = 487{ 488 { ".bss", SHT_NOBITS, SHF_ALLOC + SHF_WRITE }, 489 { ".comment", SHT_PROGBITS, 0 }, 490 { ".data", SHT_PROGBITS, SHF_ALLOC + SHF_WRITE }, 491 { ".data1", SHT_PROGBITS, SHF_ALLOC + SHF_WRITE }, 492 { ".debug", SHT_PROGBITS, 0 }, 493 { ".fini", SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR }, 494 { ".init", SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR }, 495 { ".line", SHT_PROGBITS, 0 }, 496 { ".note", SHT_NOTE, 0 }, 497 { ".rodata", SHT_PROGBITS, SHF_ALLOC }, 498 { ".rodata1", SHT_PROGBITS, SHF_ALLOC }, 499 { ".text", SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR }, 500 501#ifdef ELF_TC_SPECIAL_SECTIONS 502 ELF_TC_SPECIAL_SECTIONS 503#endif 504 505#if 0 506 /* The following section names are special, but they can not 507 reasonably appear in assembler code. Some of the attributes are 508 processor dependent. */ 509 { ".dynamic", SHT_DYNAMIC, SHF_ALLOC /* + SHF_WRITE */ }, 510 { ".dynstr", SHT_STRTAB, SHF_ALLOC }, 511 { ".dynsym", SHT_DYNSYM, SHF_ALLOC }, 512 { ".got", SHT_PROGBITS, 0 }, 513 { ".hash", SHT_HASH, SHF_ALLOC }, 514 { ".interp", SHT_PROGBITS, /* SHF_ALLOC */ }, 515 { ".plt", SHT_PROGBITS, 0 }, 516 { ".shstrtab",SHT_STRTAB, 0 }, 517 { ".strtab", SHT_STRTAB, /* SHF_ALLOC */ }, 518 { ".symtab", SHT_SYMTAB, /* SHF_ALLOC */ }, 519#endif 520 521 { NULL, 0, 0 } 522}; 523 524void 525obj_elf_section (xxx) 526 int xxx; 527{ 528 char *string; 529 int new_sec; 530 segT sec; 531 int type, attr; 532 int i; 533 flagword flags; 534 symbolS *secsym; 535 536#ifdef md_flush_pending_output 537 md_flush_pending_output (); 538#endif 539 540 if (flag_mri) 541 { 542 char mri_type; 543 544 previous_section = now_seg; 545 previous_subsection = now_subseg; 546 547 s_mri_sect (&mri_type); 548 549#ifdef md_elf_section_change_hook 550 md_elf_section_change_hook (); 551#endif 552 553 return; 554 } 555 556 /* Get name of section. */ 557 SKIP_WHITESPACE (); 558 if (*input_line_pointer == '"') 559 { 560 string = demand_copy_C_string (&xxx); 561 if (string == NULL) 562 { 563 ignore_rest_of_line (); 564 return; 565 } 566 } 567 else 568 { 569 char *p = input_line_pointer; 570 char c; 571 while (0 == strchr ("\n\t,; ", *p)) 572 p++; 573 if (p == input_line_pointer) 574 { 575 as_warn ("Missing section name"); 576 ignore_rest_of_line (); 577 return; 578 } 579 c = *p; 580 *p = 0; 581 string = xmalloc ((unsigned long) (p - input_line_pointer + 1)); 582 strcpy (string, input_line_pointer); 583 *p = c; 584 input_line_pointer = p; 585 } 586 587 /* Switch to the section, creating it if necessary. */ 588 previous_section = now_seg; 589 previous_subsection = now_subseg; 590 591 new_sec = bfd_get_section_by_name (stdoutput, string) == NULL; 592 sec = subseg_new (string, 0); 593 594 /* If this section already existed, we don't bother to change the 595 flag values. */ 596 if (! new_sec) 597 { 598 while (! is_end_of_line[(unsigned char) *input_line_pointer]) 599 ++input_line_pointer; 600 ++input_line_pointer; 601 602#ifdef md_elf_section_change_hook 603 md_elf_section_change_hook (); 604#endif 605 606 return; 607 } 608 609 SKIP_WHITESPACE (); 610 611 type = SHT_NULL; 612 attr = 0; 613 614 if (*input_line_pointer == ',') 615 { 616 /* Skip the comma. */ 617 ++input_line_pointer; 618 619 SKIP_WHITESPACE (); 620 if (*input_line_pointer == '"') 621 { 622 /* Pick up a string with a combination of a, w, x. */ 623 ++input_line_pointer; 624 while (*input_line_pointer != '"') 625 { 626 switch (*input_line_pointer) 627 { 628 case 'a': 629 attr |= SHF_ALLOC; 630 break; 631 case 'w': 632 attr |= SHF_WRITE; 633 break; 634 case 'x': 635 attr |= SHF_EXECINSTR; 636 break; 637 default: 638 { 639 char *bad_msg = "Bad .section directive: want a,w,x in string"; 640#ifdef md_elf_section_letter 641 int md_attr = md_elf_section_letter (*input_line_pointer, &bad_msg); 642 if (md_attr) 643 attr |= md_attr; 644 else 645#endif 646 { 647 as_warn (bad_msg); 648 ignore_rest_of_line (); 649 return; 650 } 651 } 652 } 653 ++input_line_pointer; 654 } 655 656 /* Skip the closing quote. */ 657 ++input_line_pointer; 658 659 SKIP_WHITESPACE (); 660 if (*input_line_pointer == ',') 661 { 662 ++input_line_pointer; 663 SKIP_WHITESPACE (); 664 if (*input_line_pointer == '@') 665 { 666 ++input_line_pointer; 667 if (strncmp (input_line_pointer, "progbits", 668 sizeof "progbits" - 1) == 0) 669 { 670 type = SHT_PROGBITS; 671 input_line_pointer += sizeof "progbits" - 1; 672 } 673 else if (strncmp (input_line_pointer, "nobits", 674 sizeof "nobits" - 1) == 0) 675 { 676 type = SHT_NOBITS; 677 input_line_pointer += sizeof "nobits" - 1; 678 } 679 else 680 { 681#ifdef md_elf_section_type 682 int md_type = md_elf_section_type (&input_line_pointer); 683 if (md_type) 684 type = md_type; 685 else 686#endif 687 { 688 as_warn ("Unrecognized section type"); 689 ignore_rest_of_line (); 690 } 691 } 692 } 693 } 694 } 695 else 696 { 697 do 698 { 699 SKIP_WHITESPACE (); 700 if (*input_line_pointer != '#') 701 { 702 as_warn ("Bad .section directive"); 703 ignore_rest_of_line (); 704 return; 705 } 706 ++input_line_pointer; 707 if (strncmp (input_line_pointer, "write", 708 sizeof "write" - 1) == 0) 709 { 710 attr |= SHF_WRITE; 711 input_line_pointer += sizeof "write" - 1; 712 } 713 else if (strncmp (input_line_pointer, "alloc", 714 sizeof "alloc" - 1) == 0) 715 { 716 attr |= SHF_ALLOC; 717 input_line_pointer += sizeof "alloc" - 1; 718 } 719 else if (strncmp (input_line_pointer, "execinstr", 720 sizeof "execinstr" - 1) == 0) 721 { 722 attr |= SHF_EXECINSTR; 723 input_line_pointer += sizeof "execinstr" - 1; 724 } 725 else 726 { 727#ifdef md_elf_section_word 728 int md_attr = md_elf_section_word (&input_line_pointer); 729 if (md_attr) 730 attr |= md_attr; 731 else 732#endif 733 { 734 as_warn ("Unrecognized section attribute"); 735 ignore_rest_of_line (); 736 return; 737 } 738 } 739 SKIP_WHITESPACE (); 740 } 741 while (*input_line_pointer++ == ','); 742 --input_line_pointer; 743 } 744 } 745 746 /* See if this is one of the special sections. */ 747 for (i = 0; special_sections[i].name != NULL; i++) 748 { 749 if (string[1] == special_sections[i].name[1] 750 && strcmp (string, special_sections[i].name) == 0) 751 { 752 if (type == SHT_NULL) 753 type = special_sections[i].type; 754 else if (type != special_sections[i].type) 755 as_warn ("Setting incorrect section type for %s", string); 756 757 if ((attr &~ special_sections[i].attributes) != 0) 758 { 759 /* As a GNU extension, we permit a .note section to be 760 allocatable. If the linker sees an allocateable 761 .note section, it will create a PT_NOTE segment in 762 the output file. */ 763 if (strcmp (string, ".note") != 0 764 || attr != SHF_ALLOC) 765 as_warn ("Setting incorrect section attributes for %s", 766 string); 767 } 768 attr |= special_sections[i].attributes; 769 770 break; 771 } 772 } 773 774 flags = (SEC_RELOC 775 | ((attr & SHF_WRITE) ? 0 : SEC_READONLY) 776 | ((attr & SHF_ALLOC) ? SEC_ALLOC : 0) 777 | (((attr & SHF_ALLOC) && type != SHT_NOBITS) ? SEC_LOAD : 0) 778 | ((attr & SHF_EXECINSTR) ? SEC_CODE : 0)); 779 if (special_sections[i].name == NULL) 780 { 781 if (type == SHT_PROGBITS) 782 flags |= SEC_ALLOC | SEC_LOAD; 783 else if (type == SHT_NOBITS) 784 { 785 flags |= SEC_ALLOC; 786 flags &=~ SEC_LOAD; 787 } 788 789#ifdef md_elf_section_flags 790 flags = md_elf_section_flags (flags, attr, type); 791#endif 792 } 793 794 bfd_set_section_flags (stdoutput, sec, flags); 795 796 /* Add a symbol for this section to the symbol table. */ 797 secsym = symbol_find (string); 798 if (secsym != NULL) 799 secsym->bsym = sec->symbol; 800 else 801 symbol_table_insert (section_symbol (sec)); 802 803#ifdef md_elf_section_change_hook 804 md_elf_section_change_hook (); 805#endif 806 807 demand_empty_rest_of_line (); 808} 809 810/* Change to the .data section. */ 811 812static void 813obj_elf_data (i) 814 int i; 815{ 816#ifdef md_flush_pending_output 817 md_flush_pending_output (); 818#endif 819 820 previous_section = now_seg; 821 previous_subsection = now_subseg; 822 s_data (i); 823 824#ifdef md_elf_section_change_hook 825 md_elf_section_change_hook (); 826#endif 827} 828 829/* Change to the .text section. */ 830 831static void 832obj_elf_text (i) 833 int i; 834{ 835#ifdef md_flush_pending_output 836 md_flush_pending_output (); 837#endif 838 839 previous_section = now_seg; 840 previous_subsection = now_subseg; 841 s_text (i); 842 843#ifdef md_elf_section_change_hook 844 md_elf_section_change_hook (); 845#endif 846} 847 848/* This can be called from the processor backends if they change 849 sections. */ 850 851void 852obj_elf_section_change_hook () 853{ 854 previous_section = now_seg; 855 previous_subsection = now_subseg; 856} 857 858void 859obj_elf_previous (ignore) 860 int ignore; 861{ 862 if (previous_section == 0) 863 { 864 as_bad (".previous without corresponding .section; ignored"); 865 return; 866 } 867 868#ifdef md_flush_pending_output 869 md_flush_pending_output (); 870#endif 871 872 subseg_set (previous_section, previous_subsection); 873 previous_section = 0; 874 875#ifdef md_elf_section_change_hook 876 md_elf_section_change_hook (); 877#endif 878} 879 880static void 881obj_elf_line (ignore) 882 int ignore; 883{ 884 /* Assume delimiter is part of expression. BSD4.2 as fails with 885 delightful bug, so we are not being incompatible here. */ 886 new_logical_line ((char *) NULL, (int) (get_absolute_expression ())); 887 demand_empty_rest_of_line (); 888} 889 890/* This handle the .symver pseudo-op, which is used to specify a 891 symbol version. The syntax is ``.symver NAME,SYMVERNAME''. 892 SYMVERNAME may contain ELF_VER_CHR ('@') characters. This 893 pseudo-op causes the assembler to emit a symbol named SYMVERNAME 894 with the same value as the symbol NAME. */ 895 896static void 897obj_elf_symver (ignore) 898 int ignore; 899{ 900 char *name; 901 char c; 902 symbolS *sym; 903 904 name = input_line_pointer; 905 c = get_symbol_end (); 906 907 sym = symbol_find_or_make (name); 908 909 *input_line_pointer = c; 910 911 if (sym->sy_obj.versioned_name != NULL) 912 { 913 as_bad ("multiple .symver directives for symbol `%s'", 914 S_GET_NAME (sym)); 915 ignore_rest_of_line (); 916 return; 917 } 918 919 SKIP_WHITESPACE (); 920 if (*input_line_pointer != ',') 921 { 922 as_bad ("expected comma after name in .symver"); 923 ignore_rest_of_line (); 924 return; 925 } 926 927 ++input_line_pointer; 928 name = input_line_pointer; 929 while (1) 930 { 931 c = get_symbol_end (); 932 if (c != ELF_VER_CHR) 933 break; 934 *input_line_pointer++ = c; 935 } 936 937 sym->sy_obj.versioned_name = xstrdup (name); 938 939 *input_line_pointer = c; 940 941 if (strchr (sym->sy_obj.versioned_name, ELF_VER_CHR) == NULL) 942 { 943 as_bad ("missing version name in `%s' for symbol `%s'", 944 sym->sy_obj.versioned_name, S_GET_NAME (sym)); 945 ignore_rest_of_line (); 946 return; 947 } 948 949 demand_empty_rest_of_line (); 950} 951 952void 953obj_read_begin_hook () 954{ 955#ifdef NEED_ECOFF_DEBUG 956 if (ECOFF_DEBUGGING) 957 ecoff_read_begin_hook (); 958#endif 959} 960 961void 962obj_symbol_new_hook (symbolP) 963 symbolS *symbolP; 964{ 965 symbolP->sy_obj.size = NULL; 966 symbolP->sy_obj.versioned_name = NULL; 967 968#ifdef NEED_ECOFF_DEBUG 969 if (ECOFF_DEBUGGING) 970 ecoff_symbol_new_hook (symbolP); 971#endif 972} 973 974void 975obj_elf_version (ignore) 976 int ignore; 977{ 978 char *name; 979 unsigned int c; 980 char ch; 981 char *p; 982 asection *seg = now_seg; 983 subsegT subseg = now_subseg; 984 Elf_Internal_Note i_note; 985 Elf_External_Note e_note; 986 asection *note_secp = (asection *) NULL; 987 int i, len; 988 989 SKIP_WHITESPACE (); 990 if (*input_line_pointer == '\"') 991 { 992 ++input_line_pointer; /* -> 1st char of string. */ 993 name = input_line_pointer; 994 995 while (is_a_char (c = next_char_of_string ())) 996 ; 997 c = *input_line_pointer; 998 *input_line_pointer = '\0'; 999 *(input_line_pointer - 1) = '\0'; 1000 *input_line_pointer = c; 1001 1002 /* create the .note section */ 1003 1004 note_secp = subseg_new (".note", 0); 1005 bfd_set_section_flags (stdoutput, 1006 note_secp, 1007 SEC_HAS_CONTENTS | SEC_READONLY); 1008 1009 /* process the version string */ 1010 1011 len = strlen (name); 1012 1013 i_note.namesz = ((len + 1) + 3) & ~3; /* round this to word boundary */ 1014 i_note.descsz = 0; /* no description */ 1015 i_note.type = NT_VERSION; 1016 p = frag_more (sizeof (e_note.namesz)); 1017 md_number_to_chars (p, (valueT) i_note.namesz, 4); 1018 p = frag_more (sizeof (e_note.descsz)); 1019 md_number_to_chars (p, (valueT) i_note.descsz, 4); 1020 p = frag_more (sizeof (e_note.type)); 1021 md_number_to_chars (p, (valueT) i_note.type, 4); 1022 1023 for (i = 0; i < len; i++) 1024 { 1025 ch = *(name + i); 1026 { 1027 FRAG_APPEND_1_CHAR (ch); 1028 } 1029 } 1030 frag_align (2, 0, 0); 1031 1032 subseg_set (seg, subseg); 1033 } 1034 else 1035 { 1036 as_bad ("Expected quoted string"); 1037 } 1038 demand_empty_rest_of_line (); 1039} 1040 1041static void 1042obj_elf_size (ignore) 1043 int ignore; 1044{ 1045 char *name = input_line_pointer; 1046 char c = get_symbol_end (); 1047 char *p; 1048 expressionS exp; 1049 symbolS *sym; 1050 1051 p = input_line_pointer; 1052 *p = c; 1053 SKIP_WHITESPACE (); 1054 if (*input_line_pointer != ',') 1055 { 1056 *p = 0; 1057 as_bad ("expected comma after name `%s' in .size directive", name); 1058 *p = c; 1059 ignore_rest_of_line (); 1060 return; 1061 } 1062 input_line_pointer++; 1063 expression (&exp); 1064 if (exp.X_op == O_absent) 1065 { 1066 as_bad ("missing expression in .size directive"); 1067 exp.X_op = O_constant; 1068 exp.X_add_number = 0; 1069 } 1070 *p = 0; 1071 sym = symbol_find_or_make (name); 1072 *p = c; 1073 if (exp.X_op == O_constant) 1074 S_SET_SIZE (sym, exp.X_add_number); 1075 else 1076 { 1077 sym->sy_obj.size = (expressionS *) xmalloc (sizeof (expressionS)); 1078 *sym->sy_obj.size = exp; 1079 } 1080 demand_empty_rest_of_line (); 1081} 1082 1083/* Handle the ELF .type pseudo-op. This sets the type of a symbol. 1084 There are three syntaxes. The first (used on Solaris) is 1085 .type SYM,#function 1086 The second (used on UnixWare) is 1087 .type SYM,@function 1088 The third (reportedly to be used on Irix 6.0) is 1089 .type SYM STT_FUNC 1090 */ 1091 1092static void 1093obj_elf_type (ignore) 1094 int ignore; 1095{ 1096 char *name; 1097 char c; 1098 int type; 1099 const char *typename; 1100 symbolS *sym; 1101 1102 name = input_line_pointer; 1103 c = get_symbol_end (); 1104 sym = symbol_find_or_make (name); 1105 *input_line_pointer = c; 1106 1107 SKIP_WHITESPACE (); 1108 if (*input_line_pointer == ',') 1109 ++input_line_pointer; 1110 1111 SKIP_WHITESPACE (); 1112 if (*input_line_pointer == '#' || *input_line_pointer == '@') 1113 ++input_line_pointer; 1114 1115 typename = input_line_pointer; 1116 c = get_symbol_end (); 1117 1118 type = 0; 1119 if (strcmp (typename, "function") == 0 1120 || strcmp (typename, "STT_FUNC") == 0) 1121 type = BSF_FUNCTION; 1122 else if (strcmp (typename, "object") == 0 1123 || strcmp (typename, "STT_OBJECT") == 0) 1124 type = BSF_OBJECT; 1125 else 1126 as_bad ("ignoring unrecognized symbol type \"%s\"", typename); 1127 1128 *input_line_pointer = c; 1129 1130 sym->bsym->flags |= type; 1131 1132 demand_empty_rest_of_line (); 1133} 1134 1135static void 1136obj_elf_ident (ignore) 1137 int ignore; 1138{ 1139 static segT comment_section; 1140 segT old_section = now_seg; 1141 int old_subsection = now_subseg; 1142 1143 if (!comment_section) 1144 { 1145 char *p; 1146 comment_section = subseg_new (".comment", 0); 1147 bfd_set_section_flags (stdoutput, comment_section, 1148 SEC_READONLY | SEC_HAS_CONTENTS); 1149 p = frag_more (1); 1150 *p = 0; 1151 } 1152 else 1153 subseg_set (comment_section, 0); 1154 stringer (1); 1155 subseg_set (old_section, old_subsection); 1156} 1157 1158#ifdef INIT_STAB_SECTION 1159 1160/* The first entry in a .stabs section is special. */ 1161 1162void 1163obj_elf_init_stab_section (seg) 1164 segT seg; 1165{ 1166 char *file; 1167 char *p; 1168 char *stabstr_name; 1169 unsigned int stroff; 1170 1171 /* Force the section to align to a longword boundary. Without this, 1172 UnixWare ar crashes. */ 1173 bfd_set_section_alignment (stdoutput, seg, 2); 1174 1175 /* Make space for this first symbol. */ 1176 p = frag_more (12); 1177 /* Zero it out. */ 1178 memset (p, 0, 12); 1179 as_where (&file, (unsigned int *) NULL); 1180 stabstr_name = (char *) alloca (strlen (segment_name (seg)) + 4); 1181 strcpy (stabstr_name, segment_name (seg)); 1182 strcat (stabstr_name, "str"); 1183 stroff = get_stab_string_offset (file, stabstr_name); 1184 know (stroff == 1); 1185 md_number_to_chars (p, stroff, 4); 1186 seg_info (seg)->stabu.p = p; 1187} 1188 1189#endif 1190 1191/* Fill in the counts in the first entry in a .stabs section. */ 1192 1193static void 1194adjust_stab_sections (abfd, sec, xxx) 1195 bfd *abfd; 1196 asection *sec; 1197 PTR xxx; 1198{ 1199 char *name; 1200 asection *strsec; 1201 char *p; 1202 int strsz, nsyms; 1203 1204 if (strncmp (".stab", sec->name, 5)) 1205 return; 1206 if (!strcmp ("str", sec->name + strlen (sec->name) - 3)) 1207 return; 1208 1209 name = (char *) alloca (strlen (sec->name) + 4); 1210 strcpy (name, sec->name); 1211 strcat (name, "str"); 1212 strsec = bfd_get_section_by_name (abfd, name); 1213 if (strsec) 1214 strsz = bfd_section_size (abfd, strsec); 1215 else 1216 strsz = 0; 1217 nsyms = bfd_section_size (abfd, sec) / 12 - 1; 1218 1219 p = seg_info (sec)->stabu.p; 1220 assert (p != 0); 1221 1222 bfd_h_put_16 (abfd, (bfd_vma) nsyms, (bfd_byte *) p + 6); 1223 bfd_h_put_32 (abfd, (bfd_vma) strsz, (bfd_byte *) p + 8); 1224} 1225 1226#ifdef NEED_ECOFF_DEBUG 1227 1228/* This function is called by the ECOFF code. It is supposed to 1229 record the external symbol information so that the backend can 1230 write it out correctly. The ELF backend doesn't actually handle 1231 this at the moment, so we do it ourselves. We save the information 1232 in the symbol. */ 1233 1234void 1235elf_ecoff_set_ext (sym, ext) 1236 symbolS *sym; 1237 struct ecoff_extr *ext; 1238{ 1239 sym->bsym->udata.p = (PTR) ext; 1240} 1241 1242/* This function is called by bfd_ecoff_debug_externals. It is 1243 supposed to *EXT to the external symbol information, and return 1244 whether the symbol should be used at all. */ 1245 1246static boolean 1247elf_get_extr (sym, ext) 1248 asymbol *sym; 1249 EXTR *ext; 1250{ 1251 if (sym->udata.p == NULL) 1252 return false; 1253 *ext = *(EXTR *) sym->udata.p; 1254 return true; 1255} 1256 1257/* This function is called by bfd_ecoff_debug_externals. It has 1258 nothing to do for ELF. */ 1259 1260/*ARGSUSED*/ 1261static void 1262elf_set_index (sym, indx) 1263 asymbol *sym; 1264 bfd_size_type indx; 1265{ 1266} 1267 1268#endif /* NEED_ECOFF_DEBUG */ 1269 1270void 1271elf_frob_symbol (symp, puntp) 1272 symbolS *symp; 1273 int *puntp; 1274{ 1275#ifdef NEED_ECOFF_DEBUG 1276 if (ECOFF_DEBUGGING) 1277 ecoff_frob_symbol (symp); 1278#endif 1279 1280 if (symp->sy_obj.size != NULL) 1281 { 1282 switch (symp->sy_obj.size->X_op) 1283 { 1284 case O_subtract: 1285 S_SET_SIZE (symp, 1286 (S_GET_VALUE (symp->sy_obj.size->X_add_symbol) 1287 + symp->sy_obj.size->X_add_number 1288 - S_GET_VALUE (symp->sy_obj.size->X_op_symbol))); 1289 break; 1290 case O_constant: 1291 S_SET_SIZE (symp, 1292 (S_GET_VALUE (symp->sy_obj.size->X_add_symbol) 1293 + symp->sy_obj.size->X_add_number)); 1294 break; 1295 default: 1296 as_bad (".size expression too complicated to fix up"); 1297 break; 1298 } 1299 free (symp->sy_obj.size); 1300 symp->sy_obj.size = NULL; 1301 } 1302 1303 if (symp->sy_obj.versioned_name != NULL) 1304 { 1305 /* This symbol was given a new name with the .symver directive. 1306 1307 If this is an external reference, just rename the symbol to 1308 include the version string. This will make the relocs be 1309 against the correct versioned symbol. 1310 1311 If this is a definition, add an alias. FIXME: Using an alias 1312 will permit the debugging information to refer to the right 1313 symbol. However, it's not clear whether it is the best 1314 approach. */ 1315 1316 if (! S_IS_DEFINED (symp)) 1317 { 1318 char *p; 1319 1320 /* Verify that the name isn't using the @@ syntax--this is 1321 reserved for definitions of the default version to link 1322 against. */ 1323 p = strchr (symp->sy_obj.versioned_name, ELF_VER_CHR); 1324 know (p != NULL); 1325 if (p[1] == ELF_VER_CHR) 1326 { 1327 as_bad ("invalid attempt to declare external version name as default in symbol `%s'", 1328 symp->sy_obj.versioned_name); 1329 *puntp = true; 1330 } 1331 S_SET_NAME (symp, symp->sy_obj.versioned_name); 1332 } 1333 else 1334 { 1335 symbolS *symp2; 1336 1337 /* FIXME: Creating a new symbol here is risky. We're in the 1338 final loop over the symbol table. We can get away with 1339 it only because the symbol goes to the end of the list, 1340 where the loop will still see it. It would probably be 1341 better to do this in obj_frob_file_before_adjust. */ 1342 1343 symp2 = symbol_find_or_make (symp->sy_obj.versioned_name); 1344 1345 /* Now we act as though we saw symp2 = sym. */ 1346 1347 S_SET_SEGMENT (symp2, S_GET_SEGMENT (symp)); 1348 1349 /* Subtracting out the frag address here is a hack because 1350 we are in the middle of the final loop. */ 1351 S_SET_VALUE (symp2, S_GET_VALUE (symp) - symp->sy_frag->fr_address); 1352 1353 symp2->sy_frag = symp->sy_frag; 1354 1355 /* This will copy over the size information. */ 1356 copy_symbol_attributes (symp2, symp); 1357 1358 if (S_IS_WEAK (symp)) 1359 S_SET_WEAK (symp2); 1360 1361 if (S_IS_EXTERNAL (symp)) 1362 S_SET_EXTERNAL (symp2); 1363 } 1364 } 1365 1366 /* Double check weak symbols. */ 1367 if (symp->bsym->flags & BSF_WEAK) 1368 { 1369 if (S_IS_COMMON (symp)) 1370 as_bad ("Symbol `%s' can not be both weak and common", 1371 S_GET_NAME (symp)); 1372 } 1373 1374#ifdef TC_MIPS 1375 /* The Irix 5 and 6 assemblers set the type of any common symbol and 1376 any undefined non-function symbol to STT_OBJECT. We try to be compatible, 1377 since newer Irix 5 and 6 linkers care. */ 1378 if (S_IS_COMMON (symp) 1379 || (! S_IS_DEFINED (symp) && ((symp->bsym->flags & BSF_FUNCTION) == 0))) 1380 symp->bsym->flags |= BSF_OBJECT; 1381#endif 1382 1383#ifdef TC_PPC 1384 /* Frob the PowerPC, so that the symbol always has object type 1385 if it is not some other type. VxWorks needs this. */ 1386 if ((symp->bsym->flags & (BSF_FUNCTION | BSF_FILE | BSF_SECTION_SYM)) == 0 1387 && S_IS_DEFINED (symp)) 1388 symp->bsym->flags |= BSF_OBJECT; 1389#endif 1390} 1391 1392void 1393elf_frob_file () 1394{ 1395 bfd_map_over_sections (stdoutput, adjust_stab_sections, (PTR) 0); 1396 1397#ifdef elf_tc_final_processing 1398 elf_tc_final_processing (); 1399#endif 1400} 1401 1402/* It is required that we let write_relocs have the opportunity to 1403 optimize away fixups before output has begun, since it is possible 1404 to eliminate all fixups for a section and thus we never should 1405 have generated the relocation section. */ 1406 1407void 1408elf_frob_file_after_relocs () 1409{ 1410#ifdef NEED_ECOFF_DEBUG 1411 if (ECOFF_DEBUGGING) 1412 /* Generate the ECOFF debugging information. */ 1413 { 1414 const struct ecoff_debug_swap *debug_swap; 1415 struct ecoff_debug_info debug; 1416 char *buf; 1417 asection *sec; 1418 1419 debug_swap 1420 = get_elf_backend_data (stdoutput)->elf_backend_ecoff_debug_swap; 1421 know (debug_swap != (const struct ecoff_debug_swap *) NULL); 1422 ecoff_build_debug (&debug.symbolic_header, &buf, debug_swap); 1423 1424 /* Set up the pointers in debug. */ 1425#define SET(ptr, offset, type) \ 1426 debug.ptr = (type) (buf + debug.symbolic_header.offset) 1427 1428 SET (line, cbLineOffset, unsigned char *); 1429 SET (external_dnr, cbDnOffset, PTR); 1430 SET (external_pdr, cbPdOffset, PTR); 1431 SET (external_sym, cbSymOffset, PTR); 1432 SET (external_opt, cbOptOffset, PTR); 1433 SET (external_aux, cbAuxOffset, union aux_ext *); 1434 SET (ss, cbSsOffset, char *); 1435 SET (external_fdr, cbFdOffset, PTR); 1436 SET (external_rfd, cbRfdOffset, PTR); 1437 /* ssext and external_ext are set up just below. */ 1438 1439#undef SET 1440 1441 /* Set up the external symbols. */ 1442 debug.ssext = debug.ssext_end = NULL; 1443 debug.external_ext = debug.external_ext_end = NULL; 1444 if (! bfd_ecoff_debug_externals (stdoutput, &debug, debug_swap, true, 1445 elf_get_extr, elf_set_index)) 1446 as_fatal ("Failed to set up debugging information: %s", 1447 bfd_errmsg (bfd_get_error ())); 1448 1449 sec = bfd_get_section_by_name (stdoutput, ".mdebug"); 1450 assert (sec != NULL); 1451 1452 know (stdoutput->output_has_begun == false); 1453 1454 /* We set the size of the section, call bfd_set_section_contents 1455 to force the ELF backend to allocate a file position, and then 1456 write out the data. FIXME: Is this really the best way to do 1457 this? */ 1458 sec->_raw_size = bfd_ecoff_debug_size (stdoutput, &debug, debug_swap); 1459 1460 if (! bfd_set_section_contents (stdoutput, sec, (PTR) NULL, 1461 (file_ptr) 0, (bfd_size_type) 0)) 1462 as_fatal ("Can't start writing .mdebug section: %s", 1463 bfd_errmsg (bfd_get_error ())); 1464 1465 know (stdoutput->output_has_begun == true); 1466 know (sec->filepos != 0); 1467 1468 if (! bfd_ecoff_write_debug (stdoutput, &debug, debug_swap, 1469 sec->filepos)) 1470 as_fatal ("Could not write .mdebug section: %s", 1471 bfd_errmsg (bfd_get_error ())); 1472 } 1473#endif /* NEED_ECOFF_DEBUG */ 1474} 1475 1476#ifdef SCO_ELF 1477 1478/* Heavily plagarized from obj_elf_version. The idea is to emit the 1479 SCO specific identifier in the .notes section to satisfy the SCO 1480 linker. 1481 1482 This looks more complicated than it really is. As opposed to the 1483 "obvious" solution, this should handle the cross dev cases 1484 correctly. (i.e, hosting on a 64 bit big endian processor, but 1485 generating SCO Elf code) Efficiency isn't a concern, as there 1486 should be exactly one of these sections per object module. 1487 1488 SCO OpenServer 5 identifies it's ELF modules with a standard ELF 1489 .note section. 1490 1491 int_32 namesz = 4 ; Name size 1492 int_32 descsz = 12 ; Descriptive information 1493 int_32 type = 1 ; 1494 char name[4] = "SCO" ; Originator name ALWAYS SCO + NULL 1495 int_32 version = (major ver # << 16) | version of tools ; 1496 int_32 source = (tool_id << 16 ) | 1 ; 1497 int_32 info = 0 ; These are set by the SCO tools, but we 1498 don't know enough about the source 1499 environment to set them. SCO ld currently 1500 ignores them, and recommends we set them 1501 to zero. */ 1502 1503#define SCO_MAJOR_VERSION 0x1 1504#define SCO_MINOR_VERSION 0x1 1505 1506void 1507sco_id () 1508{ 1509 1510 char *name; 1511 unsigned int c; 1512 char ch; 1513 char *p; 1514 asection *seg = now_seg; 1515 subsegT subseg = now_subseg; 1516 Elf_Internal_Note i_note; 1517 Elf_External_Note e_note; 1518 asection *note_secp = (asection *) NULL; 1519 int i, len; 1520 1521 /* create the .note section */ 1522 1523 note_secp = subseg_new (".note", 0); 1524 bfd_set_section_flags (stdoutput, 1525 note_secp, 1526 SEC_HAS_CONTENTS | SEC_READONLY); 1527 1528 /* process the version string */ 1529 1530 i_note.namesz = 4; 1531 i_note.descsz = 12; /* 12 descriptive bytes */ 1532 i_note.type = NT_VERSION; /* Contains a version string */ 1533 1534 p = frag_more (sizeof (i_note.namesz)); 1535 md_number_to_chars (p, (valueT) i_note.namesz, 4); 1536 1537 p = frag_more (sizeof (i_note.descsz)); 1538 md_number_to_chars (p, (valueT) i_note.descsz, 4); 1539 1540 p = frag_more (sizeof (i_note.type)); 1541 md_number_to_chars (p, (valueT) i_note.type, 4); 1542 1543 p = frag_more (4); 1544 strcpy (p, "SCO"); 1545 1546 /* Note: this is the version number of the ELF we're representing */ 1547 p = frag_more (4); 1548 md_number_to_chars (p, (SCO_MAJOR_VERSION << 16) | (SCO_MINOR_VERSION), 4); 1549 1550 /* Here, we pick a magic number for ourselves (yes, I "registered" 1551 it with SCO. The bottom bit shows that we are compat with the 1552 SCO ABI. */ 1553 p = frag_more (4); 1554 md_number_to_chars (p, 0x4c520000 | 0x0001, 4); 1555 1556 /* If we knew (or cared) what the source language options were, we'd 1557 fill them in here. SCO has given us permission to ignore these 1558 and just set them to zero. */ 1559 p = frag_more (4); 1560 md_number_to_chars (p, 0x0000, 4); 1561 1562 frag_align (2, 0, 0); 1563 1564 /* We probably can't restore the current segment, for there likely 1565 isn't one yet... */ 1566 if (seg && subseg) 1567 subseg_set (seg, subseg); 1568 1569} 1570 1571#endif /* SCO_ELF */ 1572 1573const struct format_ops elf_format_ops = 1574{ 1575 bfd_target_elf_flavour, 1576 0, 1577 1, 1578 elf_frob_symbol, 1579 elf_frob_file, 1580 elf_frob_file_after_relocs, 1581 elf_s_get_size, elf_s_set_size, 1582 elf_s_get_align, elf_s_set_align, 1583 elf_copy_symbol_attributes, 1584#ifdef NEED_ECOFF_DEBUG 1585 ecoff_generate_asm_lineno, 1586 ecoff_stab, 1587#else 1588 0, 1589 0, /* process_stab */ 1590#endif 1591 elf_sec_sym_ok_for_reloc, 1592 elf_pop_insert, 1593#ifdef NEED_ECOFF_DEBUG 1594 elf_ecoff_set_ext, 1595#else 1596 0, 1597#endif 1598 obj_read_begin_hook, 1599 obj_symbol_new_hook, 1600}; 1601