* elfcpp.h (NT_VERSION, NT_ARCH): Define as enum constants.
[binutils.git] / bfd / elf64-alpha.c
blob308b4e9c70f191743077378227d5ed63cbc4a91e
1 /* Alpha specific support for 64-bit ELF
2 Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
3 2006, 2007, 2008 Free Software Foundation, Inc.
4 Contributed by Richard Henderson <rth@tamu.edu>.
6 This file is part of BFD, the Binary File Descriptor library.
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
21 MA 02110-1301, USA. */
24 /* We need a published ABI spec for this. Until one comes out, don't
25 assume this'll remain unchanged forever. */
27 #include "sysdep.h"
28 #include "bfd.h"
29 #include "libbfd.h"
30 #include "elf-bfd.h"
32 #include "elf/alpha.h"
34 #define ALPHAECOFF
36 #define NO_COFF_RELOCS
37 #define NO_COFF_SYMBOLS
38 #define NO_COFF_LINENOS
40 /* Get the ECOFF swapping routines. Needed for the debug information. */
41 #include "coff/internal.h"
42 #include "coff/sym.h"
43 #include "coff/symconst.h"
44 #include "coff/ecoff.h"
45 #include "coff/alpha.h"
46 #include "aout/ar.h"
47 #include "libcoff.h"
48 #include "libecoff.h"
49 #define ECOFF_64
50 #include "ecoffswap.h"
53 /* Instruction data for plt generation and relaxation. */
55 #define OP_LDA 0x08
56 #define OP_LDAH 0x09
57 #define OP_LDQ 0x29
58 #define OP_BR 0x30
59 #define OP_BSR 0x34
61 #define INSN_LDA (OP_LDA << 26)
62 #define INSN_LDAH (OP_LDAH << 26)
63 #define INSN_LDQ (OP_LDQ << 26)
64 #define INSN_BR (OP_BR << 26)
66 #define INSN_ADDQ 0x40000400
67 #define INSN_RDUNIQ 0x0000009e
68 #define INSN_SUBQ 0x40000520
69 #define INSN_S4SUBQ 0x40000560
70 #define INSN_UNOP 0x2ffe0000
72 #define INSN_JSR 0x68004000
73 #define INSN_JMP 0x68000000
74 #define INSN_JSR_MASK 0xfc00c000
76 #define INSN_A(I,A) (I | (A << 21))
77 #define INSN_AB(I,A,B) (I | (A << 21) | (B << 16))
78 #define INSN_ABC(I,A,B,C) (I | (A << 21) | (B << 16) | C)
79 #define INSN_ABO(I,A,B,O) (I | (A << 21) | (B << 16) | ((O) & 0xffff))
80 #define INSN_AD(I,A,D) (I | (A << 21) | (((D) >> 2) & 0x1fffff))
82 /* PLT/GOT Stuff */
84 /* Set by ld emulation. Putting this into the link_info or hash structure
85 is simply working too hard. */
86 #ifdef USE_SECUREPLT
87 bfd_boolean elf64_alpha_use_secureplt = TRUE;
88 #else
89 bfd_boolean elf64_alpha_use_secureplt = FALSE;
90 #endif
92 #define OLD_PLT_HEADER_SIZE 32
93 #define OLD_PLT_ENTRY_SIZE 12
94 #define NEW_PLT_HEADER_SIZE 36
95 #define NEW_PLT_ENTRY_SIZE 4
97 #define PLT_HEADER_SIZE \
98 (elf64_alpha_use_secureplt ? NEW_PLT_HEADER_SIZE : OLD_PLT_HEADER_SIZE)
99 #define PLT_ENTRY_SIZE \
100 (elf64_alpha_use_secureplt ? NEW_PLT_ENTRY_SIZE : OLD_PLT_ENTRY_SIZE)
102 #define MAX_GOT_SIZE (64*1024)
104 #define ELF_DYNAMIC_INTERPRETER "/usr/lib/ld.so"
106 struct alpha_elf_link_hash_entry
108 struct elf_link_hash_entry root;
110 /* External symbol information. */
111 EXTR esym;
113 /* Cumulative flags for all the .got entries. */
114 int flags;
116 /* Contexts in which a literal was referenced. */
117 #define ALPHA_ELF_LINK_HASH_LU_ADDR 0x01
118 #define ALPHA_ELF_LINK_HASH_LU_MEM 0x02
119 #define ALPHA_ELF_LINK_HASH_LU_BYTE 0x04
120 #define ALPHA_ELF_LINK_HASH_LU_JSR 0x08
121 #define ALPHA_ELF_LINK_HASH_LU_TLSGD 0x10
122 #define ALPHA_ELF_LINK_HASH_LU_TLSLDM 0x20
123 #define ALPHA_ELF_LINK_HASH_LU_JSRDIRECT 0x40
124 #define ALPHA_ELF_LINK_HASH_LU_PLT 0x38
125 #define ALPHA_ELF_LINK_HASH_TLS_IE 0x80
127 /* Used to implement multiple .got subsections. */
128 struct alpha_elf_got_entry
130 struct alpha_elf_got_entry *next;
132 /* Which .got subsection? */
133 bfd *gotobj;
135 /* The addend in effect for this entry. */
136 bfd_vma addend;
138 /* The .got offset for this entry. */
139 int got_offset;
141 /* The .plt offset for this entry. */
142 int plt_offset;
144 /* How many references to this entry? */
145 int use_count;
147 /* The relocation type of this entry. */
148 unsigned char reloc_type;
150 /* How a LITERAL is used. */
151 unsigned char flags;
153 /* Have we initialized the dynamic relocation for this entry? */
154 unsigned char reloc_done;
156 /* Have we adjusted this entry for SEC_MERGE? */
157 unsigned char reloc_xlated;
158 } *got_entries;
160 /* Used to count non-got, non-plt relocations for delayed sizing
161 of relocation sections. */
162 struct alpha_elf_reloc_entry
164 struct alpha_elf_reloc_entry *next;
166 /* Which .reloc section? */
167 asection *srel;
169 /* What kind of relocation? */
170 unsigned int rtype;
172 /* Is this against read-only section? */
173 unsigned int reltext : 1;
175 /* How many did we find? */
176 unsigned long count;
177 } *reloc_entries;
180 /* Alpha ELF linker hash table. */
182 struct alpha_elf_link_hash_table
184 struct elf_link_hash_table root;
186 /* The head of a list of .got subsections linked through
187 alpha_elf_tdata(abfd)->got_link_next. */
188 bfd *got_list;
190 /* The most recent relax pass that we've seen. The GOTs
191 should be regenerated if this doesn't match. */
192 int relax_trip;
195 /* Look up an entry in a Alpha ELF linker hash table. */
197 #define alpha_elf_link_hash_lookup(table, string, create, copy, follow) \
198 ((struct alpha_elf_link_hash_entry *) \
199 elf_link_hash_lookup (&(table)->root, (string), (create), \
200 (copy), (follow)))
202 /* Traverse a Alpha ELF linker hash table. */
204 #define alpha_elf_link_hash_traverse(table, func, info) \
205 (elf_link_hash_traverse \
206 (&(table)->root, \
207 (bfd_boolean (*) (struct elf_link_hash_entry *, PTR)) (func), \
208 (info)))
210 /* Get the Alpha ELF linker hash table from a link_info structure. */
212 #define alpha_elf_hash_table(p) \
213 ((struct alpha_elf_link_hash_table *) ((p)->hash))
215 /* Get the object's symbols as our own entry type. */
217 #define alpha_elf_sym_hashes(abfd) \
218 ((struct alpha_elf_link_hash_entry **)elf_sym_hashes(abfd))
220 /* Should we do dynamic things to this symbol? This differs from the
221 generic version in that we never need to consider function pointer
222 equality wrt PLT entries -- we don't create a PLT entry if a symbol's
223 address is ever taken. */
225 static inline bfd_boolean
226 alpha_elf_dynamic_symbol_p (struct elf_link_hash_entry *h,
227 struct bfd_link_info *info)
229 return _bfd_elf_dynamic_symbol_p (h, info, 0);
232 /* Create an entry in a Alpha ELF linker hash table. */
234 static struct bfd_hash_entry *
235 elf64_alpha_link_hash_newfunc (struct bfd_hash_entry *entry,
236 struct bfd_hash_table *table,
237 const char *string)
239 struct alpha_elf_link_hash_entry *ret =
240 (struct alpha_elf_link_hash_entry *) entry;
242 /* Allocate the structure if it has not already been allocated by a
243 subclass. */
244 if (ret == (struct alpha_elf_link_hash_entry *) NULL)
245 ret = ((struct alpha_elf_link_hash_entry *)
246 bfd_hash_allocate (table,
247 sizeof (struct alpha_elf_link_hash_entry)));
248 if (ret == (struct alpha_elf_link_hash_entry *) NULL)
249 return (struct bfd_hash_entry *) ret;
251 /* Call the allocation method of the superclass. */
252 ret = ((struct alpha_elf_link_hash_entry *)
253 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
254 table, string));
255 if (ret != (struct alpha_elf_link_hash_entry *) NULL)
257 /* Set local fields. */
258 memset (&ret->esym, 0, sizeof (EXTR));
259 /* We use -2 as a marker to indicate that the information has
260 not been set. -1 means there is no associated ifd. */
261 ret->esym.ifd = -2;
262 ret->flags = 0;
263 ret->got_entries = NULL;
264 ret->reloc_entries = NULL;
267 return (struct bfd_hash_entry *) ret;
270 /* Create a Alpha ELF linker hash table. */
272 static struct bfd_link_hash_table *
273 elf64_alpha_bfd_link_hash_table_create (bfd *abfd)
275 struct alpha_elf_link_hash_table *ret;
276 bfd_size_type amt = sizeof (struct alpha_elf_link_hash_table);
278 ret = (struct alpha_elf_link_hash_table *) bfd_zmalloc (amt);
279 if (ret == (struct alpha_elf_link_hash_table *) NULL)
280 return NULL;
282 if (!_bfd_elf_link_hash_table_init (&ret->root, abfd,
283 elf64_alpha_link_hash_newfunc,
284 sizeof (struct alpha_elf_link_hash_entry)))
286 free (ret);
287 return NULL;
290 return &ret->root.root;
293 /* We have some private fields hanging off of the elf_tdata structure. */
295 struct alpha_elf_obj_tdata
297 struct elf_obj_tdata root;
299 /* For every input file, these are the got entries for that object's
300 local symbols. */
301 struct alpha_elf_got_entry ** local_got_entries;
303 /* For every input file, this is the object that owns the got that
304 this input file uses. */
305 bfd *gotobj;
307 /* For every got, this is a linked list through the objects using this got */
308 bfd *in_got_link_next;
310 /* For every got, this is a link to the next got subsegment. */
311 bfd *got_link_next;
313 /* For every got, this is the section. */
314 asection *got;
316 /* For every got, this is it's total number of words. */
317 int total_got_size;
319 /* For every got, this is the sum of the number of words required
320 to hold all of the member object's local got. */
321 int local_got_size;
324 #define alpha_elf_tdata(abfd) \
325 ((struct alpha_elf_obj_tdata *) (abfd)->tdata.any)
327 #define is_alpha_elf(bfd) \
328 (bfd_get_flavour (bfd) == bfd_target_elf_flavour \
329 && elf_tdata (bfd) != NULL \
330 && elf_object_id (bfd) == ALPHA_ELF_TDATA)
332 static bfd_boolean
333 elf64_alpha_mkobject (bfd *abfd)
335 return bfd_elf_allocate_object (abfd, sizeof (struct alpha_elf_obj_tdata),
336 ALPHA_ELF_TDATA);
339 static bfd_boolean
340 elf64_alpha_object_p (bfd *abfd)
342 /* Set the right machine number for an Alpha ELF file. */
343 return bfd_default_set_arch_mach (abfd, bfd_arch_alpha, 0);
346 /* A relocation function which doesn't do anything. */
348 static bfd_reloc_status_type
349 elf64_alpha_reloc_nil (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc,
350 asymbol *sym ATTRIBUTE_UNUSED,
351 PTR data ATTRIBUTE_UNUSED, asection *sec,
352 bfd *output_bfd, char **error_message ATTRIBUTE_UNUSED)
354 if (output_bfd)
355 reloc->address += sec->output_offset;
356 return bfd_reloc_ok;
359 /* A relocation function used for an unsupported reloc. */
361 static bfd_reloc_status_type
362 elf64_alpha_reloc_bad (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc,
363 asymbol *sym ATTRIBUTE_UNUSED,
364 PTR data ATTRIBUTE_UNUSED, asection *sec,
365 bfd *output_bfd, char **error_message ATTRIBUTE_UNUSED)
367 if (output_bfd)
368 reloc->address += sec->output_offset;
369 return bfd_reloc_notsupported;
372 /* Do the work of the GPDISP relocation. */
374 static bfd_reloc_status_type
375 elf64_alpha_do_reloc_gpdisp (bfd *abfd, bfd_vma gpdisp, bfd_byte *p_ldah,
376 bfd_byte *p_lda)
378 bfd_reloc_status_type ret = bfd_reloc_ok;
379 bfd_vma addend;
380 unsigned long i_ldah, i_lda;
382 i_ldah = bfd_get_32 (abfd, p_ldah);
383 i_lda = bfd_get_32 (abfd, p_lda);
385 /* Complain if the instructions are not correct. */
386 if (((i_ldah >> 26) & 0x3f) != 0x09
387 || ((i_lda >> 26) & 0x3f) != 0x08)
388 ret = bfd_reloc_dangerous;
390 /* Extract the user-supplied offset, mirroring the sign extensions
391 that the instructions perform. */
392 addend = ((i_ldah & 0xffff) << 16) | (i_lda & 0xffff);
393 addend = (addend ^ 0x80008000) - 0x80008000;
395 gpdisp += addend;
397 if ((bfd_signed_vma) gpdisp < -(bfd_signed_vma) 0x80000000
398 || (bfd_signed_vma) gpdisp >= (bfd_signed_vma) 0x7fff8000)
399 ret = bfd_reloc_overflow;
401 /* compensate for the sign extension again. */
402 i_ldah = ((i_ldah & 0xffff0000)
403 | (((gpdisp >> 16) + ((gpdisp >> 15) & 1)) & 0xffff));
404 i_lda = (i_lda & 0xffff0000) | (gpdisp & 0xffff);
406 bfd_put_32 (abfd, (bfd_vma) i_ldah, p_ldah);
407 bfd_put_32 (abfd, (bfd_vma) i_lda, p_lda);
409 return ret;
412 /* The special function for the GPDISP reloc. */
414 static bfd_reloc_status_type
415 elf64_alpha_reloc_gpdisp (bfd *abfd, arelent *reloc_entry,
416 asymbol *sym ATTRIBUTE_UNUSED, PTR data,
417 asection *input_section, bfd *output_bfd,
418 char **err_msg)
420 bfd_reloc_status_type ret;
421 bfd_vma gp, relocation;
422 bfd_vma high_address;
423 bfd_byte *p_ldah, *p_lda;
425 /* Don't do anything if we're not doing a final link. */
426 if (output_bfd)
428 reloc_entry->address += input_section->output_offset;
429 return bfd_reloc_ok;
432 high_address = bfd_get_section_limit (abfd, input_section);
433 if (reloc_entry->address > high_address
434 || reloc_entry->address + reloc_entry->addend > high_address)
435 return bfd_reloc_outofrange;
437 /* The gp used in the portion of the output object to which this
438 input object belongs is cached on the input bfd. */
439 gp = _bfd_get_gp_value (abfd);
441 relocation = (input_section->output_section->vma
442 + input_section->output_offset
443 + reloc_entry->address);
445 p_ldah = (bfd_byte *) data + reloc_entry->address;
446 p_lda = p_ldah + reloc_entry->addend;
448 ret = elf64_alpha_do_reloc_gpdisp (abfd, gp - relocation, p_ldah, p_lda);
450 /* Complain if the instructions are not correct. */
451 if (ret == bfd_reloc_dangerous)
452 *err_msg = _("GPDISP relocation did not find ldah and lda instructions");
454 return ret;
457 /* In case we're on a 32-bit machine, construct a 64-bit "-1" value
458 from smaller values. Start with zero, widen, *then* decrement. */
459 #define MINUS_ONE (((bfd_vma)0) - 1)
461 #define SKIP_HOWTO(N) \
462 HOWTO(N, 0, 0, 0, 0, 0, 0, elf64_alpha_reloc_bad, 0, 0, 0, 0, 0)
464 static reloc_howto_type elf64_alpha_howto_table[] =
466 HOWTO (R_ALPHA_NONE, /* type */
467 0, /* rightshift */
468 0, /* size (0 = byte, 1 = short, 2 = long) */
469 8, /* bitsize */
470 TRUE, /* pc_relative */
471 0, /* bitpos */
472 complain_overflow_dont, /* complain_on_overflow */
473 elf64_alpha_reloc_nil, /* special_function */
474 "NONE", /* name */
475 FALSE, /* partial_inplace */
476 0, /* src_mask */
477 0, /* dst_mask */
478 TRUE), /* pcrel_offset */
480 /* A 32 bit reference to a symbol. */
481 HOWTO (R_ALPHA_REFLONG, /* type */
482 0, /* rightshift */
483 2, /* size (0 = byte, 1 = short, 2 = long) */
484 32, /* bitsize */
485 FALSE, /* pc_relative */
486 0, /* bitpos */
487 complain_overflow_bitfield, /* complain_on_overflow */
488 0, /* special_function */
489 "REFLONG", /* name */
490 FALSE, /* partial_inplace */
491 0xffffffff, /* src_mask */
492 0xffffffff, /* dst_mask */
493 FALSE), /* pcrel_offset */
495 /* A 64 bit reference to a symbol. */
496 HOWTO (R_ALPHA_REFQUAD, /* type */
497 0, /* rightshift */
498 4, /* size (0 = byte, 1 = short, 2 = long) */
499 64, /* bitsize */
500 FALSE, /* pc_relative */
501 0, /* bitpos */
502 complain_overflow_bitfield, /* complain_on_overflow */
503 0, /* special_function */
504 "REFQUAD", /* name */
505 FALSE, /* partial_inplace */
506 MINUS_ONE, /* src_mask */
507 MINUS_ONE, /* dst_mask */
508 FALSE), /* pcrel_offset */
510 /* A 32 bit GP relative offset. This is just like REFLONG except
511 that when the value is used the value of the gp register will be
512 added in. */
513 HOWTO (R_ALPHA_GPREL32, /* type */
514 0, /* rightshift */
515 2, /* size (0 = byte, 1 = short, 2 = long) */
516 32, /* bitsize */
517 FALSE, /* pc_relative */
518 0, /* bitpos */
519 complain_overflow_bitfield, /* complain_on_overflow */
520 0, /* special_function */
521 "GPREL32", /* name */
522 FALSE, /* partial_inplace */
523 0xffffffff, /* src_mask */
524 0xffffffff, /* dst_mask */
525 FALSE), /* pcrel_offset */
527 /* Used for an instruction that refers to memory off the GP register. */
528 HOWTO (R_ALPHA_LITERAL, /* type */
529 0, /* rightshift */
530 1, /* size (0 = byte, 1 = short, 2 = long) */
531 16, /* bitsize */
532 FALSE, /* pc_relative */
533 0, /* bitpos */
534 complain_overflow_signed, /* complain_on_overflow */
535 0, /* special_function */
536 "ELF_LITERAL", /* name */
537 FALSE, /* partial_inplace */
538 0xffff, /* src_mask */
539 0xffff, /* dst_mask */
540 FALSE), /* pcrel_offset */
542 /* This reloc only appears immediately following an ELF_LITERAL reloc.
543 It identifies a use of the literal. The symbol index is special:
544 1 means the literal address is in the base register of a memory
545 format instruction; 2 means the literal address is in the byte
546 offset register of a byte-manipulation instruction; 3 means the
547 literal address is in the target register of a jsr instruction.
548 This does not actually do any relocation. */
549 HOWTO (R_ALPHA_LITUSE, /* type */
550 0, /* rightshift */
551 1, /* size (0 = byte, 1 = short, 2 = long) */
552 32, /* bitsize */
553 FALSE, /* pc_relative */
554 0, /* bitpos */
555 complain_overflow_dont, /* complain_on_overflow */
556 elf64_alpha_reloc_nil, /* special_function */
557 "LITUSE", /* name */
558 FALSE, /* partial_inplace */
559 0, /* src_mask */
560 0, /* dst_mask */
561 FALSE), /* pcrel_offset */
563 /* Load the gp register. This is always used for a ldah instruction
564 which loads the upper 16 bits of the gp register. The symbol
565 index of the GPDISP instruction is an offset in bytes to the lda
566 instruction that loads the lower 16 bits. The value to use for
567 the relocation is the difference between the GP value and the
568 current location; the load will always be done against a register
569 holding the current address.
571 NOTE: Unlike ECOFF, partial in-place relocation is not done. If
572 any offset is present in the instructions, it is an offset from
573 the register to the ldah instruction. This lets us avoid any
574 stupid hackery like inventing a gp value to do partial relocation
575 against. Also unlike ECOFF, we do the whole relocation off of
576 the GPDISP rather than a GPDISP_HI16/GPDISP_LO16 pair. An odd,
577 space consuming bit, that, since all the information was present
578 in the GPDISP_HI16 reloc. */
579 HOWTO (R_ALPHA_GPDISP, /* type */
580 16, /* rightshift */
581 2, /* size (0 = byte, 1 = short, 2 = long) */
582 16, /* bitsize */
583 FALSE, /* pc_relative */
584 0, /* bitpos */
585 complain_overflow_dont, /* complain_on_overflow */
586 elf64_alpha_reloc_gpdisp, /* special_function */
587 "GPDISP", /* name */
588 FALSE, /* partial_inplace */
589 0xffff, /* src_mask */
590 0xffff, /* dst_mask */
591 TRUE), /* pcrel_offset */
593 /* A 21 bit branch. */
594 HOWTO (R_ALPHA_BRADDR, /* type */
595 2, /* rightshift */
596 2, /* size (0 = byte, 1 = short, 2 = long) */
597 21, /* bitsize */
598 TRUE, /* pc_relative */
599 0, /* bitpos */
600 complain_overflow_signed, /* complain_on_overflow */
601 0, /* special_function */
602 "BRADDR", /* name */
603 FALSE, /* partial_inplace */
604 0x1fffff, /* src_mask */
605 0x1fffff, /* dst_mask */
606 TRUE), /* pcrel_offset */
608 /* A hint for a jump to a register. */
609 HOWTO (R_ALPHA_HINT, /* type */
610 2, /* rightshift */
611 1, /* size (0 = byte, 1 = short, 2 = long) */
612 14, /* bitsize */
613 TRUE, /* pc_relative */
614 0, /* bitpos */
615 complain_overflow_dont, /* complain_on_overflow */
616 0, /* special_function */
617 "HINT", /* name */
618 FALSE, /* partial_inplace */
619 0x3fff, /* src_mask */
620 0x3fff, /* dst_mask */
621 TRUE), /* pcrel_offset */
623 /* 16 bit PC relative offset. */
624 HOWTO (R_ALPHA_SREL16, /* type */
625 0, /* rightshift */
626 1, /* size (0 = byte, 1 = short, 2 = long) */
627 16, /* bitsize */
628 TRUE, /* pc_relative */
629 0, /* bitpos */
630 complain_overflow_signed, /* complain_on_overflow */
631 0, /* special_function */
632 "SREL16", /* name */
633 FALSE, /* partial_inplace */
634 0xffff, /* src_mask */
635 0xffff, /* dst_mask */
636 TRUE), /* pcrel_offset */
638 /* 32 bit PC relative offset. */
639 HOWTO (R_ALPHA_SREL32, /* type */
640 0, /* rightshift */
641 2, /* size (0 = byte, 1 = short, 2 = long) */
642 32, /* bitsize */
643 TRUE, /* pc_relative */
644 0, /* bitpos */
645 complain_overflow_signed, /* complain_on_overflow */
646 0, /* special_function */
647 "SREL32", /* name */
648 FALSE, /* partial_inplace */
649 0xffffffff, /* src_mask */
650 0xffffffff, /* dst_mask */
651 TRUE), /* pcrel_offset */
653 /* A 64 bit PC relative offset. */
654 HOWTO (R_ALPHA_SREL64, /* type */
655 0, /* rightshift */
656 4, /* size (0 = byte, 1 = short, 2 = long) */
657 64, /* bitsize */
658 TRUE, /* pc_relative */
659 0, /* bitpos */
660 complain_overflow_signed, /* complain_on_overflow */
661 0, /* special_function */
662 "SREL64", /* name */
663 FALSE, /* partial_inplace */
664 MINUS_ONE, /* src_mask */
665 MINUS_ONE, /* dst_mask */
666 TRUE), /* pcrel_offset */
668 /* Skip 12 - 16; deprecated ECOFF relocs. */
669 SKIP_HOWTO (12),
670 SKIP_HOWTO (13),
671 SKIP_HOWTO (14),
672 SKIP_HOWTO (15),
673 SKIP_HOWTO (16),
675 /* The high 16 bits of the displacement from GP to the target. */
676 HOWTO (R_ALPHA_GPRELHIGH,
677 0, /* rightshift */
678 1, /* size (0 = byte, 1 = short, 2 = long) */
679 16, /* bitsize */
680 FALSE, /* pc_relative */
681 0, /* bitpos */
682 complain_overflow_signed, /* complain_on_overflow */
683 0, /* special_function */
684 "GPRELHIGH", /* name */
685 FALSE, /* partial_inplace */
686 0xffff, /* src_mask */
687 0xffff, /* dst_mask */
688 FALSE), /* pcrel_offset */
690 /* The low 16 bits of the displacement from GP to the target. */
691 HOWTO (R_ALPHA_GPRELLOW,
692 0, /* rightshift */
693 1, /* size (0 = byte, 1 = short, 2 = long) */
694 16, /* bitsize */
695 FALSE, /* pc_relative */
696 0, /* bitpos */
697 complain_overflow_dont, /* complain_on_overflow */
698 0, /* special_function */
699 "GPRELLOW", /* name */
700 FALSE, /* partial_inplace */
701 0xffff, /* src_mask */
702 0xffff, /* dst_mask */
703 FALSE), /* pcrel_offset */
705 /* A 16-bit displacement from the GP to the target. */
706 HOWTO (R_ALPHA_GPREL16,
707 0, /* rightshift */
708 1, /* size (0 = byte, 1 = short, 2 = long) */
709 16, /* bitsize */
710 FALSE, /* pc_relative */
711 0, /* bitpos */
712 complain_overflow_signed, /* complain_on_overflow */
713 0, /* special_function */
714 "GPREL16", /* name */
715 FALSE, /* partial_inplace */
716 0xffff, /* src_mask */
717 0xffff, /* dst_mask */
718 FALSE), /* pcrel_offset */
720 /* Skip 20 - 23; deprecated ECOFF relocs. */
721 SKIP_HOWTO (20),
722 SKIP_HOWTO (21),
723 SKIP_HOWTO (22),
724 SKIP_HOWTO (23),
726 /* Misc ELF relocations. */
728 /* A dynamic relocation to copy the target into our .dynbss section. */
729 /* Not generated, as all Alpha objects use PIC, so it is not needed. It
730 is present because every other ELF has one, but should not be used
731 because .dynbss is an ugly thing. */
732 HOWTO (R_ALPHA_COPY,
736 FALSE,
738 complain_overflow_dont,
739 bfd_elf_generic_reloc,
740 "COPY",
741 FALSE,
744 TRUE),
746 /* A dynamic relocation for a .got entry. */
747 HOWTO (R_ALPHA_GLOB_DAT,
751 FALSE,
753 complain_overflow_dont,
754 bfd_elf_generic_reloc,
755 "GLOB_DAT",
756 FALSE,
759 TRUE),
761 /* A dynamic relocation for a .plt entry. */
762 HOWTO (R_ALPHA_JMP_SLOT,
766 FALSE,
768 complain_overflow_dont,
769 bfd_elf_generic_reloc,
770 "JMP_SLOT",
771 FALSE,
774 TRUE),
776 /* A dynamic relocation to add the base of the DSO to a 64-bit field. */
777 HOWTO (R_ALPHA_RELATIVE,
781 FALSE,
783 complain_overflow_dont,
784 bfd_elf_generic_reloc,
785 "RELATIVE",
786 FALSE,
789 TRUE),
791 /* A 21 bit branch that adjusts for gp loads. */
792 HOWTO (R_ALPHA_BRSGP, /* type */
793 2, /* rightshift */
794 2, /* size (0 = byte, 1 = short, 2 = long) */
795 21, /* bitsize */
796 TRUE, /* pc_relative */
797 0, /* bitpos */
798 complain_overflow_signed, /* complain_on_overflow */
799 0, /* special_function */
800 "BRSGP", /* name */
801 FALSE, /* partial_inplace */
802 0x1fffff, /* src_mask */
803 0x1fffff, /* dst_mask */
804 TRUE), /* pcrel_offset */
806 /* Creates a tls_index for the symbol in the got. */
807 HOWTO (R_ALPHA_TLSGD, /* type */
808 0, /* rightshift */
809 1, /* size (0 = byte, 1 = short, 2 = long) */
810 16, /* bitsize */
811 FALSE, /* pc_relative */
812 0, /* bitpos */
813 complain_overflow_signed, /* complain_on_overflow */
814 0, /* special_function */
815 "TLSGD", /* name */
816 FALSE, /* partial_inplace */
817 0xffff, /* src_mask */
818 0xffff, /* dst_mask */
819 FALSE), /* pcrel_offset */
821 /* Creates a tls_index for the (current) module in the got. */
822 HOWTO (R_ALPHA_TLSLDM, /* type */
823 0, /* rightshift */
824 1, /* size (0 = byte, 1 = short, 2 = long) */
825 16, /* bitsize */
826 FALSE, /* pc_relative */
827 0, /* bitpos */
828 complain_overflow_signed, /* complain_on_overflow */
829 0, /* special_function */
830 "TLSLDM", /* name */
831 FALSE, /* partial_inplace */
832 0xffff, /* src_mask */
833 0xffff, /* dst_mask */
834 FALSE), /* pcrel_offset */
836 /* A dynamic relocation for a DTP module entry. */
837 HOWTO (R_ALPHA_DTPMOD64, /* type */
838 0, /* rightshift */
839 4, /* size (0 = byte, 1 = short, 2 = long) */
840 64, /* bitsize */
841 FALSE, /* pc_relative */
842 0, /* bitpos */
843 complain_overflow_bitfield, /* complain_on_overflow */
844 0, /* special_function */
845 "DTPMOD64", /* name */
846 FALSE, /* partial_inplace */
847 MINUS_ONE, /* src_mask */
848 MINUS_ONE, /* dst_mask */
849 FALSE), /* pcrel_offset */
851 /* Creates a 64-bit offset in the got for the displacement
852 from DTP to the target. */
853 HOWTO (R_ALPHA_GOTDTPREL, /* type */
854 0, /* rightshift */
855 1, /* size (0 = byte, 1 = short, 2 = long) */
856 16, /* bitsize */
857 FALSE, /* pc_relative */
858 0, /* bitpos */
859 complain_overflow_signed, /* complain_on_overflow */
860 0, /* special_function */
861 "GOTDTPREL", /* name */
862 FALSE, /* partial_inplace */
863 0xffff, /* src_mask */
864 0xffff, /* dst_mask */
865 FALSE), /* pcrel_offset */
867 /* A dynamic relocation for a displacement from DTP to the target. */
868 HOWTO (R_ALPHA_DTPREL64, /* type */
869 0, /* rightshift */
870 4, /* size (0 = byte, 1 = short, 2 = long) */
871 64, /* bitsize */
872 FALSE, /* pc_relative */
873 0, /* bitpos */
874 complain_overflow_bitfield, /* complain_on_overflow */
875 0, /* special_function */
876 "DTPREL64", /* name */
877 FALSE, /* partial_inplace */
878 MINUS_ONE, /* src_mask */
879 MINUS_ONE, /* dst_mask */
880 FALSE), /* pcrel_offset */
882 /* The high 16 bits of the displacement from DTP to the target. */
883 HOWTO (R_ALPHA_DTPRELHI, /* type */
884 0, /* rightshift */
885 1, /* size (0 = byte, 1 = short, 2 = long) */
886 16, /* bitsize */
887 FALSE, /* pc_relative */
888 0, /* bitpos */
889 complain_overflow_signed, /* complain_on_overflow */
890 0, /* special_function */
891 "DTPRELHI", /* name */
892 FALSE, /* partial_inplace */
893 0xffff, /* src_mask */
894 0xffff, /* dst_mask */
895 FALSE), /* pcrel_offset */
897 /* The low 16 bits of the displacement from DTP to the target. */
898 HOWTO (R_ALPHA_DTPRELLO, /* type */
899 0, /* rightshift */
900 1, /* size (0 = byte, 1 = short, 2 = long) */
901 16, /* bitsize */
902 FALSE, /* pc_relative */
903 0, /* bitpos */
904 complain_overflow_dont, /* complain_on_overflow */
905 0, /* special_function */
906 "DTPRELLO", /* name */
907 FALSE, /* partial_inplace */
908 0xffff, /* src_mask */
909 0xffff, /* dst_mask */
910 FALSE), /* pcrel_offset */
912 /* A 16-bit displacement from DTP to the target. */
913 HOWTO (R_ALPHA_DTPREL16, /* type */
914 0, /* rightshift */
915 1, /* size (0 = byte, 1 = short, 2 = long) */
916 16, /* bitsize */
917 FALSE, /* pc_relative */
918 0, /* bitpos */
919 complain_overflow_signed, /* complain_on_overflow */
920 0, /* special_function */
921 "DTPREL16", /* name */
922 FALSE, /* partial_inplace */
923 0xffff, /* src_mask */
924 0xffff, /* dst_mask */
925 FALSE), /* pcrel_offset */
927 /* Creates a 64-bit offset in the got for the displacement
928 from TP to the target. */
929 HOWTO (R_ALPHA_GOTTPREL, /* type */
930 0, /* rightshift */
931 1, /* size (0 = byte, 1 = short, 2 = long) */
932 16, /* bitsize */
933 FALSE, /* pc_relative */
934 0, /* bitpos */
935 complain_overflow_signed, /* complain_on_overflow */
936 0, /* special_function */
937 "GOTTPREL", /* name */
938 FALSE, /* partial_inplace */
939 0xffff, /* src_mask */
940 0xffff, /* dst_mask */
941 FALSE), /* pcrel_offset */
943 /* A dynamic relocation for a displacement from TP to the target. */
944 HOWTO (R_ALPHA_TPREL64, /* type */
945 0, /* rightshift */
946 4, /* size (0 = byte, 1 = short, 2 = long) */
947 64, /* bitsize */
948 FALSE, /* pc_relative */
949 0, /* bitpos */
950 complain_overflow_bitfield, /* complain_on_overflow */
951 0, /* special_function */
952 "TPREL64", /* name */
953 FALSE, /* partial_inplace */
954 MINUS_ONE, /* src_mask */
955 MINUS_ONE, /* dst_mask */
956 FALSE), /* pcrel_offset */
958 /* The high 16 bits of the displacement from TP to the target. */
959 HOWTO (R_ALPHA_TPRELHI, /* type */
960 0, /* rightshift */
961 1, /* size (0 = byte, 1 = short, 2 = long) */
962 16, /* bitsize */
963 FALSE, /* pc_relative */
964 0, /* bitpos */
965 complain_overflow_signed, /* complain_on_overflow */
966 0, /* special_function */
967 "TPRELHI", /* name */
968 FALSE, /* partial_inplace */
969 0xffff, /* src_mask */
970 0xffff, /* dst_mask */
971 FALSE), /* pcrel_offset */
973 /* The low 16 bits of the displacement from TP to the target. */
974 HOWTO (R_ALPHA_TPRELLO, /* type */
975 0, /* rightshift */
976 1, /* size (0 = byte, 1 = short, 2 = long) */
977 16, /* bitsize */
978 FALSE, /* pc_relative */
979 0, /* bitpos */
980 complain_overflow_dont, /* complain_on_overflow */
981 0, /* special_function */
982 "TPRELLO", /* name */
983 FALSE, /* partial_inplace */
984 0xffff, /* src_mask */
985 0xffff, /* dst_mask */
986 FALSE), /* pcrel_offset */
988 /* A 16-bit displacement from TP to the target. */
989 HOWTO (R_ALPHA_TPREL16, /* type */
990 0, /* rightshift */
991 1, /* size (0 = byte, 1 = short, 2 = long) */
992 16, /* bitsize */
993 FALSE, /* pc_relative */
994 0, /* bitpos */
995 complain_overflow_signed, /* complain_on_overflow */
996 0, /* special_function */
997 "TPREL16", /* name */
998 FALSE, /* partial_inplace */
999 0xffff, /* src_mask */
1000 0xffff, /* dst_mask */
1001 FALSE), /* pcrel_offset */
1004 /* A mapping from BFD reloc types to Alpha ELF reloc types. */
1006 struct elf_reloc_map
1008 bfd_reloc_code_real_type bfd_reloc_val;
1009 int elf_reloc_val;
1012 static const struct elf_reloc_map elf64_alpha_reloc_map[] =
1014 {BFD_RELOC_NONE, R_ALPHA_NONE},
1015 {BFD_RELOC_32, R_ALPHA_REFLONG},
1016 {BFD_RELOC_64, R_ALPHA_REFQUAD},
1017 {BFD_RELOC_CTOR, R_ALPHA_REFQUAD},
1018 {BFD_RELOC_GPREL32, R_ALPHA_GPREL32},
1019 {BFD_RELOC_ALPHA_ELF_LITERAL, R_ALPHA_LITERAL},
1020 {BFD_RELOC_ALPHA_LITUSE, R_ALPHA_LITUSE},
1021 {BFD_RELOC_ALPHA_GPDISP, R_ALPHA_GPDISP},
1022 {BFD_RELOC_23_PCREL_S2, R_ALPHA_BRADDR},
1023 {BFD_RELOC_ALPHA_HINT, R_ALPHA_HINT},
1024 {BFD_RELOC_16_PCREL, R_ALPHA_SREL16},
1025 {BFD_RELOC_32_PCREL, R_ALPHA_SREL32},
1026 {BFD_RELOC_64_PCREL, R_ALPHA_SREL64},
1027 {BFD_RELOC_ALPHA_GPREL_HI16, R_ALPHA_GPRELHIGH},
1028 {BFD_RELOC_ALPHA_GPREL_LO16, R_ALPHA_GPRELLOW},
1029 {BFD_RELOC_GPREL16, R_ALPHA_GPREL16},
1030 {BFD_RELOC_ALPHA_BRSGP, R_ALPHA_BRSGP},
1031 {BFD_RELOC_ALPHA_TLSGD, R_ALPHA_TLSGD},
1032 {BFD_RELOC_ALPHA_TLSLDM, R_ALPHA_TLSLDM},
1033 {BFD_RELOC_ALPHA_DTPMOD64, R_ALPHA_DTPMOD64},
1034 {BFD_RELOC_ALPHA_GOTDTPREL16, R_ALPHA_GOTDTPREL},
1035 {BFD_RELOC_ALPHA_DTPREL64, R_ALPHA_DTPREL64},
1036 {BFD_RELOC_ALPHA_DTPREL_HI16, R_ALPHA_DTPRELHI},
1037 {BFD_RELOC_ALPHA_DTPREL_LO16, R_ALPHA_DTPRELLO},
1038 {BFD_RELOC_ALPHA_DTPREL16, R_ALPHA_DTPREL16},
1039 {BFD_RELOC_ALPHA_GOTTPREL16, R_ALPHA_GOTTPREL},
1040 {BFD_RELOC_ALPHA_TPREL64, R_ALPHA_TPREL64},
1041 {BFD_RELOC_ALPHA_TPREL_HI16, R_ALPHA_TPRELHI},
1042 {BFD_RELOC_ALPHA_TPREL_LO16, R_ALPHA_TPRELLO},
1043 {BFD_RELOC_ALPHA_TPREL16, R_ALPHA_TPREL16},
1046 /* Given a BFD reloc type, return a HOWTO structure. */
1048 static reloc_howto_type *
1049 elf64_alpha_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
1050 bfd_reloc_code_real_type code)
1052 const struct elf_reloc_map *i, *e;
1053 i = e = elf64_alpha_reloc_map;
1054 e += sizeof (elf64_alpha_reloc_map) / sizeof (struct elf_reloc_map);
1055 for (; i != e; ++i)
1057 if (i->bfd_reloc_val == code)
1058 return &elf64_alpha_howto_table[i->elf_reloc_val];
1060 return 0;
1063 static reloc_howto_type *
1064 elf64_alpha_bfd_reloc_name_lookup (bfd *abfd ATTRIBUTE_UNUSED,
1065 const char *r_name)
1067 unsigned int i;
1069 for (i = 0;
1070 i < (sizeof (elf64_alpha_howto_table)
1071 / sizeof (elf64_alpha_howto_table[0]));
1072 i++)
1073 if (elf64_alpha_howto_table[i].name != NULL
1074 && strcasecmp (elf64_alpha_howto_table[i].name, r_name) == 0)
1075 return &elf64_alpha_howto_table[i];
1077 return NULL;
1080 /* Given an Alpha ELF reloc type, fill in an arelent structure. */
1082 static void
1083 elf64_alpha_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED, arelent *cache_ptr,
1084 Elf_Internal_Rela *dst)
1086 unsigned r_type = ELF64_R_TYPE(dst->r_info);
1087 BFD_ASSERT (r_type < (unsigned int) R_ALPHA_max);
1088 cache_ptr->howto = &elf64_alpha_howto_table[r_type];
1091 /* These two relocations create a two-word entry in the got. */
1092 #define alpha_got_entry_size(r_type) \
1093 (r_type == R_ALPHA_TLSGD || r_type == R_ALPHA_TLSLDM ? 16 : 8)
1095 /* This is PT_TLS segment p_vaddr. */
1096 #define alpha_get_dtprel_base(info) \
1097 (elf_hash_table (info)->tls_sec->vma)
1099 /* Main program TLS (whose template starts at PT_TLS p_vaddr)
1100 is assigned offset round(16, PT_TLS p_align). */
1101 #define alpha_get_tprel_base(info) \
1102 (elf_hash_table (info)->tls_sec->vma \
1103 - align_power ((bfd_vma) 16, \
1104 elf_hash_table (info)->tls_sec->alignment_power))
1106 /* Handle an Alpha specific section when reading an object file. This
1107 is called when bfd_section_from_shdr finds a section with an unknown
1108 type.
1109 FIXME: We need to handle the SHF_ALPHA_GPREL flag, but I'm not sure
1110 how to. */
1112 static bfd_boolean
1113 elf64_alpha_section_from_shdr (bfd *abfd,
1114 Elf_Internal_Shdr *hdr,
1115 const char *name,
1116 int shindex)
1118 asection *newsect;
1120 /* There ought to be a place to keep ELF backend specific flags, but
1121 at the moment there isn't one. We just keep track of the
1122 sections by their name, instead. Fortunately, the ABI gives
1123 suggested names for all the MIPS specific sections, so we will
1124 probably get away with this. */
1125 switch (hdr->sh_type)
1127 case SHT_ALPHA_DEBUG:
1128 if (strcmp (name, ".mdebug") != 0)
1129 return FALSE;
1130 break;
1131 default:
1132 return FALSE;
1135 if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex))
1136 return FALSE;
1137 newsect = hdr->bfd_section;
1139 if (hdr->sh_type == SHT_ALPHA_DEBUG)
1141 if (! bfd_set_section_flags (abfd, newsect,
1142 (bfd_get_section_flags (abfd, newsect)
1143 | SEC_DEBUGGING)))
1144 return FALSE;
1147 return TRUE;
1150 /* Convert Alpha specific section flags to bfd internal section flags. */
1152 static bfd_boolean
1153 elf64_alpha_section_flags (flagword *flags, const Elf_Internal_Shdr *hdr)
1155 if (hdr->sh_flags & SHF_ALPHA_GPREL)
1156 *flags |= SEC_SMALL_DATA;
1158 return TRUE;
1161 /* Set the correct type for an Alpha ELF section. We do this by the
1162 section name, which is a hack, but ought to work. */
1164 static bfd_boolean
1165 elf64_alpha_fake_sections (bfd *abfd, Elf_Internal_Shdr *hdr, asection *sec)
1167 register const char *name;
1169 name = bfd_get_section_name (abfd, sec);
1171 if (strcmp (name, ".mdebug") == 0)
1173 hdr->sh_type = SHT_ALPHA_DEBUG;
1174 /* In a shared object on Irix 5.3, the .mdebug section has an
1175 entsize of 0. FIXME: Does this matter? */
1176 if ((abfd->flags & DYNAMIC) != 0 )
1177 hdr->sh_entsize = 0;
1178 else
1179 hdr->sh_entsize = 1;
1181 else if ((sec->flags & SEC_SMALL_DATA)
1182 || strcmp (name, ".sdata") == 0
1183 || strcmp (name, ".sbss") == 0
1184 || strcmp (name, ".lit4") == 0
1185 || strcmp (name, ".lit8") == 0)
1186 hdr->sh_flags |= SHF_ALPHA_GPREL;
1188 return TRUE;
1191 /* Hook called by the linker routine which adds symbols from an object
1192 file. We use it to put .comm items in .sbss, and not .bss. */
1194 static bfd_boolean
1195 elf64_alpha_add_symbol_hook (bfd *abfd, struct bfd_link_info *info,
1196 Elf_Internal_Sym *sym,
1197 const char **namep ATTRIBUTE_UNUSED,
1198 flagword *flagsp ATTRIBUTE_UNUSED,
1199 asection **secp, bfd_vma *valp)
1201 if (sym->st_shndx == SHN_COMMON
1202 && !info->relocatable
1203 && sym->st_size <= elf_gp_size (abfd))
1205 /* Common symbols less than or equal to -G nn bytes are
1206 automatically put into .sbss. */
1208 asection *scomm = bfd_get_section_by_name (abfd, ".scommon");
1210 if (scomm == NULL)
1212 scomm = bfd_make_section_with_flags (abfd, ".scommon",
1213 (SEC_ALLOC
1214 | SEC_IS_COMMON
1215 | SEC_LINKER_CREATED));
1216 if (scomm == NULL)
1217 return FALSE;
1220 *secp = scomm;
1221 *valp = sym->st_size;
1224 return TRUE;
1227 /* Create the .got section. */
1229 static bfd_boolean
1230 elf64_alpha_create_got_section (bfd *abfd,
1231 struct bfd_link_info *info ATTRIBUTE_UNUSED)
1233 flagword flags;
1234 asection *s;
1236 if (! is_alpha_elf (abfd))
1237 return FALSE;
1239 flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
1240 | SEC_LINKER_CREATED);
1241 s = bfd_make_section_anyway_with_flags (abfd, ".got", flags);
1242 if (s == NULL
1243 || !bfd_set_section_alignment (abfd, s, 3))
1244 return FALSE;
1246 alpha_elf_tdata (abfd)->got = s;
1248 /* Make sure the object's gotobj is set to itself so that we default
1249 to every object with its own .got. We'll merge .gots later once
1250 we've collected each object's info. */
1251 alpha_elf_tdata (abfd)->gotobj = abfd;
1253 return TRUE;
1256 /* Create all the dynamic sections. */
1258 static bfd_boolean
1259 elf64_alpha_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
1261 asection *s;
1262 flagword flags;
1263 struct elf_link_hash_entry *h;
1265 if (! is_alpha_elf (abfd))
1266 return FALSE;
1268 /* We need to create .plt, .rela.plt, .got, and .rela.got sections. */
1270 flags = (SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS | SEC_IN_MEMORY
1271 | SEC_LINKER_CREATED
1272 | (elf64_alpha_use_secureplt ? SEC_READONLY : 0));
1273 s = bfd_make_section_anyway_with_flags (abfd, ".plt", flags);
1274 if (s == NULL || ! bfd_set_section_alignment (abfd, s, 4))
1275 return FALSE;
1277 /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
1278 .plt section. */
1279 h = _bfd_elf_define_linkage_sym (abfd, info, s,
1280 "_PROCEDURE_LINKAGE_TABLE_");
1281 elf_hash_table (info)->hplt = h;
1282 if (h == NULL)
1283 return FALSE;
1285 flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
1286 | SEC_LINKER_CREATED | SEC_READONLY);
1287 s = bfd_make_section_anyway_with_flags (abfd, ".rela.plt", flags);
1288 if (s == NULL || ! bfd_set_section_alignment (abfd, s, 3))
1289 return FALSE;
1291 if (elf64_alpha_use_secureplt)
1293 flags = SEC_ALLOC | SEC_LINKER_CREATED;
1294 s = bfd_make_section_anyway_with_flags (abfd, ".got.plt", flags);
1295 if (s == NULL || ! bfd_set_section_alignment (abfd, s, 3))
1296 return FALSE;
1299 /* We may or may not have created a .got section for this object, but
1300 we definitely havn't done the rest of the work. */
1302 if (alpha_elf_tdata(abfd)->gotobj == NULL)
1304 if (!elf64_alpha_create_got_section (abfd, info))
1305 return FALSE;
1308 flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
1309 | SEC_LINKER_CREATED | SEC_READONLY);
1310 s = bfd_make_section_anyway_with_flags (abfd, ".rela.got", flags);
1311 if (s == NULL
1312 || !bfd_set_section_alignment (abfd, s, 3))
1313 return FALSE;
1315 /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the
1316 dynobj's .got section. We don't do this in the linker script
1317 because we don't want to define the symbol if we are not creating
1318 a global offset table. */
1319 h = _bfd_elf_define_linkage_sym (abfd, info, alpha_elf_tdata(abfd)->got,
1320 "_GLOBAL_OFFSET_TABLE_");
1321 elf_hash_table (info)->hgot = h;
1322 if (h == NULL)
1323 return FALSE;
1325 return TRUE;
1328 /* Read ECOFF debugging information from a .mdebug section into a
1329 ecoff_debug_info structure. */
1331 static bfd_boolean
1332 elf64_alpha_read_ecoff_info (bfd *abfd, asection *section,
1333 struct ecoff_debug_info *debug)
1335 HDRR *symhdr;
1336 const struct ecoff_debug_swap *swap;
1337 char *ext_hdr = NULL;
1339 swap = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
1340 memset (debug, 0, sizeof (*debug));
1342 ext_hdr = (char *) bfd_malloc (swap->external_hdr_size);
1343 if (ext_hdr == NULL && swap->external_hdr_size != 0)
1344 goto error_return;
1346 if (! bfd_get_section_contents (abfd, section, ext_hdr, (file_ptr) 0,
1347 swap->external_hdr_size))
1348 goto error_return;
1350 symhdr = &debug->symbolic_header;
1351 (*swap->swap_hdr_in) (abfd, ext_hdr, symhdr);
1353 /* The symbolic header contains absolute file offsets and sizes to
1354 read. */
1355 #define READ(ptr, offset, count, size, type) \
1356 if (symhdr->count == 0) \
1357 debug->ptr = NULL; \
1358 else \
1360 bfd_size_type amt = (bfd_size_type) size * symhdr->count; \
1361 debug->ptr = (type) bfd_malloc (amt); \
1362 if (debug->ptr == NULL) \
1363 goto error_return; \
1364 if (bfd_seek (abfd, (file_ptr) symhdr->offset, SEEK_SET) != 0 \
1365 || bfd_bread (debug->ptr, amt, abfd) != amt) \
1366 goto error_return; \
1369 READ (line, cbLineOffset, cbLine, sizeof (unsigned char), unsigned char *);
1370 READ (external_dnr, cbDnOffset, idnMax, swap->external_dnr_size, PTR);
1371 READ (external_pdr, cbPdOffset, ipdMax, swap->external_pdr_size, PTR);
1372 READ (external_sym, cbSymOffset, isymMax, swap->external_sym_size, PTR);
1373 READ (external_opt, cbOptOffset, ioptMax, swap->external_opt_size, PTR);
1374 READ (external_aux, cbAuxOffset, iauxMax, sizeof (union aux_ext),
1375 union aux_ext *);
1376 READ (ss, cbSsOffset, issMax, sizeof (char), char *);
1377 READ (ssext, cbSsExtOffset, issExtMax, sizeof (char), char *);
1378 READ (external_fdr, cbFdOffset, ifdMax, swap->external_fdr_size, PTR);
1379 READ (external_rfd, cbRfdOffset, crfd, swap->external_rfd_size, PTR);
1380 READ (external_ext, cbExtOffset, iextMax, swap->external_ext_size, PTR);
1381 #undef READ
1383 debug->fdr = NULL;
1385 return TRUE;
1387 error_return:
1388 if (ext_hdr != NULL)
1389 free (ext_hdr);
1390 if (debug->line != NULL)
1391 free (debug->line);
1392 if (debug->external_dnr != NULL)
1393 free (debug->external_dnr);
1394 if (debug->external_pdr != NULL)
1395 free (debug->external_pdr);
1396 if (debug->external_sym != NULL)
1397 free (debug->external_sym);
1398 if (debug->external_opt != NULL)
1399 free (debug->external_opt);
1400 if (debug->external_aux != NULL)
1401 free (debug->external_aux);
1402 if (debug->ss != NULL)
1403 free (debug->ss);
1404 if (debug->ssext != NULL)
1405 free (debug->ssext);
1406 if (debug->external_fdr != NULL)
1407 free (debug->external_fdr);
1408 if (debug->external_rfd != NULL)
1409 free (debug->external_rfd);
1410 if (debug->external_ext != NULL)
1411 free (debug->external_ext);
1412 return FALSE;
1415 /* Alpha ELF local labels start with '$'. */
1417 static bfd_boolean
1418 elf64_alpha_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED, const char *name)
1420 return name[0] == '$';
1423 /* Alpha ELF follows MIPS ELF in using a special find_nearest_line
1424 routine in order to handle the ECOFF debugging information. We
1425 still call this mips_elf_find_line because of the slot
1426 find_line_info in elf_obj_tdata is declared that way. */
1428 struct mips_elf_find_line
1430 struct ecoff_debug_info d;
1431 struct ecoff_find_line i;
1434 static bfd_boolean
1435 elf64_alpha_find_nearest_line (bfd *abfd, asection *section, asymbol **symbols,
1436 bfd_vma offset, const char **filename_ptr,
1437 const char **functionname_ptr,
1438 unsigned int *line_ptr)
1440 asection *msec;
1442 if (_bfd_dwarf2_find_nearest_line (abfd, section, symbols, offset,
1443 filename_ptr, functionname_ptr,
1444 line_ptr, 0,
1445 &elf_tdata (abfd)->dwarf2_find_line_info))
1446 return TRUE;
1448 msec = bfd_get_section_by_name (abfd, ".mdebug");
1449 if (msec != NULL)
1451 flagword origflags;
1452 struct mips_elf_find_line *fi;
1453 const struct ecoff_debug_swap * const swap =
1454 get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
1456 /* If we are called during a link, alpha_elf_final_link may have
1457 cleared the SEC_HAS_CONTENTS field. We force it back on here
1458 if appropriate (which it normally will be). */
1459 origflags = msec->flags;
1460 if (elf_section_data (msec)->this_hdr.sh_type != SHT_NOBITS)
1461 msec->flags |= SEC_HAS_CONTENTS;
1463 fi = elf_tdata (abfd)->find_line_info;
1464 if (fi == NULL)
1466 bfd_size_type external_fdr_size;
1467 char *fraw_src;
1468 char *fraw_end;
1469 struct fdr *fdr_ptr;
1470 bfd_size_type amt = sizeof (struct mips_elf_find_line);
1472 fi = (struct mips_elf_find_line *) bfd_zalloc (abfd, amt);
1473 if (fi == NULL)
1475 msec->flags = origflags;
1476 return FALSE;
1479 if (!elf64_alpha_read_ecoff_info (abfd, msec, &fi->d))
1481 msec->flags = origflags;
1482 return FALSE;
1485 /* Swap in the FDR information. */
1486 amt = fi->d.symbolic_header.ifdMax * sizeof (struct fdr);
1487 fi->d.fdr = (struct fdr *) bfd_alloc (abfd, amt);
1488 if (fi->d.fdr == NULL)
1490 msec->flags = origflags;
1491 return FALSE;
1493 external_fdr_size = swap->external_fdr_size;
1494 fdr_ptr = fi->d.fdr;
1495 fraw_src = (char *) fi->d.external_fdr;
1496 fraw_end = (fraw_src
1497 + fi->d.symbolic_header.ifdMax * external_fdr_size);
1498 for (; fraw_src < fraw_end; fraw_src += external_fdr_size, fdr_ptr++)
1499 (*swap->swap_fdr_in) (abfd, (PTR) fraw_src, fdr_ptr);
1501 elf_tdata (abfd)->find_line_info = fi;
1503 /* Note that we don't bother to ever free this information.
1504 find_nearest_line is either called all the time, as in
1505 objdump -l, so the information should be saved, or it is
1506 rarely called, as in ld error messages, so the memory
1507 wasted is unimportant. Still, it would probably be a
1508 good idea for free_cached_info to throw it away. */
1511 if (_bfd_ecoff_locate_line (abfd, section, offset, &fi->d, swap,
1512 &fi->i, filename_ptr, functionname_ptr,
1513 line_ptr))
1515 msec->flags = origflags;
1516 return TRUE;
1519 msec->flags = origflags;
1522 /* Fall back on the generic ELF find_nearest_line routine. */
1524 return _bfd_elf_find_nearest_line (abfd, section, symbols, offset,
1525 filename_ptr, functionname_ptr,
1526 line_ptr);
1529 /* Structure used to pass information to alpha_elf_output_extsym. */
1531 struct extsym_info
1533 bfd *abfd;
1534 struct bfd_link_info *info;
1535 struct ecoff_debug_info *debug;
1536 const struct ecoff_debug_swap *swap;
1537 bfd_boolean failed;
1540 static bfd_boolean
1541 elf64_alpha_output_extsym (struct alpha_elf_link_hash_entry *h, PTR data)
1543 struct extsym_info *einfo = (struct extsym_info *) data;
1544 bfd_boolean strip;
1545 asection *sec, *output_section;
1547 if (h->root.root.type == bfd_link_hash_warning)
1548 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
1550 if (h->root.indx == -2)
1551 strip = FALSE;
1552 else if ((h->root.def_dynamic
1553 || h->root.ref_dynamic
1554 || h->root.root.type == bfd_link_hash_new)
1555 && !h->root.def_regular
1556 && !h->root.ref_regular)
1557 strip = TRUE;
1558 else if (einfo->info->strip == strip_all
1559 || (einfo->info->strip == strip_some
1560 && bfd_hash_lookup (einfo->info->keep_hash,
1561 h->root.root.root.string,
1562 FALSE, FALSE) == NULL))
1563 strip = TRUE;
1564 else
1565 strip = FALSE;
1567 if (strip)
1568 return TRUE;
1570 if (h->esym.ifd == -2)
1572 h->esym.jmptbl = 0;
1573 h->esym.cobol_main = 0;
1574 h->esym.weakext = 0;
1575 h->esym.reserved = 0;
1576 h->esym.ifd = ifdNil;
1577 h->esym.asym.value = 0;
1578 h->esym.asym.st = stGlobal;
1580 if (h->root.root.type != bfd_link_hash_defined
1581 && h->root.root.type != bfd_link_hash_defweak)
1582 h->esym.asym.sc = scAbs;
1583 else
1585 const char *name;
1587 sec = h->root.root.u.def.section;
1588 output_section = sec->output_section;
1590 /* When making a shared library and symbol h is the one from
1591 the another shared library, OUTPUT_SECTION may be null. */
1592 if (output_section == NULL)
1593 h->esym.asym.sc = scUndefined;
1594 else
1596 name = bfd_section_name (output_section->owner, output_section);
1598 if (strcmp (name, ".text") == 0)
1599 h->esym.asym.sc = scText;
1600 else if (strcmp (name, ".data") == 0)
1601 h->esym.asym.sc = scData;
1602 else if (strcmp (name, ".sdata") == 0)
1603 h->esym.asym.sc = scSData;
1604 else if (strcmp (name, ".rodata") == 0
1605 || strcmp (name, ".rdata") == 0)
1606 h->esym.asym.sc = scRData;
1607 else if (strcmp (name, ".bss") == 0)
1608 h->esym.asym.sc = scBss;
1609 else if (strcmp (name, ".sbss") == 0)
1610 h->esym.asym.sc = scSBss;
1611 else if (strcmp (name, ".init") == 0)
1612 h->esym.asym.sc = scInit;
1613 else if (strcmp (name, ".fini") == 0)
1614 h->esym.asym.sc = scFini;
1615 else
1616 h->esym.asym.sc = scAbs;
1620 h->esym.asym.reserved = 0;
1621 h->esym.asym.index = indexNil;
1624 if (h->root.root.type == bfd_link_hash_common)
1625 h->esym.asym.value = h->root.root.u.c.size;
1626 else if (h->root.root.type == bfd_link_hash_defined
1627 || h->root.root.type == bfd_link_hash_defweak)
1629 if (h->esym.asym.sc == scCommon)
1630 h->esym.asym.sc = scBss;
1631 else if (h->esym.asym.sc == scSCommon)
1632 h->esym.asym.sc = scSBss;
1634 sec = h->root.root.u.def.section;
1635 output_section = sec->output_section;
1636 if (output_section != NULL)
1637 h->esym.asym.value = (h->root.root.u.def.value
1638 + sec->output_offset
1639 + output_section->vma);
1640 else
1641 h->esym.asym.value = 0;
1644 if (! bfd_ecoff_debug_one_external (einfo->abfd, einfo->debug, einfo->swap,
1645 h->root.root.root.string,
1646 &h->esym))
1648 einfo->failed = TRUE;
1649 return FALSE;
1652 return TRUE;
1655 /* Search for and possibly create a got entry. */
1657 static struct alpha_elf_got_entry *
1658 get_got_entry (bfd *abfd, struct alpha_elf_link_hash_entry *h,
1659 unsigned long r_type, unsigned long r_symndx,
1660 bfd_vma r_addend)
1662 struct alpha_elf_got_entry *gotent;
1663 struct alpha_elf_got_entry **slot;
1665 if (h)
1666 slot = &h->got_entries;
1667 else
1669 /* This is a local .got entry -- record for merge. */
1671 struct alpha_elf_got_entry **local_got_entries;
1673 local_got_entries = alpha_elf_tdata(abfd)->local_got_entries;
1674 if (!local_got_entries)
1676 bfd_size_type size;
1677 Elf_Internal_Shdr *symtab_hdr;
1679 symtab_hdr = &elf_tdata(abfd)->symtab_hdr;
1680 size = symtab_hdr->sh_info;
1681 size *= sizeof (struct alpha_elf_got_entry *);
1683 local_got_entries
1684 = (struct alpha_elf_got_entry **) bfd_zalloc (abfd, size);
1685 if (!local_got_entries)
1686 return NULL;
1688 alpha_elf_tdata (abfd)->local_got_entries = local_got_entries;
1691 slot = &local_got_entries[r_symndx];
1694 for (gotent = *slot; gotent ; gotent = gotent->next)
1695 if (gotent->gotobj == abfd
1696 && gotent->reloc_type == r_type
1697 && gotent->addend == r_addend)
1698 break;
1700 if (!gotent)
1702 int entry_size;
1703 bfd_size_type amt;
1705 amt = sizeof (struct alpha_elf_got_entry);
1706 gotent = (struct alpha_elf_got_entry *) bfd_alloc (abfd, amt);
1707 if (!gotent)
1708 return NULL;
1710 gotent->gotobj = abfd;
1711 gotent->addend = r_addend;
1712 gotent->got_offset = -1;
1713 gotent->plt_offset = -1;
1714 gotent->use_count = 1;
1715 gotent->reloc_type = r_type;
1716 gotent->reloc_done = 0;
1717 gotent->reloc_xlated = 0;
1719 gotent->next = *slot;
1720 *slot = gotent;
1722 entry_size = alpha_got_entry_size (r_type);
1723 alpha_elf_tdata (abfd)->total_got_size += entry_size;
1724 if (!h)
1725 alpha_elf_tdata(abfd)->local_got_size += entry_size;
1727 else
1728 gotent->use_count += 1;
1730 return gotent;
1733 static bfd_boolean
1734 elf64_alpha_want_plt (struct alpha_elf_link_hash_entry *ah)
1736 return ((ah->root.type == STT_FUNC
1737 || ah->root.root.type == bfd_link_hash_undefweak
1738 || ah->root.root.type == bfd_link_hash_undefined)
1739 && (ah->flags & ALPHA_ELF_LINK_HASH_LU_PLT) != 0
1740 && (ah->flags & ~ALPHA_ELF_LINK_HASH_LU_PLT) == 0);
1743 /* Handle dynamic relocations when doing an Alpha ELF link. */
1745 static bfd_boolean
1746 elf64_alpha_check_relocs (bfd *abfd, struct bfd_link_info *info,
1747 asection *sec, const Elf_Internal_Rela *relocs)
1749 bfd *dynobj;
1750 asection *sreloc;
1751 const char *rel_sec_name;
1752 Elf_Internal_Shdr *symtab_hdr;
1753 struct alpha_elf_link_hash_entry **sym_hashes;
1754 const Elf_Internal_Rela *rel, *relend;
1755 bfd_size_type amt;
1757 if (info->relocatable)
1758 return TRUE;
1760 /* Don't do anything special with non-loaded, non-alloced sections.
1761 In particular, any relocs in such sections should not affect GOT
1762 and PLT reference counting (ie. we don't allow them to create GOT
1763 or PLT entries), there's no possibility or desire to optimize TLS
1764 relocs, and there's not much point in propagating relocs to shared
1765 libs that the dynamic linker won't relocate. */
1766 if ((sec->flags & SEC_ALLOC) == 0)
1767 return TRUE;
1769 BFD_ASSERT (is_alpha_elf (abfd));
1771 dynobj = elf_hash_table (info)->dynobj;
1772 if (dynobj == NULL)
1773 elf_hash_table (info)->dynobj = dynobj = abfd;
1775 sreloc = NULL;
1776 rel_sec_name = NULL;
1777 symtab_hdr = &elf_symtab_hdr (abfd);
1778 sym_hashes = alpha_elf_sym_hashes (abfd);
1780 relend = relocs + sec->reloc_count;
1781 for (rel = relocs; rel < relend; ++rel)
1783 enum {
1784 NEED_GOT = 1,
1785 NEED_GOT_ENTRY = 2,
1786 NEED_DYNREL = 4
1789 unsigned long r_symndx, r_type;
1790 struct alpha_elf_link_hash_entry *h;
1791 unsigned int gotent_flags;
1792 bfd_boolean maybe_dynamic;
1793 unsigned int need;
1794 bfd_vma addend;
1796 r_symndx = ELF64_R_SYM (rel->r_info);
1797 if (r_symndx < symtab_hdr->sh_info)
1798 h = NULL;
1799 else
1801 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1803 while (h->root.root.type == bfd_link_hash_indirect
1804 || h->root.root.type == bfd_link_hash_warning)
1805 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
1807 h->root.ref_regular = 1;
1810 /* We can only get preliminary data on whether a symbol is
1811 locally or externally defined, as not all of the input files
1812 have yet been processed. Do something with what we know, as
1813 this may help reduce memory usage and processing time later. */
1814 maybe_dynamic = FALSE;
1815 if (h && ((info->shared
1816 && (!info->symbolic
1817 || info->unresolved_syms_in_shared_libs == RM_IGNORE))
1818 || !h->root.def_regular
1819 || h->root.root.type == bfd_link_hash_defweak))
1820 maybe_dynamic = TRUE;
1822 need = 0;
1823 gotent_flags = 0;
1824 r_type = ELF64_R_TYPE (rel->r_info);
1825 addend = rel->r_addend;
1827 switch (r_type)
1829 case R_ALPHA_LITERAL:
1830 need = NEED_GOT | NEED_GOT_ENTRY;
1832 /* Remember how this literal is used from its LITUSEs.
1833 This will be important when it comes to decide if we can
1834 create a .plt entry for a function symbol. */
1835 while (++rel < relend && ELF64_R_TYPE (rel->r_info) == R_ALPHA_LITUSE)
1836 if (rel->r_addend >= 1 && rel->r_addend <= 6)
1837 gotent_flags |= 1 << rel->r_addend;
1838 --rel;
1840 /* No LITUSEs -- presumably the address is used somehow. */
1841 if (gotent_flags == 0)
1842 gotent_flags = ALPHA_ELF_LINK_HASH_LU_ADDR;
1843 break;
1845 case R_ALPHA_GPDISP:
1846 case R_ALPHA_GPREL16:
1847 case R_ALPHA_GPREL32:
1848 case R_ALPHA_GPRELHIGH:
1849 case R_ALPHA_GPRELLOW:
1850 case R_ALPHA_BRSGP:
1851 need = NEED_GOT;
1852 break;
1854 case R_ALPHA_REFLONG:
1855 case R_ALPHA_REFQUAD:
1856 if (info->shared || maybe_dynamic)
1857 need = NEED_DYNREL;
1858 break;
1860 case R_ALPHA_TLSLDM:
1861 /* The symbol for a TLSLDM reloc is ignored. Collapse the
1862 reloc to the 0 symbol so that they all match. */
1863 r_symndx = 0;
1864 h = 0;
1865 maybe_dynamic = FALSE;
1866 /* FALLTHRU */
1868 case R_ALPHA_TLSGD:
1869 case R_ALPHA_GOTDTPREL:
1870 need = NEED_GOT | NEED_GOT_ENTRY;
1871 break;
1873 case R_ALPHA_GOTTPREL:
1874 need = NEED_GOT | NEED_GOT_ENTRY;
1875 gotent_flags = ALPHA_ELF_LINK_HASH_TLS_IE;
1876 if (info->shared)
1877 info->flags |= DF_STATIC_TLS;
1878 break;
1880 case R_ALPHA_TPREL64:
1881 if (info->shared || maybe_dynamic)
1882 need = NEED_DYNREL;
1883 if (info->shared)
1884 info->flags |= DF_STATIC_TLS;
1885 break;
1888 if (need & NEED_GOT)
1890 if (alpha_elf_tdata(abfd)->gotobj == NULL)
1892 if (!elf64_alpha_create_got_section (abfd, info))
1893 return FALSE;
1897 if (need & NEED_GOT_ENTRY)
1899 struct alpha_elf_got_entry *gotent;
1901 gotent = get_got_entry (abfd, h, r_type, r_symndx, addend);
1902 if (!gotent)
1903 return FALSE;
1905 if (gotent_flags)
1907 gotent->flags |= gotent_flags;
1908 if (h)
1910 gotent_flags |= h->flags;
1911 h->flags = gotent_flags;
1913 /* Make a guess as to whether a .plt entry is needed. */
1914 /* ??? It appears that we won't make it into
1915 adjust_dynamic_symbol for symbols that remain
1916 totally undefined. Copying this check here means
1917 we can create a plt entry for them too. */
1918 h->root.needs_plt
1919 = (maybe_dynamic && elf64_alpha_want_plt (h));
1924 if (need & NEED_DYNREL)
1926 if (rel_sec_name == NULL)
1928 rel_sec_name = (bfd_elf_string_from_elf_section
1929 (abfd, elf_elfheader(abfd)->e_shstrndx,
1930 elf_section_data(sec)->rel_hdr.sh_name));
1931 if (rel_sec_name == NULL)
1932 return FALSE;
1934 BFD_ASSERT (CONST_STRNEQ (rel_sec_name, ".rela")
1935 && strcmp (bfd_get_section_name (abfd, sec),
1936 rel_sec_name+5) == 0);
1939 /* We need to create the section here now whether we eventually
1940 use it or not so that it gets mapped to an output section by
1941 the linker. If not used, we'll kill it in
1942 size_dynamic_sections. */
1943 if (sreloc == NULL)
1945 sreloc = bfd_get_section_by_name (dynobj, rel_sec_name);
1946 if (sreloc == NULL)
1948 flagword flags;
1950 flags = (SEC_HAS_CONTENTS | SEC_IN_MEMORY
1951 | SEC_LINKER_CREATED | SEC_READONLY);
1952 if (sec->flags & SEC_ALLOC)
1953 flags |= SEC_ALLOC | SEC_LOAD;
1954 sreloc = bfd_make_section_with_flags (dynobj,
1955 rel_sec_name,
1956 flags);
1957 if (sreloc == NULL
1958 || !bfd_set_section_alignment (dynobj, sreloc, 3))
1959 return FALSE;
1963 if (h)
1965 /* Since we havn't seen all of the input symbols yet, we
1966 don't know whether we'll actually need a dynamic relocation
1967 entry for this reloc. So make a record of it. Once we
1968 find out if this thing needs dynamic relocation we'll
1969 expand the relocation sections by the appropriate amount. */
1971 struct alpha_elf_reloc_entry *rent;
1973 for (rent = h->reloc_entries; rent; rent = rent->next)
1974 if (rent->rtype == r_type && rent->srel == sreloc)
1975 break;
1977 if (!rent)
1979 amt = sizeof (struct alpha_elf_reloc_entry);
1980 rent = (struct alpha_elf_reloc_entry *) bfd_alloc (abfd, amt);
1981 if (!rent)
1982 return FALSE;
1984 rent->srel = sreloc;
1985 rent->rtype = r_type;
1986 rent->count = 1;
1987 rent->reltext = (sec->flags & SEC_READONLY) != 0;
1989 rent->next = h->reloc_entries;
1990 h->reloc_entries = rent;
1992 else
1993 rent->count++;
1995 else if (info->shared)
1997 /* If this is a shared library, and the section is to be
1998 loaded into memory, we need a RELATIVE reloc. */
1999 sreloc->size += sizeof (Elf64_External_Rela);
2000 if (sec->flags & SEC_READONLY)
2001 info->flags |= DF_TEXTREL;
2006 return TRUE;
2009 /* Adjust a symbol defined by a dynamic object and referenced by a
2010 regular object. The current definition is in some section of the
2011 dynamic object, but we're not including those sections. We have to
2012 change the definition to something the rest of the link can
2013 understand. */
2015 static bfd_boolean
2016 elf64_alpha_adjust_dynamic_symbol (struct bfd_link_info *info,
2017 struct elf_link_hash_entry *h)
2019 bfd *dynobj;
2020 asection *s;
2021 struct alpha_elf_link_hash_entry *ah;
2023 dynobj = elf_hash_table(info)->dynobj;
2024 ah = (struct alpha_elf_link_hash_entry *)h;
2026 /* Now that we've seen all of the input symbols, finalize our decision
2027 about whether this symbol should get a .plt entry. Irritatingly, it
2028 is common for folk to leave undefined symbols in shared libraries,
2029 and they still expect lazy binding; accept undefined symbols in lieu
2030 of STT_FUNC. */
2031 if (alpha_elf_dynamic_symbol_p (h, info) && elf64_alpha_want_plt (ah))
2033 h->needs_plt = TRUE;
2035 s = bfd_get_section_by_name(dynobj, ".plt");
2036 if (!s && !elf64_alpha_create_dynamic_sections (dynobj, info))
2037 return FALSE;
2039 /* We need one plt entry per got subsection. Delay allocation of
2040 the actual plt entries until size_plt_section, called from
2041 size_dynamic_sections or during relaxation. */
2043 return TRUE;
2045 else
2046 h->needs_plt = FALSE;
2048 /* If this is a weak symbol, and there is a real definition, the
2049 processor independent code will have arranged for us to see the
2050 real definition first, and we can just use the same value. */
2051 if (h->u.weakdef != NULL)
2053 BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
2054 || h->u.weakdef->root.type == bfd_link_hash_defweak);
2055 h->root.u.def.section = h->u.weakdef->root.u.def.section;
2056 h->root.u.def.value = h->u.weakdef->root.u.def.value;
2057 return TRUE;
2060 /* This is a reference to a symbol defined by a dynamic object which
2061 is not a function. The Alpha, since it uses .got entries for all
2062 symbols even in regular objects, does not need the hackery of a
2063 .dynbss section and COPY dynamic relocations. */
2065 return TRUE;
2068 /* Record STO_ALPHA_NOPV and STO_ALPHA_STD_GPLOAD. */
2070 static void
2071 elf64_alpha_merge_symbol_attribute (struct elf_link_hash_entry *h,
2072 const Elf_Internal_Sym *isym,
2073 bfd_boolean definition,
2074 bfd_boolean dynamic)
2076 if (!dynamic && definition)
2077 h->other = ((h->other & ELF_ST_VISIBILITY (-1))
2078 | (isym->st_other & ~ELF_ST_VISIBILITY (-1)));
2081 /* Symbol versioning can create new symbols, and make our old symbols
2082 indirect to the new ones. Consolidate the got and reloc information
2083 in these situations. */
2085 static bfd_boolean
2086 elf64_alpha_merge_ind_symbols (struct alpha_elf_link_hash_entry *hi,
2087 PTR dummy ATTRIBUTE_UNUSED)
2089 struct alpha_elf_link_hash_entry *hs;
2091 if (hi->root.root.type != bfd_link_hash_indirect)
2092 return TRUE;
2093 hs = hi;
2094 do {
2095 hs = (struct alpha_elf_link_hash_entry *)hs->root.root.u.i.link;
2096 } while (hs->root.root.type == bfd_link_hash_indirect);
2098 /* Merge the flags. Whee. */
2100 hs->flags |= hi->flags;
2102 /* Merge the .got entries. Cannibalize the old symbol's list in
2103 doing so, since we don't need it anymore. */
2105 if (hs->got_entries == NULL)
2106 hs->got_entries = hi->got_entries;
2107 else
2109 struct alpha_elf_got_entry *gi, *gs, *gin, *gsh;
2111 gsh = hs->got_entries;
2112 for (gi = hi->got_entries; gi ; gi = gin)
2114 gin = gi->next;
2115 for (gs = gsh; gs ; gs = gs->next)
2116 if (gi->gotobj == gs->gotobj
2117 && gi->reloc_type == gs->reloc_type
2118 && gi->addend == gs->addend)
2120 gi->use_count += gs->use_count;
2121 goto got_found;
2123 gi->next = hs->got_entries;
2124 hs->got_entries = gi;
2125 got_found:;
2128 hi->got_entries = NULL;
2130 /* And similar for the reloc entries. */
2132 if (hs->reloc_entries == NULL)
2133 hs->reloc_entries = hi->reloc_entries;
2134 else
2136 struct alpha_elf_reloc_entry *ri, *rs, *rin, *rsh;
2138 rsh = hs->reloc_entries;
2139 for (ri = hi->reloc_entries; ri ; ri = rin)
2141 rin = ri->next;
2142 for (rs = rsh; rs ; rs = rs->next)
2143 if (ri->rtype == rs->rtype && ri->srel == rs->srel)
2145 rs->count += ri->count;
2146 goto found_reloc;
2148 ri->next = hs->reloc_entries;
2149 hs->reloc_entries = ri;
2150 found_reloc:;
2153 hi->reloc_entries = NULL;
2155 return TRUE;
2158 /* Is it possible to merge two object file's .got tables? */
2160 static bfd_boolean
2161 elf64_alpha_can_merge_gots (bfd *a, bfd *b)
2163 int total = alpha_elf_tdata (a)->total_got_size;
2164 bfd *bsub;
2166 /* Trivial quick fallout test. */
2167 if (total + alpha_elf_tdata (b)->total_got_size <= MAX_GOT_SIZE)
2168 return TRUE;
2170 /* By their nature, local .got entries cannot be merged. */
2171 if ((total += alpha_elf_tdata (b)->local_got_size) > MAX_GOT_SIZE)
2172 return FALSE;
2174 /* Failing the common trivial comparison, we must effectively
2175 perform the merge. Not actually performing the merge means that
2176 we don't have to store undo information in case we fail. */
2177 for (bsub = b; bsub ; bsub = alpha_elf_tdata (bsub)->in_got_link_next)
2179 struct alpha_elf_link_hash_entry **hashes = alpha_elf_sym_hashes (bsub);
2180 Elf_Internal_Shdr *symtab_hdr = &elf_tdata (bsub)->symtab_hdr;
2181 int i, n;
2183 n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info;
2184 for (i = 0; i < n; ++i)
2186 struct alpha_elf_got_entry *ae, *be;
2187 struct alpha_elf_link_hash_entry *h;
2189 h = hashes[i];
2190 while (h->root.root.type == bfd_link_hash_indirect
2191 || h->root.root.type == bfd_link_hash_warning)
2192 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
2194 for (be = h->got_entries; be ; be = be->next)
2196 if (be->use_count == 0)
2197 continue;
2198 if (be->gotobj != b)
2199 continue;
2201 for (ae = h->got_entries; ae ; ae = ae->next)
2202 if (ae->gotobj == a
2203 && ae->reloc_type == be->reloc_type
2204 && ae->addend == be->addend)
2205 goto global_found;
2207 total += alpha_got_entry_size (be->reloc_type);
2208 if (total > MAX_GOT_SIZE)
2209 return FALSE;
2210 global_found:;
2215 return TRUE;
2218 /* Actually merge two .got tables. */
2220 static void
2221 elf64_alpha_merge_gots (bfd *a, bfd *b)
2223 int total = alpha_elf_tdata (a)->total_got_size;
2224 bfd *bsub;
2226 /* Remember local expansion. */
2228 int e = alpha_elf_tdata (b)->local_got_size;
2229 total += e;
2230 alpha_elf_tdata (a)->local_got_size += e;
2233 for (bsub = b; bsub ; bsub = alpha_elf_tdata (bsub)->in_got_link_next)
2235 struct alpha_elf_got_entry **local_got_entries;
2236 struct alpha_elf_link_hash_entry **hashes;
2237 Elf_Internal_Shdr *symtab_hdr;
2238 int i, n;
2240 /* Let the local .got entries know they are part of a new subsegment. */
2241 local_got_entries = alpha_elf_tdata (bsub)->local_got_entries;
2242 if (local_got_entries)
2244 n = elf_tdata (bsub)->symtab_hdr.sh_info;
2245 for (i = 0; i < n; ++i)
2247 struct alpha_elf_got_entry *ent;
2248 for (ent = local_got_entries[i]; ent; ent = ent->next)
2249 ent->gotobj = a;
2253 /* Merge the global .got entries. */
2254 hashes = alpha_elf_sym_hashes (bsub);
2255 symtab_hdr = &elf_tdata (bsub)->symtab_hdr;
2257 n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info;
2258 for (i = 0; i < n; ++i)
2260 struct alpha_elf_got_entry *ae, *be, **pbe, **start;
2261 struct alpha_elf_link_hash_entry *h;
2263 h = hashes[i];
2264 while (h->root.root.type == bfd_link_hash_indirect
2265 || h->root.root.type == bfd_link_hash_warning)
2266 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
2268 pbe = start = &h->got_entries;
2269 while ((be = *pbe) != NULL)
2271 if (be->use_count == 0)
2273 *pbe = be->next;
2274 memset (be, 0xa5, sizeof (*be));
2275 goto kill;
2277 if (be->gotobj != b)
2278 goto next;
2280 for (ae = *start; ae ; ae = ae->next)
2281 if (ae->gotobj == a
2282 && ae->reloc_type == be->reloc_type
2283 && ae->addend == be->addend)
2285 ae->flags |= be->flags;
2286 ae->use_count += be->use_count;
2287 *pbe = be->next;
2288 memset (be, 0xa5, sizeof (*be));
2289 goto kill;
2291 be->gotobj = a;
2292 total += alpha_got_entry_size (be->reloc_type);
2294 next:;
2295 pbe = &be->next;
2296 kill:;
2300 alpha_elf_tdata (bsub)->gotobj = a;
2302 alpha_elf_tdata (a)->total_got_size = total;
2304 /* Merge the two in_got chains. */
2306 bfd *next;
2308 bsub = a;
2309 while ((next = alpha_elf_tdata (bsub)->in_got_link_next) != NULL)
2310 bsub = next;
2312 alpha_elf_tdata (bsub)->in_got_link_next = b;
2316 /* Calculate the offsets for the got entries. */
2318 static bfd_boolean
2319 elf64_alpha_calc_got_offsets_for_symbol (struct alpha_elf_link_hash_entry *h,
2320 PTR arg ATTRIBUTE_UNUSED)
2322 struct alpha_elf_got_entry *gotent;
2324 if (h->root.root.type == bfd_link_hash_warning)
2325 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
2327 for (gotent = h->got_entries; gotent; gotent = gotent->next)
2328 if (gotent->use_count > 0)
2330 struct alpha_elf_obj_tdata *td;
2331 bfd_size_type *plge;
2333 td = alpha_elf_tdata (gotent->gotobj);
2334 plge = &td->got->size;
2335 gotent->got_offset = *plge;
2336 *plge += alpha_got_entry_size (gotent->reloc_type);
2339 return TRUE;
2342 static void
2343 elf64_alpha_calc_got_offsets (struct bfd_link_info *info)
2345 bfd *i, *got_list = alpha_elf_hash_table(info)->got_list;
2347 /* First, zero out the .got sizes, as we may be recalculating the
2348 .got after optimizing it. */
2349 for (i = got_list; i ; i = alpha_elf_tdata(i)->got_link_next)
2350 alpha_elf_tdata(i)->got->size = 0;
2352 /* Next, fill in the offsets for all the global entries. */
2353 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
2354 elf64_alpha_calc_got_offsets_for_symbol,
2355 NULL);
2357 /* Finally, fill in the offsets for the local entries. */
2358 for (i = got_list; i ; i = alpha_elf_tdata(i)->got_link_next)
2360 bfd_size_type got_offset = alpha_elf_tdata(i)->got->size;
2361 bfd *j;
2363 for (j = i; j ; j = alpha_elf_tdata(j)->in_got_link_next)
2365 struct alpha_elf_got_entry **local_got_entries, *gotent;
2366 int k, n;
2368 local_got_entries = alpha_elf_tdata(j)->local_got_entries;
2369 if (!local_got_entries)
2370 continue;
2372 for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k)
2373 for (gotent = local_got_entries[k]; gotent; gotent = gotent->next)
2374 if (gotent->use_count > 0)
2376 gotent->got_offset = got_offset;
2377 got_offset += alpha_got_entry_size (gotent->reloc_type);
2381 alpha_elf_tdata(i)->got->size = got_offset;
2385 /* Constructs the gots. */
2387 static bfd_boolean
2388 elf64_alpha_size_got_sections (struct bfd_link_info *info)
2390 bfd *i, *got_list, *cur_got_obj = NULL;
2392 got_list = alpha_elf_hash_table (info)->got_list;
2394 /* On the first time through, pretend we have an existing got list
2395 consisting of all of the input files. */
2396 if (got_list == NULL)
2398 for (i = info->input_bfds; i ; i = i->link_next)
2400 bfd *this_got;
2402 if (! is_alpha_elf (i))
2403 continue;
2405 this_got = alpha_elf_tdata (i)->gotobj;
2406 if (this_got == NULL)
2407 continue;
2409 /* We are assuming no merging has yet occurred. */
2410 BFD_ASSERT (this_got == i);
2412 if (alpha_elf_tdata (this_got)->total_got_size > MAX_GOT_SIZE)
2414 /* Yikes! A single object file has too many entries. */
2415 (*_bfd_error_handler)
2416 (_("%B: .got subsegment exceeds 64K (size %d)"),
2417 i, alpha_elf_tdata (this_got)->total_got_size);
2418 return FALSE;
2421 if (got_list == NULL)
2422 got_list = this_got;
2423 else
2424 alpha_elf_tdata(cur_got_obj)->got_link_next = this_got;
2425 cur_got_obj = this_got;
2428 /* Strange degenerate case of no got references. */
2429 if (got_list == NULL)
2430 return TRUE;
2432 alpha_elf_hash_table (info)->got_list = got_list;
2435 cur_got_obj = got_list;
2436 if (cur_got_obj == NULL)
2437 return FALSE;
2439 i = alpha_elf_tdata(cur_got_obj)->got_link_next;
2440 while (i != NULL)
2442 if (elf64_alpha_can_merge_gots (cur_got_obj, i))
2444 elf64_alpha_merge_gots (cur_got_obj, i);
2446 alpha_elf_tdata(i)->got->size = 0;
2447 i = alpha_elf_tdata(i)->got_link_next;
2448 alpha_elf_tdata(cur_got_obj)->got_link_next = i;
2450 else
2452 cur_got_obj = i;
2453 i = alpha_elf_tdata(i)->got_link_next;
2457 /* Once the gots have been merged, fill in the got offsets for
2458 everything therein. */
2459 elf64_alpha_calc_got_offsets (info);
2461 return TRUE;
2464 static bfd_boolean
2465 elf64_alpha_size_plt_section_1 (struct alpha_elf_link_hash_entry *h, PTR data)
2467 asection *splt = (asection *) data;
2468 struct alpha_elf_got_entry *gotent;
2469 bfd_boolean saw_one = FALSE;
2471 /* If we didn't need an entry before, we still don't. */
2472 if (!h->root.needs_plt)
2473 return TRUE;
2475 /* For each LITERAL got entry still in use, allocate a plt entry. */
2476 for (gotent = h->got_entries; gotent ; gotent = gotent->next)
2477 if (gotent->reloc_type == R_ALPHA_LITERAL
2478 && gotent->use_count > 0)
2480 if (splt->size == 0)
2481 splt->size = PLT_HEADER_SIZE;
2482 gotent->plt_offset = splt->size;
2483 splt->size += PLT_ENTRY_SIZE;
2484 saw_one = TRUE;
2487 /* If there weren't any, there's no longer a need for the PLT entry. */
2488 if (!saw_one)
2489 h->root.needs_plt = FALSE;
2491 return TRUE;
2494 /* Called from relax_section to rebuild the PLT in light of potential changes
2495 in the function's status. */
2497 static void
2498 elf64_alpha_size_plt_section (struct bfd_link_info *info)
2500 asection *splt, *spltrel, *sgotplt;
2501 unsigned long entries;
2502 bfd *dynobj;
2504 dynobj = elf_hash_table(info)->dynobj;
2505 splt = bfd_get_section_by_name (dynobj, ".plt");
2506 if (splt == NULL)
2507 return;
2509 splt->size = 0;
2511 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
2512 elf64_alpha_size_plt_section_1, splt);
2514 /* Every plt entry requires a JMP_SLOT relocation. */
2515 spltrel = bfd_get_section_by_name (dynobj, ".rela.plt");
2516 entries = 0;
2517 if (splt->size)
2519 if (elf64_alpha_use_secureplt)
2520 entries = (splt->size - NEW_PLT_HEADER_SIZE) / NEW_PLT_ENTRY_SIZE;
2521 else
2522 entries = (splt->size - OLD_PLT_HEADER_SIZE) / OLD_PLT_ENTRY_SIZE;
2524 spltrel->size = entries * sizeof (Elf64_External_Rela);
2526 /* When using the secureplt, we need two words somewhere in the data
2527 segment for the dynamic linker to tell us where to go. This is the
2528 entire contents of the .got.plt section. */
2529 if (elf64_alpha_use_secureplt)
2531 sgotplt = bfd_get_section_by_name (dynobj, ".got.plt");
2532 sgotplt->size = entries ? 16 : 0;
2536 static bfd_boolean
2537 elf64_alpha_always_size_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
2538 struct bfd_link_info *info)
2540 bfd *i;
2542 if (info->relocatable)
2543 return TRUE;
2545 /* First, take care of the indirect symbols created by versioning. */
2546 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
2547 elf64_alpha_merge_ind_symbols,
2548 NULL);
2550 if (!elf64_alpha_size_got_sections (info))
2551 return FALSE;
2553 /* Allocate space for all of the .got subsections. */
2554 i = alpha_elf_hash_table (info)->got_list;
2555 for ( ; i ; i = alpha_elf_tdata(i)->got_link_next)
2557 asection *s = alpha_elf_tdata(i)->got;
2558 if (s->size > 0)
2560 s->contents = (bfd_byte *) bfd_zalloc (i, s->size);
2561 if (s->contents == NULL)
2562 return FALSE;
2566 return TRUE;
2569 /* The number of dynamic relocations required by a static relocation. */
2571 static int
2572 alpha_dynamic_entries_for_reloc (int r_type, int dynamic, int shared)
2574 switch (r_type)
2576 /* May appear in GOT entries. */
2577 case R_ALPHA_TLSGD:
2578 return (dynamic ? 2 : shared ? 1 : 0);
2579 case R_ALPHA_TLSLDM:
2580 return shared;
2581 case R_ALPHA_LITERAL:
2582 case R_ALPHA_GOTTPREL:
2583 return dynamic || shared;
2584 case R_ALPHA_GOTDTPREL:
2585 return dynamic;
2587 /* May appear in data sections. */
2588 case R_ALPHA_REFLONG:
2589 case R_ALPHA_REFQUAD:
2590 case R_ALPHA_TPREL64:
2591 return dynamic || shared;
2593 /* Everything else is illegal. We'll issue an error during
2594 relocate_section. */
2595 default:
2596 return 0;
2600 /* Work out the sizes of the dynamic relocation entries. */
2602 static bfd_boolean
2603 elf64_alpha_calc_dynrel_sizes (struct alpha_elf_link_hash_entry *h,
2604 struct bfd_link_info *info)
2606 bfd_boolean dynamic;
2607 struct alpha_elf_reloc_entry *relent;
2608 unsigned long entries;
2610 if (h->root.root.type == bfd_link_hash_warning)
2611 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
2613 /* If the symbol was defined as a common symbol in a regular object
2614 file, and there was no definition in any dynamic object, then the
2615 linker will have allocated space for the symbol in a common
2616 section but the ELF_LINK_HASH_DEF_REGULAR flag will not have been
2617 set. This is done for dynamic symbols in
2618 elf_adjust_dynamic_symbol but this is not done for non-dynamic
2619 symbols, somehow. */
2620 if (!h->root.def_regular
2621 && h->root.ref_regular
2622 && !h->root.def_dynamic
2623 && (h->root.root.type == bfd_link_hash_defined
2624 || h->root.root.type == bfd_link_hash_defweak)
2625 && !(h->root.root.u.def.section->owner->flags & DYNAMIC))
2626 h->root.def_regular = 1;
2628 /* If the symbol is dynamic, we'll need all the relocations in their
2629 natural form. If this is a shared object, and it has been forced
2630 local, we'll need the same number of RELATIVE relocations. */
2631 dynamic = alpha_elf_dynamic_symbol_p (&h->root, info);
2633 /* If the symbol is a hidden undefined weak, then we never have any
2634 relocations. Avoid the loop which may want to add RELATIVE relocs
2635 based on info->shared. */
2636 if (h->root.root.type == bfd_link_hash_undefweak && !dynamic)
2637 return TRUE;
2639 for (relent = h->reloc_entries; relent; relent = relent->next)
2641 entries = alpha_dynamic_entries_for_reloc (relent->rtype, dynamic,
2642 info->shared);
2643 if (entries)
2645 relent->srel->size +=
2646 entries * sizeof (Elf64_External_Rela) * relent->count;
2647 if (relent->reltext)
2648 info->flags |= DT_TEXTREL;
2652 return TRUE;
2655 /* Subroutine of elf64_alpha_size_rela_got_section for doing the
2656 global symbols. */
2658 static bfd_boolean
2659 elf64_alpha_size_rela_got_1 (struct alpha_elf_link_hash_entry *h,
2660 struct bfd_link_info *info)
2662 bfd_boolean dynamic;
2663 struct alpha_elf_got_entry *gotent;
2664 unsigned long entries;
2666 if (h->root.root.type == bfd_link_hash_warning)
2667 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
2669 /* If we're using a plt for this symbol, then all of its relocations
2670 for its got entries go into .rela.plt. */
2671 if (h->root.needs_plt)
2672 return TRUE;
2674 /* If the symbol is dynamic, we'll need all the relocations in their
2675 natural form. If this is a shared object, and it has been forced
2676 local, we'll need the same number of RELATIVE relocations. */
2677 dynamic = alpha_elf_dynamic_symbol_p (&h->root, info);
2679 /* If the symbol is a hidden undefined weak, then we never have any
2680 relocations. Avoid the loop which may want to add RELATIVE relocs
2681 based on info->shared. */
2682 if (h->root.root.type == bfd_link_hash_undefweak && !dynamic)
2683 return TRUE;
2685 entries = 0;
2686 for (gotent = h->got_entries; gotent ; gotent = gotent->next)
2687 if (gotent->use_count > 0)
2688 entries += alpha_dynamic_entries_for_reloc (gotent->reloc_type,
2689 dynamic, info->shared);
2691 if (entries > 0)
2693 bfd *dynobj = elf_hash_table(info)->dynobj;
2694 asection *srel = bfd_get_section_by_name (dynobj, ".rela.got");
2695 BFD_ASSERT (srel != NULL);
2696 srel->size += sizeof (Elf64_External_Rela) * entries;
2699 return TRUE;
2702 /* Set the sizes of the dynamic relocation sections. */
2704 static void
2705 elf64_alpha_size_rela_got_section (struct bfd_link_info *info)
2707 unsigned long entries;
2708 bfd *i, *dynobj;
2709 asection *srel;
2711 /* Shared libraries often require RELATIVE relocs, and some relocs
2712 require attention for the main application as well. */
2714 entries = 0;
2715 for (i = alpha_elf_hash_table(info)->got_list;
2716 i ; i = alpha_elf_tdata(i)->got_link_next)
2718 bfd *j;
2720 for (j = i; j ; j = alpha_elf_tdata(j)->in_got_link_next)
2722 struct alpha_elf_got_entry **local_got_entries, *gotent;
2723 int k, n;
2725 local_got_entries = alpha_elf_tdata(j)->local_got_entries;
2726 if (!local_got_entries)
2727 continue;
2729 for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k)
2730 for (gotent = local_got_entries[k];
2731 gotent ; gotent = gotent->next)
2732 if (gotent->use_count > 0)
2733 entries += (alpha_dynamic_entries_for_reloc
2734 (gotent->reloc_type, 0, info->shared));
2738 dynobj = elf_hash_table(info)->dynobj;
2739 srel = bfd_get_section_by_name (dynobj, ".rela.got");
2740 if (!srel)
2742 BFD_ASSERT (entries == 0);
2743 return;
2745 srel->size = sizeof (Elf64_External_Rela) * entries;
2747 /* Now do the non-local symbols. */
2748 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
2749 elf64_alpha_size_rela_got_1, info);
2752 /* Set the sizes of the dynamic sections. */
2754 static bfd_boolean
2755 elf64_alpha_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
2756 struct bfd_link_info *info)
2758 bfd *dynobj;
2759 asection *s;
2760 bfd_boolean relplt;
2762 dynobj = elf_hash_table(info)->dynobj;
2763 BFD_ASSERT(dynobj != NULL);
2765 if (elf_hash_table (info)->dynamic_sections_created)
2767 /* Set the contents of the .interp section to the interpreter. */
2768 if (info->executable)
2770 s = bfd_get_section_by_name (dynobj, ".interp");
2771 BFD_ASSERT (s != NULL);
2772 s->size = sizeof ELF_DYNAMIC_INTERPRETER;
2773 s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
2776 /* Now that we've seen all of the input files, we can decide which
2777 symbols need dynamic relocation entries and which don't. We've
2778 collected information in check_relocs that we can now apply to
2779 size the dynamic relocation sections. */
2780 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
2781 elf64_alpha_calc_dynrel_sizes, info);
2783 elf64_alpha_size_rela_got_section (info);
2784 elf64_alpha_size_plt_section (info);
2786 /* else we're not dynamic and by definition we don't need such things. */
2788 /* The check_relocs and adjust_dynamic_symbol entry points have
2789 determined the sizes of the various dynamic sections. Allocate
2790 memory for them. */
2791 relplt = FALSE;
2792 for (s = dynobj->sections; s != NULL; s = s->next)
2794 const char *name;
2796 if (!(s->flags & SEC_LINKER_CREATED))
2797 continue;
2799 /* It's OK to base decisions on the section name, because none
2800 of the dynobj section names depend upon the input files. */
2801 name = bfd_get_section_name (dynobj, s);
2803 if (CONST_STRNEQ (name, ".rela"))
2805 if (s->size != 0)
2807 if (strcmp (name, ".rela.plt") == 0)
2808 relplt = TRUE;
2810 /* We use the reloc_count field as a counter if we need
2811 to copy relocs into the output file. */
2812 s->reloc_count = 0;
2815 else if (! CONST_STRNEQ (name, ".got")
2816 && strcmp (name, ".plt") != 0
2817 && strcmp (name, ".dynbss") != 0)
2819 /* It's not one of our dynamic sections, so don't allocate space. */
2820 continue;
2823 if (s->size == 0)
2825 /* If we don't need this section, strip it from the output file.
2826 This is to handle .rela.bss and .rela.plt. We must create it
2827 in create_dynamic_sections, because it must be created before
2828 the linker maps input sections to output sections. The
2829 linker does that before adjust_dynamic_symbol is called, and
2830 it is that function which decides whether anything needs to
2831 go into these sections. */
2832 s->flags |= SEC_EXCLUDE;
2834 else if ((s->flags & SEC_HAS_CONTENTS) != 0)
2836 /* Allocate memory for the section contents. */
2837 s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
2838 if (s->contents == NULL)
2839 return FALSE;
2843 if (elf_hash_table (info)->dynamic_sections_created)
2845 /* Add some entries to the .dynamic section. We fill in the
2846 values later, in elf64_alpha_finish_dynamic_sections, but we
2847 must add the entries now so that we get the correct size for
2848 the .dynamic section. The DT_DEBUG entry is filled in by the
2849 dynamic linker and used by the debugger. */
2850 #define add_dynamic_entry(TAG, VAL) \
2851 _bfd_elf_add_dynamic_entry (info, TAG, VAL)
2853 if (info->executable)
2855 if (!add_dynamic_entry (DT_DEBUG, 0))
2856 return FALSE;
2859 if (relplt)
2861 if (!add_dynamic_entry (DT_PLTGOT, 0)
2862 || !add_dynamic_entry (DT_PLTRELSZ, 0)
2863 || !add_dynamic_entry (DT_PLTREL, DT_RELA)
2864 || !add_dynamic_entry (DT_JMPREL, 0))
2865 return FALSE;
2867 if (elf64_alpha_use_secureplt
2868 && !add_dynamic_entry (DT_ALPHA_PLTRO, 1))
2869 return FALSE;
2872 if (!add_dynamic_entry (DT_RELA, 0)
2873 || !add_dynamic_entry (DT_RELASZ, 0)
2874 || !add_dynamic_entry (DT_RELAENT, sizeof (Elf64_External_Rela)))
2875 return FALSE;
2877 if (info->flags & DF_TEXTREL)
2879 if (!add_dynamic_entry (DT_TEXTREL, 0))
2880 return FALSE;
2883 #undef add_dynamic_entry
2885 return TRUE;
2888 /* These functions do relaxation for Alpha ELF.
2890 Currently I'm only handling what I can do with existing compiler
2891 and assembler support, which means no instructions are removed,
2892 though some may be nopped. At this time GCC does not emit enough
2893 information to do all of the relaxing that is possible. It will
2894 take some not small amount of work for that to happen.
2896 There are a couple of interesting papers that I once read on this
2897 subject, that I cannot find references to at the moment, that
2898 related to Alpha in particular. They are by David Wall, then of
2899 DEC WRL. */
2901 struct alpha_relax_info
2903 bfd *abfd;
2904 asection *sec;
2905 bfd_byte *contents;
2906 Elf_Internal_Shdr *symtab_hdr;
2907 Elf_Internal_Rela *relocs, *relend;
2908 struct bfd_link_info *link_info;
2909 bfd_vma gp;
2910 bfd *gotobj;
2911 asection *tsec;
2912 struct alpha_elf_link_hash_entry *h;
2913 struct alpha_elf_got_entry **first_gotent;
2914 struct alpha_elf_got_entry *gotent;
2915 bfd_boolean changed_contents;
2916 bfd_boolean changed_relocs;
2917 unsigned char other;
2920 static Elf_Internal_Rela *
2921 elf64_alpha_find_reloc_at_ofs (Elf_Internal_Rela *rel,
2922 Elf_Internal_Rela *relend,
2923 bfd_vma offset, int type)
2925 while (rel < relend)
2927 if (rel->r_offset == offset
2928 && ELF64_R_TYPE (rel->r_info) == (unsigned int) type)
2929 return rel;
2930 ++rel;
2932 return NULL;
2935 static bfd_boolean
2936 elf64_alpha_relax_got_load (struct alpha_relax_info *info, bfd_vma symval,
2937 Elf_Internal_Rela *irel, unsigned long r_type)
2939 unsigned int insn;
2940 bfd_signed_vma disp;
2942 /* Get the instruction. */
2943 insn = bfd_get_32 (info->abfd, info->contents + irel->r_offset);
2945 if (insn >> 26 != OP_LDQ)
2947 reloc_howto_type *howto = elf64_alpha_howto_table + r_type;
2948 ((*_bfd_error_handler)
2949 ("%B: %A+0x%lx: warning: %s relocation against unexpected insn",
2950 info->abfd, info->sec,
2951 (unsigned long) irel->r_offset, howto->name));
2952 return TRUE;
2955 /* Can't relax dynamic symbols. */
2956 if (alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info))
2957 return TRUE;
2959 /* Can't use local-exec relocations in shared libraries. */
2960 if (r_type == R_ALPHA_GOTTPREL && info->link_info->shared)
2961 return TRUE;
2963 if (r_type == R_ALPHA_LITERAL)
2965 /* Look for nice constant addresses. This includes the not-uncommon
2966 special case of 0 for undefweak symbols. */
2967 if ((info->h && info->h->root.root.type == bfd_link_hash_undefweak)
2968 || (!info->link_info->shared
2969 && (symval >= (bfd_vma)-0x8000 || symval < 0x8000)))
2971 disp = 0;
2972 insn = (OP_LDA << 26) | (insn & (31 << 21)) | (31 << 16);
2973 insn |= (symval & 0xffff);
2974 r_type = R_ALPHA_NONE;
2976 else
2978 disp = symval - info->gp;
2979 insn = (OP_LDA << 26) | (insn & 0x03ff0000);
2980 r_type = R_ALPHA_GPREL16;
2983 else
2985 bfd_vma dtp_base, tp_base;
2987 BFD_ASSERT (elf_hash_table (info->link_info)->tls_sec != NULL);
2988 dtp_base = alpha_get_dtprel_base (info->link_info);
2989 tp_base = alpha_get_tprel_base (info->link_info);
2990 disp = symval - (r_type == R_ALPHA_GOTDTPREL ? dtp_base : tp_base);
2992 insn = (OP_LDA << 26) | (insn & (31 << 21)) | (31 << 16);
2994 switch (r_type)
2996 case R_ALPHA_GOTDTPREL:
2997 r_type = R_ALPHA_DTPREL16;
2998 break;
2999 case R_ALPHA_GOTTPREL:
3000 r_type = R_ALPHA_TPREL16;
3001 break;
3002 default:
3003 BFD_ASSERT (0);
3004 return FALSE;
3008 if (disp < -0x8000 || disp >= 0x8000)
3009 return TRUE;
3011 bfd_put_32 (info->abfd, (bfd_vma) insn, info->contents + irel->r_offset);
3012 info->changed_contents = TRUE;
3014 /* Reduce the use count on this got entry by one, possibly
3015 eliminating it. */
3016 if (--info->gotent->use_count == 0)
3018 int sz = alpha_got_entry_size (r_type);
3019 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3020 if (!info->h)
3021 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
3024 /* Smash the existing GOT relocation for its 16-bit immediate pair. */
3025 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), r_type);
3026 info->changed_relocs = TRUE;
3028 /* ??? Search forward through this basic block looking for insns
3029 that use the target register. Stop after an insn modifying the
3030 register is seen, or after a branch or call.
3032 Any such memory load insn may be substituted by a load directly
3033 off the GP. This allows the memory load insn to be issued before
3034 the calculated GP register would otherwise be ready.
3036 Any such jsr insn can be replaced by a bsr if it is in range.
3038 This would mean that we'd have to _add_ relocations, the pain of
3039 which gives one pause. */
3041 return TRUE;
3044 static bfd_vma
3045 elf64_alpha_relax_opt_call (struct alpha_relax_info *info, bfd_vma symval)
3047 /* If the function has the same gp, and we can identify that the
3048 function does not use its function pointer, we can eliminate the
3049 address load. */
3051 /* If the symbol is marked NOPV, we are being told the function never
3052 needs its procedure value. */
3053 if ((info->other & STO_ALPHA_STD_GPLOAD) == STO_ALPHA_NOPV)
3054 return symval;
3056 /* If the symbol is marked STD_GP, we are being told the function does
3057 a normal ldgp in the first two words. */
3058 else if ((info->other & STO_ALPHA_STD_GPLOAD) == STO_ALPHA_STD_GPLOAD)
3061 /* Otherwise, we may be able to identify a GP load in the first two
3062 words, which we can then skip. */
3063 else
3065 Elf_Internal_Rela *tsec_relocs, *tsec_relend, *tsec_free, *gpdisp;
3066 bfd_vma ofs;
3068 /* Load the relocations from the section that the target symbol is in. */
3069 if (info->sec == info->tsec)
3071 tsec_relocs = info->relocs;
3072 tsec_relend = info->relend;
3073 tsec_free = NULL;
3075 else
3077 tsec_relocs = (_bfd_elf_link_read_relocs
3078 (info->abfd, info->tsec, (PTR) NULL,
3079 (Elf_Internal_Rela *) NULL,
3080 info->link_info->keep_memory));
3081 if (tsec_relocs == NULL)
3082 return 0;
3083 tsec_relend = tsec_relocs + info->tsec->reloc_count;
3084 tsec_free = (info->link_info->keep_memory ? NULL : tsec_relocs);
3087 /* Recover the symbol's offset within the section. */
3088 ofs = (symval - info->tsec->output_section->vma
3089 - info->tsec->output_offset);
3091 /* Look for a GPDISP reloc. */
3092 gpdisp = (elf64_alpha_find_reloc_at_ofs
3093 (tsec_relocs, tsec_relend, ofs, R_ALPHA_GPDISP));
3095 if (!gpdisp || gpdisp->r_addend != 4)
3097 if (tsec_free)
3098 free (tsec_free);
3099 return 0;
3101 if (tsec_free)
3102 free (tsec_free);
3105 /* We've now determined that we can skip an initial gp load. Verify
3106 that the call and the target use the same gp. */
3107 if (info->link_info->output_bfd->xvec != info->tsec->owner->xvec
3108 || info->gotobj != alpha_elf_tdata (info->tsec->owner)->gotobj)
3109 return 0;
3111 return symval + 8;
3114 static bfd_boolean
3115 elf64_alpha_relax_with_lituse (struct alpha_relax_info *info,
3116 bfd_vma symval, Elf_Internal_Rela *irel)
3118 Elf_Internal_Rela *urel, *irelend = info->relend;
3119 int flags, count, i;
3120 bfd_signed_vma disp;
3121 bfd_boolean fits16;
3122 bfd_boolean fits32;
3123 bfd_boolean lit_reused = FALSE;
3124 bfd_boolean all_optimized = TRUE;
3125 unsigned int lit_insn;
3127 lit_insn = bfd_get_32 (info->abfd, info->contents + irel->r_offset);
3128 if (lit_insn >> 26 != OP_LDQ)
3130 ((*_bfd_error_handler)
3131 ("%B: %A+0x%lx: warning: LITERAL relocation against unexpected insn",
3132 info->abfd, info->sec,
3133 (unsigned long) irel->r_offset));
3134 return TRUE;
3137 /* Can't relax dynamic symbols. */
3138 if (alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info))
3139 return TRUE;
3141 /* Summarize how this particular LITERAL is used. */
3142 for (urel = irel+1, flags = count = 0; urel < irelend; ++urel, ++count)
3144 if (ELF64_R_TYPE (urel->r_info) != R_ALPHA_LITUSE)
3145 break;
3146 if (urel->r_addend <= 6)
3147 flags |= 1 << urel->r_addend;
3150 /* A little preparation for the loop... */
3151 disp = symval - info->gp;
3153 for (urel = irel+1, i = 0; i < count; ++i, ++urel)
3155 unsigned int insn;
3156 int insn_disp;
3157 bfd_signed_vma xdisp;
3159 insn = bfd_get_32 (info->abfd, info->contents + urel->r_offset);
3161 switch (urel->r_addend)
3163 case LITUSE_ALPHA_ADDR:
3164 default:
3165 /* This type is really just a placeholder to note that all
3166 uses cannot be optimized, but to still allow some. */
3167 all_optimized = FALSE;
3168 break;
3170 case LITUSE_ALPHA_BASE:
3171 /* We can always optimize 16-bit displacements. */
3173 /* Extract the displacement from the instruction, sign-extending
3174 it if necessary, then test whether it is within 16 or 32 bits
3175 displacement from GP. */
3176 insn_disp = ((insn & 0xffff) ^ 0x8000) - 0x8000;
3178 xdisp = disp + insn_disp;
3179 fits16 = (xdisp >= - (bfd_signed_vma) 0x8000 && xdisp < 0x8000);
3180 fits32 = (xdisp >= - (bfd_signed_vma) 0x80000000
3181 && xdisp < 0x7fff8000);
3183 if (fits16)
3185 /* Take the op code and dest from this insn, take the base
3186 register from the literal insn. Leave the offset alone. */
3187 insn = (insn & 0xffe0ffff) | (lit_insn & 0x001f0000);
3188 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
3189 R_ALPHA_GPREL16);
3190 urel->r_addend = irel->r_addend;
3191 info->changed_relocs = TRUE;
3193 bfd_put_32 (info->abfd, (bfd_vma) insn,
3194 info->contents + urel->r_offset);
3195 info->changed_contents = TRUE;
3198 /* If all mem+byte, we can optimize 32-bit mem displacements. */
3199 else if (fits32 && !(flags & ~6))
3201 /* FIXME: sanity check that lit insn Ra is mem insn Rb. */
3203 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
3204 R_ALPHA_GPRELHIGH);
3205 lit_insn = (OP_LDAH << 26) | (lit_insn & 0x03ff0000);
3206 bfd_put_32 (info->abfd, (bfd_vma) lit_insn,
3207 info->contents + irel->r_offset);
3208 lit_reused = TRUE;
3209 info->changed_contents = TRUE;
3211 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
3212 R_ALPHA_GPRELLOW);
3213 urel->r_addend = irel->r_addend;
3214 info->changed_relocs = TRUE;
3216 else
3217 all_optimized = FALSE;
3218 break;
3220 case LITUSE_ALPHA_BYTOFF:
3221 /* We can always optimize byte instructions. */
3223 /* FIXME: sanity check the insn for byte op. Check that the
3224 literal dest reg is indeed Rb in the byte insn. */
3226 insn &= ~ (unsigned) 0x001ff000;
3227 insn |= ((symval & 7) << 13) | 0x1000;
3229 urel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3230 urel->r_addend = 0;
3231 info->changed_relocs = TRUE;
3233 bfd_put_32 (info->abfd, (bfd_vma) insn,
3234 info->contents + urel->r_offset);
3235 info->changed_contents = TRUE;
3236 break;
3238 case LITUSE_ALPHA_JSR:
3239 case LITUSE_ALPHA_TLSGD:
3240 case LITUSE_ALPHA_TLSLDM:
3241 case LITUSE_ALPHA_JSRDIRECT:
3243 bfd_vma optdest, org;
3244 bfd_signed_vma odisp;
3246 /* For undefined weak symbols, we're mostly interested in getting
3247 rid of the got entry whenever possible, so optimize this to a
3248 use of the zero register. */
3249 if (info->h && info->h->root.root.type == bfd_link_hash_undefweak)
3251 insn |= 31 << 16;
3252 bfd_put_32 (info->abfd, (bfd_vma) insn,
3253 info->contents + urel->r_offset);
3255 info->changed_contents = TRUE;
3256 break;
3259 /* If not zero, place to jump without needing pv. */
3260 optdest = elf64_alpha_relax_opt_call (info, symval);
3261 org = (info->sec->output_section->vma
3262 + info->sec->output_offset
3263 + urel->r_offset + 4);
3264 odisp = (optdest ? optdest : symval) - org;
3266 if (odisp >= -0x400000 && odisp < 0x400000)
3268 Elf_Internal_Rela *xrel;
3270 /* Preserve branch prediction call stack when possible. */
3271 if ((insn & INSN_JSR_MASK) == INSN_JSR)
3272 insn = (OP_BSR << 26) | (insn & 0x03e00000);
3273 else
3274 insn = (OP_BR << 26) | (insn & 0x03e00000);
3276 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
3277 R_ALPHA_BRADDR);
3278 urel->r_addend = irel->r_addend;
3280 if (optdest)
3281 urel->r_addend += optdest - symval;
3282 else
3283 all_optimized = FALSE;
3285 bfd_put_32 (info->abfd, (bfd_vma) insn,
3286 info->contents + urel->r_offset);
3288 /* Kill any HINT reloc that might exist for this insn. */
3289 xrel = (elf64_alpha_find_reloc_at_ofs
3290 (info->relocs, info->relend, urel->r_offset,
3291 R_ALPHA_HINT));
3292 if (xrel)
3293 xrel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3295 info->changed_contents = TRUE;
3296 info->changed_relocs = TRUE;
3298 else
3299 all_optimized = FALSE;
3301 /* Even if the target is not in range for a direct branch,
3302 if we share a GP, we can eliminate the gp reload. */
3303 if (optdest)
3305 Elf_Internal_Rela *gpdisp
3306 = (elf64_alpha_find_reloc_at_ofs
3307 (info->relocs, irelend, urel->r_offset + 4,
3308 R_ALPHA_GPDISP));
3309 if (gpdisp)
3311 bfd_byte *p_ldah = info->contents + gpdisp->r_offset;
3312 bfd_byte *p_lda = p_ldah + gpdisp->r_addend;
3313 unsigned int ldah = bfd_get_32 (info->abfd, p_ldah);
3314 unsigned int lda = bfd_get_32 (info->abfd, p_lda);
3316 /* Verify that the instruction is "ldah $29,0($26)".
3317 Consider a function that ends in a noreturn call,
3318 and that the next function begins with an ldgp,
3319 and that by accident there is no padding between.
3320 In that case the insn would use $27 as the base. */
3321 if (ldah == 0x27ba0000 && lda == 0x23bd0000)
3323 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, p_ldah);
3324 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, p_lda);
3326 gpdisp->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3327 info->changed_contents = TRUE;
3328 info->changed_relocs = TRUE;
3333 break;
3337 /* If all cases were optimized, we can reduce the use count on this
3338 got entry by one, possibly eliminating it. */
3339 if (all_optimized)
3341 if (--info->gotent->use_count == 0)
3343 int sz = alpha_got_entry_size (R_ALPHA_LITERAL);
3344 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3345 if (!info->h)
3346 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
3349 /* If the literal instruction is no longer needed (it may have been
3350 reused. We can eliminate it. */
3351 /* ??? For now, I don't want to deal with compacting the section,
3352 so just nop it out. */
3353 if (!lit_reused)
3355 irel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3356 info->changed_relocs = TRUE;
3358 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP,
3359 info->contents + irel->r_offset);
3360 info->changed_contents = TRUE;
3363 return TRUE;
3365 else
3366 return elf64_alpha_relax_got_load (info, symval, irel, R_ALPHA_LITERAL);
3369 static bfd_boolean
3370 elf64_alpha_relax_tls_get_addr (struct alpha_relax_info *info, bfd_vma symval,
3371 Elf_Internal_Rela *irel, bfd_boolean is_gd)
3373 bfd_byte *pos[5];
3374 unsigned int insn;
3375 Elf_Internal_Rela *gpdisp, *hint;
3376 bfd_boolean dynamic, use_gottprel, pos1_unusable;
3377 unsigned long new_symndx;
3379 dynamic = alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info);
3381 /* If a TLS symbol is accessed using IE at least once, there is no point
3382 to use dynamic model for it. */
3383 if (is_gd && info->h && (info->h->flags & ALPHA_ELF_LINK_HASH_TLS_IE))
3386 /* If the symbol is local, and we've already committed to DF_STATIC_TLS,
3387 then we might as well relax to IE. */
3388 else if (info->link_info->shared && !dynamic
3389 && (info->link_info->flags & DF_STATIC_TLS))
3392 /* Otherwise we must be building an executable to do anything. */
3393 else if (info->link_info->shared)
3394 return TRUE;
3396 /* The TLSGD/TLSLDM relocation must be followed by a LITERAL and
3397 the matching LITUSE_TLS relocations. */
3398 if (irel + 2 >= info->relend)
3399 return TRUE;
3400 if (ELF64_R_TYPE (irel[1].r_info) != R_ALPHA_LITERAL
3401 || ELF64_R_TYPE (irel[2].r_info) != R_ALPHA_LITUSE
3402 || irel[2].r_addend != (is_gd ? LITUSE_ALPHA_TLSGD : LITUSE_ALPHA_TLSLDM))
3403 return TRUE;
3405 /* There must be a GPDISP relocation positioned immediately after the
3406 LITUSE relocation. */
3407 gpdisp = elf64_alpha_find_reloc_at_ofs (info->relocs, info->relend,
3408 irel[2].r_offset + 4, R_ALPHA_GPDISP);
3409 if (!gpdisp)
3410 return TRUE;
3412 pos[0] = info->contents + irel[0].r_offset;
3413 pos[1] = info->contents + irel[1].r_offset;
3414 pos[2] = info->contents + irel[2].r_offset;
3415 pos[3] = info->contents + gpdisp->r_offset;
3416 pos[4] = pos[3] + gpdisp->r_addend;
3417 pos1_unusable = FALSE;
3419 /* Generally, the positions are not allowed to be out of order, lest the
3420 modified insn sequence have different register lifetimes. We can make
3421 an exception when pos 1 is adjacent to pos 0. */
3422 if (pos[1] + 4 == pos[0])
3424 bfd_byte *tmp = pos[0];
3425 pos[0] = pos[1];
3426 pos[1] = tmp;
3428 else if (pos[1] < pos[0])
3429 pos1_unusable = TRUE;
3430 if (pos[1] >= pos[2] || pos[2] >= pos[3])
3431 return TRUE;
3433 /* Reduce the use count on the LITERAL relocation. Do this before we
3434 smash the symndx when we adjust the relocations below. */
3436 struct alpha_elf_got_entry *lit_gotent;
3437 struct alpha_elf_link_hash_entry *lit_h;
3438 unsigned long indx;
3440 BFD_ASSERT (ELF64_R_SYM (irel[1].r_info) >= info->symtab_hdr->sh_info);
3441 indx = ELF64_R_SYM (irel[1].r_info) - info->symtab_hdr->sh_info;
3442 lit_h = alpha_elf_sym_hashes (info->abfd)[indx];
3444 while (lit_h->root.root.type == bfd_link_hash_indirect
3445 || lit_h->root.root.type == bfd_link_hash_warning)
3446 lit_h = (struct alpha_elf_link_hash_entry *) lit_h->root.root.u.i.link;
3448 for (lit_gotent = lit_h->got_entries; lit_gotent ;
3449 lit_gotent = lit_gotent->next)
3450 if (lit_gotent->gotobj == info->gotobj
3451 && lit_gotent->reloc_type == R_ALPHA_LITERAL
3452 && lit_gotent->addend == irel[1].r_addend)
3453 break;
3454 BFD_ASSERT (lit_gotent);
3456 if (--lit_gotent->use_count == 0)
3458 int sz = alpha_got_entry_size (R_ALPHA_LITERAL);
3459 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3463 /* Change
3465 lda $16,x($gp) !tlsgd!1
3466 ldq $27,__tls_get_addr($gp) !literal!1
3467 jsr $26,($27),__tls_get_addr !lituse_tlsgd!1
3468 ldah $29,0($26) !gpdisp!2
3469 lda $29,0($29) !gpdisp!2
3471 ldq $16,x($gp) !gottprel
3472 unop
3473 call_pal rduniq
3474 addq $16,$0,$0
3475 unop
3476 or the first pair to
3477 lda $16,x($gp) !tprel
3478 unop
3480 ldah $16,x($gp) !tprelhi
3481 lda $16,x($16) !tprello
3483 as appropriate. */
3485 use_gottprel = FALSE;
3486 new_symndx = is_gd ? ELF64_R_SYM (irel->r_info) : 0;
3487 switch (!dynamic && !info->link_info->shared)
3489 case 1:
3491 bfd_vma tp_base;
3492 bfd_signed_vma disp;
3494 BFD_ASSERT (elf_hash_table (info->link_info)->tls_sec != NULL);
3495 tp_base = alpha_get_tprel_base (info->link_info);
3496 disp = symval - tp_base;
3498 if (disp >= -0x8000 && disp < 0x8000)
3500 insn = (OP_LDA << 26) | (16 << 21) | (31 << 16);
3501 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
3502 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]);
3504 irel[0].r_offset = pos[0] - info->contents;
3505 irel[0].r_info = ELF64_R_INFO (new_symndx, R_ALPHA_TPREL16);
3506 irel[1].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3507 break;
3509 else if (disp >= -(bfd_signed_vma) 0x80000000
3510 && disp < (bfd_signed_vma) 0x7fff8000
3511 && !pos1_unusable)
3513 insn = (OP_LDAH << 26) | (16 << 21) | (31 << 16);
3514 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
3515 insn = (OP_LDA << 26) | (16 << 21) | (16 << 16);
3516 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[1]);
3518 irel[0].r_offset = pos[0] - info->contents;
3519 irel[0].r_info = ELF64_R_INFO (new_symndx, R_ALPHA_TPRELHI);
3520 irel[1].r_offset = pos[1] - info->contents;
3521 irel[1].r_info = ELF64_R_INFO (new_symndx, R_ALPHA_TPRELLO);
3522 break;
3525 /* FALLTHRU */
3527 default:
3528 use_gottprel = TRUE;
3530 insn = (OP_LDQ << 26) | (16 << 21) | (29 << 16);
3531 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
3532 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]);
3534 irel[0].r_offset = pos[0] - info->contents;
3535 irel[0].r_info = ELF64_R_INFO (new_symndx, R_ALPHA_GOTTPREL);
3536 irel[1].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3537 break;
3540 bfd_put_32 (info->abfd, (bfd_vma) INSN_RDUNIQ, pos[2]);
3542 insn = INSN_ADDQ | (16 << 21) | (0 << 16) | (0 << 0);
3543 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[3]);
3545 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[4]);
3547 irel[2].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3548 gpdisp->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3550 hint = elf64_alpha_find_reloc_at_ofs (info->relocs, info->relend,
3551 irel[2].r_offset, R_ALPHA_HINT);
3552 if (hint)
3553 hint->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
3555 info->changed_contents = TRUE;
3556 info->changed_relocs = TRUE;
3558 /* Reduce the use count on the TLSGD/TLSLDM relocation. */
3559 if (--info->gotent->use_count == 0)
3561 int sz = alpha_got_entry_size (info->gotent->reloc_type);
3562 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3563 if (!info->h)
3564 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
3567 /* If we've switched to a GOTTPREL relocation, increment the reference
3568 count on that got entry. */
3569 if (use_gottprel)
3571 struct alpha_elf_got_entry *tprel_gotent;
3573 for (tprel_gotent = *info->first_gotent; tprel_gotent ;
3574 tprel_gotent = tprel_gotent->next)
3575 if (tprel_gotent->gotobj == info->gotobj
3576 && tprel_gotent->reloc_type == R_ALPHA_GOTTPREL
3577 && tprel_gotent->addend == irel->r_addend)
3578 break;
3579 if (tprel_gotent)
3580 tprel_gotent->use_count++;
3581 else
3583 if (info->gotent->use_count == 0)
3584 tprel_gotent = info->gotent;
3585 else
3587 tprel_gotent = (struct alpha_elf_got_entry *)
3588 bfd_alloc (info->abfd, sizeof (struct alpha_elf_got_entry));
3589 if (!tprel_gotent)
3590 return FALSE;
3592 tprel_gotent->next = *info->first_gotent;
3593 *info->first_gotent = tprel_gotent;
3595 tprel_gotent->gotobj = info->gotobj;
3596 tprel_gotent->addend = irel->r_addend;
3597 tprel_gotent->got_offset = -1;
3598 tprel_gotent->reloc_done = 0;
3599 tprel_gotent->reloc_xlated = 0;
3602 tprel_gotent->use_count = 1;
3603 tprel_gotent->reloc_type = R_ALPHA_GOTTPREL;
3607 return TRUE;
3610 static bfd_boolean
3611 elf64_alpha_relax_section (bfd *abfd, asection *sec,
3612 struct bfd_link_info *link_info, bfd_boolean *again)
3614 Elf_Internal_Shdr *symtab_hdr;
3615 Elf_Internal_Rela *internal_relocs;
3616 Elf_Internal_Rela *irel, *irelend;
3617 Elf_Internal_Sym *isymbuf = NULL;
3618 struct alpha_elf_got_entry **local_got_entries;
3619 struct alpha_relax_info info;
3621 /* There's nothing to change, yet. */
3622 *again = FALSE;
3624 if (link_info->relocatable
3625 || ((sec->flags & (SEC_CODE | SEC_RELOC | SEC_ALLOC))
3626 != (SEC_CODE | SEC_RELOC | SEC_ALLOC))
3627 || sec->reloc_count == 0)
3628 return TRUE;
3630 BFD_ASSERT (is_alpha_elf (abfd));
3632 /* Make sure our GOT and PLT tables are up-to-date. */
3633 if (alpha_elf_hash_table(link_info)->relax_trip != link_info->relax_trip)
3635 alpha_elf_hash_table(link_info)->relax_trip = link_info->relax_trip;
3637 /* This should never fail after the initial round, since the only
3638 error is GOT overflow, and relaxation only shrinks the table. */
3639 if (!elf64_alpha_size_got_sections (link_info))
3640 abort ();
3641 if (elf_hash_table (link_info)->dynamic_sections_created)
3643 elf64_alpha_size_plt_section (link_info);
3644 elf64_alpha_size_rela_got_section (link_info);
3648 symtab_hdr = &elf_symtab_hdr (abfd);
3649 local_got_entries = alpha_elf_tdata(abfd)->local_got_entries;
3651 /* Load the relocations for this section. */
3652 internal_relocs = (_bfd_elf_link_read_relocs
3653 (abfd, sec, (PTR) NULL, (Elf_Internal_Rela *) NULL,
3654 link_info->keep_memory));
3655 if (internal_relocs == NULL)
3656 return FALSE;
3658 memset(&info, 0, sizeof (info));
3659 info.abfd = abfd;
3660 info.sec = sec;
3661 info.link_info = link_info;
3662 info.symtab_hdr = symtab_hdr;
3663 info.relocs = internal_relocs;
3664 info.relend = irelend = internal_relocs + sec->reloc_count;
3666 /* Find the GP for this object. Do not store the result back via
3667 _bfd_set_gp_value, since this could change again before final. */
3668 info.gotobj = alpha_elf_tdata (abfd)->gotobj;
3669 if (info.gotobj)
3671 asection *sgot = alpha_elf_tdata (info.gotobj)->got;
3672 info.gp = (sgot->output_section->vma
3673 + sgot->output_offset
3674 + 0x8000);
3677 /* Get the section contents. */
3678 if (elf_section_data (sec)->this_hdr.contents != NULL)
3679 info.contents = elf_section_data (sec)->this_hdr.contents;
3680 else
3682 if (!bfd_malloc_and_get_section (abfd, sec, &info.contents))
3683 goto error_return;
3686 for (irel = internal_relocs; irel < irelend; irel++)
3688 bfd_vma symval;
3689 struct alpha_elf_got_entry *gotent;
3690 unsigned long r_type = ELF64_R_TYPE (irel->r_info);
3691 unsigned long r_symndx = ELF64_R_SYM (irel->r_info);
3693 /* Early exit for unhandled or unrelaxable relocations. */
3694 switch (r_type)
3696 case R_ALPHA_LITERAL:
3697 case R_ALPHA_GPRELHIGH:
3698 case R_ALPHA_GPRELLOW:
3699 case R_ALPHA_GOTDTPREL:
3700 case R_ALPHA_GOTTPREL:
3701 case R_ALPHA_TLSGD:
3702 break;
3704 case R_ALPHA_TLSLDM:
3705 /* The symbol for a TLSLDM reloc is ignored. Collapse the
3706 reloc to the 0 symbol so that they all match. */
3707 r_symndx = 0;
3708 break;
3710 default:
3711 continue;
3714 /* Get the value of the symbol referred to by the reloc. */
3715 if (r_symndx < symtab_hdr->sh_info)
3717 /* A local symbol. */
3718 Elf_Internal_Sym *isym;
3720 /* Read this BFD's local symbols. */
3721 if (isymbuf == NULL)
3723 isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
3724 if (isymbuf == NULL)
3725 isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
3726 symtab_hdr->sh_info, 0,
3727 NULL, NULL, NULL);
3728 if (isymbuf == NULL)
3729 goto error_return;
3732 isym = isymbuf + r_symndx;
3734 /* Given the symbol for a TLSLDM reloc is ignored, this also
3735 means forcing the symbol value to the tp base. */
3736 if (r_type == R_ALPHA_TLSLDM)
3738 info.tsec = bfd_abs_section_ptr;
3739 symval = alpha_get_tprel_base (info.link_info);
3741 else
3743 symval = isym->st_value;
3744 if (isym->st_shndx == SHN_UNDEF)
3745 continue;
3746 else if (isym->st_shndx == SHN_ABS)
3747 info.tsec = bfd_abs_section_ptr;
3748 else if (isym->st_shndx == SHN_COMMON)
3749 info.tsec = bfd_com_section_ptr;
3750 else
3751 info.tsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
3754 info.h = NULL;
3755 info.other = isym->st_other;
3756 if (local_got_entries)
3757 info.first_gotent = &local_got_entries[r_symndx];
3758 else
3760 info.first_gotent = &info.gotent;
3761 info.gotent = NULL;
3764 else
3766 unsigned long indx;
3767 struct alpha_elf_link_hash_entry *h;
3769 indx = r_symndx - symtab_hdr->sh_info;
3770 h = alpha_elf_sym_hashes (abfd)[indx];
3771 BFD_ASSERT (h != NULL);
3773 while (h->root.root.type == bfd_link_hash_indirect
3774 || h->root.root.type == bfd_link_hash_warning)
3775 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
3777 /* If the symbol is undefined, we can't do anything with it. */
3778 if (h->root.root.type == bfd_link_hash_undefined)
3779 continue;
3781 /* If the symbol isn't defined in the current module,
3782 again we can't do anything. */
3783 if (h->root.root.type == bfd_link_hash_undefweak)
3785 info.tsec = bfd_abs_section_ptr;
3786 symval = 0;
3788 else if (!h->root.def_regular)
3790 /* Except for TLSGD relocs, which can sometimes be
3791 relaxed to GOTTPREL relocs. */
3792 if (r_type != R_ALPHA_TLSGD)
3793 continue;
3794 info.tsec = bfd_abs_section_ptr;
3795 symval = 0;
3797 else
3799 info.tsec = h->root.root.u.def.section;
3800 symval = h->root.root.u.def.value;
3803 info.h = h;
3804 info.other = h->root.other;
3805 info.first_gotent = &h->got_entries;
3808 /* Search for the got entry to be used by this relocation. */
3809 for (gotent = *info.first_gotent; gotent ; gotent = gotent->next)
3810 if (gotent->gotobj == info.gotobj
3811 && gotent->reloc_type == r_type
3812 && gotent->addend == irel->r_addend)
3813 break;
3814 info.gotent = gotent;
3816 symval += info.tsec->output_section->vma + info.tsec->output_offset;
3817 symval += irel->r_addend;
3819 switch (r_type)
3821 case R_ALPHA_LITERAL:
3822 BFD_ASSERT(info.gotent != NULL);
3824 /* If there exist LITUSE relocations immediately following, this
3825 opens up all sorts of interesting optimizations, because we
3826 now know every location that this address load is used. */
3827 if (irel+1 < irelend
3828 && ELF64_R_TYPE (irel[1].r_info) == R_ALPHA_LITUSE)
3830 if (!elf64_alpha_relax_with_lituse (&info, symval, irel))
3831 goto error_return;
3833 else
3835 if (!elf64_alpha_relax_got_load (&info, symval, irel, r_type))
3836 goto error_return;
3838 break;
3840 case R_ALPHA_GOTDTPREL:
3841 case R_ALPHA_GOTTPREL:
3842 BFD_ASSERT(info.gotent != NULL);
3843 if (!elf64_alpha_relax_got_load (&info, symval, irel, r_type))
3844 goto error_return;
3845 break;
3847 case R_ALPHA_TLSGD:
3848 case R_ALPHA_TLSLDM:
3849 BFD_ASSERT(info.gotent != NULL);
3850 if (!elf64_alpha_relax_tls_get_addr (&info, symval, irel,
3851 r_type == R_ALPHA_TLSGD))
3852 goto error_return;
3853 break;
3857 if (isymbuf != NULL
3858 && symtab_hdr->contents != (unsigned char *) isymbuf)
3860 if (!link_info->keep_memory)
3861 free (isymbuf);
3862 else
3864 /* Cache the symbols for elf_link_input_bfd. */
3865 symtab_hdr->contents = (unsigned char *) isymbuf;
3869 if (info.contents != NULL
3870 && elf_section_data (sec)->this_hdr.contents != info.contents)
3872 if (!info.changed_contents && !link_info->keep_memory)
3873 free (info.contents);
3874 else
3876 /* Cache the section contents for elf_link_input_bfd. */
3877 elf_section_data (sec)->this_hdr.contents = info.contents;
3881 if (elf_section_data (sec)->relocs != internal_relocs)
3883 if (!info.changed_relocs)
3884 free (internal_relocs);
3885 else
3886 elf_section_data (sec)->relocs = internal_relocs;
3889 *again = info.changed_contents || info.changed_relocs;
3891 return TRUE;
3893 error_return:
3894 if (isymbuf != NULL
3895 && symtab_hdr->contents != (unsigned char *) isymbuf)
3896 free (isymbuf);
3897 if (info.contents != NULL
3898 && elf_section_data (sec)->this_hdr.contents != info.contents)
3899 free (info.contents);
3900 if (internal_relocs != NULL
3901 && elf_section_data (sec)->relocs != internal_relocs)
3902 free (internal_relocs);
3903 return FALSE;
3906 /* Emit a dynamic relocation for (DYNINDX, RTYPE, ADDEND) at (SEC, OFFSET)
3907 into the next available slot in SREL. */
3909 static void
3910 elf64_alpha_emit_dynrel (bfd *abfd, struct bfd_link_info *info,
3911 asection *sec, asection *srel, bfd_vma offset,
3912 long dynindx, long rtype, bfd_vma addend)
3914 Elf_Internal_Rela outrel;
3915 bfd_byte *loc;
3917 BFD_ASSERT (srel != NULL);
3919 outrel.r_info = ELF64_R_INFO (dynindx, rtype);
3920 outrel.r_addend = addend;
3922 offset = _bfd_elf_section_offset (abfd, info, sec, offset);
3923 if ((offset | 1) != (bfd_vma) -1)
3924 outrel.r_offset = sec->output_section->vma + sec->output_offset + offset;
3925 else
3926 memset (&outrel, 0, sizeof (outrel));
3928 loc = srel->contents;
3929 loc += srel->reloc_count++ * sizeof (Elf64_External_Rela);
3930 bfd_elf64_swap_reloca_out (abfd, &outrel, loc);
3931 BFD_ASSERT (sizeof (Elf64_External_Rela) * srel->reloc_count <= srel->size);
3934 /* Relocate an Alpha ELF section for a relocatable link.
3936 We don't have to change anything unless the reloc is against a section
3937 symbol, in which case we have to adjust according to where the section
3938 symbol winds up in the output section. */
3940 static bfd_boolean
3941 elf64_alpha_relocate_section_r (bfd *output_bfd ATTRIBUTE_UNUSED,
3942 struct bfd_link_info *info ATTRIBUTE_UNUSED,
3943 bfd *input_bfd, asection *input_section,
3944 bfd_byte *contents ATTRIBUTE_UNUSED,
3945 Elf_Internal_Rela *relocs,
3946 Elf_Internal_Sym *local_syms,
3947 asection **local_sections)
3949 unsigned long symtab_hdr_sh_info;
3950 Elf_Internal_Rela *rel;
3951 Elf_Internal_Rela *relend;
3952 struct elf_link_hash_entry **sym_hashes;
3953 bfd_boolean ret_val = TRUE;
3955 symtab_hdr_sh_info = elf_symtab_hdr (input_bfd).sh_info;
3956 sym_hashes = elf_sym_hashes (input_bfd);
3958 relend = relocs + input_section->reloc_count;
3959 for (rel = relocs; rel < relend; rel++)
3961 unsigned long r_symndx;
3962 Elf_Internal_Sym *sym;
3963 asection *sec;
3964 unsigned long r_type;
3966 r_type = ELF64_R_TYPE (rel->r_info);
3967 if (r_type >= R_ALPHA_max)
3969 (*_bfd_error_handler)
3970 (_("%B: unknown relocation type %d"),
3971 input_bfd, (int) r_type);
3972 bfd_set_error (bfd_error_bad_value);
3973 ret_val = FALSE;
3974 continue;
3977 /* The symbol associated with GPDISP and LITUSE is
3978 immaterial. Only the addend is significant. */
3979 if (r_type == R_ALPHA_GPDISP || r_type == R_ALPHA_LITUSE)
3980 continue;
3982 r_symndx = ELF64_R_SYM (rel->r_info);
3983 if (r_symndx < symtab_hdr_sh_info)
3985 sym = local_syms + r_symndx;
3986 sec = local_sections[r_symndx];
3988 else
3990 struct elf_link_hash_entry *h;
3992 h = sym_hashes[r_symndx - symtab_hdr_sh_info];
3994 while (h->root.type == bfd_link_hash_indirect
3995 || h->root.type == bfd_link_hash_warning)
3996 h = (struct elf_link_hash_entry *) h->root.u.i.link;
3998 if (h->root.type != bfd_link_hash_defined
3999 && h->root.type != bfd_link_hash_defweak)
4000 continue;
4002 sym = NULL;
4003 sec = h->root.u.def.section;
4006 if (sec != NULL && elf_discarded_section (sec))
4008 /* For relocs against symbols from removed linkonce sections,
4009 or sections discarded by a linker script, we just want the
4010 section contents zeroed. */
4011 _bfd_clear_contents (elf64_alpha_howto_table + r_type,
4012 input_bfd, contents + rel->r_offset);
4013 rel->r_info = 0;
4014 rel->r_addend = 0;
4015 continue;
4018 if (sym != NULL && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
4019 rel->r_addend += sec->output_offset;
4022 return ret_val;
4025 /* Relocate an Alpha ELF section. */
4027 static bfd_boolean
4028 elf64_alpha_relocate_section (bfd *output_bfd, struct bfd_link_info *info,
4029 bfd *input_bfd, asection *input_section,
4030 bfd_byte *contents, Elf_Internal_Rela *relocs,
4031 Elf_Internal_Sym *local_syms,
4032 asection **local_sections)
4034 Elf_Internal_Shdr *symtab_hdr;
4035 Elf_Internal_Rela *rel;
4036 Elf_Internal_Rela *relend;
4037 asection *sgot, *srel, *srelgot;
4038 bfd *dynobj, *gotobj;
4039 bfd_vma gp, tp_base, dtp_base;
4040 struct alpha_elf_got_entry **local_got_entries;
4041 bfd_boolean ret_val;
4043 BFD_ASSERT (is_alpha_elf (input_bfd));
4045 /* Handle relocatable links with a smaller loop. */
4046 if (info->relocatable)
4047 return elf64_alpha_relocate_section_r (output_bfd, info, input_bfd,
4048 input_section, contents, relocs,
4049 local_syms, local_sections);
4051 /* This is a final link. */
4053 ret_val = TRUE;
4055 symtab_hdr = &elf_symtab_hdr (input_bfd);
4057 dynobj = elf_hash_table (info)->dynobj;
4058 if (dynobj)
4059 srelgot = bfd_get_section_by_name (dynobj, ".rela.got");
4060 else
4061 srelgot = NULL;
4063 if (input_section->flags & SEC_ALLOC)
4065 const char *section_name;
4066 section_name = (bfd_elf_string_from_elf_section
4067 (input_bfd, elf_elfheader(input_bfd)->e_shstrndx,
4068 elf_section_data(input_section)->rel_hdr.sh_name));
4069 BFD_ASSERT(section_name != NULL);
4070 srel = bfd_get_section_by_name (dynobj, section_name);
4072 else
4073 srel = NULL;
4075 /* Find the gp value for this input bfd. */
4076 gotobj = alpha_elf_tdata (input_bfd)->gotobj;
4077 if (gotobj)
4079 sgot = alpha_elf_tdata (gotobj)->got;
4080 gp = _bfd_get_gp_value (gotobj);
4081 if (gp == 0)
4083 gp = (sgot->output_section->vma
4084 + sgot->output_offset
4085 + 0x8000);
4086 _bfd_set_gp_value (gotobj, gp);
4089 else
4091 sgot = NULL;
4092 gp = 0;
4095 local_got_entries = alpha_elf_tdata(input_bfd)->local_got_entries;
4097 if (elf_hash_table (info)->tls_sec != NULL)
4099 dtp_base = alpha_get_dtprel_base (info);
4100 tp_base = alpha_get_tprel_base (info);
4102 else
4103 dtp_base = tp_base = 0;
4105 relend = relocs + input_section->reloc_count;
4106 for (rel = relocs; rel < relend; rel++)
4108 struct alpha_elf_link_hash_entry *h = NULL;
4109 struct alpha_elf_got_entry *gotent;
4110 bfd_reloc_status_type r;
4111 reloc_howto_type *howto;
4112 unsigned long r_symndx;
4113 Elf_Internal_Sym *sym = NULL;
4114 asection *sec = NULL;
4115 bfd_vma value;
4116 bfd_vma addend;
4117 bfd_boolean dynamic_symbol_p;
4118 bfd_boolean undef_weak_ref = FALSE;
4119 unsigned long r_type;
4121 r_type = ELF64_R_TYPE(rel->r_info);
4122 if (r_type >= R_ALPHA_max)
4124 (*_bfd_error_handler)
4125 (_("%B: unknown relocation type %d"),
4126 input_bfd, (int) r_type);
4127 bfd_set_error (bfd_error_bad_value);
4128 ret_val = FALSE;
4129 continue;
4132 howto = elf64_alpha_howto_table + r_type;
4133 r_symndx = ELF64_R_SYM(rel->r_info);
4135 /* The symbol for a TLSLDM reloc is ignored. Collapse the
4136 reloc to the 0 symbol so that they all match. */
4137 if (r_type == R_ALPHA_TLSLDM)
4138 r_symndx = 0;
4140 if (r_symndx < symtab_hdr->sh_info)
4142 asection *msec;
4143 sym = local_syms + r_symndx;
4144 sec = local_sections[r_symndx];
4145 msec = sec;
4146 value = _bfd_elf_rela_local_sym (output_bfd, sym, &msec, rel);
4148 /* If this is a tp-relative relocation against sym 0,
4149 this is hackery from relax_section. Force the value to
4150 be the tls module base. */
4151 if (r_symndx == 0
4152 && (r_type == R_ALPHA_TLSLDM
4153 || r_type == R_ALPHA_GOTTPREL
4154 || r_type == R_ALPHA_TPREL64
4155 || r_type == R_ALPHA_TPRELHI
4156 || r_type == R_ALPHA_TPRELLO
4157 || r_type == R_ALPHA_TPREL16))
4158 value = dtp_base;
4160 if (local_got_entries)
4161 gotent = local_got_entries[r_symndx];
4162 else
4163 gotent = NULL;
4165 /* Need to adjust local GOT entries' addends for SEC_MERGE
4166 unless it has been done already. */
4167 if ((sec->flags & SEC_MERGE)
4168 && ELF_ST_TYPE (sym->st_info) == STT_SECTION
4169 && sec->sec_info_type == ELF_INFO_TYPE_MERGE
4170 && gotent
4171 && !gotent->reloc_xlated)
4173 struct alpha_elf_got_entry *ent;
4175 for (ent = gotent; ent; ent = ent->next)
4177 ent->reloc_xlated = 1;
4178 if (ent->use_count == 0)
4179 continue;
4180 msec = sec;
4181 ent->addend =
4182 _bfd_merged_section_offset (output_bfd, &msec,
4183 elf_section_data (sec)->
4184 sec_info,
4185 sym->st_value + ent->addend);
4186 ent->addend -= sym->st_value;
4187 ent->addend += msec->output_section->vma
4188 + msec->output_offset
4189 - sec->output_section->vma
4190 - sec->output_offset;
4194 dynamic_symbol_p = FALSE;
4196 else
4198 bfd_boolean warned;
4199 bfd_boolean unresolved_reloc;
4200 struct elf_link_hash_entry *hh;
4201 struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (input_bfd);
4203 RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
4204 r_symndx, symtab_hdr, sym_hashes,
4205 hh, sec, value,
4206 unresolved_reloc, warned);
4208 if (warned)
4209 continue;
4211 if (value == 0
4212 && ! unresolved_reloc
4213 && hh->root.type == bfd_link_hash_undefweak)
4214 undef_weak_ref = TRUE;
4216 h = (struct alpha_elf_link_hash_entry *) hh;
4217 dynamic_symbol_p = alpha_elf_dynamic_symbol_p (&h->root, info);
4218 gotent = h->got_entries;
4221 if (sec != NULL && elf_discarded_section (sec))
4223 /* For relocs against symbols from removed linkonce sections,
4224 or sections discarded by a linker script, we just want the
4225 section contents zeroed. Avoid any special processing. */
4226 _bfd_clear_contents (howto, input_bfd, contents + rel->r_offset);
4227 rel->r_info = 0;
4228 rel->r_addend = 0;
4229 continue;
4232 addend = rel->r_addend;
4233 value += addend;
4235 /* Search for the proper got entry. */
4236 for (; gotent ; gotent = gotent->next)
4237 if (gotent->gotobj == gotobj
4238 && gotent->reloc_type == r_type
4239 && gotent->addend == addend)
4240 break;
4242 switch (r_type)
4244 case R_ALPHA_GPDISP:
4246 bfd_byte *p_ldah, *p_lda;
4248 BFD_ASSERT(gp != 0);
4250 value = (input_section->output_section->vma
4251 + input_section->output_offset
4252 + rel->r_offset);
4254 p_ldah = contents + rel->r_offset;
4255 p_lda = p_ldah + rel->r_addend;
4257 r = elf64_alpha_do_reloc_gpdisp (input_bfd, gp - value,
4258 p_ldah, p_lda);
4260 break;
4262 case R_ALPHA_LITERAL:
4263 BFD_ASSERT(sgot != NULL);
4264 BFD_ASSERT(gp != 0);
4265 BFD_ASSERT(gotent != NULL);
4266 BFD_ASSERT(gotent->use_count >= 1);
4268 if (!gotent->reloc_done)
4270 gotent->reloc_done = 1;
4272 bfd_put_64 (output_bfd, value,
4273 sgot->contents + gotent->got_offset);
4275 /* If the symbol has been forced local, output a
4276 RELATIVE reloc, otherwise it will be handled in
4277 finish_dynamic_symbol. */
4278 if (info->shared && !dynamic_symbol_p && !undef_weak_ref)
4279 elf64_alpha_emit_dynrel (output_bfd, info, sgot, srelgot,
4280 gotent->got_offset, 0,
4281 R_ALPHA_RELATIVE, value);
4284 value = (sgot->output_section->vma
4285 + sgot->output_offset
4286 + gotent->got_offset);
4287 value -= gp;
4288 goto default_reloc;
4290 case R_ALPHA_GPREL32:
4291 case R_ALPHA_GPREL16:
4292 case R_ALPHA_GPRELLOW:
4293 if (dynamic_symbol_p)
4295 (*_bfd_error_handler)
4296 (_("%B: gp-relative relocation against dynamic symbol %s"),
4297 input_bfd, h->root.root.root.string);
4298 ret_val = FALSE;
4300 BFD_ASSERT(gp != 0);
4301 value -= gp;
4302 goto default_reloc;
4304 case R_ALPHA_GPRELHIGH:
4305 if (dynamic_symbol_p)
4307 (*_bfd_error_handler)
4308 (_("%B: gp-relative relocation against dynamic symbol %s"),
4309 input_bfd, h->root.root.root.string);
4310 ret_val = FALSE;
4312 BFD_ASSERT(gp != 0);
4313 value -= gp;
4314 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
4315 goto default_reloc;
4317 case R_ALPHA_HINT:
4318 /* A call to a dynamic symbol is definitely out of range of
4319 the 16-bit displacement. Don't bother writing anything. */
4320 if (dynamic_symbol_p)
4322 r = bfd_reloc_ok;
4323 break;
4325 /* The regular PC-relative stuff measures from the start of
4326 the instruction rather than the end. */
4327 value -= 4;
4328 goto default_reloc;
4330 case R_ALPHA_BRADDR:
4331 if (dynamic_symbol_p)
4333 (*_bfd_error_handler)
4334 (_("%B: pc-relative relocation against dynamic symbol %s"),
4335 input_bfd, h->root.root.root.string);
4336 ret_val = FALSE;
4338 /* The regular PC-relative stuff measures from the start of
4339 the instruction rather than the end. */
4340 value -= 4;
4341 goto default_reloc;
4343 case R_ALPHA_BRSGP:
4345 int other;
4346 const char *name;
4348 /* The regular PC-relative stuff measures from the start of
4349 the instruction rather than the end. */
4350 value -= 4;
4352 /* The source and destination gp must be the same. Note that
4353 the source will always have an assigned gp, since we forced
4354 one in check_relocs, but that the destination may not, as
4355 it might not have had any relocations at all. Also take
4356 care not to crash if H is an undefined symbol. */
4357 if (h != NULL && sec != NULL
4358 && alpha_elf_tdata (sec->owner)->gotobj
4359 && gotobj != alpha_elf_tdata (sec->owner)->gotobj)
4361 (*_bfd_error_handler)
4362 (_("%B: change in gp: BRSGP %s"),
4363 input_bfd, h->root.root.root.string);
4364 ret_val = FALSE;
4367 /* The symbol should be marked either NOPV or STD_GPLOAD. */
4368 if (h != NULL)
4369 other = h->root.other;
4370 else
4371 other = sym->st_other;
4372 switch (other & STO_ALPHA_STD_GPLOAD)
4374 case STO_ALPHA_NOPV:
4375 break;
4376 case STO_ALPHA_STD_GPLOAD:
4377 value += 8;
4378 break;
4379 default:
4380 if (h != NULL)
4381 name = h->root.root.root.string;
4382 else
4384 name = (bfd_elf_string_from_elf_section
4385 (input_bfd, symtab_hdr->sh_link, sym->st_name));
4386 if (name == NULL)
4387 name = _("<unknown>");
4388 else if (name[0] == 0)
4389 name = bfd_section_name (input_bfd, sec);
4391 (*_bfd_error_handler)
4392 (_("%B: !samegp reloc against symbol without .prologue: %s"),
4393 input_bfd, name);
4394 ret_val = FALSE;
4395 break;
4398 goto default_reloc;
4401 case R_ALPHA_REFLONG:
4402 case R_ALPHA_REFQUAD:
4403 case R_ALPHA_DTPREL64:
4404 case R_ALPHA_TPREL64:
4406 long dynindx, dyntype = r_type;
4407 bfd_vma dynaddend;
4409 /* Careful here to remember RELATIVE relocations for global
4410 variables for symbolic shared objects. */
4412 if (dynamic_symbol_p)
4414 BFD_ASSERT(h->root.dynindx != -1);
4415 dynindx = h->root.dynindx;
4416 dynaddend = addend;
4417 addend = 0, value = 0;
4419 else if (r_type == R_ALPHA_DTPREL64)
4421 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4422 value -= dtp_base;
4423 goto default_reloc;
4425 else if (r_type == R_ALPHA_TPREL64)
4427 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4428 if (!info->shared)
4430 value -= tp_base;
4431 goto default_reloc;
4433 dynindx = 0;
4434 dynaddend = value - dtp_base;
4436 else if (info->shared
4437 && r_symndx != 0
4438 && (input_section->flags & SEC_ALLOC)
4439 && !undef_weak_ref)
4441 if (r_type == R_ALPHA_REFLONG)
4443 (*_bfd_error_handler)
4444 (_("%B: unhandled dynamic relocation against %s"),
4445 input_bfd,
4446 h->root.root.root.string);
4447 ret_val = FALSE;
4449 dynindx = 0;
4450 dyntype = R_ALPHA_RELATIVE;
4451 dynaddend = value;
4453 else
4454 goto default_reloc;
4456 if (input_section->flags & SEC_ALLOC)
4457 elf64_alpha_emit_dynrel (output_bfd, info, input_section,
4458 srel, rel->r_offset, dynindx,
4459 dyntype, dynaddend);
4461 goto default_reloc;
4463 case R_ALPHA_SREL16:
4464 case R_ALPHA_SREL32:
4465 case R_ALPHA_SREL64:
4466 if (dynamic_symbol_p)
4468 (*_bfd_error_handler)
4469 (_("%B: pc-relative relocation against dynamic symbol %s"),
4470 input_bfd, h->root.root.root.string);
4471 ret_val = FALSE;
4473 else if ((info->shared || info->pie) && undef_weak_ref)
4475 (*_bfd_error_handler)
4476 (_("%B: pc-relative relocation against undefined weak symbol %s"),
4477 input_bfd, h->root.root.root.string);
4478 ret_val = FALSE;
4482 /* ??? .eh_frame references to discarded sections will be smashed
4483 to relocations against SHN_UNDEF. The .eh_frame format allows
4484 NULL to be encoded as 0 in any format, so this works here. */
4485 if (r_symndx == 0)
4486 howto = (elf64_alpha_howto_table
4487 + (r_type - R_ALPHA_SREL32 + R_ALPHA_REFLONG));
4488 goto default_reloc;
4490 case R_ALPHA_TLSLDM:
4491 /* Ignore the symbol for the relocation. The result is always
4492 the current module. */
4493 dynamic_symbol_p = 0;
4494 /* FALLTHRU */
4496 case R_ALPHA_TLSGD:
4497 if (!gotent->reloc_done)
4499 gotent->reloc_done = 1;
4501 /* Note that the module index for the main program is 1. */
4502 bfd_put_64 (output_bfd, !info->shared && !dynamic_symbol_p,
4503 sgot->contents + gotent->got_offset);
4505 /* If the symbol has been forced local, output a
4506 DTPMOD64 reloc, otherwise it will be handled in
4507 finish_dynamic_symbol. */
4508 if (info->shared && !dynamic_symbol_p)
4509 elf64_alpha_emit_dynrel (output_bfd, info, sgot, srelgot,
4510 gotent->got_offset, 0,
4511 R_ALPHA_DTPMOD64, 0);
4513 if (dynamic_symbol_p || r_type == R_ALPHA_TLSLDM)
4514 value = 0;
4515 else
4517 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4518 value -= dtp_base;
4520 bfd_put_64 (output_bfd, value,
4521 sgot->contents + gotent->got_offset + 8);
4524 value = (sgot->output_section->vma
4525 + sgot->output_offset
4526 + gotent->got_offset);
4527 value -= gp;
4528 goto default_reloc;
4530 case R_ALPHA_DTPRELHI:
4531 case R_ALPHA_DTPRELLO:
4532 case R_ALPHA_DTPREL16:
4533 if (dynamic_symbol_p)
4535 (*_bfd_error_handler)
4536 (_("%B: dtp-relative relocation against dynamic symbol %s"),
4537 input_bfd, h->root.root.root.string);
4538 ret_val = FALSE;
4540 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4541 value -= dtp_base;
4542 if (r_type == R_ALPHA_DTPRELHI)
4543 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
4544 goto default_reloc;
4546 case R_ALPHA_TPRELHI:
4547 case R_ALPHA_TPRELLO:
4548 case R_ALPHA_TPREL16:
4549 if (info->shared)
4551 (*_bfd_error_handler)
4552 (_("%B: TLS local exec code cannot be linked into shared objects"),
4553 input_bfd);
4554 ret_val = FALSE;
4556 else if (dynamic_symbol_p)
4558 (*_bfd_error_handler)
4559 (_("%B: tp-relative relocation against dynamic symbol %s"),
4560 input_bfd, h->root.root.root.string);
4561 ret_val = FALSE;
4563 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4564 value -= tp_base;
4565 if (r_type == R_ALPHA_TPRELHI)
4566 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
4567 goto default_reloc;
4569 case R_ALPHA_GOTDTPREL:
4570 case R_ALPHA_GOTTPREL:
4571 BFD_ASSERT(sgot != NULL);
4572 BFD_ASSERT(gp != 0);
4573 BFD_ASSERT(gotent != NULL);
4574 BFD_ASSERT(gotent->use_count >= 1);
4576 if (!gotent->reloc_done)
4578 gotent->reloc_done = 1;
4580 if (dynamic_symbol_p)
4581 value = 0;
4582 else
4584 BFD_ASSERT (elf_hash_table (info)->tls_sec != NULL);
4585 if (r_type == R_ALPHA_GOTDTPREL)
4586 value -= dtp_base;
4587 else if (!info->shared)
4588 value -= tp_base;
4589 else
4591 elf64_alpha_emit_dynrel (output_bfd, info, sgot, srelgot,
4592 gotent->got_offset, 0,
4593 R_ALPHA_TPREL64,
4594 value - dtp_base);
4595 value = 0;
4598 bfd_put_64 (output_bfd, value,
4599 sgot->contents + gotent->got_offset);
4602 value = (sgot->output_section->vma
4603 + sgot->output_offset
4604 + gotent->got_offset);
4605 value -= gp;
4606 goto default_reloc;
4608 default:
4609 default_reloc:
4610 r = _bfd_final_link_relocate (howto, input_bfd, input_section,
4611 contents, rel->r_offset, value, 0);
4612 break;
4615 switch (r)
4617 case bfd_reloc_ok:
4618 break;
4620 case bfd_reloc_overflow:
4622 const char *name;
4624 /* Don't warn if the overflow is due to pc relative reloc
4625 against discarded section. Section optimization code should
4626 handle it. */
4628 if (r_symndx < symtab_hdr->sh_info
4629 && sec != NULL && howto->pc_relative
4630 && elf_discarded_section (sec))
4631 break;
4633 if (h != NULL)
4634 name = NULL;
4635 else
4637 name = (bfd_elf_string_from_elf_section
4638 (input_bfd, symtab_hdr->sh_link, sym->st_name));
4639 if (name == NULL)
4640 return FALSE;
4641 if (*name == '\0')
4642 name = bfd_section_name (input_bfd, sec);
4644 if (! ((*info->callbacks->reloc_overflow)
4645 (info, (h ? &h->root.root : NULL), name, howto->name,
4646 (bfd_vma) 0, input_bfd, input_section,
4647 rel->r_offset)))
4648 ret_val = FALSE;
4650 break;
4652 default:
4653 case bfd_reloc_outofrange:
4654 abort ();
4658 return ret_val;
4661 /* Finish up dynamic symbol handling. We set the contents of various
4662 dynamic sections here. */
4664 static bfd_boolean
4665 elf64_alpha_finish_dynamic_symbol (bfd *output_bfd, struct bfd_link_info *info,
4666 struct elf_link_hash_entry *h,
4667 Elf_Internal_Sym *sym)
4669 struct alpha_elf_link_hash_entry *ah = (struct alpha_elf_link_hash_entry *)h;
4670 bfd *dynobj = elf_hash_table(info)->dynobj;
4672 if (h->needs_plt)
4674 /* Fill in the .plt entry for this symbol. */
4675 asection *splt, *sgot, *srel;
4676 Elf_Internal_Rela outrel;
4677 bfd_byte *loc;
4678 bfd_vma got_addr, plt_addr;
4679 bfd_vma plt_index;
4680 struct alpha_elf_got_entry *gotent;
4682 BFD_ASSERT (h->dynindx != -1);
4684 splt = bfd_get_section_by_name (dynobj, ".plt");
4685 BFD_ASSERT (splt != NULL);
4686 srel = bfd_get_section_by_name (dynobj, ".rela.plt");
4687 BFD_ASSERT (srel != NULL);
4689 for (gotent = ah->got_entries; gotent ; gotent = gotent->next)
4690 if (gotent->reloc_type == R_ALPHA_LITERAL
4691 && gotent->use_count > 0)
4693 unsigned int insn;
4694 int disp;
4696 sgot = alpha_elf_tdata (gotent->gotobj)->got;
4697 BFD_ASSERT (sgot != NULL);
4699 BFD_ASSERT (gotent->got_offset != -1);
4700 BFD_ASSERT (gotent->plt_offset != -1);
4702 got_addr = (sgot->output_section->vma
4703 + sgot->output_offset
4704 + gotent->got_offset);
4705 plt_addr = (splt->output_section->vma
4706 + splt->output_offset
4707 + gotent->plt_offset);
4709 plt_index = (gotent->plt_offset-PLT_HEADER_SIZE) / PLT_ENTRY_SIZE;
4711 /* Fill in the entry in the procedure linkage table. */
4712 if (elf64_alpha_use_secureplt)
4714 disp = (PLT_HEADER_SIZE - 4) - (gotent->plt_offset + 4);
4715 insn = INSN_AD (INSN_BR, 31, disp);
4716 bfd_put_32 (output_bfd, insn,
4717 splt->contents + gotent->plt_offset);
4719 plt_index = ((gotent->plt_offset - NEW_PLT_HEADER_SIZE)
4720 / NEW_PLT_ENTRY_SIZE);
4722 else
4724 disp = -(gotent->plt_offset + 4);
4725 insn = INSN_AD (INSN_BR, 28, disp);
4726 bfd_put_32 (output_bfd, insn,
4727 splt->contents + gotent->plt_offset);
4728 bfd_put_32 (output_bfd, INSN_UNOP,
4729 splt->contents + gotent->plt_offset + 4);
4730 bfd_put_32 (output_bfd, INSN_UNOP,
4731 splt->contents + gotent->plt_offset + 8);
4733 plt_index = ((gotent->plt_offset - OLD_PLT_HEADER_SIZE)
4734 / OLD_PLT_ENTRY_SIZE);
4737 /* Fill in the entry in the .rela.plt section. */
4738 outrel.r_offset = got_addr;
4739 outrel.r_info = ELF64_R_INFO(h->dynindx, R_ALPHA_JMP_SLOT);
4740 outrel.r_addend = 0;
4742 loc = srel->contents + plt_index * sizeof (Elf64_External_Rela);
4743 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
4745 /* Fill in the entry in the .got. */
4746 bfd_put_64 (output_bfd, plt_addr,
4747 sgot->contents + gotent->got_offset);
4750 else if (alpha_elf_dynamic_symbol_p (h, info))
4752 /* Fill in the dynamic relocations for this symbol's .got entries. */
4753 asection *srel;
4754 struct alpha_elf_got_entry *gotent;
4756 srel = bfd_get_section_by_name (dynobj, ".rela.got");
4757 BFD_ASSERT (srel != NULL);
4759 for (gotent = ((struct alpha_elf_link_hash_entry *) h)->got_entries;
4760 gotent != NULL;
4761 gotent = gotent->next)
4763 asection *sgot;
4764 long r_type;
4766 if (gotent->use_count == 0)
4767 continue;
4769 sgot = alpha_elf_tdata (gotent->gotobj)->got;
4771 r_type = gotent->reloc_type;
4772 switch (r_type)
4774 case R_ALPHA_LITERAL:
4775 r_type = R_ALPHA_GLOB_DAT;
4776 break;
4777 case R_ALPHA_TLSGD:
4778 r_type = R_ALPHA_DTPMOD64;
4779 break;
4780 case R_ALPHA_GOTDTPREL:
4781 r_type = R_ALPHA_DTPREL64;
4782 break;
4783 case R_ALPHA_GOTTPREL:
4784 r_type = R_ALPHA_TPREL64;
4785 break;
4786 case R_ALPHA_TLSLDM:
4787 default:
4788 abort ();
4791 elf64_alpha_emit_dynrel (output_bfd, info, sgot, srel,
4792 gotent->got_offset, h->dynindx,
4793 r_type, gotent->addend);
4795 if (gotent->reloc_type == R_ALPHA_TLSGD)
4796 elf64_alpha_emit_dynrel (output_bfd, info, sgot, srel,
4797 gotent->got_offset + 8, h->dynindx,
4798 R_ALPHA_DTPREL64, gotent->addend);
4802 /* Mark some specially defined symbols as absolute. */
4803 if (strcmp (h->root.root.string, "_DYNAMIC") == 0
4804 || h == elf_hash_table (info)->hgot
4805 || h == elf_hash_table (info)->hplt)
4806 sym->st_shndx = SHN_ABS;
4808 return TRUE;
4811 /* Finish up the dynamic sections. */
4813 static bfd_boolean
4814 elf64_alpha_finish_dynamic_sections (bfd *output_bfd,
4815 struct bfd_link_info *info)
4817 bfd *dynobj;
4818 asection *sdyn;
4820 dynobj = elf_hash_table (info)->dynobj;
4821 sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
4823 if (elf_hash_table (info)->dynamic_sections_created)
4825 asection *splt, *sgotplt, *srelaplt;
4826 Elf64_External_Dyn *dyncon, *dynconend;
4827 bfd_vma plt_vma, gotplt_vma;
4829 splt = bfd_get_section_by_name (dynobj, ".plt");
4830 srelaplt = bfd_get_section_by_name (output_bfd, ".rela.plt");
4831 BFD_ASSERT (splt != NULL && sdyn != NULL);
4833 plt_vma = splt->output_section->vma + splt->output_offset;
4835 gotplt_vma = 0;
4836 if (elf64_alpha_use_secureplt)
4838 sgotplt = bfd_get_section_by_name (dynobj, ".got.plt");
4839 BFD_ASSERT (sgotplt != NULL);
4840 if (sgotplt->size > 0)
4841 gotplt_vma = sgotplt->output_section->vma + sgotplt->output_offset;
4844 dyncon = (Elf64_External_Dyn *) sdyn->contents;
4845 dynconend = (Elf64_External_Dyn *) (sdyn->contents + sdyn->size);
4846 for (; dyncon < dynconend; dyncon++)
4848 Elf_Internal_Dyn dyn;
4850 bfd_elf64_swap_dyn_in (dynobj, dyncon, &dyn);
4852 switch (dyn.d_tag)
4854 case DT_PLTGOT:
4855 dyn.d_un.d_ptr
4856 = elf64_alpha_use_secureplt ? gotplt_vma : plt_vma;
4857 break;
4858 case DT_PLTRELSZ:
4859 dyn.d_un.d_val = srelaplt ? srelaplt->size : 0;
4860 break;
4861 case DT_JMPREL:
4862 dyn.d_un.d_ptr = srelaplt ? srelaplt->vma : 0;
4863 break;
4865 case DT_RELASZ:
4866 /* My interpretation of the TIS v1.1 ELF document indicates
4867 that RELASZ should not include JMPREL. This is not what
4868 the rest of the BFD does. It is, however, what the
4869 glibc ld.so wants. Do this fixup here until we found
4870 out who is right. */
4871 if (srelaplt)
4872 dyn.d_un.d_val -= srelaplt->size;
4873 break;
4876 bfd_elf64_swap_dyn_out (output_bfd, &dyn, dyncon);
4879 /* Initialize the plt header. */
4880 if (splt->size > 0)
4882 unsigned int insn;
4883 int ofs;
4885 if (elf64_alpha_use_secureplt)
4887 ofs = gotplt_vma - (plt_vma + PLT_HEADER_SIZE);
4889 insn = INSN_ABC (INSN_SUBQ, 27, 28, 25);
4890 bfd_put_32 (output_bfd, insn, splt->contents);
4892 insn = INSN_ABO (INSN_LDAH, 28, 28, (ofs + 0x8000) >> 16);
4893 bfd_put_32 (output_bfd, insn, splt->contents + 4);
4895 insn = INSN_ABC (INSN_S4SUBQ, 25, 25, 25);
4896 bfd_put_32 (output_bfd, insn, splt->contents + 8);
4898 insn = INSN_ABO (INSN_LDA, 28, 28, ofs);
4899 bfd_put_32 (output_bfd, insn, splt->contents + 12);
4901 insn = INSN_ABO (INSN_LDQ, 27, 28, 0);
4902 bfd_put_32 (output_bfd, insn, splt->contents + 16);
4904 insn = INSN_ABC (INSN_ADDQ, 25, 25, 25);
4905 bfd_put_32 (output_bfd, insn, splt->contents + 20);
4907 insn = INSN_ABO (INSN_LDQ, 28, 28, 8);
4908 bfd_put_32 (output_bfd, insn, splt->contents + 24);
4910 insn = INSN_AB (INSN_JMP, 31, 27);
4911 bfd_put_32 (output_bfd, insn, splt->contents + 28);
4913 insn = INSN_AD (INSN_BR, 28, -PLT_HEADER_SIZE);
4914 bfd_put_32 (output_bfd, insn, splt->contents + 32);
4916 else
4918 insn = INSN_AD (INSN_BR, 27, 0); /* br $27, .+4 */
4919 bfd_put_32 (output_bfd, insn, splt->contents);
4921 insn = INSN_ABO (INSN_LDQ, 27, 27, 12);
4922 bfd_put_32 (output_bfd, insn, splt->contents + 4);
4924 insn = INSN_UNOP;
4925 bfd_put_32 (output_bfd, insn, splt->contents + 8);
4927 insn = INSN_AB (INSN_JMP, 27, 27);
4928 bfd_put_32 (output_bfd, insn, splt->contents + 12);
4930 /* The next two words will be filled in by ld.so. */
4931 bfd_put_64 (output_bfd, 0, splt->contents + 16);
4932 bfd_put_64 (output_bfd, 0, splt->contents + 24);
4935 elf_section_data (splt->output_section)->this_hdr.sh_entsize = 0;
4939 return TRUE;
4942 /* We need to use a special link routine to handle the .mdebug section.
4943 We need to merge all instances of these sections together, not write
4944 them all out sequentially. */
4946 static bfd_boolean
4947 elf64_alpha_final_link (bfd *abfd, struct bfd_link_info *info)
4949 asection *o;
4950 struct bfd_link_order *p;
4951 asection *mdebug_sec;
4952 struct ecoff_debug_info debug;
4953 const struct ecoff_debug_swap *swap
4954 = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
4955 HDRR *symhdr = &debug.symbolic_header;
4956 PTR mdebug_handle = NULL;
4958 /* Go through the sections and collect the mdebug information. */
4959 mdebug_sec = NULL;
4960 for (o = abfd->sections; o != (asection *) NULL; o = o->next)
4962 if (strcmp (o->name, ".mdebug") == 0)
4964 struct extsym_info einfo;
4966 /* We have found the .mdebug section in the output file.
4967 Look through all the link_orders comprising it and merge
4968 the information together. */
4969 symhdr->magic = swap->sym_magic;
4970 /* FIXME: What should the version stamp be? */
4971 symhdr->vstamp = 0;
4972 symhdr->ilineMax = 0;
4973 symhdr->cbLine = 0;
4974 symhdr->idnMax = 0;
4975 symhdr->ipdMax = 0;
4976 symhdr->isymMax = 0;
4977 symhdr->ioptMax = 0;
4978 symhdr->iauxMax = 0;
4979 symhdr->issMax = 0;
4980 symhdr->issExtMax = 0;
4981 symhdr->ifdMax = 0;
4982 symhdr->crfd = 0;
4983 symhdr->iextMax = 0;
4985 /* We accumulate the debugging information itself in the
4986 debug_info structure. */
4987 debug.line = NULL;
4988 debug.external_dnr = NULL;
4989 debug.external_pdr = NULL;
4990 debug.external_sym = NULL;
4991 debug.external_opt = NULL;
4992 debug.external_aux = NULL;
4993 debug.ss = NULL;
4994 debug.ssext = debug.ssext_end = NULL;
4995 debug.external_fdr = NULL;
4996 debug.external_rfd = NULL;
4997 debug.external_ext = debug.external_ext_end = NULL;
4999 mdebug_handle = bfd_ecoff_debug_init (abfd, &debug, swap, info);
5000 if (mdebug_handle == (PTR) NULL)
5001 return FALSE;
5003 if (1)
5005 asection *s;
5006 EXTR esym;
5007 bfd_vma last = 0;
5008 unsigned int i;
5009 static const char * const name[] =
5011 ".text", ".init", ".fini", ".data",
5012 ".rodata", ".sdata", ".sbss", ".bss"
5014 static const int sc[] = { scText, scInit, scFini, scData,
5015 scRData, scSData, scSBss, scBss };
5017 esym.jmptbl = 0;
5018 esym.cobol_main = 0;
5019 esym.weakext = 0;
5020 esym.reserved = 0;
5021 esym.ifd = ifdNil;
5022 esym.asym.iss = issNil;
5023 esym.asym.st = stLocal;
5024 esym.asym.reserved = 0;
5025 esym.asym.index = indexNil;
5026 for (i = 0; i < 8; i++)
5028 esym.asym.sc = sc[i];
5029 s = bfd_get_section_by_name (abfd, name[i]);
5030 if (s != NULL)
5032 esym.asym.value = s->vma;
5033 last = s->vma + s->size;
5035 else
5036 esym.asym.value = last;
5038 if (! bfd_ecoff_debug_one_external (abfd, &debug, swap,
5039 name[i], &esym))
5040 return FALSE;
5044 for (p = o->map_head.link_order;
5045 p != (struct bfd_link_order *) NULL;
5046 p = p->next)
5048 asection *input_section;
5049 bfd *input_bfd;
5050 const struct ecoff_debug_swap *input_swap;
5051 struct ecoff_debug_info input_debug;
5052 char *eraw_src;
5053 char *eraw_end;
5055 if (p->type != bfd_indirect_link_order)
5057 if (p->type == bfd_data_link_order)
5058 continue;
5059 abort ();
5062 input_section = p->u.indirect.section;
5063 input_bfd = input_section->owner;
5065 if (! is_alpha_elf (input_bfd))
5066 /* I don't know what a non ALPHA ELF bfd would be
5067 doing with a .mdebug section, but I don't really
5068 want to deal with it. */
5069 continue;
5071 input_swap = (get_elf_backend_data (input_bfd)
5072 ->elf_backend_ecoff_debug_swap);
5074 BFD_ASSERT (p->size == input_section->size);
5076 /* The ECOFF linking code expects that we have already
5077 read in the debugging information and set up an
5078 ecoff_debug_info structure, so we do that now. */
5079 if (!elf64_alpha_read_ecoff_info (input_bfd, input_section,
5080 &input_debug))
5081 return FALSE;
5083 if (! (bfd_ecoff_debug_accumulate
5084 (mdebug_handle, abfd, &debug, swap, input_bfd,
5085 &input_debug, input_swap, info)))
5086 return FALSE;
5088 /* Loop through the external symbols. For each one with
5089 interesting information, try to find the symbol in
5090 the linker global hash table and save the information
5091 for the output external symbols. */
5092 eraw_src = input_debug.external_ext;
5093 eraw_end = (eraw_src
5094 + (input_debug.symbolic_header.iextMax
5095 * input_swap->external_ext_size));
5096 for (;
5097 eraw_src < eraw_end;
5098 eraw_src += input_swap->external_ext_size)
5100 EXTR ext;
5101 const char *name;
5102 struct alpha_elf_link_hash_entry *h;
5104 (*input_swap->swap_ext_in) (input_bfd, (PTR) eraw_src, &ext);
5105 if (ext.asym.sc == scNil
5106 || ext.asym.sc == scUndefined
5107 || ext.asym.sc == scSUndefined)
5108 continue;
5110 name = input_debug.ssext + ext.asym.iss;
5111 h = alpha_elf_link_hash_lookup (alpha_elf_hash_table (info),
5112 name, FALSE, FALSE, TRUE);
5113 if (h == NULL || h->esym.ifd != -2)
5114 continue;
5116 if (ext.ifd != -1)
5118 BFD_ASSERT (ext.ifd
5119 < input_debug.symbolic_header.ifdMax);
5120 ext.ifd = input_debug.ifdmap[ext.ifd];
5123 h->esym = ext;
5126 /* Free up the information we just read. */
5127 free (input_debug.line);
5128 free (input_debug.external_dnr);
5129 free (input_debug.external_pdr);
5130 free (input_debug.external_sym);
5131 free (input_debug.external_opt);
5132 free (input_debug.external_aux);
5133 free (input_debug.ss);
5134 free (input_debug.ssext);
5135 free (input_debug.external_fdr);
5136 free (input_debug.external_rfd);
5137 free (input_debug.external_ext);
5139 /* Hack: reset the SEC_HAS_CONTENTS flag so that
5140 elf_link_input_bfd ignores this section. */
5141 input_section->flags &=~ SEC_HAS_CONTENTS;
5144 /* Build the external symbol information. */
5145 einfo.abfd = abfd;
5146 einfo.info = info;
5147 einfo.debug = &debug;
5148 einfo.swap = swap;
5149 einfo.failed = FALSE;
5150 elf_link_hash_traverse (elf_hash_table (info),
5151 elf64_alpha_output_extsym,
5152 (PTR) &einfo);
5153 if (einfo.failed)
5154 return FALSE;
5156 /* Set the size of the .mdebug section. */
5157 o->size = bfd_ecoff_debug_size (abfd, &debug, swap);
5159 /* Skip this section later on (I don't think this currently
5160 matters, but someday it might). */
5161 o->map_head.link_order = (struct bfd_link_order *) NULL;
5163 mdebug_sec = o;
5167 /* Invoke the regular ELF backend linker to do all the work. */
5168 if (! bfd_elf_final_link (abfd, info))
5169 return FALSE;
5171 /* Now write out the computed sections. */
5173 /* The .got subsections... */
5175 bfd *i, *dynobj = elf_hash_table(info)->dynobj;
5176 for (i = alpha_elf_hash_table(info)->got_list;
5177 i != NULL;
5178 i = alpha_elf_tdata(i)->got_link_next)
5180 asection *sgot;
5182 /* elf_bfd_final_link already did everything in dynobj. */
5183 if (i == dynobj)
5184 continue;
5186 sgot = alpha_elf_tdata(i)->got;
5187 if (! bfd_set_section_contents (abfd, sgot->output_section,
5188 sgot->contents,
5189 (file_ptr) sgot->output_offset,
5190 sgot->size))
5191 return FALSE;
5195 if (mdebug_sec != (asection *) NULL)
5197 BFD_ASSERT (abfd->output_has_begun);
5198 if (! bfd_ecoff_write_accumulated_debug (mdebug_handle, abfd, &debug,
5199 swap, info,
5200 mdebug_sec->filepos))
5201 return FALSE;
5203 bfd_ecoff_debug_free (mdebug_handle, abfd, &debug, swap, info);
5206 return TRUE;
5209 static enum elf_reloc_type_class
5210 elf64_alpha_reloc_type_class (const Elf_Internal_Rela *rela)
5212 switch ((int) ELF64_R_TYPE (rela->r_info))
5214 case R_ALPHA_RELATIVE:
5215 return reloc_class_relative;
5216 case R_ALPHA_JMP_SLOT:
5217 return reloc_class_plt;
5218 case R_ALPHA_COPY:
5219 return reloc_class_copy;
5220 default:
5221 return reloc_class_normal;
5225 static const struct bfd_elf_special_section elf64_alpha_special_sections[] =
5227 { STRING_COMMA_LEN (".sbss"), -2, SHT_NOBITS, SHF_ALLOC + SHF_WRITE + SHF_ALPHA_GPREL },
5228 { STRING_COMMA_LEN (".sdata"), -2, SHT_PROGBITS, SHF_ALLOC + SHF_WRITE + SHF_ALPHA_GPREL },
5229 { NULL, 0, 0, 0, 0 }
5232 /* ECOFF swapping routines. These are used when dealing with the
5233 .mdebug section, which is in the ECOFF debugging format. Copied
5234 from elf32-mips.c. */
5235 static const struct ecoff_debug_swap
5236 elf64_alpha_ecoff_debug_swap =
5238 /* Symbol table magic number. */
5239 magicSym2,
5240 /* Alignment of debugging information. E.g., 4. */
5242 /* Sizes of external symbolic information. */
5243 sizeof (struct hdr_ext),
5244 sizeof (struct dnr_ext),
5245 sizeof (struct pdr_ext),
5246 sizeof (struct sym_ext),
5247 sizeof (struct opt_ext),
5248 sizeof (struct fdr_ext),
5249 sizeof (struct rfd_ext),
5250 sizeof (struct ext_ext),
5251 /* Functions to swap in external symbolic data. */
5252 ecoff_swap_hdr_in,
5253 ecoff_swap_dnr_in,
5254 ecoff_swap_pdr_in,
5255 ecoff_swap_sym_in,
5256 ecoff_swap_opt_in,
5257 ecoff_swap_fdr_in,
5258 ecoff_swap_rfd_in,
5259 ecoff_swap_ext_in,
5260 _bfd_ecoff_swap_tir_in,
5261 _bfd_ecoff_swap_rndx_in,
5262 /* Functions to swap out external symbolic data. */
5263 ecoff_swap_hdr_out,
5264 ecoff_swap_dnr_out,
5265 ecoff_swap_pdr_out,
5266 ecoff_swap_sym_out,
5267 ecoff_swap_opt_out,
5268 ecoff_swap_fdr_out,
5269 ecoff_swap_rfd_out,
5270 ecoff_swap_ext_out,
5271 _bfd_ecoff_swap_tir_out,
5272 _bfd_ecoff_swap_rndx_out,
5273 /* Function to read in symbolic data. */
5274 elf64_alpha_read_ecoff_info
5277 /* Use a non-standard hash bucket size of 8. */
5279 static const struct elf_size_info alpha_elf_size_info =
5281 sizeof (Elf64_External_Ehdr),
5282 sizeof (Elf64_External_Phdr),
5283 sizeof (Elf64_External_Shdr),
5284 sizeof (Elf64_External_Rel),
5285 sizeof (Elf64_External_Rela),
5286 sizeof (Elf64_External_Sym),
5287 sizeof (Elf64_External_Dyn),
5288 sizeof (Elf_External_Note),
5291 64, 3,
5292 ELFCLASS64, EV_CURRENT,
5293 bfd_elf64_write_out_phdrs,
5294 bfd_elf64_write_shdrs_and_ehdr,
5295 bfd_elf64_checksum_contents,
5296 bfd_elf64_write_relocs,
5297 bfd_elf64_swap_symbol_in,
5298 bfd_elf64_swap_symbol_out,
5299 bfd_elf64_slurp_reloc_table,
5300 bfd_elf64_slurp_symbol_table,
5301 bfd_elf64_swap_dyn_in,
5302 bfd_elf64_swap_dyn_out,
5303 bfd_elf64_swap_reloc_in,
5304 bfd_elf64_swap_reloc_out,
5305 bfd_elf64_swap_reloca_in,
5306 bfd_elf64_swap_reloca_out
5309 #define TARGET_LITTLE_SYM bfd_elf64_alpha_vec
5310 #define TARGET_LITTLE_NAME "elf64-alpha"
5311 #define ELF_ARCH bfd_arch_alpha
5312 #define ELF_MACHINE_CODE EM_ALPHA
5313 #define ELF_MAXPAGESIZE 0x10000
5314 #define ELF_COMMONPAGESIZE 0x2000
5316 #define bfd_elf64_bfd_link_hash_table_create \
5317 elf64_alpha_bfd_link_hash_table_create
5319 #define bfd_elf64_bfd_reloc_type_lookup \
5320 elf64_alpha_bfd_reloc_type_lookup
5321 #define bfd_elf64_bfd_reloc_name_lookup \
5322 elf64_alpha_bfd_reloc_name_lookup
5323 #define elf_info_to_howto \
5324 elf64_alpha_info_to_howto
5326 #define bfd_elf64_mkobject \
5327 elf64_alpha_mkobject
5328 #define elf_backend_object_p \
5329 elf64_alpha_object_p
5331 #define elf_backend_section_from_shdr \
5332 elf64_alpha_section_from_shdr
5333 #define elf_backend_section_flags \
5334 elf64_alpha_section_flags
5335 #define elf_backend_fake_sections \
5336 elf64_alpha_fake_sections
5338 #define bfd_elf64_bfd_is_local_label_name \
5339 elf64_alpha_is_local_label_name
5340 #define bfd_elf64_find_nearest_line \
5341 elf64_alpha_find_nearest_line
5342 #define bfd_elf64_bfd_relax_section \
5343 elf64_alpha_relax_section
5345 #define elf_backend_add_symbol_hook \
5346 elf64_alpha_add_symbol_hook
5347 #define elf_backend_relocs_compatible \
5348 _bfd_elf_relocs_compatible
5349 #define elf_backend_check_relocs \
5350 elf64_alpha_check_relocs
5351 #define elf_backend_create_dynamic_sections \
5352 elf64_alpha_create_dynamic_sections
5353 #define elf_backend_adjust_dynamic_symbol \
5354 elf64_alpha_adjust_dynamic_symbol
5355 #define elf_backend_merge_symbol_attribute \
5356 elf64_alpha_merge_symbol_attribute
5357 #define elf_backend_always_size_sections \
5358 elf64_alpha_always_size_sections
5359 #define elf_backend_size_dynamic_sections \
5360 elf64_alpha_size_dynamic_sections
5361 #define elf_backend_omit_section_dynsym \
5362 ((bfd_boolean (*) (bfd *, struct bfd_link_info *, asection *)) bfd_true)
5363 #define elf_backend_relocate_section \
5364 elf64_alpha_relocate_section
5365 #define elf_backend_finish_dynamic_symbol \
5366 elf64_alpha_finish_dynamic_symbol
5367 #define elf_backend_finish_dynamic_sections \
5368 elf64_alpha_finish_dynamic_sections
5369 #define bfd_elf64_bfd_final_link \
5370 elf64_alpha_final_link
5371 #define elf_backend_reloc_type_class \
5372 elf64_alpha_reloc_type_class
5374 #define elf_backend_ecoff_debug_swap \
5375 &elf64_alpha_ecoff_debug_swap
5377 #define elf_backend_size_info \
5378 alpha_elf_size_info
5380 #define elf_backend_special_sections \
5381 elf64_alpha_special_sections
5383 /* A few constants that determine how the .plt section is set up. */
5384 #define elf_backend_want_got_plt 0
5385 #define elf_backend_plt_readonly 0
5386 #define elf_backend_want_plt_sym 1
5387 #define elf_backend_got_header_size 0
5389 #include "elf64-target.h"
5391 /* FreeBSD support. */
5393 #undef TARGET_LITTLE_SYM
5394 #define TARGET_LITTLE_SYM bfd_elf64_alpha_freebsd_vec
5395 #undef TARGET_LITTLE_NAME
5396 #define TARGET_LITTLE_NAME "elf64-alpha-freebsd"
5397 #undef ELF_OSABI
5398 #define ELF_OSABI ELFOSABI_FREEBSD
5400 /* The kernel recognizes executables as valid only if they carry a
5401 "FreeBSD" label in the ELF header. So we put this label on all
5402 executables and (for simplicity) also all other object files. */
5404 static void
5405 elf64_alpha_fbsd_post_process_headers (bfd * abfd,
5406 struct bfd_link_info * link_info ATTRIBUTE_UNUSED)
5408 Elf_Internal_Ehdr * i_ehdrp; /* ELF file header, internal form. */
5410 i_ehdrp = elf_elfheader (abfd);
5412 /* Put an ABI label supported by FreeBSD >= 4.1. */
5413 i_ehdrp->e_ident[EI_OSABI] = get_elf_backend_data (abfd)->elf_osabi;
5414 #ifdef OLD_FREEBSD_ABI_LABEL
5415 /* The ABI label supported by FreeBSD <= 4.0 is quite nonstandard. */
5416 memcpy (&i_ehdrp->e_ident[EI_ABIVERSION], "FreeBSD", 8);
5417 #endif
5420 #undef elf_backend_post_process_headers
5421 #define elf_backend_post_process_headers \
5422 elf64_alpha_fbsd_post_process_headers
5424 #undef elf64_bed
5425 #define elf64_bed elf64_alpha_fbsd_bed
5427 #include "elf64-target.h"