]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blame - bfd/elf64-alpha.c
*** empty log message ***
[thirdparty/binutils-gdb.git] / bfd / elf64-alpha.c
CommitLineData
252b5132 1/* Alpha specific support for 64-bit ELF
571fe01f 2 Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003
7898deda 3 Free Software Foundation, Inc.
252b5132
RH
4 Contributed by Richard Henderson <rth@tamu.edu>.
5
571fe01f 6 This file is part of BFD, the Binary File Descriptor library.
252b5132 7
571fe01f
NC
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
252b5132 12
571fe01f
NC
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.
252b5132 17
571fe01f
NC
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
252b5132
RH
21
22/* We need a published ABI spec for this. Until one comes out, don't
23 assume this'll remain unchanged forever. */
24
25#include "bfd.h"
26#include "sysdep.h"
27#include "libbfd.h"
28#include "elf-bfd.h"
29
30#include "elf/alpha.h"
31
32#define ALPHAECOFF
33
34#define NO_COFF_RELOCS
35#define NO_COFF_SYMBOLS
36#define NO_COFF_LINENOS
37
fe8bc63d 38/* Get the ECOFF swapping routines. Needed for the debug information. */
252b5132
RH
39#include "coff/internal.h"
40#include "coff/sym.h"
41#include "coff/symconst.h"
42#include "coff/ecoff.h"
43#include "coff/alpha.h"
44#include "aout/ar.h"
45#include "libcoff.h"
46#include "libecoff.h"
47#define ECOFF_64
48#include "ecoffswap.h"
49
8fb35fed 50static int alpha_elf_dynamic_symbol_p
571fe01f 51 PARAMS ((struct elf_link_hash_entry *, struct bfd_link_info *));
252b5132 52static struct bfd_hash_entry * elf64_alpha_link_hash_newfunc
571fe01f 53 PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
252b5132 54static struct bfd_link_hash_table * elf64_alpha_bfd_link_hash_table_create
571fe01f 55 PARAMS ((bfd *));
252b5132
RH
56
57static bfd_reloc_status_type elf64_alpha_reloc_nil
571fe01f 58 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
252b5132 59static bfd_reloc_status_type elf64_alpha_reloc_bad
571fe01f 60 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
252b5132 61static bfd_reloc_status_type elf64_alpha_do_reloc_gpdisp
571fe01f 62 PARAMS ((bfd *, bfd_vma, bfd_byte *, bfd_byte *));
252b5132 63static bfd_reloc_status_type elf64_alpha_reloc_gpdisp
571fe01f 64 PARAMS ((bfd *, arelent *, asymbol *, PTR, asection *, bfd *, char **));
252b5132
RH
65
66static reloc_howto_type * elf64_alpha_bfd_reloc_type_lookup
571fe01f 67 PARAMS ((bfd *, bfd_reloc_code_real_type));
252b5132 68static void elf64_alpha_info_to_howto
571fe01f 69 PARAMS ((bfd *, arelent *, Elf_Internal_Rela *));
252b5132 70
b34976b6 71static bfd_boolean elf64_alpha_mkobject
571fe01f 72 PARAMS ((bfd *));
b34976b6 73static bfd_boolean elf64_alpha_object_p
571fe01f 74 PARAMS ((bfd *));
b34976b6 75static bfd_boolean elf64_alpha_section_from_shdr
571fe01f 76 PARAMS ((bfd *, Elf_Internal_Shdr *, const char *));
b34976b6 77static bfd_boolean elf64_alpha_section_flags
571fe01f 78 PARAMS ((flagword *, Elf_Internal_Shdr *));
b34976b6 79static bfd_boolean elf64_alpha_fake_sections
571fe01f 80 PARAMS ((bfd *, Elf_Internal_Shdr *, asection *));
b34976b6 81static bfd_boolean elf64_alpha_create_got_section
571fe01f 82 PARAMS ((bfd *, struct bfd_link_info *));
b34976b6 83static bfd_boolean elf64_alpha_create_dynamic_sections
571fe01f 84 PARAMS ((bfd *, struct bfd_link_info *));
252b5132 85
b34976b6 86static bfd_boolean elf64_alpha_read_ecoff_info
571fe01f 87 PARAMS ((bfd *, asection *, struct ecoff_debug_info *));
b34976b6 88static bfd_boolean elf64_alpha_is_local_label_name
571fe01f 89 PARAMS ((bfd *, const char *));
b34976b6 90static bfd_boolean elf64_alpha_find_nearest_line
571fe01f
NC
91 PARAMS ((bfd *, asection *, asymbol **, bfd_vma, const char **,
92 const char **, unsigned int *));
252b5132
RH
93
94#if defined(__STDC__) || defined(ALMOST_STDC)
95struct alpha_elf_link_hash_entry;
96#endif
97
b34976b6 98static bfd_boolean elf64_alpha_output_extsym
571fe01f 99 PARAMS ((struct alpha_elf_link_hash_entry *, PTR));
252b5132 100
b34976b6 101static bfd_boolean elf64_alpha_can_merge_gots
571fe01f 102 PARAMS ((bfd *, bfd *));
252b5132 103static void elf64_alpha_merge_gots
571fe01f 104 PARAMS ((bfd *, bfd *));
b34976b6 105static bfd_boolean elf64_alpha_calc_got_offsets_for_symbol
252b5132 106 PARAMS ((struct alpha_elf_link_hash_entry *, PTR));
b34976b6 107static void elf64_alpha_calc_got_offsets
f44f99a5 108 PARAMS ((struct bfd_link_info *));
b34976b6 109static bfd_boolean elf64_alpha_size_got_sections
f44f99a5 110 PARAMS ((struct bfd_link_info *));
b34976b6
AM
111static bfd_boolean elf64_alpha_size_plt_section
112 PARAMS ((struct bfd_link_info *));
113static bfd_boolean elf64_alpha_size_plt_section_1
f44f99a5 114 PARAMS ((struct alpha_elf_link_hash_entry *, PTR));
b34976b6 115static bfd_boolean elf64_alpha_always_size_sections
252b5132 116 PARAMS ((bfd *, struct bfd_link_info *));
3765b1be
RH
117static int alpha_dynamic_entries_for_reloc
118 PARAMS ((int, int, int));
b34976b6 119static bfd_boolean elf64_alpha_calc_dynrel_sizes
252b5132 120 PARAMS ((struct alpha_elf_link_hash_entry *, struct bfd_link_info *));
b34976b6 121static bfd_boolean elf64_alpha_size_rela_got_section
f44f99a5 122 PARAMS ((struct bfd_link_info *));
b34976b6 123static bfd_boolean elf64_alpha_size_rela_got_1
f44f99a5 124 PARAMS ((struct alpha_elf_link_hash_entry *, struct bfd_link_info *));
b34976b6 125static bfd_boolean elf64_alpha_add_symbol_hook
252b5132
RH
126 PARAMS ((bfd *, struct bfd_link_info *, const Elf_Internal_Sym *,
127 const char **, flagword *, asection **, bfd_vma *));
3765b1be
RH
128static struct alpha_elf_got_entry *get_got_entry
129 PARAMS ((bfd *, struct alpha_elf_link_hash_entry *, unsigned long,
130 unsigned long, bfd_vma));
b34976b6 131static bfd_boolean elf64_alpha_check_relocs
571fe01f 132 PARAMS ((bfd *, struct bfd_link_info *, asection *sec,
252b5132 133 const Elf_Internal_Rela *));
b34976b6 134static bfd_boolean elf64_alpha_adjust_dynamic_symbol
571fe01f 135 PARAMS ((struct bfd_link_info *, struct elf_link_hash_entry *));
b34976b6 136static bfd_boolean elf64_alpha_size_dynamic_sections
571fe01f 137 PARAMS ((bfd *, struct bfd_link_info *));
b34976b6 138static bfd_boolean elf64_alpha_relocate_section_r
571fe01f
NC
139 PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
140 Elf_Internal_Rela *, Elf_Internal_Sym *, asection **));
b34976b6 141static bfd_boolean elf64_alpha_relocate_section
571fe01f 142 PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
252b5132 143 Elf_Internal_Rela *, Elf_Internal_Sym *, asection **));
b34976b6 144static bfd_boolean elf64_alpha_finish_dynamic_symbol
571fe01f
NC
145 PARAMS ((bfd *, struct bfd_link_info *, struct elf_link_hash_entry *,
146 Elf_Internal_Sym *));
b34976b6 147static bfd_boolean elf64_alpha_finish_dynamic_sections
571fe01f 148 PARAMS ((bfd *, struct bfd_link_info *));
b34976b6 149static bfd_boolean elf64_alpha_final_link
571fe01f 150 PARAMS ((bfd *, struct bfd_link_info *));
b34976b6 151static bfd_boolean elf64_alpha_merge_ind_symbols
571fe01f 152 PARAMS ((struct alpha_elf_link_hash_entry *, PTR));
cd6f9321
L
153static Elf_Internal_Rela * elf64_alpha_find_reloc_at_ofs
154 PARAMS ((Elf_Internal_Rela *, Elf_Internal_Rela *, bfd_vma, int));
fcfbdf31 155static enum elf_reloc_type_class elf64_alpha_reloc_type_class
f51e552e 156 PARAMS ((const Elf_Internal_Rela *));
252b5132
RH
157\f
158struct alpha_elf_link_hash_entry
159{
160 struct elf_link_hash_entry root;
161
162 /* External symbol information. */
163 EXTR esym;
164
165 /* Cumulative flags for all the .got entries. */
166 int flags;
167
9e756d64 168 /* Contexts in which a literal was referenced. */
3765b1be
RH
169#define ALPHA_ELF_LINK_HASH_LU_ADDR 0x01
170#define ALPHA_ELF_LINK_HASH_LU_MEM 0x02
171#define ALPHA_ELF_LINK_HASH_LU_BYTE 0x04
172#define ALPHA_ELF_LINK_HASH_LU_JSR 0x08
173#define ALPHA_ELF_LINK_HASH_LU_TLSGD 0x10
174#define ALPHA_ELF_LINK_HASH_LU_TLSLDM 0x20
175#define ALPHA_ELF_LINK_HASH_LU_FUNC 0x38
9e756d64 176#define ALPHA_ELF_LINK_HASH_TLS_IE 0x40
252b5132
RH
177
178 /* Used to implement multiple .got subsections. */
179 struct alpha_elf_got_entry
180 {
181 struct alpha_elf_got_entry *next;
182
571fe01f 183 /* Which .got subsection? */
252b5132
RH
184 bfd *gotobj;
185
571fe01f 186 /* The addend in effect for this entry. */
dc810e39 187 bfd_vma addend;
252b5132 188
571fe01f 189 /* The .got offset for this entry. */
252b5132
RH
190 int got_offset;
191
3765b1be
RH
192 /* How many references to this entry? */
193 int use_count;
252b5132 194
3765b1be
RH
195 /* The relocation type of this entry. */
196 unsigned char reloc_type;
252b5132 197
3765b1be
RH
198 /* How a LITERAL is used. */
199 unsigned char flags;
200
201 /* Have we initialized the dynamic relocation for this entry? */
202 unsigned char reloc_done;
203
204 /* Have we adjusted this entry for SEC_MERGE? */
205 unsigned char reloc_xlated;
252b5132
RH
206 } *got_entries;
207
571fe01f 208 /* Used to count non-got, non-plt relocations for delayed sizing
252b5132
RH
209 of relocation sections. */
210 struct alpha_elf_reloc_entry
211 {
212 struct alpha_elf_reloc_entry *next;
213
571fe01f 214 /* Which .reloc section? */
252b5132
RH
215 asection *srel;
216
571fe01f 217 /* What kind of relocation? */
fcfbdf31
JJ
218 unsigned int rtype;
219
571fe01f 220 /* Is this against read-only section? */
fcfbdf31 221 unsigned int reltext : 1;
252b5132 222
571fe01f 223 /* How many did we find? */
252b5132
RH
224 unsigned long count;
225 } *reloc_entries;
226};
227
228/* Alpha ELF linker hash table. */
229
230struct alpha_elf_link_hash_table
231{
232 struct elf_link_hash_table root;
233
234 /* The head of a list of .got subsections linked through
235 alpha_elf_tdata(abfd)->got_link_next. */
236 bfd *got_list;
237};
238
239/* Look up an entry in a Alpha ELF linker hash table. */
240
241#define alpha_elf_link_hash_lookup(table, string, create, copy, follow) \
242 ((struct alpha_elf_link_hash_entry *) \
243 elf_link_hash_lookup (&(table)->root, (string), (create), \
244 (copy), (follow)))
245
246/* Traverse a Alpha ELF linker hash table. */
247
248#define alpha_elf_link_hash_traverse(table, func, info) \
249 (elf_link_hash_traverse \
250 (&(table)->root, \
b34976b6 251 (bfd_boolean (*) PARAMS ((struct elf_link_hash_entry *, PTR))) (func), \
252b5132
RH
252 (info)))
253
254/* Get the Alpha ELF linker hash table from a link_info structure. */
255
256#define alpha_elf_hash_table(p) \
257 ((struct alpha_elf_link_hash_table *) ((p)->hash))
258
259/* Get the object's symbols as our own entry type. */
260
261#define alpha_elf_sym_hashes(abfd) \
262 ((struct alpha_elf_link_hash_entry **)elf_sym_hashes(abfd))
263
264/* Should we do dynamic things to this symbol? */
265
8fb35fed
RH
266static int
267alpha_elf_dynamic_symbol_p (h, info)
268 struct elf_link_hash_entry *h;
269 struct bfd_link_info *info;
270{
271 if (h == NULL)
b34976b6 272 return FALSE;
8fb35fed
RH
273
274 while (h->root.type == bfd_link_hash_indirect
275 || h->root.type == bfd_link_hash_warning)
276 h = (struct elf_link_hash_entry *) h->root.u.i.link;
277
278 if (h->dynindx == -1)
b34976b6 279 return FALSE;
ca88208a
RH
280
281 if (h->root.type == bfd_link_hash_undefweak
282 || h->root.type == bfd_link_hash_defweak)
b34976b6 283 return TRUE;
ca88208a 284
2719f880
L
285 switch (ELF_ST_VISIBILITY (h->other))
286 {
ca88208a
RH
287 case STV_DEFAULT:
288 break;
2719f880 289 case STV_HIDDEN:
ca88208a 290 case STV_INTERNAL:
b34976b6 291 return FALSE;
ca88208a
RH
292 case STV_PROTECTED:
293 if (h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR)
b34976b6 294 return FALSE;
ca88208a 295 break;
2719f880 296 }
8fb35fed 297
8fb35fed
RH
298 if ((info->shared && !info->symbolic)
299 || ((h->elf_link_hash_flags
300 & (ELF_LINK_HASH_DEF_DYNAMIC | ELF_LINK_HASH_REF_REGULAR))
301 == (ELF_LINK_HASH_DEF_DYNAMIC | ELF_LINK_HASH_REF_REGULAR)))
b34976b6 302 return TRUE;
8fb35fed 303
b34976b6 304 return FALSE;
8fb35fed 305}
252b5132
RH
306
307/* Create an entry in a Alpha ELF linker hash table. */
308
309static struct bfd_hash_entry *
310elf64_alpha_link_hash_newfunc (entry, table, string)
311 struct bfd_hash_entry *entry;
312 struct bfd_hash_table *table;
313 const char *string;
314{
315 struct alpha_elf_link_hash_entry *ret =
316 (struct alpha_elf_link_hash_entry *) entry;
317
318 /* Allocate the structure if it has not already been allocated by a
319 subclass. */
320 if (ret == (struct alpha_elf_link_hash_entry *) NULL)
321 ret = ((struct alpha_elf_link_hash_entry *)
322 bfd_hash_allocate (table,
323 sizeof (struct alpha_elf_link_hash_entry)));
324 if (ret == (struct alpha_elf_link_hash_entry *) NULL)
325 return (struct bfd_hash_entry *) ret;
326
327 /* Call the allocation method of the superclass. */
328 ret = ((struct alpha_elf_link_hash_entry *)
329 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
330 table, string));
331 if (ret != (struct alpha_elf_link_hash_entry *) NULL)
332 {
333 /* Set local fields. */
334 memset (&ret->esym, 0, sizeof (EXTR));
335 /* We use -2 as a marker to indicate that the information has
336 not been set. -1 means there is no associated ifd. */
337 ret->esym.ifd = -2;
338 ret->flags = 0;
339 ret->got_entries = NULL;
340 ret->reloc_entries = NULL;
341 }
342
343 return (struct bfd_hash_entry *) ret;
344}
345
346/* Create a Alpha ELF linker hash table. */
347
348static struct bfd_link_hash_table *
349elf64_alpha_bfd_link_hash_table_create (abfd)
350 bfd *abfd;
351{
352 struct alpha_elf_link_hash_table *ret;
dc810e39 353 bfd_size_type amt = sizeof (struct alpha_elf_link_hash_table);
252b5132 354
e2d34d7d 355 ret = (struct alpha_elf_link_hash_table *) bfd_zmalloc (amt);
252b5132
RH
356 if (ret == (struct alpha_elf_link_hash_table *) NULL)
357 return NULL;
358
359 if (! _bfd_elf_link_hash_table_init (&ret->root, abfd,
360 elf64_alpha_link_hash_newfunc))
361 {
e2d34d7d 362 free (ret);
252b5132
RH
363 return NULL;
364 }
365
366 return &ret->root.root;
367}
368\f
369/* We have some private fields hanging off of the elf_tdata structure. */
370
371struct alpha_elf_obj_tdata
372{
373 struct elf_obj_tdata root;
374
375 /* For every input file, these are the got entries for that object's
376 local symbols. */
377 struct alpha_elf_got_entry ** local_got_entries;
378
379 /* For every input file, this is the object that owns the got that
380 this input file uses. */
381 bfd *gotobj;
382
383 /* For every got, this is a linked list through the objects using this got */
384 bfd *in_got_link_next;
385
386 /* For every got, this is a link to the next got subsegment. */
387 bfd *got_link_next;
388
389 /* For every got, this is the section. */
390 asection *got;
391
3765b1be
RH
392 /* For every got, this is it's total number of words. */
393 int total_got_size;
252b5132 394
3765b1be 395 /* For every got, this is the sum of the number of words required
252b5132 396 to hold all of the member object's local got. */
3765b1be 397 int local_got_size;
252b5132
RH
398};
399
400#define alpha_elf_tdata(abfd) \
401 ((struct alpha_elf_obj_tdata *) (abfd)->tdata.any)
402
b34976b6 403static bfd_boolean
252b5132
RH
404elf64_alpha_mkobject (abfd)
405 bfd *abfd;
406{
dc810e39
AM
407 bfd_size_type amt = sizeof (struct alpha_elf_obj_tdata);
408 abfd->tdata.any = bfd_zalloc (abfd, amt);
252b5132 409 if (abfd->tdata.any == NULL)
b34976b6
AM
410 return FALSE;
411 return TRUE;
252b5132
RH
412}
413
b34976b6 414static bfd_boolean
252b5132
RH
415elf64_alpha_object_p (abfd)
416 bfd *abfd;
417{
418 /* Allocate our special target data. */
419 struct alpha_elf_obj_tdata *new_tdata;
dc810e39
AM
420 bfd_size_type amt = sizeof (struct alpha_elf_obj_tdata);
421 new_tdata = bfd_zalloc (abfd, amt);
252b5132 422 if (new_tdata == NULL)
b34976b6 423 return FALSE;
252b5132
RH
424 new_tdata->root = *abfd->tdata.elf_obj_data;
425 abfd->tdata.any = new_tdata;
426
427 /* Set the right machine number for an Alpha ELF file. */
428 return bfd_default_set_arch_mach (abfd, bfd_arch_alpha, 0);
429}
430\f
431/* In case we're on a 32-bit machine, construct a 64-bit "-1" value
432 from smaller values. Start with zero, widen, *then* decrement. */
433#define MINUS_ONE (((bfd_vma)0) - 1)
434
dfe57ca0
RH
435#define SKIP_HOWTO(N) \
436 HOWTO(N, 0, 0, 0, 0, 0, 0, elf64_alpha_reloc_bad, 0, 0, 0, 0, 0)
437
252b5132
RH
438static reloc_howto_type elf64_alpha_howto_table[] =
439{
440 HOWTO (R_ALPHA_NONE, /* type */
441 0, /* rightshift */
442 0, /* size (0 = byte, 1 = short, 2 = long) */
443 8, /* bitsize */
b34976b6 444 TRUE, /* pc_relative */
252b5132
RH
445 0, /* bitpos */
446 complain_overflow_dont, /* complain_on_overflow */
447 elf64_alpha_reloc_nil, /* special_function */
448 "NONE", /* name */
b34976b6 449 FALSE, /* partial_inplace */
252b5132
RH
450 0, /* src_mask */
451 0, /* dst_mask */
b34976b6 452 TRUE), /* pcrel_offset */
252b5132
RH
453
454 /* A 32 bit reference to a symbol. */
455 HOWTO (R_ALPHA_REFLONG, /* type */
456 0, /* rightshift */
457 2, /* size (0 = byte, 1 = short, 2 = long) */
458 32, /* bitsize */
b34976b6 459 FALSE, /* pc_relative */
252b5132
RH
460 0, /* bitpos */
461 complain_overflow_bitfield, /* complain_on_overflow */
462 0, /* special_function */
463 "REFLONG", /* name */
b34976b6 464 FALSE, /* partial_inplace */
252b5132
RH
465 0xffffffff, /* src_mask */
466 0xffffffff, /* dst_mask */
b34976b6 467 FALSE), /* pcrel_offset */
252b5132
RH
468
469 /* A 64 bit reference to a symbol. */
470 HOWTO (R_ALPHA_REFQUAD, /* type */
471 0, /* rightshift */
472 4, /* size (0 = byte, 1 = short, 2 = long) */
473 64, /* bitsize */
b34976b6 474 FALSE, /* pc_relative */
252b5132
RH
475 0, /* bitpos */
476 complain_overflow_bitfield, /* complain_on_overflow */
477 0, /* special_function */
478 "REFQUAD", /* name */
b34976b6 479 FALSE, /* partial_inplace */
252b5132
RH
480 MINUS_ONE, /* src_mask */
481 MINUS_ONE, /* dst_mask */
b34976b6 482 FALSE), /* pcrel_offset */
252b5132
RH
483
484 /* A 32 bit GP relative offset. This is just like REFLONG except
485 that when the value is used the value of the gp register will be
486 added in. */
487 HOWTO (R_ALPHA_GPREL32, /* type */
488 0, /* rightshift */
489 2, /* size (0 = byte, 1 = short, 2 = long) */
490 32, /* bitsize */
b34976b6 491 FALSE, /* pc_relative */
252b5132
RH
492 0, /* bitpos */
493 complain_overflow_bitfield, /* complain_on_overflow */
494 0, /* special_function */
495 "GPREL32", /* name */
b34976b6 496 FALSE, /* partial_inplace */
252b5132
RH
497 0xffffffff, /* src_mask */
498 0xffffffff, /* dst_mask */
b34976b6 499 FALSE), /* pcrel_offset */
252b5132
RH
500
501 /* Used for an instruction that refers to memory off the GP register. */
502 HOWTO (R_ALPHA_LITERAL, /* type */
503 0, /* rightshift */
dfe57ca0 504 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 505 16, /* bitsize */
b34976b6 506 FALSE, /* pc_relative */
252b5132
RH
507 0, /* bitpos */
508 complain_overflow_signed, /* complain_on_overflow */
509 0, /* special_function */
510 "ELF_LITERAL", /* name */
b34976b6 511 FALSE, /* partial_inplace */
252b5132
RH
512 0xffff, /* src_mask */
513 0xffff, /* dst_mask */
b34976b6 514 FALSE), /* pcrel_offset */
252b5132
RH
515
516 /* This reloc only appears immediately following an ELF_LITERAL reloc.
517 It identifies a use of the literal. The symbol index is special:
518 1 means the literal address is in the base register of a memory
519 format instruction; 2 means the literal address is in the byte
520 offset register of a byte-manipulation instruction; 3 means the
521 literal address is in the target register of a jsr instruction.
522 This does not actually do any relocation. */
523 HOWTO (R_ALPHA_LITUSE, /* type */
524 0, /* rightshift */
dfe57ca0 525 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 526 32, /* bitsize */
b34976b6 527 FALSE, /* pc_relative */
252b5132
RH
528 0, /* bitpos */
529 complain_overflow_dont, /* complain_on_overflow */
530 elf64_alpha_reloc_nil, /* special_function */
531 "LITUSE", /* name */
b34976b6 532 FALSE, /* partial_inplace */
252b5132
RH
533 0, /* src_mask */
534 0, /* dst_mask */
b34976b6 535 FALSE), /* pcrel_offset */
252b5132
RH
536
537 /* Load the gp register. This is always used for a ldah instruction
538 which loads the upper 16 bits of the gp register. The symbol
539 index of the GPDISP instruction is an offset in bytes to the lda
540 instruction that loads the lower 16 bits. The value to use for
541 the relocation is the difference between the GP value and the
542 current location; the load will always be done against a register
543 holding the current address.
544
545 NOTE: Unlike ECOFF, partial in-place relocation is not done. If
546 any offset is present in the instructions, it is an offset from
547 the register to the ldah instruction. This lets us avoid any
548 stupid hackery like inventing a gp value to do partial relocation
549 against. Also unlike ECOFF, we do the whole relocation off of
550 the GPDISP rather than a GPDISP_HI16/GPDISP_LO16 pair. An odd,
551 space consuming bit, that, since all the information was present
552 in the GPDISP_HI16 reloc. */
553 HOWTO (R_ALPHA_GPDISP, /* type */
554 16, /* rightshift */
555 2, /* size (0 = byte, 1 = short, 2 = long) */
556 16, /* bitsize */
b34976b6 557 FALSE, /* pc_relative */
252b5132
RH
558 0, /* bitpos */
559 complain_overflow_dont, /* complain_on_overflow */
560 elf64_alpha_reloc_gpdisp, /* special_function */
561 "GPDISP", /* name */
b34976b6 562 FALSE, /* partial_inplace */
252b5132
RH
563 0xffff, /* src_mask */
564 0xffff, /* dst_mask */
b34976b6 565 TRUE), /* pcrel_offset */
252b5132
RH
566
567 /* A 21 bit branch. */
568 HOWTO (R_ALPHA_BRADDR, /* type */
569 2, /* rightshift */
570 2, /* size (0 = byte, 1 = short, 2 = long) */
571 21, /* bitsize */
b34976b6 572 TRUE, /* pc_relative */
252b5132
RH
573 0, /* bitpos */
574 complain_overflow_signed, /* complain_on_overflow */
575 0, /* special_function */
576 "BRADDR", /* name */
b34976b6 577 FALSE, /* partial_inplace */
252b5132
RH
578 0x1fffff, /* src_mask */
579 0x1fffff, /* dst_mask */
b34976b6 580 TRUE), /* pcrel_offset */
252b5132
RH
581
582 /* A hint for a jump to a register. */
583 HOWTO (R_ALPHA_HINT, /* type */
584 2, /* rightshift */
dfe57ca0 585 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 586 14, /* bitsize */
b34976b6 587 TRUE, /* pc_relative */
252b5132
RH
588 0, /* bitpos */
589 complain_overflow_dont, /* complain_on_overflow */
590 0, /* special_function */
591 "HINT", /* name */
b34976b6 592 FALSE, /* partial_inplace */
252b5132
RH
593 0x3fff, /* src_mask */
594 0x3fff, /* dst_mask */
b34976b6 595 TRUE), /* pcrel_offset */
252b5132
RH
596
597 /* 16 bit PC relative offset. */
598 HOWTO (R_ALPHA_SREL16, /* type */
599 0, /* rightshift */
600 1, /* size (0 = byte, 1 = short, 2 = long) */
601 16, /* bitsize */
b34976b6 602 TRUE, /* pc_relative */
252b5132
RH
603 0, /* bitpos */
604 complain_overflow_signed, /* complain_on_overflow */
605 0, /* special_function */
606 "SREL16", /* name */
b34976b6 607 FALSE, /* partial_inplace */
252b5132
RH
608 0xffff, /* src_mask */
609 0xffff, /* dst_mask */
b34976b6 610 TRUE), /* pcrel_offset */
252b5132
RH
611
612 /* 32 bit PC relative offset. */
613 HOWTO (R_ALPHA_SREL32, /* type */
614 0, /* rightshift */
615 2, /* size (0 = byte, 1 = short, 2 = long) */
616 32, /* bitsize */
b34976b6 617 TRUE, /* pc_relative */
252b5132
RH
618 0, /* bitpos */
619 complain_overflow_signed, /* complain_on_overflow */
620 0, /* special_function */
621 "SREL32", /* name */
b34976b6 622 FALSE, /* partial_inplace */
252b5132
RH
623 0xffffffff, /* src_mask */
624 0xffffffff, /* dst_mask */
b34976b6 625 TRUE), /* pcrel_offset */
252b5132
RH
626
627 /* A 64 bit PC relative offset. */
628 HOWTO (R_ALPHA_SREL64, /* type */
629 0, /* rightshift */
630 4, /* size (0 = byte, 1 = short, 2 = long) */
631 64, /* bitsize */
b34976b6 632 TRUE, /* pc_relative */
252b5132
RH
633 0, /* bitpos */
634 complain_overflow_signed, /* complain_on_overflow */
635 0, /* special_function */
636 "SREL64", /* name */
b34976b6 637 FALSE, /* partial_inplace */
252b5132
RH
638 MINUS_ONE, /* src_mask */
639 MINUS_ONE, /* dst_mask */
b34976b6 640 TRUE), /* pcrel_offset */
252b5132 641
dfe57ca0
RH
642 /* Skip 12 - 16; deprecated ECOFF relocs. */
643 SKIP_HOWTO (12),
644 SKIP_HOWTO (13),
645 SKIP_HOWTO (14),
646 SKIP_HOWTO (15),
647 SKIP_HOWTO (16),
252b5132
RH
648
649 /* The high 16 bits of the displacement from GP to the target. */
650 HOWTO (R_ALPHA_GPRELHIGH,
651 0, /* rightshift */
dfe57ca0 652 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 653 16, /* bitsize */
b34976b6 654 FALSE, /* pc_relative */
252b5132
RH
655 0, /* bitpos */
656 complain_overflow_signed, /* complain_on_overflow */
dfe57ca0 657 0, /* special_function */
252b5132 658 "GPRELHIGH", /* name */
b34976b6 659 FALSE, /* partial_inplace */
252b5132
RH
660 0xffff, /* src_mask */
661 0xffff, /* dst_mask */
b34976b6 662 FALSE), /* pcrel_offset */
252b5132
RH
663
664 /* The low 16 bits of the displacement from GP to the target. */
665 HOWTO (R_ALPHA_GPRELLOW,
666 0, /* rightshift */
dfe57ca0 667 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 668 16, /* bitsize */
b34976b6 669 FALSE, /* pc_relative */
252b5132
RH
670 0, /* bitpos */
671 complain_overflow_dont, /* complain_on_overflow */
dfe57ca0 672 0, /* special_function */
252b5132 673 "GPRELLOW", /* name */
b34976b6 674 FALSE, /* partial_inplace */
252b5132
RH
675 0xffff, /* src_mask */
676 0xffff, /* dst_mask */
b34976b6 677 FALSE), /* pcrel_offset */
252b5132
RH
678
679 /* A 16-bit displacement from the GP to the target. */
dfe57ca0 680 HOWTO (R_ALPHA_GPREL16,
252b5132 681 0, /* rightshift */
dfe57ca0 682 1, /* size (0 = byte, 1 = short, 2 = long) */
252b5132 683 16, /* bitsize */
b34976b6 684 FALSE, /* pc_relative */
252b5132
RH
685 0, /* bitpos */
686 complain_overflow_signed, /* complain_on_overflow */
687 0, /* special_function */
dfe57ca0 688 "GPREL16", /* name */
b34976b6 689 FALSE, /* partial_inplace */
252b5132
RH
690 0xffff, /* src_mask */
691 0xffff, /* dst_mask */
b34976b6 692 FALSE), /* pcrel_offset */
252b5132 693
dfe57ca0
RH
694 /* Skip 20 - 23; deprecated ECOFF relocs. */
695 SKIP_HOWTO (20),
696 SKIP_HOWTO (21),
697 SKIP_HOWTO (22),
698 SKIP_HOWTO (23),
252b5132 699
fe8bc63d 700 /* Misc ELF relocations. */
252b5132
RH
701
702 /* A dynamic relocation to copy the target into our .dynbss section. */
703 /* Not generated, as all Alpha objects use PIC, so it is not needed. It
704 is present because every other ELF has one, but should not be used
705 because .dynbss is an ugly thing. */
706 HOWTO (R_ALPHA_COPY,
707 0,
708 0,
709 0,
b34976b6 710 FALSE,
252b5132
RH
711 0,
712 complain_overflow_dont,
713 bfd_elf_generic_reloc,
714 "COPY",
b34976b6 715 FALSE,
252b5132
RH
716 0,
717 0,
b34976b6 718 TRUE),
252b5132
RH
719
720 /* A dynamic relocation for a .got entry. */
721 HOWTO (R_ALPHA_GLOB_DAT,
722 0,
723 0,
724 0,
b34976b6 725 FALSE,
252b5132
RH
726 0,
727 complain_overflow_dont,
728 bfd_elf_generic_reloc,
729 "GLOB_DAT",
b34976b6 730 FALSE,
252b5132
RH
731 0,
732 0,
b34976b6 733 TRUE),
252b5132
RH
734
735 /* A dynamic relocation for a .plt entry. */
736 HOWTO (R_ALPHA_JMP_SLOT,
737 0,
738 0,
739 0,
b34976b6 740 FALSE,
252b5132
RH
741 0,
742 complain_overflow_dont,
743 bfd_elf_generic_reloc,
744 "JMP_SLOT",
b34976b6 745 FALSE,
252b5132
RH
746 0,
747 0,
b34976b6 748 TRUE),
252b5132
RH
749
750 /* A dynamic relocation to add the base of the DSO to a 64-bit field. */
751 HOWTO (R_ALPHA_RELATIVE,
752 0,
753 0,
754 0,
b34976b6 755 FALSE,
252b5132
RH
756 0,
757 complain_overflow_dont,
758 bfd_elf_generic_reloc,
759 "RELATIVE",
b34976b6 760 FALSE,
252b5132
RH
761 0,
762 0,
b34976b6 763 TRUE),
7793f4d0
RH
764
765 /* A 21 bit branch that adjusts for gp loads. */
766 HOWTO (R_ALPHA_BRSGP, /* type */
767 2, /* rightshift */
768 2, /* size (0 = byte, 1 = short, 2 = long) */
769 21, /* bitsize */
b34976b6 770 TRUE, /* pc_relative */
7793f4d0
RH
771 0, /* bitpos */
772 complain_overflow_signed, /* complain_on_overflow */
773 0, /* special_function */
774 "BRSGP", /* name */
b34976b6 775 FALSE, /* partial_inplace */
7793f4d0
RH
776 0x1fffff, /* src_mask */
777 0x1fffff, /* dst_mask */
b34976b6 778 TRUE), /* pcrel_offset */
3765b1be
RH
779
780 /* Creates a tls_index for the symbol in the got. */
781 HOWTO (R_ALPHA_TLSGD, /* type */
782 0, /* rightshift */
783 1, /* size (0 = byte, 1 = short, 2 = long) */
784 16, /* bitsize */
b34976b6 785 FALSE, /* pc_relative */
3765b1be
RH
786 0, /* bitpos */
787 complain_overflow_signed, /* complain_on_overflow */
788 0, /* special_function */
789 "TLSGD", /* name */
b34976b6 790 FALSE, /* partial_inplace */
3765b1be
RH
791 0xffff, /* src_mask */
792 0xffff, /* dst_mask */
b34976b6 793 FALSE), /* pcrel_offset */
3765b1be
RH
794
795 /* Creates a tls_index for the (current) module in the got. */
796 HOWTO (R_ALPHA_TLSLDM, /* type */
797 0, /* rightshift */
798 1, /* size (0 = byte, 1 = short, 2 = long) */
799 16, /* bitsize */
b34976b6 800 FALSE, /* pc_relative */
3765b1be
RH
801 0, /* bitpos */
802 complain_overflow_signed, /* complain_on_overflow */
803 0, /* special_function */
804 "TLSLDM", /* name */
b34976b6 805 FALSE, /* partial_inplace */
3765b1be
RH
806 0xffff, /* src_mask */
807 0xffff, /* dst_mask */
b34976b6 808 FALSE), /* pcrel_offset */
3765b1be
RH
809
810 /* A dynamic relocation for a DTP module entry. */
811 HOWTO (R_ALPHA_DTPMOD64, /* type */
812 0, /* rightshift */
813 4, /* size (0 = byte, 1 = short, 2 = long) */
814 64, /* bitsize */
b34976b6 815 FALSE, /* pc_relative */
3765b1be
RH
816 0, /* bitpos */
817 complain_overflow_bitfield, /* complain_on_overflow */
818 0, /* special_function */
819 "DTPMOD64", /* name */
b34976b6 820 FALSE, /* partial_inplace */
3765b1be
RH
821 MINUS_ONE, /* src_mask */
822 MINUS_ONE, /* dst_mask */
b34976b6 823 FALSE), /* pcrel_offset */
3765b1be
RH
824
825 /* Creates a 64-bit offset in the got for the displacement
826 from DTP to the target. */
827 HOWTO (R_ALPHA_GOTDTPREL, /* type */
828 0, /* rightshift */
829 1, /* size (0 = byte, 1 = short, 2 = long) */
830 16, /* bitsize */
b34976b6 831 FALSE, /* pc_relative */
3765b1be
RH
832 0, /* bitpos */
833 complain_overflow_signed, /* complain_on_overflow */
834 0, /* special_function */
835 "GOTDTPREL", /* name */
b34976b6 836 FALSE, /* partial_inplace */
3765b1be
RH
837 0xffff, /* src_mask */
838 0xffff, /* dst_mask */
b34976b6 839 FALSE), /* pcrel_offset */
3765b1be
RH
840
841 /* A dynamic relocation for a displacement from DTP to the target. */
842 HOWTO (R_ALPHA_DTPREL64, /* type */
843 0, /* rightshift */
844 4, /* size (0 = byte, 1 = short, 2 = long) */
845 64, /* bitsize */
b34976b6 846 FALSE, /* pc_relative */
3765b1be
RH
847 0, /* bitpos */
848 complain_overflow_bitfield, /* complain_on_overflow */
849 0, /* special_function */
850 "DTPREL64", /* name */
b34976b6 851 FALSE, /* partial_inplace */
3765b1be
RH
852 MINUS_ONE, /* src_mask */
853 MINUS_ONE, /* dst_mask */
b34976b6 854 FALSE), /* pcrel_offset */
3765b1be
RH
855
856 /* The high 16 bits of the displacement from DTP to the target. */
857 HOWTO (R_ALPHA_DTPRELHI, /* type */
858 0, /* rightshift */
859 1, /* size (0 = byte, 1 = short, 2 = long) */
860 16, /* bitsize */
b34976b6 861 FALSE, /* pc_relative */
3765b1be
RH
862 0, /* bitpos */
863 complain_overflow_signed, /* complain_on_overflow */
864 0, /* special_function */
865 "DTPRELHI", /* name */
b34976b6 866 FALSE, /* partial_inplace */
3765b1be
RH
867 0xffff, /* src_mask */
868 0xffff, /* dst_mask */
b34976b6 869 FALSE), /* pcrel_offset */
3765b1be
RH
870
871 /* The low 16 bits of the displacement from DTP to the target. */
872 HOWTO (R_ALPHA_DTPRELLO, /* type */
873 0, /* rightshift */
874 1, /* size (0 = byte, 1 = short, 2 = long) */
875 16, /* bitsize */
b34976b6 876 FALSE, /* pc_relative */
3765b1be
RH
877 0, /* bitpos */
878 complain_overflow_dont, /* complain_on_overflow */
879 0, /* special_function */
880 "DTPRELLO", /* name */
b34976b6 881 FALSE, /* partial_inplace */
3765b1be
RH
882 0xffff, /* src_mask */
883 0xffff, /* dst_mask */
b34976b6 884 FALSE), /* pcrel_offset */
3765b1be
RH
885
886 /* A 16-bit displacement from DTP to the target. */
887 HOWTO (R_ALPHA_DTPREL16, /* type */
888 0, /* rightshift */
889 1, /* size (0 = byte, 1 = short, 2 = long) */
890 16, /* bitsize */
b34976b6 891 FALSE, /* pc_relative */
3765b1be
RH
892 0, /* bitpos */
893 complain_overflow_signed, /* complain_on_overflow */
894 0, /* special_function */
895 "DTPREL16", /* name */
b34976b6 896 FALSE, /* partial_inplace */
3765b1be
RH
897 0xffff, /* src_mask */
898 0xffff, /* dst_mask */
b34976b6 899 FALSE), /* pcrel_offset */
3765b1be
RH
900
901 /* Creates a 64-bit offset in the got for the displacement
902 from TP to the target. */
903 HOWTO (R_ALPHA_GOTTPREL, /* type */
904 0, /* rightshift */
905 1, /* size (0 = byte, 1 = short, 2 = long) */
906 16, /* bitsize */
b34976b6 907 FALSE, /* pc_relative */
3765b1be
RH
908 0, /* bitpos */
909 complain_overflow_signed, /* complain_on_overflow */
910 0, /* special_function */
911 "GOTTPREL", /* name */
b34976b6 912 FALSE, /* partial_inplace */
3765b1be
RH
913 0xffff, /* src_mask */
914 0xffff, /* dst_mask */
b34976b6 915 FALSE), /* pcrel_offset */
3765b1be
RH
916
917 /* A dynamic relocation for a displacement from TP to the target. */
918 HOWTO (R_ALPHA_TPREL64, /* type */
919 0, /* rightshift */
920 4, /* size (0 = byte, 1 = short, 2 = long) */
921 64, /* bitsize */
b34976b6 922 FALSE, /* pc_relative */
3765b1be
RH
923 0, /* bitpos */
924 complain_overflow_bitfield, /* complain_on_overflow */
925 0, /* special_function */
926 "TPREL64", /* name */
b34976b6 927 FALSE, /* partial_inplace */
3765b1be
RH
928 MINUS_ONE, /* src_mask */
929 MINUS_ONE, /* dst_mask */
b34976b6 930 FALSE), /* pcrel_offset */
3765b1be
RH
931
932 /* The high 16 bits of the displacement from TP to the target. */
933 HOWTO (R_ALPHA_TPRELHI, /* type */
934 0, /* rightshift */
935 1, /* size (0 = byte, 1 = short, 2 = long) */
936 16, /* bitsize */
b34976b6 937 FALSE, /* pc_relative */
3765b1be
RH
938 0, /* bitpos */
939 complain_overflow_signed, /* complain_on_overflow */
940 0, /* special_function */
941 "TPRELHI", /* name */
b34976b6 942 FALSE, /* partial_inplace */
3765b1be
RH
943 0xffff, /* src_mask */
944 0xffff, /* dst_mask */
b34976b6 945 FALSE), /* pcrel_offset */
3765b1be
RH
946
947 /* The low 16 bits of the displacement from TP to the target. */
948 HOWTO (R_ALPHA_TPRELLO, /* type */
949 0, /* rightshift */
950 1, /* size (0 = byte, 1 = short, 2 = long) */
951 16, /* bitsize */
b34976b6 952 FALSE, /* pc_relative */
3765b1be
RH
953 0, /* bitpos */
954 complain_overflow_dont, /* complain_on_overflow */
955 0, /* special_function */
956 "TPRELLO", /* name */
b34976b6 957 FALSE, /* partial_inplace */
3765b1be
RH
958 0xffff, /* src_mask */
959 0xffff, /* dst_mask */
b34976b6 960 FALSE), /* pcrel_offset */
3765b1be
RH
961
962 /* A 16-bit displacement from TP to the target. */
963 HOWTO (R_ALPHA_TPREL16, /* type */
964 0, /* rightshift */
965 1, /* size (0 = byte, 1 = short, 2 = long) */
966 16, /* bitsize */
b34976b6 967 FALSE, /* pc_relative */
3765b1be
RH
968 0, /* bitpos */
969 complain_overflow_signed, /* complain_on_overflow */
970 0, /* special_function */
971 "TPREL16", /* name */
b34976b6 972 FALSE, /* partial_inplace */
3765b1be
RH
973 0xffff, /* src_mask */
974 0xffff, /* dst_mask */
b34976b6 975 FALSE), /* pcrel_offset */
252b5132
RH
976};
977
978/* A relocation function which doesn't do anything. */
979
980static bfd_reloc_status_type
981elf64_alpha_reloc_nil (abfd, reloc, sym, data, sec, output_bfd, error_message)
56fc028e 982 bfd *abfd ATTRIBUTE_UNUSED;
252b5132 983 arelent *reloc;
56fc028e
AJ
984 asymbol *sym ATTRIBUTE_UNUSED;
985 PTR data ATTRIBUTE_UNUSED;
252b5132
RH
986 asection *sec;
987 bfd *output_bfd;
56fc028e 988 char **error_message ATTRIBUTE_UNUSED;
252b5132
RH
989{
990 if (output_bfd)
991 reloc->address += sec->output_offset;
992 return bfd_reloc_ok;
993}
994
995/* A relocation function used for an unsupported reloc. */
996
997static bfd_reloc_status_type
998elf64_alpha_reloc_bad (abfd, reloc, sym, data, sec, output_bfd, error_message)
56fc028e 999 bfd *abfd ATTRIBUTE_UNUSED;
252b5132 1000 arelent *reloc;
56fc028e
AJ
1001 asymbol *sym ATTRIBUTE_UNUSED;
1002 PTR data ATTRIBUTE_UNUSED;
252b5132
RH
1003 asection *sec;
1004 bfd *output_bfd;
56fc028e 1005 char **error_message ATTRIBUTE_UNUSED;
252b5132
RH
1006{
1007 if (output_bfd)
1008 reloc->address += sec->output_offset;
1009 return bfd_reloc_notsupported;
1010}
1011
1012/* Do the work of the GPDISP relocation. */
1013
1014static bfd_reloc_status_type
1015elf64_alpha_do_reloc_gpdisp (abfd, gpdisp, p_ldah, p_lda)
1016 bfd *abfd;
1017 bfd_vma gpdisp;
1018 bfd_byte *p_ldah;
1019 bfd_byte *p_lda;
1020{
1021 bfd_reloc_status_type ret = bfd_reloc_ok;
1022 bfd_vma addend;
1023 unsigned long i_ldah, i_lda;
1024
1025 i_ldah = bfd_get_32 (abfd, p_ldah);
1026 i_lda = bfd_get_32 (abfd, p_lda);
1027
1028 /* Complain if the instructions are not correct. */
1029 if (((i_ldah >> 26) & 0x3f) != 0x09
1030 || ((i_lda >> 26) & 0x3f) != 0x08)
1031 ret = bfd_reloc_dangerous;
1032
1033 /* Extract the user-supplied offset, mirroring the sign extensions
1034 that the instructions perform. */
1035 addend = ((i_ldah & 0xffff) << 16) | (i_lda & 0xffff);
1036 addend = (addend ^ 0x80008000) - 0x80008000;
1037
1038 gpdisp += addend;
1039
1040 if ((bfd_signed_vma) gpdisp < -(bfd_signed_vma) 0x80000000
1041 || (bfd_signed_vma) gpdisp >= (bfd_signed_vma) 0x7fff8000)
1042 ret = bfd_reloc_overflow;
1043
1044 /* compensate for the sign extension again. */
1045 i_ldah = ((i_ldah & 0xffff0000)
1046 | (((gpdisp >> 16) + ((gpdisp >> 15) & 1)) & 0xffff));
1047 i_lda = (i_lda & 0xffff0000) | (gpdisp & 0xffff);
1048
dc810e39
AM
1049 bfd_put_32 (abfd, (bfd_vma) i_ldah, p_ldah);
1050 bfd_put_32 (abfd, (bfd_vma) i_lda, p_lda);
252b5132
RH
1051
1052 return ret;
1053}
1054
1055/* The special function for the GPDISP reloc. */
1056
1057static bfd_reloc_status_type
1058elf64_alpha_reloc_gpdisp (abfd, reloc_entry, sym, data, input_section,
1059 output_bfd, err_msg)
1060 bfd *abfd;
1061 arelent *reloc_entry;
56fc028e 1062 asymbol *sym ATTRIBUTE_UNUSED;
252b5132
RH
1063 PTR data;
1064 asection *input_section;
1065 bfd *output_bfd;
1066 char **err_msg;
1067{
1068 bfd_reloc_status_type ret;
1069 bfd_vma gp, relocation;
1070 bfd_byte *p_ldah, *p_lda;
1071
1072 /* Don't do anything if we're not doing a final link. */
1073 if (output_bfd)
1074 {
1075 reloc_entry->address += input_section->output_offset;
1076 return bfd_reloc_ok;
1077 }
1078
1079 if (reloc_entry->address > input_section->_cooked_size ||
1080 reloc_entry->address + reloc_entry->addend > input_section->_cooked_size)
1081 return bfd_reloc_outofrange;
1082
1083 /* The gp used in the portion of the output object to which this
1084 input object belongs is cached on the input bfd. */
1085 gp = _bfd_get_gp_value (abfd);
1086
1087 relocation = (input_section->output_section->vma
1088 + input_section->output_offset
1089 + reloc_entry->address);
1090
1091 p_ldah = (bfd_byte *) data + reloc_entry->address;
1092 p_lda = p_ldah + reloc_entry->addend;
1093
1094 ret = elf64_alpha_do_reloc_gpdisp (abfd, gp - relocation, p_ldah, p_lda);
1095
1096 /* Complain if the instructions are not correct. */
1097 if (ret == bfd_reloc_dangerous)
1098 *err_msg = _("GPDISP relocation did not find ldah and lda instructions");
1099
1100 return ret;
1101}
1102
1103/* A mapping from BFD reloc types to Alpha ELF reloc types. */
1104
1105struct elf_reloc_map
1106{
1107 bfd_reloc_code_real_type bfd_reloc_val;
1108 int elf_reloc_val;
1109};
1110
1111static const struct elf_reloc_map elf64_alpha_reloc_map[] =
1112{
dfe57ca0
RH
1113 {BFD_RELOC_NONE, R_ALPHA_NONE},
1114 {BFD_RELOC_32, R_ALPHA_REFLONG},
1115 {BFD_RELOC_64, R_ALPHA_REFQUAD},
1116 {BFD_RELOC_CTOR, R_ALPHA_REFQUAD},
1117 {BFD_RELOC_GPREL32, R_ALPHA_GPREL32},
1118 {BFD_RELOC_ALPHA_ELF_LITERAL, R_ALPHA_LITERAL},
1119 {BFD_RELOC_ALPHA_LITUSE, R_ALPHA_LITUSE},
1120 {BFD_RELOC_ALPHA_GPDISP, R_ALPHA_GPDISP},
1121 {BFD_RELOC_23_PCREL_S2, R_ALPHA_BRADDR},
1122 {BFD_RELOC_ALPHA_HINT, R_ALPHA_HINT},
1123 {BFD_RELOC_16_PCREL, R_ALPHA_SREL16},
1124 {BFD_RELOC_32_PCREL, R_ALPHA_SREL32},
1125 {BFD_RELOC_64_PCREL, R_ALPHA_SREL64},
1126 {BFD_RELOC_ALPHA_GPREL_HI16, R_ALPHA_GPRELHIGH},
1127 {BFD_RELOC_ALPHA_GPREL_LO16, R_ALPHA_GPRELLOW},
1128 {BFD_RELOC_GPREL16, R_ALPHA_GPREL16},
7793f4d0 1129 {BFD_RELOC_ALPHA_BRSGP, R_ALPHA_BRSGP},
3765b1be
RH
1130 {BFD_RELOC_ALPHA_TLSGD, R_ALPHA_TLSGD},
1131 {BFD_RELOC_ALPHA_TLSLDM, R_ALPHA_TLSLDM},
1132 {BFD_RELOC_ALPHA_DTPMOD64, R_ALPHA_DTPMOD64},
1133 {BFD_RELOC_ALPHA_GOTDTPREL16, R_ALPHA_GOTDTPREL},
1134 {BFD_RELOC_ALPHA_DTPREL64, R_ALPHA_DTPREL64},
1135 {BFD_RELOC_ALPHA_DTPREL_HI16, R_ALPHA_DTPRELHI},
1136 {BFD_RELOC_ALPHA_DTPREL_LO16, R_ALPHA_DTPRELLO},
1137 {BFD_RELOC_ALPHA_DTPREL16, R_ALPHA_DTPREL16},
1138 {BFD_RELOC_ALPHA_GOTTPREL16, R_ALPHA_GOTTPREL},
1139 {BFD_RELOC_ALPHA_TPREL64, R_ALPHA_TPREL64},
1140 {BFD_RELOC_ALPHA_TPREL_HI16, R_ALPHA_TPRELHI},
1141 {BFD_RELOC_ALPHA_TPREL_LO16, R_ALPHA_TPRELLO},
1142 {BFD_RELOC_ALPHA_TPREL16, R_ALPHA_TPREL16},
252b5132
RH
1143};
1144
1145/* Given a BFD reloc type, return a HOWTO structure. */
1146
1147static reloc_howto_type *
1148elf64_alpha_bfd_reloc_type_lookup (abfd, code)
56fc028e 1149 bfd *abfd ATTRIBUTE_UNUSED;
252b5132
RH
1150 bfd_reloc_code_real_type code;
1151{
1152 const struct elf_reloc_map *i, *e;
1153 i = e = elf64_alpha_reloc_map;
1154 e += sizeof (elf64_alpha_reloc_map) / sizeof (struct elf_reloc_map);
1155 for (; i != e; ++i)
1156 {
1157 if (i->bfd_reloc_val == code)
1158 return &elf64_alpha_howto_table[i->elf_reloc_val];
1159 }
1160 return 0;
1161}
1162
1163/* Given an Alpha ELF reloc type, fill in an arelent structure. */
1164
1165static void
1166elf64_alpha_info_to_howto (abfd, cache_ptr, dst)
56fc028e 1167 bfd *abfd ATTRIBUTE_UNUSED;
252b5132 1168 arelent *cache_ptr;
947216bf 1169 Elf_Internal_Rela *dst;
252b5132
RH
1170{
1171 unsigned r_type;
1172
1173 r_type = ELF64_R_TYPE(dst->r_info);
1174 BFD_ASSERT (r_type < (unsigned int) R_ALPHA_max);
1175 cache_ptr->howto = &elf64_alpha_howto_table[r_type];
1176}
3765b1be
RH
1177
1178/* These two relocations create a two-word entry in the got. */
1179#define alpha_got_entry_size(r_type) \
1180 (r_type == R_ALPHA_TLSGD || r_type == R_ALPHA_TLSLDM ? 16 : 8)
9e756d64
RH
1181
1182/* This is PT_TLS segment p_vaddr. */
1183#define alpha_get_dtprel_base(tlss) \
1184 ((tlss)->start)
1185
1186/* Main program TLS (whose template starts at PT_TLS p_vaddr)
1187 is assigned offset round(16, PT_TLS p_align). */
1188#define alpha_get_tprel_base(tlss) \
1189 ((tlss)->start - align_power ((bfd_vma) 16, (tlss)->align))
252b5132 1190\f
fe8bc63d 1191/* These functions do relaxation for Alpha ELF.
252b5132
RH
1192
1193 Currently I'm only handling what I can do with existing compiler
1194 and assembler support, which means no instructions are removed,
1195 though some may be nopped. At this time GCC does not emit enough
1196 information to do all of the relaxing that is possible. It will
1197 take some not small amount of work for that to happen.
1198
1199 There are a couple of interesting papers that I once read on this
1200 subject, that I cannot find references to at the moment, that
1201 related to Alpha in particular. They are by David Wall, then of
1202 DEC WRL. */
1203
1204#define OP_LDA 0x08
1205#define OP_LDAH 0x09
1206#define INSN_JSR 0x68004000
1207#define INSN_JSR_MASK 0xfc00c000
1208#define OP_LDQ 0x29
1209#define OP_BR 0x30
1210#define OP_BSR 0x34
f304919d 1211#define INSN_UNOP 0x2ffe0000
9e756d64
RH
1212#define INSN_ADDQ 0x40000400
1213#define INSN_RDUNIQ 0x0000009e
252b5132
RH
1214
1215struct alpha_relax_info
1216{
1217 bfd *abfd;
1218 asection *sec;
1219 bfd_byte *contents;
9e756d64 1220 Elf_Internal_Shdr *symtab_hdr;
252b5132
RH
1221 Elf_Internal_Rela *relocs, *relend;
1222 struct bfd_link_info *link_info;
9e756d64 1223 struct elf_link_tls_segment *tls_segment;
252b5132
RH
1224 bfd_vma gp;
1225 bfd *gotobj;
1226 asection *tsec;
1227 struct alpha_elf_link_hash_entry *h;
9e756d64 1228 struct alpha_elf_got_entry **first_gotent;
252b5132 1229 struct alpha_elf_got_entry *gotent;
b34976b6
AM
1230 bfd_boolean changed_contents;
1231 bfd_boolean changed_relocs;
252b5132
RH
1232 unsigned char other;
1233};
1234
b34976b6 1235static bfd_boolean elf64_alpha_relax_with_lituse
fe8bc63d 1236 PARAMS((struct alpha_relax_info *info, bfd_vma symval,
252b5132 1237 Elf_Internal_Rela *irel));
252b5132
RH
1238static bfd_vma elf64_alpha_relax_opt_call
1239 PARAMS((struct alpha_relax_info *info, bfd_vma symval));
b34976b6 1240static bfd_boolean elf64_alpha_relax_got_load
9e756d64
RH
1241 PARAMS((struct alpha_relax_info *info, bfd_vma symval,
1242 Elf_Internal_Rela *irel, unsigned long));
b34976b6 1243static bfd_boolean elf64_alpha_relax_gprelhilo
9e756d64 1244 PARAMS((struct alpha_relax_info *info, bfd_vma symval,
b34976b6
AM
1245 Elf_Internal_Rela *irel, bfd_boolean));
1246static bfd_boolean elf64_alpha_relax_tls_get_addr
9e756d64 1247 PARAMS((struct alpha_relax_info *info, bfd_vma symval,
b34976b6 1248 Elf_Internal_Rela *irel, bfd_boolean));
9e756d64
RH
1249static struct elf_link_tls_segment *elf64_alpha_relax_find_tls_segment
1250 PARAMS((struct alpha_relax_info *, struct elf_link_tls_segment *));
b34976b6 1251static bfd_boolean elf64_alpha_relax_section
252b5132 1252 PARAMS((bfd *abfd, asection *sec, struct bfd_link_info *link_info,
b34976b6 1253 bfd_boolean *again));
252b5132
RH
1254
1255static Elf_Internal_Rela *
1256elf64_alpha_find_reloc_at_ofs (rel, relend, offset, type)
1257 Elf_Internal_Rela *rel, *relend;
1258 bfd_vma offset;
1259 int type;
1260{
1261 while (rel < relend)
1262 {
52b9d213
AM
1263 if (rel->r_offset == offset
1264 && ELF64_R_TYPE (rel->r_info) == (unsigned int) type)
252b5132
RH
1265 return rel;
1266 ++rel;
1267 }
1268 return NULL;
1269}
1270
b34976b6 1271static bfd_boolean
9e756d64 1272elf64_alpha_relax_with_lituse (info, symval, irel)
252b5132
RH
1273 struct alpha_relax_info *info;
1274 bfd_vma symval;
9e756d64 1275 Elf_Internal_Rela *irel;
252b5132 1276{
9e756d64 1277 Elf_Internal_Rela *urel, *irelend = info->relend;
252b5132
RH
1278 int flags, count, i;
1279 bfd_signed_vma disp;
b34976b6
AM
1280 bfd_boolean fits16;
1281 bfd_boolean fits32;
1282 bfd_boolean lit_reused = FALSE;
1283 bfd_boolean all_optimized = TRUE;
252b5132
RH
1284 unsigned int lit_insn;
1285
1286 lit_insn = bfd_get_32 (info->abfd, info->contents + irel->r_offset);
1287 if (lit_insn >> 26 != OP_LDQ)
1288 {
1289 ((*_bfd_error_handler)
1290 ("%s: %s+0x%lx: warning: LITERAL relocation against unexpected insn",
8f615d07
AM
1291 bfd_archive_filename (info->abfd), info->sec->name,
1292 (unsigned long) irel->r_offset));
b34976b6 1293 return TRUE;
252b5132
RH
1294 }
1295
9e756d64
RH
1296 /* Can't relax dynamic symbols. */
1297 if (alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info))
b34976b6 1298 return TRUE;
9e756d64 1299
252b5132
RH
1300 /* Summarize how this particular LITERAL is used. */
1301 for (urel = irel+1, flags = count = 0; urel < irelend; ++urel, ++count)
1302 {
1303 if (ELF64_R_TYPE (urel->r_info) != R_ALPHA_LITUSE)
1304 break;
1e738b87 1305 if (urel->r_addend <= 3)
252b5132
RH
1306 flags |= 1 << urel->r_addend;
1307 }
1308
fe8bc63d 1309 /* A little preparation for the loop... */
252b5132 1310 disp = symval - info->gp;
252b5132
RH
1311
1312 for (urel = irel+1, i = 0; i < count; ++i, ++urel)
1313 {
1314 unsigned int insn;
ffcb7aff
NC
1315 int insn_disp;
1316 bfd_signed_vma xdisp;
1317
252b5132
RH
1318 insn = bfd_get_32 (info->abfd, info->contents + urel->r_offset);
1319
1320 switch (urel->r_addend)
1321 {
9e756d64
RH
1322 case LITUSE_ALPHA_ADDR:
1323 default:
252b5132
RH
1324 /* This type is really just a placeholder to note that all
1325 uses cannot be optimized, but to still allow some. */
b34976b6 1326 all_optimized = FALSE;
252b5132
RH
1327 break;
1328
9e756d64 1329 case LITUSE_ALPHA_BASE:
252b5132 1330 /* We can always optimize 16-bit displacements. */
ffcb7aff
NC
1331
1332 /* Extract the displacement from the instruction, sign-extending
1333 it if necessary, then test whether it is within 16 or 32 bits
1334 displacement from GP. */
1335 insn_disp = insn & 0x0000ffff;
9e756d64
RH
1336 if (insn_disp & 0x8000)
1337 insn_disp |= ~0xffff; /* Negative: sign-extend. */
ffcb7aff
NC
1338
1339 xdisp = disp + insn_disp;
9e756d64
RH
1340 fits16 = (xdisp >= - (bfd_signed_vma) 0x8000 && xdisp < 0x8000);
1341 fits32 = (xdisp >= - (bfd_signed_vma) 0x80000000
1342 && xdisp < 0x7fff8000);
ffcb7aff 1343
252b5132
RH
1344 if (fits16)
1345 {
ffcb7aff 1346 /* Take the op code and dest from this insn, take the base
fe8bc63d 1347 register from the literal insn. Leave the offset alone. */
ffcb7aff 1348 insn = (insn & 0xffe0ffff) | (lit_insn & 0x001f0000);
252b5132 1349 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
dfe57ca0 1350 R_ALPHA_GPREL16);
252b5132 1351 urel->r_addend = irel->r_addend;
b34976b6 1352 info->changed_relocs = TRUE;
252b5132 1353
dc810e39
AM
1354 bfd_put_32 (info->abfd, (bfd_vma) insn,
1355 info->contents + urel->r_offset);
b34976b6 1356 info->changed_contents = TRUE;
252b5132
RH
1357 }
1358
1359 /* If all mem+byte, we can optimize 32-bit mem displacements. */
1360 else if (fits32 && !(flags & ~6))
1361 {
ffcb7aff 1362 /* FIXME: sanity check that lit insn Ra is mem insn Rb. */
252b5132
RH
1363
1364 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1365 R_ALPHA_GPRELHIGH);
1366 lit_insn = (OP_LDAH << 26) | (lit_insn & 0x03ff0000);
dc810e39 1367 bfd_put_32 (info->abfd, (bfd_vma) lit_insn,
252b5132 1368 info->contents + irel->r_offset);
b34976b6
AM
1369 lit_reused = TRUE;
1370 info->changed_contents = TRUE;
252b5132
RH
1371
1372 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1373 R_ALPHA_GPRELLOW);
1374 urel->r_addend = irel->r_addend;
b34976b6 1375 info->changed_relocs = TRUE;
252b5132
RH
1376 }
1377 else
b34976b6 1378 all_optimized = FALSE;
252b5132
RH
1379 break;
1380
9e756d64 1381 case LITUSE_ALPHA_BYTOFF:
252b5132
RH
1382 /* We can always optimize byte instructions. */
1383
1384 /* FIXME: sanity check the insn for byte op. Check that the
1385 literal dest reg is indeed Rb in the byte insn. */
1386
dc810e39
AM
1387 insn &= ~ (unsigned) 0x001ff000;
1388 insn |= ((symval & 7) << 13) | 0x1000;
252b5132
RH
1389
1390 urel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1391 urel->r_addend = 0;
b34976b6 1392 info->changed_relocs = TRUE;
252b5132 1393
dc810e39
AM
1394 bfd_put_32 (info->abfd, (bfd_vma) insn,
1395 info->contents + urel->r_offset);
b34976b6 1396 info->changed_contents = TRUE;
252b5132
RH
1397 break;
1398
9e756d64
RH
1399 case LITUSE_ALPHA_JSR:
1400 case LITUSE_ALPHA_TLSGD:
1401 case LITUSE_ALPHA_TLSLDM:
252b5132 1402 {
f44f99a5 1403 bfd_vma optdest, org;
252b5132
RH
1404 bfd_signed_vma odisp;
1405
f44f99a5
RH
1406 /* If not zero, place to jump without needing pv. */
1407 optdest = elf64_alpha_relax_opt_call (info, symval);
1408 org = (info->sec->output_section->vma
1409 + info->sec->output_offset
1410 + urel->r_offset + 4);
252b5132 1411 odisp = (optdest ? optdest : symval) - org;
f44f99a5 1412
252b5132
RH
1413 if (odisp >= -0x400000 && odisp < 0x400000)
1414 {
1415 Elf_Internal_Rela *xrel;
1416
fe8bc63d 1417 /* Preserve branch prediction call stack when possible. */
252b5132
RH
1418 if ((insn & INSN_JSR_MASK) == INSN_JSR)
1419 insn = (OP_BSR << 26) | (insn & 0x03e00000);
1420 else
1421 insn = (OP_BR << 26) | (insn & 0x03e00000);
fe8bc63d 1422
252b5132
RH
1423 urel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1424 R_ALPHA_BRADDR);
1425 urel->r_addend = irel->r_addend;
1426
1427 if (optdest)
1428 urel->r_addend += optdest - symval;
1429 else
b34976b6 1430 all_optimized = FALSE;
252b5132 1431
dc810e39
AM
1432 bfd_put_32 (info->abfd, (bfd_vma) insn,
1433 info->contents + urel->r_offset);
252b5132
RH
1434
1435 /* Kill any HINT reloc that might exist for this insn. */
1436 xrel = (elf64_alpha_find_reloc_at_ofs
fe8bc63d 1437 (info->relocs, info->relend, urel->r_offset,
252b5132
RH
1438 R_ALPHA_HINT));
1439 if (xrel)
1440 xrel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1441
b34976b6
AM
1442 info->changed_contents = TRUE;
1443 info->changed_relocs = TRUE;
252b5132
RH
1444 }
1445 else
b34976b6 1446 all_optimized = FALSE;
252b5132 1447
1cd6895c
RH
1448 /* Even if the target is not in range for a direct branch,
1449 if we share a GP, we can eliminate the gp reload. */
1450 if (optdest)
1451 {
1452 Elf_Internal_Rela *gpdisp
1453 = (elf64_alpha_find_reloc_at_ofs
9e756d64
RH
1454 (info->relocs, irelend, urel->r_offset + 4,
1455 R_ALPHA_GPDISP));
1cd6895c
RH
1456 if (gpdisp)
1457 {
cedb70c5 1458 bfd_byte *p_ldah = info->contents + gpdisp->r_offset;
1cd6895c
RH
1459 bfd_byte *p_lda = p_ldah + gpdisp->r_addend;
1460 unsigned int ldah = bfd_get_32 (info->abfd, p_ldah);
1461 unsigned int lda = bfd_get_32 (info->abfd, p_lda);
1462
1463 /* Verify that the instruction is "ldah $29,0($26)".
1464 Consider a function that ends in a noreturn call,
1465 and that the next function begins with an ldgp,
1466 and that by accident there is no padding between.
1467 In that case the insn would use $27 as the base. */
1468 if (ldah == 0x27ba0000 && lda == 0x23bd0000)
1469 {
dc810e39
AM
1470 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, p_ldah);
1471 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, p_lda);
1cd6895c
RH
1472
1473 gpdisp->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
b34976b6
AM
1474 info->changed_contents = TRUE;
1475 info->changed_relocs = TRUE;
1cd6895c
RH
1476 }
1477 }
1478 }
252b5132
RH
1479 }
1480 break;
1481 }
1482 }
1483
1484 /* If all cases were optimized, we can reduce the use count on this
1485 got entry by one, possibly eliminating it. */
1486 if (all_optimized)
1487 {
3765b1be
RH
1488 if (--info->gotent->use_count == 0)
1489 {
9e756d64
RH
1490 int sz = alpha_got_entry_size (R_ALPHA_LITERAL);
1491 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3765b1be 1492 if (!info->h)
9e756d64 1493 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
3765b1be 1494 }
252b5132
RH
1495
1496 /* If the literal instruction is no longer needed (it may have been
3765b1be
RH
1497 reused. We can eliminate it. */
1498 /* ??? For now, I don't want to deal with compacting the section,
252b5132
RH
1499 so just nop it out. */
1500 if (!lit_reused)
1501 {
1502 irel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
b34976b6 1503 info->changed_relocs = TRUE;
252b5132 1504
dc810e39
AM
1505 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP,
1506 info->contents + irel->r_offset);
b34976b6 1507 info->changed_contents = TRUE;
252b5132
RH
1508 }
1509 }
1510
b34976b6 1511 return TRUE;
252b5132
RH
1512}
1513
1514static bfd_vma
1515elf64_alpha_relax_opt_call (info, symval)
1516 struct alpha_relax_info *info;
1517 bfd_vma symval;
1518{
1519 /* If the function has the same gp, and we can identify that the
1520 function does not use its function pointer, we can eliminate the
1521 address load. */
1522
1523 /* If the symbol is marked NOPV, we are being told the function never
1524 needs its procedure value. */
c810873d 1525 if ((info->other & STO_ALPHA_STD_GPLOAD) == STO_ALPHA_NOPV)
252b5132
RH
1526 return symval;
1527
1528 /* If the symbol is marked STD_GP, we are being told the function does
fe8bc63d 1529 a normal ldgp in the first two words. */
c810873d 1530 else if ((info->other & STO_ALPHA_STD_GPLOAD) == STO_ALPHA_STD_GPLOAD)
252b5132
RH
1531 ;
1532
1533 /* Otherwise, we may be able to identify a GP load in the first two
1534 words, which we can then skip. */
fe8bc63d 1535 else
252b5132
RH
1536 {
1537 Elf_Internal_Rela *tsec_relocs, *tsec_relend, *tsec_free, *gpdisp;
1538 bfd_vma ofs;
1539
fe8bc63d 1540 /* Load the relocations from the section that the target symbol is in. */
252b5132
RH
1541 if (info->sec == info->tsec)
1542 {
1543 tsec_relocs = info->relocs;
1544 tsec_relend = info->relend;
1545 tsec_free = NULL;
1546 }
1547 else
1548 {
1549 tsec_relocs = (_bfd_elf64_link_read_relocs
1550 (info->abfd, info->tsec, (PTR) NULL,
1551 (Elf_Internal_Rela *) NULL,
1552 info->link_info->keep_memory));
1553 if (tsec_relocs == NULL)
1554 return 0;
1555 tsec_relend = tsec_relocs + info->tsec->reloc_count;
1556 tsec_free = (info->link_info->keep_memory ? NULL : tsec_relocs);
1557 }
1558
1559 /* Recover the symbol's offset within the section. */
1560 ofs = (symval - info->tsec->output_section->vma
1561 - info->tsec->output_offset);
fe8bc63d 1562
252b5132
RH
1563 /* Look for a GPDISP reloc. */
1564 gpdisp = (elf64_alpha_find_reloc_at_ofs
1565 (tsec_relocs, tsec_relend, ofs, R_ALPHA_GPDISP));
1566
1567 if (!gpdisp || gpdisp->r_addend != 4)
1568 {
1569 if (tsec_free)
1570 free (tsec_free);
1571 return 0;
1572 }
1573 if (tsec_free)
1574 free (tsec_free);
1575 }
1576
fe8bc63d 1577 /* We've now determined that we can skip an initial gp load. Verify
252b5132
RH
1578 that the call and the target use the same gp. */
1579 if (info->link_info->hash->creator != info->tsec->owner->xvec
1580 || info->gotobj != alpha_elf_tdata (info->tsec->owner)->gotobj)
1581 return 0;
1582
1583 return symval + 8;
1584}
1585
b34976b6 1586static bfd_boolean
9e756d64 1587elf64_alpha_relax_got_load (info, symval, irel, r_type)
252b5132
RH
1588 struct alpha_relax_info *info;
1589 bfd_vma symval;
1590 Elf_Internal_Rela *irel;
9e756d64 1591 unsigned long r_type;
252b5132
RH
1592{
1593 unsigned int insn;
1594 bfd_signed_vma disp;
1595
1596 /* Get the instruction. */
1597 insn = bfd_get_32 (info->abfd, info->contents + irel->r_offset);
1598
1599 if (insn >> 26 != OP_LDQ)
1600 {
9e756d64 1601 reloc_howto_type *howto = elf64_alpha_howto_table + r_type;
252b5132 1602 ((*_bfd_error_handler)
9e756d64 1603 ("%s: %s+0x%lx: warning: %s relocation against unexpected insn",
8f615d07 1604 bfd_archive_filename (info->abfd), info->sec->name,
9e756d64 1605 (unsigned long) irel->r_offset, howto->name));
b34976b6 1606 return TRUE;
252b5132
RH
1607 }
1608
9e756d64
RH
1609 /* Can't relax dynamic symbols. */
1610 if (alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info))
b34976b6 1611 return TRUE;
252b5132 1612
9e756d64
RH
1613 /* Can't use local-exec relocations in shared libraries. */
1614 if (r_type == R_ALPHA_GOTTPREL && info->link_info->shared)
b34976b6 1615 return TRUE;
252b5132 1616
9e756d64
RH
1617 if (r_type == R_ALPHA_LITERAL)
1618 disp = symval - info->gp;
1619 else
1620 {
1621 bfd_vma dtp_base, tp_base;
1622
1623 BFD_ASSERT (info->tls_segment != NULL);
1624 dtp_base = alpha_get_dtprel_base (info->tls_segment);
1625 tp_base = alpha_get_tprel_base (info->tls_segment);
1626 disp = symval - (r_type == R_ALPHA_GOTDTPREL ? dtp_base : tp_base);
1627 }
252b5132 1628
9e756d64 1629 if (disp < -0x8000 || disp >= 0x8000)
b34976b6 1630 return TRUE;
9e756d64
RH
1631
1632 /* Exchange LDQ for LDA. In the case of the TLS relocs, we're loading
1633 a constant, so force the base register to be $31. */
1634 if (r_type == R_ALPHA_LITERAL)
1635 insn = (OP_LDA << 26) | (insn & 0x03ff0000);
1636 else
1637 insn = (OP_LDA << 26) | (insn & (31 << 21)) | (31 << 16);
dc810e39 1638 bfd_put_32 (info->abfd, (bfd_vma) insn, info->contents + irel->r_offset);
b34976b6 1639 info->changed_contents = TRUE;
cedb70c5 1640
9e756d64
RH
1641 switch (r_type)
1642 {
1643 case R_ALPHA_LITERAL:
1644 r_type = R_ALPHA_GPREL16;
1645 break;
1646 case R_ALPHA_GOTDTPREL:
1647 r_type = R_ALPHA_DTPREL16;
1648 break;
1649 case R_ALPHA_GOTTPREL:
1650 r_type = R_ALPHA_TPREL16;
1651 break;
1652 default:
1653 BFD_ASSERT (0);
b34976b6 1654 return FALSE;
9e756d64 1655 }
252b5132 1656
9e756d64 1657 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info), r_type);
b34976b6 1658 info->changed_relocs = TRUE;
252b5132
RH
1659
1660 /* Reduce the use count on this got entry by one, possibly
1661 eliminating it. */
3765b1be
RH
1662 if (--info->gotent->use_count == 0)
1663 {
9e756d64
RH
1664 int sz = alpha_got_entry_size (r_type);
1665 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
3765b1be 1666 if (!info->h)
9e756d64 1667 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
3765b1be 1668 }
252b5132
RH
1669
1670 /* ??? Search forward through this basic block looking for insns
1671 that use the target register. Stop after an insn modifying the
1672 register is seen, or after a branch or call.
1673
1674 Any such memory load insn may be substituted by a load directly
1675 off the GP. This allows the memory load insn to be issued before
fe8bc63d 1676 the calculated GP register would otherwise be ready.
252b5132
RH
1677
1678 Any such jsr insn can be replaced by a bsr if it is in range.
1679
1680 This would mean that we'd have to _add_ relocations, the pain of
1681 which gives one pause. */
1682
b34976b6 1683 return TRUE;
252b5132
RH
1684}
1685
b34976b6 1686static bfd_boolean
9e756d64
RH
1687elf64_alpha_relax_gprelhilo (info, symval, irel, hi)
1688 struct alpha_relax_info *info;
1689 bfd_vma symval;
1690 Elf_Internal_Rela *irel;
b34976b6 1691 bfd_boolean hi;
9e756d64
RH
1692{
1693 unsigned int insn;
1694 bfd_signed_vma disp;
1695 bfd_byte *pos = info->contents + irel->r_offset;
1696
1697 /* ??? This assumes that the compiler doesn't render
1698
1699 array[i]
1700 as
1701 ldah t, array(gp) !gprelhigh
1702 s8addl i, t, t
1703 ldq r, array(t) !gprellow
1704
1705 which would indeed be the most efficient way to implement this. */
1706
b34976b6 1707 return TRUE;
9e756d64
RH
1708
1709 disp = symval - info->gp;
1710 if (disp < -0x8000 || disp >= 0x8000)
b34976b6 1711 return TRUE;
9e756d64
RH
1712
1713 if (hi)
1714 {
1715 /* Nop out the high instruction. */
1716
1717 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos);
b34976b6 1718 info->changed_contents = TRUE;
9e756d64
RH
1719
1720 irel->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1721 irel->r_addend = 0;
b34976b6 1722 info->changed_relocs = TRUE;
9e756d64
RH
1723 }
1724 else
1725 {
1726 /* Adjust the low instruction to reference GP directly. */
1727
1728 insn = bfd_get_32 (info->abfd, pos);
1729 insn = (insn & 0xffe00000) | (29 << 16);
1730 bfd_put_32 (info->abfd, (bfd_vma) insn, pos);
b34976b6 1731 info->changed_contents = TRUE;
9e756d64
RH
1732
1733 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1734 R_ALPHA_GPREL16);
b34976b6 1735 info->changed_relocs = TRUE;
9e756d64
RH
1736 }
1737
b34976b6 1738 return TRUE;
9e756d64
RH
1739}
1740
b34976b6 1741static bfd_boolean
9e756d64
RH
1742elf64_alpha_relax_tls_get_addr (info, symval, irel, is_gd)
1743 struct alpha_relax_info *info;
1744 bfd_vma symval;
1745 Elf_Internal_Rela *irel;
b34976b6 1746 bfd_boolean is_gd;
9e756d64
RH
1747{
1748 bfd_byte *pos[5];
1749 unsigned int insn;
1750 Elf_Internal_Rela *gpdisp, *hint;
b34976b6 1751 bfd_boolean dynamic, use_gottprel;
9e756d64
RH
1752
1753 dynamic = alpha_elf_dynamic_symbol_p (&info->h->root, info->link_info);
1754
1755 /* ??? For LD relaxation, we need a symbol referencing the beginning
1756 of the TLS segment. */
1757 if (!is_gd)
b34976b6 1758 return TRUE;
9e756d64
RH
1759
1760 /* If a TLS symbol is accessed using IE at least once, there is no point
1761 to use dynamic model for it. */
1762 if (is_gd && info->h && (info->h->flags & ALPHA_ELF_LINK_HASH_TLS_IE))
1763 ;
1764
1765 /* If the symbol is local, and we've already committed to DF_STATIC_TLS,
1766 then we might as well relax to IE. */
1767 else if (info->link_info->shared && !dynamic
1768 && (info->link_info->flags & DF_STATIC_TLS))
1769 ;
1770
1771 /* Otherwise we must be building an executable to do anything. */
1772 else if (info->link_info->shared)
b34976b6 1773 return TRUE;
9e756d64
RH
1774
1775 /* The TLSGD/TLSLDM relocation must be followed by a LITERAL and
1776 the matching LITUSE_TLS relocations. */
1777 if (irel + 2 >= info->relend)
b34976b6 1778 return TRUE;
9e756d64
RH
1779 if (ELF64_R_TYPE (irel[1].r_info) != R_ALPHA_LITERAL
1780 || ELF64_R_TYPE (irel[2].r_info) != R_ALPHA_LITUSE
1781 || irel[2].r_addend != (is_gd ? LITUSE_ALPHA_TLSGD : LITUSE_ALPHA_TLSLDM))
b34976b6 1782 return TRUE;
9e756d64
RH
1783
1784 /* There must be a GPDISP relocation positioned immediately after the
1785 LITUSE relocation. */
1786 gpdisp = elf64_alpha_find_reloc_at_ofs (info->relocs, info->relend,
1787 irel[2].r_offset + 4, R_ALPHA_GPDISP);
1788 if (!gpdisp)
b34976b6 1789 return TRUE;
9e756d64
RH
1790
1791 pos[0] = info->contents + irel[0].r_offset;
1792 pos[1] = info->contents + irel[1].r_offset;
1793 pos[2] = info->contents + irel[2].r_offset;
1794 pos[3] = info->contents + gpdisp->r_offset;
1795 pos[4] = pos[3] + gpdisp->r_addend;
1796
1797 /* Only positions 0 and 1 are allowed to be out of order. */
1798 if (pos[1] < pos[0])
1799 {
1800 bfd_byte *tmp = pos[0];
1801 pos[0] = pos[1];
1802 pos[1] = tmp;
1803 }
1804 if (pos[1] >= pos[2] || pos[2] >= pos[3] || pos[3] >= pos[4])
b34976b6 1805 return TRUE;
9e756d64
RH
1806
1807 /* Reduce the use count on the LITERAL relocation. Do this before we
1808 smash the symndx when we adjust the relocations below. */
1809 {
1810 struct alpha_elf_got_entry *lit_gotent;
1811 struct alpha_elf_link_hash_entry *lit_h;
1812 unsigned long indx;
1813
1814 BFD_ASSERT (ELF64_R_SYM (irel[1].r_info) >= info->symtab_hdr->sh_info);
1815 indx = ELF64_R_SYM (irel[1].r_info) - info->symtab_hdr->sh_info;
1816 lit_h = alpha_elf_sym_hashes (info->abfd)[indx];
1817
1818 while (lit_h->root.root.type == bfd_link_hash_indirect
1819 || lit_h->root.root.type == bfd_link_hash_warning)
1820 lit_h = (struct alpha_elf_link_hash_entry *) lit_h->root.root.u.i.link;
1821
1822 for (lit_gotent = lit_h->got_entries; lit_gotent ;
1823 lit_gotent = lit_gotent->next)
1824 if (lit_gotent->gotobj == info->gotobj
1825 && lit_gotent->reloc_type == R_ALPHA_LITERAL
1826 && lit_gotent->addend == irel[1].r_addend)
1827 break;
1828 BFD_ASSERT (lit_gotent);
1829
1830 if (--lit_gotent->use_count == 0)
1831 {
1832 int sz = alpha_got_entry_size (R_ALPHA_LITERAL);
1833 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
1834 }
1835 }
1836
1837 /* Change
1838
1839 lda $16,x($gp) !tlsgd!1
1840 ldq $27,__tls_get_addr($gp) !literal!1
1841 jsr $26,($27)__tls_get_addr !lituse_tlsgd!1
1842 ldah $29,0($26) !gpdisp!2
1843 lda $29,0($29) !gpdisp!2
1844 to
1845 ldq $16,x($gp) !gottprel
1846 unop
1847 call_pal rduniq
1848 addq $16,$0,$0
1849 unop
1850 or the first pair to
1851 lda $16,x($gp) !tprel
1852 unop
1853 or
1854 ldah $16,x($gp) !tprelhi
1855 lda $16,x($16) !tprello
1856
1857 as appropriate. */
1858
b34976b6 1859 use_gottprel = FALSE;
9e756d64
RH
1860 switch (!dynamic && !info->link_info->shared)
1861 {
1862 case 1:
1863 {
1864 bfd_vma tp_base;
1865 bfd_signed_vma disp;
1866
1867 BFD_ASSERT (info->tls_segment != NULL);
1868 tp_base = alpha_get_tprel_base (info->tls_segment);
1869 disp = symval - tp_base;
1870
1871 if (disp >= -0x8000 && disp < 0x8000)
1872 {
1873 insn = (OP_LDA << 26) | (16 << 21) | (31 << 16);
1874 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
1875 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]);
1876
1877 irel[0].r_offset = pos[0] - info->contents;
1878 irel[0].r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1879 R_ALPHA_TPREL16);
1880 irel[1].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1881 break;
1882 }
1883 else if (disp >= -(bfd_signed_vma) 0x80000000
1884 && disp < (bfd_signed_vma) 0x7fff8000)
1885 {
1886 insn = (OP_LDAH << 26) | (16 << 21) | (31 << 16);
1887 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
1888 insn = (OP_LDA << 26) | (16 << 21) | (16 << 16);
1889 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[1]);
1890
1891 irel[0].r_offset = pos[0] - info->contents;
1892 irel[0].r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1893 R_ALPHA_TPRELHI);
1894 irel[1].r_offset = pos[1] - info->contents;
1895 irel[1].r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1896 R_ALPHA_TPRELLO);
1897 break;
1898 }
1899 }
1900 /* FALLTHRU */
1901
1902 default:
b34976b6 1903 use_gottprel = TRUE;
9e756d64
RH
1904
1905 insn = (OP_LDQ << 26) | (16 << 21) | (29 << 16);
1906 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[0]);
1907 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[1]);
1908
1909 irel[0].r_offset = pos[0] - info->contents;
1910 irel[0].r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
1911 R_ALPHA_GOTTPREL);
1912 irel[1].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1913 break;
1914 }
1915
1916 bfd_put_32 (info->abfd, (bfd_vma) INSN_RDUNIQ, pos[2]);
1917
1918 insn = INSN_ADDQ | (16 << 21) | (0 << 16) | (0 << 0);
1919 bfd_put_32 (info->abfd, (bfd_vma) insn, pos[3]);
1920
1921 bfd_put_32 (info->abfd, (bfd_vma) INSN_UNOP, pos[4]);
1922
1923 irel[2].r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1924 gpdisp->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1925
1926 hint = elf64_alpha_find_reloc_at_ofs (info->relocs, info->relend,
1927 irel[2].r_offset, R_ALPHA_HINT);
1928 if (hint)
1929 hint->r_info = ELF64_R_INFO (0, R_ALPHA_NONE);
1930
b34976b6
AM
1931 info->changed_contents = TRUE;
1932 info->changed_relocs = TRUE;
9e756d64
RH
1933
1934 /* Reduce the use count on the TLSGD/TLSLDM relocation. */
1935 if (--info->gotent->use_count == 0)
1936 {
1937 int sz = alpha_got_entry_size (info->gotent->reloc_type);
1938 alpha_elf_tdata (info->gotobj)->total_got_size -= sz;
1939 if (!info->h)
1940 alpha_elf_tdata (info->gotobj)->local_got_size -= sz;
1941 }
1942
1943 /* If we've switched to a GOTTPREL relocation, increment the reference
1944 count on that got entry. */
1945 if (use_gottprel)
1946 {
1947 struct alpha_elf_got_entry *tprel_gotent;
1948
1949 for (tprel_gotent = *info->first_gotent; tprel_gotent ;
1950 tprel_gotent = tprel_gotent->next)
1951 if (tprel_gotent->gotobj == info->gotobj
1952 && tprel_gotent->reloc_type == R_ALPHA_GOTTPREL
1953 && tprel_gotent->addend == irel->r_addend)
1954 break;
1955 if (tprel_gotent)
1956 tprel_gotent->use_count++;
1957 else
1958 {
1959 if (info->gotent->use_count == 0)
1960 tprel_gotent = info->gotent;
1961 else
1962 {
1963 tprel_gotent = (struct alpha_elf_got_entry *)
1964 bfd_alloc (info->abfd, sizeof (struct alpha_elf_got_entry));
1965 if (!tprel_gotent)
b34976b6 1966 return FALSE;
9e756d64
RH
1967
1968 tprel_gotent->next = *info->first_gotent;
1969 *info->first_gotent = tprel_gotent;
1970
1971 tprel_gotent->gotobj = info->gotobj;
1972 tprel_gotent->addend = irel->r_addend;
1973 tprel_gotent->got_offset = -1;
1974 tprel_gotent->reloc_done = 0;
1975 tprel_gotent->reloc_xlated = 0;
1976 }
1977
1978 tprel_gotent->use_count = 1;
1979 tprel_gotent->reloc_type = R_ALPHA_GOTTPREL;
1980 }
1981 }
1982
b34976b6 1983 return TRUE;
9e756d64
RH
1984}
1985
1986static struct elf_link_tls_segment *
1987elf64_alpha_relax_find_tls_segment (info, seg)
1988 struct alpha_relax_info *info;
1989 struct elf_link_tls_segment *seg;
1990{
1991 bfd *output_bfd = info->sec->output_section->owner;
048d873d 1992 asection *o;
9e756d64
RH
1993 unsigned int align;
1994 bfd_vma base, end;
1995
1996 for (o = output_bfd->sections; o ; o = o->next)
1997 if ((o->flags & SEC_THREAD_LOCAL) != 0
1998 && (o->flags & SEC_LOAD) != 0)
048d873d
RH
1999 break;
2000 if (!o)
9e756d64
RH
2001 return NULL;
2002
048d873d 2003 base = o->vma;
9e756d64
RH
2004 align = 0;
2005
048d873d 2006 do
9e756d64
RH
2007 {
2008 bfd_vma size;
2009
2010 if (bfd_get_section_alignment (output_bfd, o) > align)
2011 align = bfd_get_section_alignment (output_bfd, o);
2012
2013 size = o->_raw_size;
2014 if (size == 0 && (o->flags & SEC_HAS_CONTENTS) == 0)
2015 {
2016 struct bfd_link_order *lo;
2017 for (lo = o->link_order_head; lo ; lo = lo->next)
2018 if (size < lo->offset + lo->size)
2019 size = lo->offset + lo->size;
2020 }
2021 end = o->vma + size;
048d873d 2022 o = o->next;
9e756d64 2023 }
048d873d 2024 while (o && (o->flags & SEC_THREAD_LOCAL));
9e756d64
RH
2025
2026 seg->start = base;
2027 seg->size = end - base;
2028 seg->align = align;
2029
2030 return seg;
2031}
2032
b34976b6 2033static bfd_boolean
252b5132
RH
2034elf64_alpha_relax_section (abfd, sec, link_info, again)
2035 bfd *abfd;
2036 asection *sec;
2037 struct bfd_link_info *link_info;
b34976b6 2038 bfd_boolean *again;
252b5132
RH
2039{
2040 Elf_Internal_Shdr *symtab_hdr;
2041 Elf_Internal_Rela *internal_relocs;
252b5132 2042 Elf_Internal_Rela *irel, *irelend;
6cdc0ccc 2043 Elf_Internal_Sym *isymbuf = NULL;
252b5132
RH
2044 struct alpha_elf_got_entry **local_got_entries;
2045 struct alpha_relax_info info;
9e756d64 2046 struct elf_link_tls_segment tls_segment;
252b5132
RH
2047
2048 /* We are not currently changing any sizes, so only one pass. */
b34976b6 2049 *again = FALSE;
252b5132
RH
2050
2051 if (link_info->relocateable
2052 || (sec->flags & SEC_RELOC) == 0
2053 || sec->reloc_count == 0)
b34976b6 2054 return TRUE;
252b5132
RH
2055
2056 /* If this is the first time we have been called for this section,
2057 initialize the cooked size. */
2058 if (sec->_cooked_size == 0)
2059 sec->_cooked_size = sec->_raw_size;
2060
2061 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
2062 local_got_entries = alpha_elf_tdata(abfd)->local_got_entries;
2063
2064 /* Load the relocations for this section. */
2065 internal_relocs = (_bfd_elf64_link_read_relocs
2066 (abfd, sec, (PTR) NULL, (Elf_Internal_Rela *) NULL,
2067 link_info->keep_memory));
2068 if (internal_relocs == NULL)
b34976b6 2069 return FALSE;
252b5132 2070
fe8bc63d 2071 memset(&info, 0, sizeof (info));
252b5132
RH
2072 info.abfd = abfd;
2073 info.sec = sec;
2074 info.link_info = link_info;
9e756d64 2075 info.symtab_hdr = symtab_hdr;
252b5132
RH
2076 info.relocs = internal_relocs;
2077 info.relend = irelend = internal_relocs + sec->reloc_count;
2078
cedb70c5 2079 /* Find the GP for this object. Do not store the result back via
b646261c 2080 _bfd_set_gp_value, since this could change again before final. */
252b5132
RH
2081 info.gotobj = alpha_elf_tdata (abfd)->gotobj;
2082 if (info.gotobj)
2083 {
2084 asection *sgot = alpha_elf_tdata (info.gotobj)->got;
b646261c
RH
2085 info.gp = (sgot->output_section->vma
2086 + sgot->output_offset
2087 + 0x8000);
252b5132
RH
2088 }
2089
9e756d64
RH
2090 /* Get the section contents. */
2091 if (elf_section_data (sec)->this_hdr.contents != NULL)
2092 info.contents = elf_section_data (sec)->this_hdr.contents;
2093 else
252b5132 2094 {
9e756d64 2095 info.contents = (bfd_byte *) bfd_malloc (sec->_raw_size);
252b5132 2096 if (info.contents == NULL)
9e756d64 2097 goto error_return;
252b5132 2098
9e756d64
RH
2099 if (! bfd_get_section_contents (abfd, sec, info.contents,
2100 (file_ptr) 0, sec->_raw_size))
2101 goto error_return;
2102 }
252b5132 2103
9e756d64
RH
2104 /* Compute the TLS segment information. The version normally found in
2105 elf_hash_table (link_info)->tls_segment isn't built until final_link.
2106 ??? Probably should look into extracting this into a common function. */
2107 info.tls_segment = elf64_alpha_relax_find_tls_segment (&info, &tls_segment);
2108
2109 for (irel = internal_relocs; irel < irelend; irel++)
2110 {
2111 bfd_vma symval;
9e756d64
RH
2112 struct alpha_elf_got_entry *gotent;
2113 unsigned long r_type = ELF64_R_TYPE (irel->r_info);
2114
2115 /* Early exit for unhandled or unrelaxable relocations. */
2116 switch (r_type)
2117 {
2118 case R_ALPHA_LITERAL:
2119 case R_ALPHA_GPRELHIGH:
2120 case R_ALPHA_GPRELLOW:
2121 case R_ALPHA_GOTDTPREL:
2122 case R_ALPHA_GOTTPREL:
2123 case R_ALPHA_TLSGD:
2124 case R_ALPHA_TLSLDM:
2125 break;
2126 default:
2127 continue;
252b5132
RH
2128 }
2129
2130 /* Get the value of the symbol referred to by the reloc. */
2131 if (ELF64_R_SYM (irel->r_info) < symtab_hdr->sh_info)
2132 {
2133 /* A local symbol. */
6cdc0ccc
AM
2134 Elf_Internal_Sym *isym;
2135
2136 /* Read this BFD's local symbols. */
2137 if (isymbuf == NULL)
2138 {
2139 isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
2140 if (isymbuf == NULL)
2141 isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
2142 symtab_hdr->sh_info, 0,
2143 NULL, NULL, NULL);
2144 if (isymbuf == NULL)
2145 goto error_return;
2146 }
2147
2148 isym = isymbuf + ELF64_R_SYM (irel->r_info);
2149 if (isym->st_shndx == SHN_UNDEF)
4a67a098 2150 continue;
6cdc0ccc 2151 else if (isym->st_shndx == SHN_ABS)
252b5132 2152 info.tsec = bfd_abs_section_ptr;
6cdc0ccc 2153 else if (isym->st_shndx == SHN_COMMON)
252b5132 2154 info.tsec = bfd_com_section_ptr;
fe8bc63d 2155 else
6cdc0ccc 2156 info.tsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
252b5132
RH
2157
2158 info.h = NULL;
6cdc0ccc 2159 info.other = isym->st_other;
9e756d64 2160 info.first_gotent = &local_got_entries[ELF64_R_SYM(irel->r_info)];
6cdc0ccc 2161 symval = isym->st_value;
252b5132
RH
2162 }
2163 else
2164 {
2165 unsigned long indx;
2166 struct alpha_elf_link_hash_entry *h;
2167
2168 indx = ELF64_R_SYM (irel->r_info) - symtab_hdr->sh_info;
2169 h = alpha_elf_sym_hashes (abfd)[indx];
2170 BFD_ASSERT (h != NULL);
2171
2172 while (h->root.root.type == bfd_link_hash_indirect
2173 || h->root.root.type == bfd_link_hash_warning)
2174 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
2175
4a67a098
RH
2176 /* If the symbol is undefined, we can't do anything with it. */
2177 if (h->root.root.type == bfd_link_hash_undefweak
2178 || h->root.root.type == bfd_link_hash_undefined)
2179 continue;
2180
2181 /* If the symbol isn't defined in the current module, again
2182 we can't do anything. */
2183 if (!(h->root.elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR))
2184 continue;
2185
252b5132 2186 info.h = h;
252b5132
RH
2187 info.tsec = h->root.root.u.def.section;
2188 info.other = h->root.other;
9e756d64 2189 info.first_gotent = &h->got_entries;
252b5132
RH
2190 symval = h->root.root.u.def.value;
2191 }
2192
2193 /* Search for the got entry to be used by this relocation. */
9e756d64
RH
2194 for (gotent = *info.first_gotent; gotent ; gotent = gotent->next)
2195 if (gotent->gotobj == info.gotobj
2196 && gotent->reloc_type == r_type
2197 && gotent->addend == irel->r_addend)
2198 break;
252b5132
RH
2199 info.gotent = gotent;
2200
2201 symval += info.tsec->output_section->vma + info.tsec->output_offset;
2202 symval += irel->r_addend;
2203
9e756d64
RH
2204 switch (r_type)
2205 {
2206 case R_ALPHA_LITERAL:
2207 BFD_ASSERT(info.gotent != NULL);
252b5132 2208
9e756d64
RH
2209 /* If there exist LITUSE relocations immediately following, this
2210 opens up all sorts of interesting optimizations, because we
2211 now know every location that this address load is used. */
2212 if (irel+1 < irelend
2213 && ELF64_R_TYPE (irel[1].r_info) == R_ALPHA_LITUSE)
2214 {
2215 if (!elf64_alpha_relax_with_lituse (&info, symval, irel))
2216 goto error_return;
2217 }
2218 else
2219 {
2220 if (!elf64_alpha_relax_got_load (&info, symval, irel, r_type))
2221 goto error_return;
2222 }
2223 break;
252b5132 2224
9e756d64
RH
2225 case R_ALPHA_GPRELHIGH:
2226 case R_ALPHA_GPRELLOW:
2227 if (!elf64_alpha_relax_gprelhilo (&info, symval, irel,
2228 r_type == R_ALPHA_GPRELHIGH))
252b5132 2229 goto error_return;
9e756d64
RH
2230 break;
2231
2232 case R_ALPHA_GOTDTPREL:
2233 case R_ALPHA_GOTTPREL:
2234 BFD_ASSERT(info.gotent != NULL);
2235 if (!elf64_alpha_relax_got_load (&info, symval, irel, r_type))
252b5132 2236 goto error_return;
9e756d64
RH
2237 break;
2238
2239 case R_ALPHA_TLSGD:
2240 case R_ALPHA_TLSLDM:
2241 BFD_ASSERT(info.gotent != NULL);
2242 if (!elf64_alpha_relax_tls_get_addr (&info, symval, irel,
2243 r_type == R_ALPHA_TLSGD))
2244 goto error_return;
2245 break;
252b5132
RH
2246 }
2247 }
2248
f44f99a5 2249 if (!elf64_alpha_size_plt_section (link_info))
b34976b6 2250 return FALSE;
f44f99a5 2251 if (!elf64_alpha_size_got_sections (link_info))
b34976b6 2252 return FALSE;
f44f99a5 2253 if (!elf64_alpha_size_rela_got_section (link_info))
b34976b6 2254 return FALSE;
252b5132 2255
6cdc0ccc
AM
2256 if (isymbuf != NULL
2257 && symtab_hdr->contents != (unsigned char *) isymbuf)
2258 {
2259 if (!link_info->keep_memory)
2260 free (isymbuf);
2261 else
2262 {
2263 /* Cache the symbols for elf_link_input_bfd. */
2264 symtab_hdr->contents = (unsigned char *) isymbuf;
2265 }
2266 }
252b5132 2267
6cdc0ccc
AM
2268 if (info.contents != NULL
2269 && elf_section_data (sec)->this_hdr.contents != info.contents)
252b5132 2270 {
6cdc0ccc
AM
2271 if (!info.changed_contents && !link_info->keep_memory)
2272 free (info.contents);
252b5132
RH
2273 else
2274 {
2275 /* Cache the section contents for elf_link_input_bfd. */
2276 elf_section_data (sec)->this_hdr.contents = info.contents;
2277 }
2278 }
2279
6cdc0ccc 2280 if (elf_section_data (sec)->relocs != internal_relocs)
252b5132 2281 {
6cdc0ccc
AM
2282 if (!info.changed_relocs)
2283 free (internal_relocs);
252b5132 2284 else
6cdc0ccc 2285 elf_section_data (sec)->relocs = internal_relocs;
252b5132
RH
2286 }
2287
2288 *again = info.changed_contents || info.changed_relocs;
2289
b34976b6 2290 return TRUE;
252b5132
RH
2291
2292 error_return:
6cdc0ccc
AM
2293 if (isymbuf != NULL
2294 && symtab_hdr->contents != (unsigned char *) isymbuf)
2295 free (isymbuf);
2296 if (info.contents != NULL
2297 && elf_section_data (sec)->this_hdr.contents != info.contents)
2298 free (info.contents);
2299 if (internal_relocs != NULL
2300 && elf_section_data (sec)->relocs != internal_relocs)
2301 free (internal_relocs);
b34976b6 2302 return FALSE;
252b5132
RH
2303}
2304\f
2305/* PLT/GOT Stuff */
2306#define PLT_HEADER_SIZE 32
dc810e39
AM
2307#define PLT_HEADER_WORD1 (bfd_vma) 0xc3600000 /* br $27,.+4 */
2308#define PLT_HEADER_WORD2 (bfd_vma) 0xa77b000c /* ldq $27,12($27) */
2309#define PLT_HEADER_WORD3 (bfd_vma) 0x47ff041f /* nop */
2310#define PLT_HEADER_WORD4 (bfd_vma) 0x6b7b0000 /* jmp $27,($27) */
252b5132
RH
2311
2312#define PLT_ENTRY_SIZE 12
2313#define PLT_ENTRY_WORD1 0xc3800000 /* br $28, plt0 */
2314#define PLT_ENTRY_WORD2 0
2315#define PLT_ENTRY_WORD3 0
2316
3765b1be 2317#define MAX_GOT_SIZE (64*1024)
252b5132
RH
2318
2319#define ELF_DYNAMIC_INTERPRETER "/usr/lib/ld.so"
2320\f
2321/* Handle an Alpha specific section when reading an object file. This
2322 is called when elfcode.h finds a section with an unknown type.
2323 FIXME: We need to handle the SHF_ALPHA_GPREL flag, but I'm not sure
2324 how to. */
2325
b34976b6 2326static bfd_boolean
252b5132
RH
2327elf64_alpha_section_from_shdr (abfd, hdr, name)
2328 bfd *abfd;
947216bf 2329 Elf_Internal_Shdr *hdr;
90937f86 2330 const char *name;
252b5132
RH
2331{
2332 asection *newsect;
2333
2334 /* There ought to be a place to keep ELF backend specific flags, but
2335 at the moment there isn't one. We just keep track of the
2336 sections by their name, instead. Fortunately, the ABI gives
2337 suggested names for all the MIPS specific sections, so we will
2338 probably get away with this. */
2339 switch (hdr->sh_type)
2340 {
2341 case SHT_ALPHA_DEBUG:
2342 if (strcmp (name, ".mdebug") != 0)
b34976b6 2343 return FALSE;
252b5132 2344 break;
252b5132 2345 default:
b34976b6 2346 return FALSE;
252b5132
RH
2347 }
2348
2349 if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name))
b34976b6 2350 return FALSE;
252b5132
RH
2351 newsect = hdr->bfd_section;
2352
2353 if (hdr->sh_type == SHT_ALPHA_DEBUG)
2354 {
2355 if (! bfd_set_section_flags (abfd, newsect,
2356 (bfd_get_section_flags (abfd, newsect)
2357 | SEC_DEBUGGING)))
b34976b6 2358 return FALSE;
252b5132
RH
2359 }
2360
b34976b6 2361 return TRUE;
252b5132
RH
2362}
2363
204692d7
RH
2364/* Convert Alpha specific section flags to bfd internal section flags. */
2365
b34976b6 2366static bfd_boolean
204692d7
RH
2367elf64_alpha_section_flags (flags, hdr)
2368 flagword *flags;
947216bf 2369 Elf_Internal_Shdr *hdr;
204692d7
RH
2370{
2371 if (hdr->sh_flags & SHF_ALPHA_GPREL)
2372 *flags |= SEC_SMALL_DATA;
2373
b34976b6 2374 return TRUE;
204692d7
RH
2375}
2376
252b5132
RH
2377/* Set the correct type for an Alpha ELF section. We do this by the
2378 section name, which is a hack, but ought to work. */
2379
b34976b6 2380static bfd_boolean
252b5132
RH
2381elf64_alpha_fake_sections (abfd, hdr, sec)
2382 bfd *abfd;
947216bf 2383 Elf_Internal_Shdr *hdr;
252b5132
RH
2384 asection *sec;
2385{
2386 register const char *name;
2387
2388 name = bfd_get_section_name (abfd, sec);
2389
2390 if (strcmp (name, ".mdebug") == 0)
2391 {
2392 hdr->sh_type = SHT_ALPHA_DEBUG;
2393 /* In a shared object on Irix 5.3, the .mdebug section has an
2394 entsize of 0. FIXME: Does this matter? */
2395 if ((abfd->flags & DYNAMIC) != 0 )
2396 hdr->sh_entsize = 0;
2397 else
2398 hdr->sh_entsize = 1;
2399 }
204692d7
RH
2400 else if ((sec->flags & SEC_SMALL_DATA)
2401 || strcmp (name, ".sdata") == 0
252b5132
RH
2402 || strcmp (name, ".sbss") == 0
2403 || strcmp (name, ".lit4") == 0
2404 || strcmp (name, ".lit8") == 0)
2405 hdr->sh_flags |= SHF_ALPHA_GPREL;
2406
b34976b6 2407 return TRUE;
252b5132
RH
2408}
2409
2410/* Hook called by the linker routine which adds symbols from an object
2411 file. We use it to put .comm items in .sbss, and not .bss. */
2412
b34976b6 2413static bfd_boolean
252b5132
RH
2414elf64_alpha_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
2415 bfd *abfd;
2416 struct bfd_link_info *info;
2417 const Elf_Internal_Sym *sym;
56fc028e
AJ
2418 const char **namep ATTRIBUTE_UNUSED;
2419 flagword *flagsp ATTRIBUTE_UNUSED;
252b5132
RH
2420 asection **secp;
2421 bfd_vma *valp;
2422{
2423 if (sym->st_shndx == SHN_COMMON
2424 && !info->relocateable
c0846b23 2425 && sym->st_size <= elf_gp_size (abfd))
252b5132
RH
2426 {
2427 /* Common symbols less than or equal to -G nn bytes are
2428 automatically put into .sbss. */
2429
2430 asection *scomm = bfd_get_section_by_name (abfd, ".scommon");
2431
2432 if (scomm == NULL)
2433 {
2434 scomm = bfd_make_section (abfd, ".scommon");
2435 if (scomm == NULL
2436 || !bfd_set_section_flags (abfd, scomm, (SEC_ALLOC
2437 | SEC_IS_COMMON
2438 | SEC_LINKER_CREATED)))
b34976b6 2439 return FALSE;
252b5132
RH
2440 }
2441
2442 *secp = scomm;
2443 *valp = sym->st_size;
2444 }
2445
b34976b6 2446 return TRUE;
252b5132
RH
2447}
2448
2449/* Create the .got section. */
2450
b34976b6 2451static bfd_boolean
252b5132
RH
2452elf64_alpha_create_got_section(abfd, info)
2453 bfd *abfd;
56fc028e 2454 struct bfd_link_info *info ATTRIBUTE_UNUSED;
252b5132
RH
2455{
2456 asection *s;
2457
2458 if (bfd_get_section_by_name (abfd, ".got"))
b34976b6 2459 return TRUE;
252b5132
RH
2460
2461 s = bfd_make_section (abfd, ".got");
2462 if (s == NULL
2463 || !bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
2464 | SEC_HAS_CONTENTS
2465 | SEC_IN_MEMORY
2466 | SEC_LINKER_CREATED))
2467 || !bfd_set_section_alignment (abfd, s, 3))
b34976b6 2468 return FALSE;
252b5132
RH
2469
2470 alpha_elf_tdata (abfd)->got = s;
2471
b34976b6 2472 return TRUE;
252b5132
RH
2473}
2474
2475/* Create all the dynamic sections. */
2476
b34976b6 2477static bfd_boolean
252b5132
RH
2478elf64_alpha_create_dynamic_sections (abfd, info)
2479 bfd *abfd;
2480 struct bfd_link_info *info;
2481{
2482 asection *s;
2483 struct elf_link_hash_entry *h;
14a793b2 2484 struct bfd_link_hash_entry *bh;
252b5132
RH
2485
2486 /* We need to create .plt, .rela.plt, .got, and .rela.got sections. */
2487
2488 s = bfd_make_section (abfd, ".plt");
2489 if (s == NULL
2490 || ! bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
2491 | SEC_HAS_CONTENTS
2492 | SEC_IN_MEMORY
2493 | SEC_LINKER_CREATED
2494 | SEC_CODE))
2495 || ! bfd_set_section_alignment (abfd, s, 3))
b34976b6 2496 return FALSE;
252b5132
RH
2497
2498 /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
2499 .plt section. */
14a793b2 2500 bh = NULL;
252b5132
RH
2501 if (! (_bfd_generic_link_add_one_symbol
2502 (info, abfd, "_PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s,
b34976b6 2503 (bfd_vma) 0, (const char *) NULL, FALSE,
14a793b2 2504 get_elf_backend_data (abfd)->collect, &bh)))
b34976b6 2505 return FALSE;
14a793b2 2506 h = (struct elf_link_hash_entry *) bh;
252b5132
RH
2507 h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
2508 h->type = STT_OBJECT;
2509
2510 if (info->shared
2511 && ! _bfd_elf_link_record_dynamic_symbol (info, h))
b34976b6 2512 return FALSE;
252b5132
RH
2513
2514 s = bfd_make_section (abfd, ".rela.plt");
2515 if (s == NULL
2516 || !bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
2517 | SEC_HAS_CONTENTS
2518 | SEC_IN_MEMORY
2519 | SEC_LINKER_CREATED
2520 | SEC_READONLY))
2521 || ! bfd_set_section_alignment (abfd, s, 3))
b34976b6 2522 return FALSE;
252b5132
RH
2523
2524 /* We may or may not have created a .got section for this object, but
2525 we definitely havn't done the rest of the work. */
2526
2527 if (!elf64_alpha_create_got_section (abfd, info))
b34976b6 2528 return FALSE;
252b5132
RH
2529
2530 s = bfd_make_section(abfd, ".rela.got");
2531 if (s == NULL
2532 || !bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
2533 | SEC_HAS_CONTENTS
2534 | SEC_IN_MEMORY
2535 | SEC_LINKER_CREATED
2536 | SEC_READONLY))
2537 || !bfd_set_section_alignment (abfd, s, 3))
b34976b6 2538 return FALSE;
252b5132
RH
2539
2540 /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the
2541 dynobj's .got section. We don't do this in the linker script
2542 because we don't want to define the symbol if we are not creating
2543 a global offset table. */
14a793b2 2544 bh = NULL;
252b5132
RH
2545 if (!(_bfd_generic_link_add_one_symbol
2546 (info, abfd, "_GLOBAL_OFFSET_TABLE_", BSF_GLOBAL,
2547 alpha_elf_tdata(abfd)->got, (bfd_vma) 0, (const char *) NULL,
b34976b6
AM
2548 FALSE, get_elf_backend_data (abfd)->collect, &bh)))
2549 return FALSE;
14a793b2 2550 h = (struct elf_link_hash_entry *) bh;
252b5132
RH
2551 h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
2552 h->type = STT_OBJECT;
2553
2554 if (info->shared
2555 && ! _bfd_elf_link_record_dynamic_symbol (info, h))
b34976b6 2556 return FALSE;
252b5132
RH
2557
2558 elf_hash_table (info)->hgot = h;
2559
b34976b6 2560 return TRUE;
252b5132
RH
2561}
2562\f
2563/* Read ECOFF debugging information from a .mdebug section into a
2564 ecoff_debug_info structure. */
2565
b34976b6 2566static bfd_boolean
252b5132
RH
2567elf64_alpha_read_ecoff_info (abfd, section, debug)
2568 bfd *abfd;
2569 asection *section;
2570 struct ecoff_debug_info *debug;
2571{
2572 HDRR *symhdr;
2573 const struct ecoff_debug_swap *swap;
2574 char *ext_hdr = NULL;
2575
2576 swap = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
fe8bc63d 2577 memset (debug, 0, sizeof (*debug));
252b5132 2578
dc810e39 2579 ext_hdr = (char *) bfd_malloc (swap->external_hdr_size);
252b5132
RH
2580 if (ext_hdr == NULL && swap->external_hdr_size != 0)
2581 goto error_return;
2582
82e51918
AM
2583 if (! bfd_get_section_contents (abfd, section, ext_hdr, (file_ptr) 0,
2584 swap->external_hdr_size))
252b5132
RH
2585 goto error_return;
2586
2587 symhdr = &debug->symbolic_header;
2588 (*swap->swap_hdr_in) (abfd, ext_hdr, symhdr);
2589
2590 /* The symbolic header contains absolute file offsets and sizes to
2591 read. */
2592#define READ(ptr, offset, count, size, type) \
2593 if (symhdr->count == 0) \
2594 debug->ptr = NULL; \
2595 else \
2596 { \
dc810e39
AM
2597 bfd_size_type amt = (bfd_size_type) size * symhdr->count; \
2598 debug->ptr = (type) bfd_malloc (amt); \
252b5132
RH
2599 if (debug->ptr == NULL) \
2600 goto error_return; \
2601 if (bfd_seek (abfd, (file_ptr) symhdr->offset, SEEK_SET) != 0 \
dc810e39 2602 || bfd_bread (debug->ptr, amt, abfd) != amt) \
252b5132
RH
2603 goto error_return; \
2604 }
2605
2606 READ (line, cbLineOffset, cbLine, sizeof (unsigned char), unsigned char *);
2607 READ (external_dnr, cbDnOffset, idnMax, swap->external_dnr_size, PTR);
2608 READ (external_pdr, cbPdOffset, ipdMax, swap->external_pdr_size, PTR);
2609 READ (external_sym, cbSymOffset, isymMax, swap->external_sym_size, PTR);
2610 READ (external_opt, cbOptOffset, ioptMax, swap->external_opt_size, PTR);
2611 READ (external_aux, cbAuxOffset, iauxMax, sizeof (union aux_ext),
2612 union aux_ext *);
2613 READ (ss, cbSsOffset, issMax, sizeof (char), char *);
2614 READ (ssext, cbSsExtOffset, issExtMax, sizeof (char), char *);
2615 READ (external_fdr, cbFdOffset, ifdMax, swap->external_fdr_size, PTR);
2616 READ (external_rfd, cbRfdOffset, crfd, swap->external_rfd_size, PTR);
2617 READ (external_ext, cbExtOffset, iextMax, swap->external_ext_size, PTR);
2618#undef READ
2619
2620 debug->fdr = NULL;
2621 debug->adjust = NULL;
2622
b34976b6 2623 return TRUE;
252b5132
RH
2624
2625 error_return:
2626 if (ext_hdr != NULL)
2627 free (ext_hdr);
2628 if (debug->line != NULL)
2629 free (debug->line);
2630 if (debug->external_dnr != NULL)
2631 free (debug->external_dnr);
2632 if (debug->external_pdr != NULL)
2633 free (debug->external_pdr);
2634 if (debug->external_sym != NULL)
2635 free (debug->external_sym);
2636 if (debug->external_opt != NULL)
2637 free (debug->external_opt);
2638 if (debug->external_aux != NULL)
2639 free (debug->external_aux);
2640 if (debug->ss != NULL)
2641 free (debug->ss);
2642 if (debug->ssext != NULL)
2643 free (debug->ssext);
2644 if (debug->external_fdr != NULL)
2645 free (debug->external_fdr);
2646 if (debug->external_rfd != NULL)
2647 free (debug->external_rfd);
2648 if (debug->external_ext != NULL)
2649 free (debug->external_ext);
b34976b6 2650 return FALSE;
252b5132
RH
2651}
2652
2653/* Alpha ELF local labels start with '$'. */
2654
b34976b6 2655static bfd_boolean
252b5132 2656elf64_alpha_is_local_label_name (abfd, name)
56fc028e 2657 bfd *abfd ATTRIBUTE_UNUSED;
252b5132
RH
2658 const char *name;
2659{
2660 return name[0] == '$';
2661}
2662
2663/* Alpha ELF follows MIPS ELF in using a special find_nearest_line
2664 routine in order to handle the ECOFF debugging information. We
2665 still call this mips_elf_find_line because of the slot
2666 find_line_info in elf_obj_tdata is declared that way. */
2667
2668struct mips_elf_find_line
2669{
2670 struct ecoff_debug_info d;
2671 struct ecoff_find_line i;
2672};
2673
b34976b6 2674static bfd_boolean
252b5132
RH
2675elf64_alpha_find_nearest_line (abfd, section, symbols, offset, filename_ptr,
2676 functionname_ptr, line_ptr)
2677 bfd *abfd;
2678 asection *section;
2679 asymbol **symbols;
2680 bfd_vma offset;
2681 const char **filename_ptr;
2682 const char **functionname_ptr;
2683 unsigned int *line_ptr;
2684{
2685 asection *msec;
2686
95404643
RH
2687 if (_bfd_dwarf2_find_nearest_line (abfd, section, symbols, offset,
2688 filename_ptr, functionname_ptr,
2689 line_ptr, 0,
2690 &elf_tdata (abfd)->dwarf2_find_line_info))
b34976b6 2691 return TRUE;
95404643 2692
252b5132
RH
2693 msec = bfd_get_section_by_name (abfd, ".mdebug");
2694 if (msec != NULL)
2695 {
2696 flagword origflags;
2697 struct mips_elf_find_line *fi;
2698 const struct ecoff_debug_swap * const swap =
2699 get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
2700
2701 /* If we are called during a link, alpha_elf_final_link may have
2702 cleared the SEC_HAS_CONTENTS field. We force it back on here
2703 if appropriate (which it normally will be). */
2704 origflags = msec->flags;
2705 if (elf_section_data (msec)->this_hdr.sh_type != SHT_NOBITS)
2706 msec->flags |= SEC_HAS_CONTENTS;
2707
2708 fi = elf_tdata (abfd)->find_line_info;
2709 if (fi == NULL)
2710 {
2711 bfd_size_type external_fdr_size;
2712 char *fraw_src;
2713 char *fraw_end;
2714 struct fdr *fdr_ptr;
dc810e39 2715 bfd_size_type amt = sizeof (struct mips_elf_find_line);
252b5132 2716
dc810e39 2717 fi = (struct mips_elf_find_line *) bfd_zalloc (abfd, amt);
252b5132
RH
2718 if (fi == NULL)
2719 {
2720 msec->flags = origflags;
b34976b6 2721 return FALSE;
252b5132
RH
2722 }
2723
2724 if (!elf64_alpha_read_ecoff_info (abfd, msec, &fi->d))
2725 {
2726 msec->flags = origflags;
b34976b6 2727 return FALSE;
252b5132
RH
2728 }
2729
2730 /* Swap in the FDR information. */
dc810e39
AM
2731 amt = fi->d.symbolic_header.ifdMax * sizeof (struct fdr);
2732 fi->d.fdr = (struct fdr *) bfd_alloc (abfd, amt);
252b5132
RH
2733 if (fi->d.fdr == NULL)
2734 {
2735 msec->flags = origflags;
b34976b6 2736 return FALSE;
252b5132
RH
2737 }
2738 external_fdr_size = swap->external_fdr_size;
2739 fdr_ptr = fi->d.fdr;
2740 fraw_src = (char *) fi->d.external_fdr;
2741 fraw_end = (fraw_src
2742 + fi->d.symbolic_header.ifdMax * external_fdr_size);
2743 for (; fraw_src < fraw_end; fraw_src += external_fdr_size, fdr_ptr++)
2744 (*swap->swap_fdr_in) (abfd, (PTR) fraw_src, fdr_ptr);
2745
2746 elf_tdata (abfd)->find_line_info = fi;
2747
2748 /* Note that we don't bother to ever free this information.
2749 find_nearest_line is either called all the time, as in
2750 objdump -l, so the information should be saved, or it is
2751 rarely called, as in ld error messages, so the memory
2752 wasted is unimportant. Still, it would probably be a
2753 good idea for free_cached_info to throw it away. */
2754 }
2755
2756 if (_bfd_ecoff_locate_line (abfd, section, offset, &fi->d, swap,
2757 &fi->i, filename_ptr, functionname_ptr,
2758 line_ptr))
2759 {
2760 msec->flags = origflags;
b34976b6 2761 return TRUE;
252b5132
RH
2762 }
2763
2764 msec->flags = origflags;
2765 }
2766
2767 /* Fall back on the generic ELF find_nearest_line routine. */
2768
2769 return _bfd_elf_find_nearest_line (abfd, section, symbols, offset,
2770 filename_ptr, functionname_ptr,
2771 line_ptr);
2772}
2773\f
2774/* Structure used to pass information to alpha_elf_output_extsym. */
2775
2776struct extsym_info
2777{
2778 bfd *abfd;
2779 struct bfd_link_info *info;
2780 struct ecoff_debug_info *debug;
2781 const struct ecoff_debug_swap *swap;
b34976b6 2782 bfd_boolean failed;
252b5132
RH
2783};
2784
b34976b6 2785static bfd_boolean
252b5132
RH
2786elf64_alpha_output_extsym (h, data)
2787 struct alpha_elf_link_hash_entry *h;
2788 PTR data;
2789{
2790 struct extsym_info *einfo = (struct extsym_info *) data;
b34976b6 2791 bfd_boolean strip;
252b5132
RH
2792 asection *sec, *output_section;
2793
e92d460e
AM
2794 if (h->root.root.type == bfd_link_hash_warning)
2795 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
2796
252b5132 2797 if (h->root.indx == -2)
b34976b6 2798 strip = FALSE;
252b5132 2799 else if (((h->root.elf_link_hash_flags & ELF_LINK_HASH_DEF_DYNAMIC) != 0
e92d460e
AM
2800 || (h->root.elf_link_hash_flags & ELF_LINK_HASH_REF_DYNAMIC) != 0)
2801 && (h->root.elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR) == 0
2802 && (h->root.elf_link_hash_flags & ELF_LINK_HASH_REF_REGULAR) == 0)
b34976b6 2803 strip = TRUE;
252b5132 2804 else if (einfo->info->strip == strip_all
e92d460e
AM
2805 || (einfo->info->strip == strip_some
2806 && bfd_hash_lookup (einfo->info->keep_hash,
2807 h->root.root.root.string,
b34976b6
AM
2808 FALSE, FALSE) == NULL))
2809 strip = TRUE;
252b5132 2810 else
b34976b6 2811 strip = FALSE;
252b5132
RH
2812
2813 if (strip)
b34976b6 2814 return TRUE;
252b5132
RH
2815
2816 if (h->esym.ifd == -2)
2817 {
2818 h->esym.jmptbl = 0;
2819 h->esym.cobol_main = 0;
2820 h->esym.weakext = 0;
2821 h->esym.reserved = 0;
2822 h->esym.ifd = ifdNil;
2823 h->esym.asym.value = 0;
2824 h->esym.asym.st = stGlobal;
2825
2826 if (h->root.root.type != bfd_link_hash_defined
e92d460e
AM
2827 && h->root.root.type != bfd_link_hash_defweak)
2828 h->esym.asym.sc = scAbs;
252b5132 2829 else
e92d460e
AM
2830 {
2831 const char *name;
2832
2833 sec = h->root.root.u.def.section;
2834 output_section = sec->output_section;
2835
2836 /* When making a shared library and symbol h is the one from
2837 the another shared library, OUTPUT_SECTION may be null. */
2838 if (output_section == NULL)
2839 h->esym.asym.sc = scUndefined;
2840 else
2841 {
2842 name = bfd_section_name (output_section->owner, output_section);
2843
2844 if (strcmp (name, ".text") == 0)
2845 h->esym.asym.sc = scText;
2846 else if (strcmp (name, ".data") == 0)
2847 h->esym.asym.sc = scData;
2848 else if (strcmp (name, ".sdata") == 0)
2849 h->esym.asym.sc = scSData;
2850 else if (strcmp (name, ".rodata") == 0
2851 || strcmp (name, ".rdata") == 0)
2852 h->esym.asym.sc = scRData;
2853 else if (strcmp (name, ".bss") == 0)
2854 h->esym.asym.sc = scBss;
2855 else if (strcmp (name, ".sbss") == 0)
2856 h->esym.asym.sc = scSBss;
2857 else if (strcmp (name, ".init") == 0)
2858 h->esym.asym.sc = scInit;
2859 else if (strcmp (name, ".fini") == 0)
2860 h->esym.asym.sc = scFini;
2861 else
2862 h->esym.asym.sc = scAbs;
2863 }
2864 }
252b5132
RH
2865
2866 h->esym.asym.reserved = 0;
2867 h->esym.asym.index = indexNil;
2868 }
2869
2870 if (h->root.root.type == bfd_link_hash_common)
2871 h->esym.asym.value = h->root.root.u.c.size;
2872 else if (h->root.root.type == bfd_link_hash_defined
2873 || h->root.root.type == bfd_link_hash_defweak)
2874 {
2875 if (h->esym.asym.sc == scCommon)
e92d460e 2876 h->esym.asym.sc = scBss;
252b5132 2877 else if (h->esym.asym.sc == scSCommon)
e92d460e 2878 h->esym.asym.sc = scSBss;
252b5132
RH
2879
2880 sec = h->root.root.u.def.section;
2881 output_section = sec->output_section;
2882 if (output_section != NULL)
e92d460e
AM
2883 h->esym.asym.value = (h->root.root.u.def.value
2884 + sec->output_offset
2885 + output_section->vma);
252b5132 2886 else
e92d460e 2887 h->esym.asym.value = 0;
252b5132
RH
2888 }
2889 else if ((h->root.elf_link_hash_flags & ELF_LINK_HASH_NEEDS_PLT) != 0)
2890 {
2891 /* Set type and value for a symbol with a function stub. */
2892 h->esym.asym.st = stProc;
2893 sec = bfd_get_section_by_name (einfo->abfd, ".plt");
2894 if (sec == NULL)
2895 h->esym.asym.value = 0;
2896 else
2897 {
2898 output_section = sec->output_section;
2899 if (output_section != NULL)
2900 h->esym.asym.value = (h->root.plt.offset
2901 + sec->output_offset
2902 + output_section->vma);
2903 else
2904 h->esym.asym.value = 0;
2905 }
252b5132
RH
2906 }
2907
2908 if (! bfd_ecoff_debug_one_external (einfo->abfd, einfo->debug, einfo->swap,
e92d460e
AM
2909 h->root.root.root.string,
2910 &h->esym))
252b5132 2911 {
b34976b6
AM
2912 einfo->failed = TRUE;
2913 return FALSE;
252b5132
RH
2914 }
2915
b34976b6 2916 return TRUE;
252b5132 2917}
252b5132 2918\f
3765b1be
RH
2919/* Search for and possibly create a got entry. */
2920
2921static struct alpha_elf_got_entry *
2922get_got_entry (abfd, h, r_type, r_symndx, r_addend)
2923 bfd *abfd;
2924 struct alpha_elf_link_hash_entry *h;
2925 unsigned long r_type, r_symndx;
2926 bfd_vma r_addend;
2927{
2928 struct alpha_elf_got_entry *gotent;
2929 struct alpha_elf_got_entry **slot;
2930
2931 if (h)
2932 slot = &h->got_entries;
2933 else
2934 {
2935 /* This is a local .got entry -- record for merge. */
2936
2937 struct alpha_elf_got_entry **local_got_entries;
2938
2939 local_got_entries = alpha_elf_tdata(abfd)->local_got_entries;
2940 if (!local_got_entries)
2941 {
2942 bfd_size_type size;
2943 Elf_Internal_Shdr *symtab_hdr;
2944
2945 symtab_hdr = &elf_tdata(abfd)->symtab_hdr;
2946 size = symtab_hdr->sh_info;
2947 size *= sizeof (struct alpha_elf_got_entry *);
2948
2949 local_got_entries
9bab7074 2950 = (struct alpha_elf_got_entry **) bfd_zalloc (abfd, size);
3765b1be
RH
2951 if (!local_got_entries)
2952 return NULL;
2953
3765b1be
RH
2954 alpha_elf_tdata (abfd)->local_got_entries = local_got_entries;
2955 }
2956
2957 slot = &local_got_entries[r_symndx];
2958 }
2959
2960 for (gotent = *slot; gotent ; gotent = gotent->next)
2961 if (gotent->gotobj == abfd
2962 && gotent->reloc_type == r_type
2963 && gotent->addend == r_addend)
2964 break;
2965
2966 if (!gotent)
2967 {
2968 int entry_size;
2969 bfd_size_type amt;
2970
2971 amt = sizeof (struct alpha_elf_got_entry);
2972 gotent = (struct alpha_elf_got_entry *) bfd_alloc (abfd, amt);
2973 if (!gotent)
2974 return NULL;
2975
2976 gotent->gotobj = abfd;
2977 gotent->addend = r_addend;
2978 gotent->got_offset = -1;
2979 gotent->use_count = 1;
2980 gotent->reloc_type = r_type;
2981 gotent->reloc_done = 0;
2982 gotent->reloc_xlated = 0;
2983
2984 gotent->next = *slot;
2985 *slot = gotent;
2986
2987 entry_size = alpha_got_entry_size (r_type);
2988 alpha_elf_tdata (abfd)->total_got_size += entry_size;
2989 if (!h)
2990 alpha_elf_tdata(abfd)->local_got_size += entry_size;
2991 }
2992 else
2993 gotent->use_count += 1;
2994
2995 return gotent;
2996}
2997
252b5132
RH
2998/* Handle dynamic relocations when doing an Alpha ELF link. */
2999
b34976b6 3000static bfd_boolean
252b5132
RH
3001elf64_alpha_check_relocs (abfd, info, sec, relocs)
3002 bfd *abfd;
3003 struct bfd_link_info *info;
3004 asection *sec;
3005 const Elf_Internal_Rela *relocs;
3006{
3007 bfd *dynobj;
3008 asection *sreloc;
3009 const char *rel_sec_name;
3010 Elf_Internal_Shdr *symtab_hdr;
3011 struct alpha_elf_link_hash_entry **sym_hashes;
252b5132 3012 const Elf_Internal_Rela *rel, *relend;
b34976b6 3013 bfd_boolean got_created;
dc810e39 3014 bfd_size_type amt;
252b5132
RH
3015
3016 if (info->relocateable)
b34976b6 3017 return TRUE;
252b5132
RH
3018
3019 dynobj = elf_hash_table(info)->dynobj;
3020 if (dynobj == NULL)
3021 elf_hash_table(info)->dynobj = dynobj = abfd;
3022
3023 sreloc = NULL;
3024 rel_sec_name = NULL;
3025 symtab_hdr = &elf_tdata(abfd)->symtab_hdr;
3026 sym_hashes = alpha_elf_sym_hashes(abfd);
b34976b6 3027 got_created = FALSE;
252b5132
RH
3028
3029 relend = relocs + sec->reloc_count;
3030 for (rel = relocs; rel < relend; ++rel)
3031 {
3765b1be
RH
3032 enum {
3033 NEED_GOT = 1,
3034 NEED_GOT_ENTRY = 2,
3035 NEED_DYNREL = 4
3036 };
3037
252b5132
RH
3038 unsigned long r_symndx, r_type;
3039 struct alpha_elf_link_hash_entry *h;
3765b1be 3040 unsigned int gotent_flags;
b34976b6 3041 bfd_boolean maybe_dynamic;
3765b1be
RH
3042 unsigned int need;
3043 bfd_vma addend;
252b5132
RH
3044
3045 r_symndx = ELF64_R_SYM (rel->r_info);
3046 if (r_symndx < symtab_hdr->sh_info)
3047 h = NULL;
3048 else
3049 {
3050 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
3051
3052 while (h->root.root.type == bfd_link_hash_indirect
3053 || h->root.root.type == bfd_link_hash_warning)
3054 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
3055
3056 h->root.elf_link_hash_flags |= ELF_LINK_HASH_REF_REGULAR;
3057 }
3765b1be
RH
3058
3059 /* We can only get preliminary data on whether a symbol is
3060 locally or externally defined, as not all of the input files
3061 have yet been processed. Do something with what we know, as
3062 this may help reduce memory usage and processing time later. */
b34976b6 3063 maybe_dynamic = FALSE;
3765b1be
RH
3064 if (h && ((info->shared
3065 && (!info->symbolic || info->allow_shlib_undefined))
3066 || ! (h->root.elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR)
c853d7f6 3067 || h->root.root.type == bfd_link_hash_defweak))
b34976b6 3068 maybe_dynamic = TRUE;
3765b1be
RH
3069
3070 need = 0;
3071 gotent_flags = 0;
252b5132 3072 r_type = ELF64_R_TYPE (rel->r_info);
3765b1be 3073 addend = rel->r_addend;
252b5132
RH
3074
3075 switch (r_type)
3076 {
3077 case R_ALPHA_LITERAL:
3765b1be
RH
3078 need = NEED_GOT | NEED_GOT_ENTRY;
3079
3080 /* Remember how this literal is used from its LITUSEs.
3081 This will be important when it comes to decide if we can
3082 create a .plt entry for a function symbol. */
3083 while (++rel < relend && ELF64_R_TYPE (rel->r_info) == R_ALPHA_LITUSE)
3084 if (rel->r_addend >= 1 && rel->r_addend <= 5)
3085 gotent_flags |= 1 << rel->r_addend;
3086 --rel;
3087
3088 /* No LITUSEs -- presumably the address is used somehow. */
3089 if (gotent_flags == 0)
3090 gotent_flags = ALPHA_ELF_LINK_HASH_LU_ADDR;
3091 break;
252b5132
RH
3092
3093 case R_ALPHA_GPDISP:
dfe57ca0 3094 case R_ALPHA_GPREL16:
252b5132
RH
3095 case R_ALPHA_GPREL32:
3096 case R_ALPHA_GPRELHIGH:
3097 case R_ALPHA_GPRELLOW:
7793f4d0 3098 case R_ALPHA_BRSGP:
3765b1be
RH
3099 need = NEED_GOT;
3100 break;
3101
3102 case R_ALPHA_REFLONG:
3103 case R_ALPHA_REFQUAD:
475c2a7e 3104 if ((info->shared && (sec->flags & SEC_ALLOC)) || maybe_dynamic)
3765b1be
RH
3105 need = NEED_DYNREL;
3106 break;
3107
3108 case R_ALPHA_TLSGD:
3109 case R_ALPHA_TLSLDM:
3110 case R_ALPHA_GOTDTPREL:
3111 need = NEED_GOT | NEED_GOT_ENTRY;
3112 break;
3113
3114 case R_ALPHA_GOTTPREL:
3115 need = NEED_GOT | NEED_GOT_ENTRY;
9e756d64 3116 gotent_flags = ALPHA_ELF_LINK_HASH_TLS_IE;
3765b1be
RH
3117 if (info->shared)
3118 info->flags |= DF_STATIC_TLS;
3119 break;
3120
3121 case R_ALPHA_TPREL64:
3122 if (info->shared || maybe_dynamic)
3123 need = NEED_DYNREL;
3124 if (info->shared)
3125 info->flags |= DF_STATIC_TLS;
3126 break;
3127 }
3128
3129 if (need & NEED_GOT)
3130 {
252b5132
RH
3131 if (!got_created)
3132 {
3133 if (!elf64_alpha_create_got_section (abfd, info))
b34976b6 3134 return FALSE;
252b5132
RH
3135
3136 /* Make sure the object's gotobj is set to itself so
3137 that we default to every object with its own .got.
3138 We'll merge .gots later once we've collected each
3139 object's info. */
3140 alpha_elf_tdata(abfd)->gotobj = abfd;
3141
3142 got_created = 1;
3143 }
3765b1be 3144 }
252b5132 3145
3765b1be
RH
3146 if (need & NEED_GOT_ENTRY)
3147 {
3148 struct alpha_elf_got_entry *gotent;
252b5132 3149
3765b1be
RH
3150 gotent = get_got_entry (abfd, h, r_type, r_symndx, addend);
3151 if (!gotent)
b34976b6 3152 return FALSE;
3765b1be
RH
3153
3154 if (gotent_flags)
3155 {
3156 gotent->flags |= gotent_flags;
3157 if (h)
3158 {
3159 gotent_flags |= h->flags;
3160 h->flags = gotent_flags;
3161
3162 /* Make a guess as to whether a .plt entry is needed. */
3163 if ((gotent_flags & ALPHA_ELF_LINK_HASH_LU_FUNC)
3164 && !(gotent_flags & ~ALPHA_ELF_LINK_HASH_LU_FUNC))
3165 h->root.elf_link_hash_flags |= ELF_LINK_HASH_NEEDS_PLT;
3166 else
3167 h->root.elf_link_hash_flags &= ~ELF_LINK_HASH_NEEDS_PLT;
3168 }
3169 }
3170 }
3171
3172 if (need & NEED_DYNREL)
3173 {
252b5132
RH
3174 if (rel_sec_name == NULL)
3175 {
3176 rel_sec_name = (bfd_elf_string_from_elf_section
3177 (abfd, elf_elfheader(abfd)->e_shstrndx,
3178 elf_section_data(sec)->rel_hdr.sh_name));
3179 if (rel_sec_name == NULL)
b34976b6 3180 return FALSE;
252b5132
RH
3181
3182 BFD_ASSERT (strncmp (rel_sec_name, ".rela", 5) == 0
3183 && strcmp (bfd_get_section_name (abfd, sec),
3184 rel_sec_name+5) == 0);
3185 }
3186
3187 /* We need to create the section here now whether we eventually
3188 use it or not so that it gets mapped to an output section by
3189 the linker. If not used, we'll kill it in
3190 size_dynamic_sections. */
3191 if (sreloc == NULL)
3192 {
3193 sreloc = bfd_get_section_by_name (dynobj, rel_sec_name);
3194 if (sreloc == NULL)
3195 {
dc810e39
AM
3196 flagword flags;
3197
252b5132 3198 sreloc = bfd_make_section (dynobj, rel_sec_name);
dc810e39
AM
3199 flags = (SEC_HAS_CONTENTS | SEC_IN_MEMORY
3200 | SEC_LINKER_CREATED | SEC_READONLY);
3201 if (sec->flags & SEC_ALLOC)
3202 flags |= SEC_ALLOC | SEC_LOAD;
252b5132 3203 if (sreloc == NULL
dc810e39 3204 || !bfd_set_section_flags (dynobj, sreloc, flags)
252b5132 3205 || !bfd_set_section_alignment (dynobj, sreloc, 3))
b34976b6 3206 return FALSE;
252b5132
RH
3207 }
3208 }
3209
3210 if (h)
3211 {
3212 /* Since we havn't seen all of the input symbols yet, we
3213 don't know whether we'll actually need a dynamic relocation
3214 entry for this reloc. So make a record of it. Once we
3215 find out if this thing needs dynamic relocation we'll
fe8bc63d 3216 expand the relocation sections by the appropriate amount. */
252b5132
RH
3217
3218 struct alpha_elf_reloc_entry *rent;
3219
3220 for (rent = h->reloc_entries; rent; rent = rent->next)
3221 if (rent->rtype == r_type && rent->srel == sreloc)
3222 break;
3223
3224 if (!rent)
3225 {
dc810e39
AM
3226 amt = sizeof (struct alpha_elf_reloc_entry);
3227 rent = (struct alpha_elf_reloc_entry *) bfd_alloc (abfd, amt);
252b5132 3228 if (!rent)
b34976b6 3229 return FALSE;
252b5132
RH
3230
3231 rent->srel = sreloc;
3232 rent->rtype = r_type;
3233 rent->count = 1;
73896efb
RH
3234 rent->reltext = ((sec->flags & (SEC_READONLY | SEC_ALLOC))
3235 == (SEC_READONLY | SEC_ALLOC));
252b5132
RH
3236
3237 rent->next = h->reloc_entries;
3238 h->reloc_entries = rent;
3239 }
3240 else
3241 rent->count++;
3242 }
c853d7f6 3243 else if (info->shared)
252b5132 3244 {
c555c5c5
AM
3245 /* If this is a shared library, and the section is to be
3246 loaded into memory, we need a RELATIVE reloc. */
252b5132 3247 sreloc->_raw_size += sizeof (Elf64_External_Rela);
c853d7f6
RH
3248 if ((sec->flags & (SEC_READONLY | SEC_ALLOC))
3249 == (SEC_READONLY | SEC_ALLOC))
fcfbdf31 3250 info->flags |= DF_TEXTREL;
252b5132 3251 }
252b5132
RH
3252 }
3253 }
3254
b34976b6 3255 return TRUE;
252b5132
RH
3256}
3257
3258/* Adjust a symbol defined by a dynamic object and referenced by a
3259 regular object. The current definition is in some section of the
3260 dynamic object, but we're not including those sections. We have to
3261 change the definition to something the rest of the link can
3262 understand. */
3263
b34976b6 3264static bfd_boolean
252b5132
RH
3265elf64_alpha_adjust_dynamic_symbol (info, h)
3266 struct bfd_link_info *info;
3267 struct elf_link_hash_entry *h;
3268{
3269 bfd *dynobj;
3270 asection *s;
3271 struct alpha_elf_link_hash_entry *ah;
3272
3273 dynobj = elf_hash_table(info)->dynobj;
3274 ah = (struct alpha_elf_link_hash_entry *)h;
3275
3276 /* Now that we've seen all of the input symbols, finalize our decision
3277 about whether this symbol should get a .plt entry. */
3278
8ba89f17 3279 if (alpha_elf_dynamic_symbol_p (h, info)
252b5132
RH
3280 && ((h->type == STT_FUNC
3281 && !(ah->flags & ALPHA_ELF_LINK_HASH_LU_ADDR))
3282 || (h->type == STT_NOTYPE
3765b1be
RH
3283 && (ah->flags & ALPHA_ELF_LINK_HASH_LU_FUNC)
3284 && !(ah->flags & ~ALPHA_ELF_LINK_HASH_LU_FUNC)))
252b5132
RH
3285 /* Don't prevent otherwise valid programs from linking by attempting
3286 to create a new .got entry somewhere. A Correct Solution would be
3287 to add a new .got section to a new object file and let it be merged
3288 somewhere later. But for now don't bother. */
3289 && ah->got_entries)
3290 {
3291 h->elf_link_hash_flags |= ELF_LINK_HASH_NEEDS_PLT;
3292
3293 s = bfd_get_section_by_name(dynobj, ".plt");
3294 if (!s && !elf64_alpha_create_dynamic_sections (dynobj, info))
b34976b6 3295 return FALSE;
252b5132
RH
3296
3297 /* The first bit of the .plt is reserved. */
3298 if (s->_raw_size == 0)
3299 s->_raw_size = PLT_HEADER_SIZE;
3300
3301 h->plt.offset = s->_raw_size;
3302 s->_raw_size += PLT_ENTRY_SIZE;
3303
3304 /* If this symbol is not defined in a regular file, and we are not
3305 generating a shared library, then set the symbol to the location
3306 in the .plt. This is required to make function pointers compare
3307 equal between the normal executable and the shared library. */
3308 if (! info->shared
3309 && h->root.type != bfd_link_hash_defweak)
3310 {
3311 h->root.u.def.section = s;
3312 h->root.u.def.value = h->plt.offset;
3313 }
3314
3315 /* We also need a JMP_SLOT entry in the .rela.plt section. */
3316 s = bfd_get_section_by_name (dynobj, ".rela.plt");
3317 BFD_ASSERT (s != NULL);
3318 s->_raw_size += sizeof (Elf64_External_Rela);
3319
b34976b6 3320 return TRUE;
252b5132
RH
3321 }
3322 else
3323 h->elf_link_hash_flags &= ~ELF_LINK_HASH_NEEDS_PLT;
3324
3325 /* If this is a weak symbol, and there is a real definition, the
3326 processor independent code will have arranged for us to see the
3327 real definition first, and we can just use the same value. */
3328 if (h->weakdef != NULL)
3329 {
3330 BFD_ASSERT (h->weakdef->root.type == bfd_link_hash_defined
3331 || h->weakdef->root.type == bfd_link_hash_defweak);
3332 h->root.u.def.section = h->weakdef->root.u.def.section;
3333 h->root.u.def.value = h->weakdef->root.u.def.value;
b34976b6 3334 return TRUE;
252b5132
RH
3335 }
3336
3337 /* This is a reference to a symbol defined by a dynamic object which
3338 is not a function. The Alpha, since it uses .got entries for all
3339 symbols even in regular objects, does not need the hackery of a
3340 .dynbss section and COPY dynamic relocations. */
3341
b34976b6 3342 return TRUE;
252b5132
RH
3343}
3344
3345/* Symbol versioning can create new symbols, and make our old symbols
3346 indirect to the new ones. Consolidate the got and reloc information
3347 in these situations. */
3348
b34976b6 3349static bfd_boolean
252b5132
RH
3350elf64_alpha_merge_ind_symbols (hi, dummy)
3351 struct alpha_elf_link_hash_entry *hi;
56fc028e 3352 PTR dummy ATTRIBUTE_UNUSED;
252b5132
RH
3353{
3354 struct alpha_elf_link_hash_entry *hs;
3355
3356 if (hi->root.root.type != bfd_link_hash_indirect)
b34976b6 3357 return TRUE;
252b5132
RH
3358 hs = hi;
3359 do {
3360 hs = (struct alpha_elf_link_hash_entry *)hs->root.root.u.i.link;
3361 } while (hs->root.root.type == bfd_link_hash_indirect);
3362
3363 /* Merge the flags. Whee. */
3364
3365 hs->flags |= hi->flags;
3366
3367 /* Merge the .got entries. Cannibalize the old symbol's list in
3368 doing so, since we don't need it anymore. */
3369
3370 if (hs->got_entries == NULL)
3371 hs->got_entries = hi->got_entries;
3372 else
3373 {
3374 struct alpha_elf_got_entry *gi, *gs, *gin, *gsh;
3375
3376 gsh = hs->got_entries;
3377 for (gi = hi->got_entries; gi ; gi = gin)
3378 {
3379 gin = gi->next;
3380 for (gs = gsh; gs ; gs = gs->next)
3765b1be
RH
3381 if (gi->gotobj == gs->gotobj
3382 && gi->reloc_type == gs->reloc_type
3383 && gi->addend == gs->addend)
3384 {
3385 gi->use_count += gs->use_count;
3386 goto got_found;
3387 }
252b5132
RH
3388 gi->next = hs->got_entries;
3389 hs->got_entries = gi;
3390 got_found:;
3391 }
3392 }
3393 hi->got_entries = NULL;
3394
3395 /* And similar for the reloc entries. */
3396
3397 if (hs->reloc_entries == NULL)
3398 hs->reloc_entries = hi->reloc_entries;
3399 else
3400 {
3401 struct alpha_elf_reloc_entry *ri, *rs, *rin, *rsh;
3402
3403 rsh = hs->reloc_entries;
3404 for (ri = hi->reloc_entries; ri ; ri = rin)
3405 {
3406 rin = ri->next;
3407 for (rs = rsh; rs ; rs = rs->next)
82988bff 3408 if (ri->rtype == rs->rtype && ri->srel == rs->srel)
252b5132
RH
3409 {
3410 rs->count += ri->count;
3411 goto found_reloc;
3412 }
3413 ri->next = hs->reloc_entries;
3414 hs->reloc_entries = ri;
3415 found_reloc:;
3416 }
3417 }
3418 hi->reloc_entries = NULL;
3419
b34976b6 3420 return TRUE;
252b5132
RH
3421}
3422
3423/* Is it possible to merge two object file's .got tables? */
3424
b34976b6 3425static bfd_boolean
252b5132
RH
3426elf64_alpha_can_merge_gots (a, b)
3427 bfd *a, *b;
3428{
3765b1be 3429 int total = alpha_elf_tdata (a)->total_got_size;
252b5132
RH
3430 bfd *bsub;
3431
3432 /* Trivial quick fallout test. */
3765b1be 3433 if (total + alpha_elf_tdata (b)->total_got_size <= MAX_GOT_SIZE)
b34976b6 3434 return TRUE;
252b5132
RH
3435
3436 /* By their nature, local .got entries cannot be merged. */
3765b1be 3437 if ((total += alpha_elf_tdata (b)->local_got_size) > MAX_GOT_SIZE)
b34976b6 3438 return FALSE;
252b5132
RH
3439
3440 /* Failing the common trivial comparison, we must effectively
3441 perform the merge. Not actually performing the merge means that
3442 we don't have to store undo information in case we fail. */
3443 for (bsub = b; bsub ; bsub = alpha_elf_tdata (bsub)->in_got_link_next)
3444 {
3445 struct alpha_elf_link_hash_entry **hashes = alpha_elf_sym_hashes (bsub);
3446 Elf_Internal_Shdr *symtab_hdr = &elf_tdata (bsub)->symtab_hdr;
3447 int i, n;
3448
d9bc7a44 3449 n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info;
252b5132
RH
3450 for (i = 0; i < n; ++i)
3451 {
3452 struct alpha_elf_got_entry *ae, *be;
3453 struct alpha_elf_link_hash_entry *h;
3454
3455 h = hashes[i];
3456 while (h->root.root.type == bfd_link_hash_indirect
3457 || h->root.root.type == bfd_link_hash_warning)
3458 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
3459
3460 for (be = h->got_entries; be ; be = be->next)
3461 {
3462 if (be->use_count == 0)
3463 continue;
3464 if (be->gotobj != b)
3465 continue;
3466
3467 for (ae = h->got_entries; ae ; ae = ae->next)
3765b1be
RH
3468 if (ae->gotobj == a
3469 && ae->reloc_type == be->reloc_type
3470 && ae->addend == be->addend)
252b5132
RH
3471 goto global_found;
3472
3765b1be
RH
3473 total += alpha_got_entry_size (be->reloc_type);
3474 if (total > MAX_GOT_SIZE)
b34976b6 3475 return FALSE;
252b5132
RH
3476 global_found:;
3477 }
3478 }
3479 }
3480
b34976b6 3481 return TRUE;
252b5132
RH
3482}
3483
3484/* Actually merge two .got tables. */
3485
3486static void
3487elf64_alpha_merge_gots (a, b)
3488 bfd *a, *b;
3489{
3765b1be 3490 int total = alpha_elf_tdata (a)->total_got_size;
252b5132
RH
3491 bfd *bsub;
3492
3493 /* Remember local expansion. */
3494 {
3765b1be 3495 int e = alpha_elf_tdata (b)->local_got_size;
252b5132 3496 total += e;
3765b1be 3497 alpha_elf_tdata (a)->local_got_size += e;
252b5132
RH
3498 }
3499
3500 for (bsub = b; bsub ; bsub = alpha_elf_tdata (bsub)->in_got_link_next)
3501 {
3502 struct alpha_elf_got_entry **local_got_entries;
3503 struct alpha_elf_link_hash_entry **hashes;
3504 Elf_Internal_Shdr *symtab_hdr;
3505 int i, n;
3506
3507 /* Let the local .got entries know they are part of a new subsegment. */
3508 local_got_entries = alpha_elf_tdata (bsub)->local_got_entries;
3509 if (local_got_entries)
3510 {
3511 n = elf_tdata (bsub)->symtab_hdr.sh_info;
3512 for (i = 0; i < n; ++i)
3513 {
3514 struct alpha_elf_got_entry *ent;
3515 for (ent = local_got_entries[i]; ent; ent = ent->next)
3516 ent->gotobj = a;
3517 }
3518 }
3519
3520 /* Merge the global .got entries. */
3521 hashes = alpha_elf_sym_hashes (bsub);
3522 symtab_hdr = &elf_tdata (bsub)->symtab_hdr;
3523
d9bc7a44 3524 n = NUM_SHDR_ENTRIES (symtab_hdr) - symtab_hdr->sh_info;
252b5132
RH
3525 for (i = 0; i < n; ++i)
3526 {
3527 struct alpha_elf_got_entry *ae, *be, **pbe, **start;
3528 struct alpha_elf_link_hash_entry *h;
3529
3530 h = hashes[i];
3531 while (h->root.root.type == bfd_link_hash_indirect
3532 || h->root.root.type == bfd_link_hash_warning)
3533 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
3534
3535 start = &h->got_entries;
3536 for (pbe = start, be = *start; be ; pbe = &be->next, be = be->next)
3537 {
3538 if (be->use_count == 0)
3539 {
3540 *pbe = be->next;
3541 continue;
3542 }
3543 if (be->gotobj != b)
3544 continue;
3545
3546 for (ae = *start; ae ; ae = ae->next)
3765b1be
RH
3547 if (ae->gotobj == a
3548 && ae->reloc_type == be->reloc_type
3549 && ae->addend == be->addend)
252b5132
RH
3550 {
3551 ae->flags |= be->flags;
3552 ae->use_count += be->use_count;
3553 *pbe = be->next;
3554 goto global_found;
3555 }
3556 be->gotobj = a;
3765b1be 3557 total += alpha_got_entry_size (be->reloc_type);
252b5132
RH
3558
3559 global_found:;
3560 }
3561 }
3562
3563 alpha_elf_tdata (bsub)->gotobj = a;
3564 }
3765b1be 3565 alpha_elf_tdata (a)->total_got_size = total;
252b5132
RH
3566
3567 /* Merge the two in_got chains. */
3568 {
3569 bfd *next;
3570
3571 bsub = a;
3572 while ((next = alpha_elf_tdata (bsub)->in_got_link_next) != NULL)
3573 bsub = next;
3574
3575 alpha_elf_tdata (bsub)->in_got_link_next = b;
3576 }
3577}
3578
3579/* Calculate the offsets for the got entries. */
3580
b34976b6 3581static bfd_boolean
252b5132
RH
3582elf64_alpha_calc_got_offsets_for_symbol (h, arg)
3583 struct alpha_elf_link_hash_entry *h;
52b9d213 3584 PTR arg ATTRIBUTE_UNUSED;
252b5132
RH
3585{
3586 struct alpha_elf_got_entry *gotent;
3587
e92d460e
AM
3588 if (h->root.root.type == bfd_link_hash_warning)
3589 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
3590
252b5132
RH
3591 for (gotent = h->got_entries; gotent; gotent = gotent->next)
3592 if (gotent->use_count > 0)
3593 {
3594 bfd_size_type *plge
3595 = &alpha_elf_tdata (gotent->gotobj)->got->_raw_size;
3596
3597 gotent->got_offset = *plge;
3765b1be 3598 *plge += alpha_got_entry_size (gotent->reloc_type);
252b5132
RH
3599 }
3600
b34976b6 3601 return TRUE;
252b5132
RH
3602}
3603
3604static void
3605elf64_alpha_calc_got_offsets (info)
3606 struct bfd_link_info *info;
3607{
3608 bfd *i, *got_list = alpha_elf_hash_table(info)->got_list;
3609
3610 /* First, zero out the .got sizes, as we may be recalculating the
3611 .got after optimizing it. */
3612 for (i = got_list; i ; i = alpha_elf_tdata(i)->got_link_next)
3613 alpha_elf_tdata(i)->got->_raw_size = 0;
3614
3615 /* Next, fill in the offsets for all the global entries. */
3616 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
3617 elf64_alpha_calc_got_offsets_for_symbol,
3618 NULL);
3619
3620 /* Finally, fill in the offsets for the local entries. */
3621 for (i = got_list; i ; i = alpha_elf_tdata(i)->got_link_next)
3622 {
3623 bfd_size_type got_offset = alpha_elf_tdata(i)->got->_raw_size;
3624 bfd *j;
3625
3626 for (j = i; j ; j = alpha_elf_tdata(j)->in_got_link_next)
3627 {
3628 struct alpha_elf_got_entry **local_got_entries, *gotent;
3629 int k, n;
3630
3631 local_got_entries = alpha_elf_tdata(j)->local_got_entries;
3632 if (!local_got_entries)
3633 continue;
3634
3635 for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k)
3636 for (gotent = local_got_entries[k]; gotent; gotent = gotent->next)
3637 if (gotent->use_count > 0)
3638 {
3639 gotent->got_offset = got_offset;
3765b1be 3640 got_offset += alpha_got_entry_size (gotent->reloc_type);
252b5132
RH
3641 }
3642 }
3643
3644 alpha_elf_tdata(i)->got->_raw_size = got_offset;
3645 alpha_elf_tdata(i)->got->_cooked_size = got_offset;
3646 }
3647}
3648
3649/* Constructs the gots. */
3650
b34976b6 3651static bfd_boolean
f44f99a5 3652elf64_alpha_size_got_sections (info)
252b5132
RH
3653 struct bfd_link_info *info;
3654{
52b9d213 3655 bfd *i, *got_list, *cur_got_obj = NULL;
252b5132
RH
3656 int something_changed = 0;
3657
3658 got_list = alpha_elf_hash_table (info)->got_list;
3659
3660 /* On the first time through, pretend we have an existing got list
3661 consisting of all of the input files. */
3662 if (got_list == NULL)
3663 {
3664 for (i = info->input_bfds; i ; i = i->link_next)
3665 {
3666 bfd *this_got = alpha_elf_tdata (i)->gotobj;
3667 if (this_got == NULL)
3668 continue;
3669
3670 /* We are assuming no merging has yet ocurred. */
3671 BFD_ASSERT (this_got == i);
3672
3765b1be 3673 if (alpha_elf_tdata (this_got)->total_got_size > MAX_GOT_SIZE)
252b5132
RH
3674 {
3675 /* Yikes! A single object file has too many entries. */
3676 (*_bfd_error_handler)
3677 (_("%s: .got subsegment exceeds 64K (size %d)"),
8f615d07 3678 bfd_archive_filename (i),
3765b1be 3679 alpha_elf_tdata (this_got)->total_got_size);
b34976b6 3680 return FALSE;
252b5132
RH
3681 }
3682
3683 if (got_list == NULL)
3684 got_list = this_got;
3685 else
3686 alpha_elf_tdata(cur_got_obj)->got_link_next = this_got;
3687 cur_got_obj = this_got;
3688 }
3689
3690 /* Strange degenerate case of no got references. */
3691 if (got_list == NULL)
b34976b6 3692 return TRUE;
252b5132
RH
3693
3694 alpha_elf_hash_table (info)->got_list = got_list;
3695
3696 /* Force got offsets to be recalculated. */
3697 something_changed = 1;
3698 }
3699
3700 cur_got_obj = got_list;
3701 i = alpha_elf_tdata(cur_got_obj)->got_link_next;
3702 while (i != NULL)
3703 {
3704 if (elf64_alpha_can_merge_gots (cur_got_obj, i))
3705 {
3706 elf64_alpha_merge_gots (cur_got_obj, i);
3707 i = alpha_elf_tdata(i)->got_link_next;
3708 alpha_elf_tdata(cur_got_obj)->got_link_next = i;
3709 something_changed = 1;
3710 }
3711 else
3712 {
3713 cur_got_obj = i;
3714 i = alpha_elf_tdata(i)->got_link_next;
3715 }
3716 }
3717
3718 /* Once the gots have been merged, fill in the got offsets for
3719 everything therein. */
3720 if (1 || something_changed)
3721 elf64_alpha_calc_got_offsets (info);
3722
b34976b6 3723 return TRUE;
252b5132
RH
3724}
3725
cedb70c5 3726/* Called from relax_section to rebuild the PLT in light of
f44f99a5
RH
3727 potential changes in the function's status. */
3728
b34976b6 3729static bfd_boolean
f44f99a5
RH
3730elf64_alpha_size_plt_section (info)
3731 struct bfd_link_info *info;
3732{
3733 asection *splt, *spltrel;
3734 unsigned long entries;
3735 bfd *dynobj;
3736
3737 dynobj = elf_hash_table(info)->dynobj;
3738 splt = bfd_get_section_by_name(dynobj, ".plt");
3739 if (splt == NULL)
b34976b6 3740 return TRUE;
f44f99a5
RH
3741
3742 splt->_raw_size = 0;
3743
3744 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
3745 elf64_alpha_size_plt_section_1, splt);
3746
3747 splt->_cooked_size = splt->_raw_size;
3748
3749 /* Every plt entry requires a JMP_SLOT relocation. */
3750 spltrel = bfd_get_section_by_name (dynobj, ".rela.plt");
3751 if (splt->_raw_size)
3752 entries = (splt->_raw_size - PLT_HEADER_SIZE) / PLT_ENTRY_SIZE;
3753 else
3754 entries = 0;
3755 spltrel->_raw_size = entries * sizeof (Elf64_External_Rela);
3756 spltrel->_cooked_size = spltrel->_raw_size;
3757
b34976b6 3758 return TRUE;
f44f99a5
RH
3759}
3760
b34976b6 3761static bfd_boolean
f44f99a5
RH
3762elf64_alpha_size_plt_section_1 (h, data)
3763 struct alpha_elf_link_hash_entry *h;
3764 PTR data;
3765{
3766 asection *splt = (asection *) data;
3767 struct alpha_elf_got_entry *gotent;
3768
3769 /* If we didn't need an entry before, we still don't. */
3770 if (!(h->root.elf_link_hash_flags & ELF_LINK_HASH_NEEDS_PLT))
b34976b6 3771 return TRUE;
f44f99a5
RH
3772
3773 /* There must still be a LITERAL got entry for the function. */
3774 for (gotent = h->got_entries; gotent ; gotent = gotent->next)
3775 if (gotent->reloc_type == R_ALPHA_LITERAL
3776 && gotent->use_count > 0)
3777 break;
3778
3779 /* If there is, reset the PLT offset. If not, there's no longer
3780 a need for the PLT entry. */
3781 if (gotent)
3782 {
3783 if (splt->_raw_size == 0)
3784 splt->_raw_size = PLT_HEADER_SIZE;
3785 h->root.plt.offset = splt->_raw_size;
3786 splt->_raw_size += PLT_ENTRY_SIZE;
3787 }
3788 else
3789 {
3790 h->root.elf_link_hash_flags &= ~ELF_LINK_HASH_NEEDS_PLT;
3791 h->root.plt.offset = -1;
3792 }
3793
b34976b6 3794 return TRUE;
f44f99a5
RH
3795}
3796
b34976b6 3797static bfd_boolean
252b5132 3798elf64_alpha_always_size_sections (output_bfd, info)
f44f99a5 3799 bfd *output_bfd ATTRIBUTE_UNUSED;
252b5132
RH
3800 struct bfd_link_info *info;
3801{
3802 bfd *i;
3803
3804 if (info->relocateable)
b34976b6 3805 return TRUE;
252b5132
RH
3806
3807 /* First, take care of the indirect symbols created by versioning. */
3808 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
3809 elf64_alpha_merge_ind_symbols,
3810 NULL);
3811
f44f99a5 3812 if (!elf64_alpha_size_got_sections (info))
b34976b6 3813 return FALSE;
252b5132
RH
3814
3815 /* Allocate space for all of the .got subsections. */
3816 i = alpha_elf_hash_table (info)->got_list;
3817 for ( ; i ; i = alpha_elf_tdata(i)->got_link_next)
3818 {
3819 asection *s = alpha_elf_tdata(i)->got;
3820 if (s->_raw_size > 0)
3821 {
3822 s->contents = (bfd_byte *) bfd_zalloc (i, s->_raw_size);
3823 if (s->contents == NULL)
b34976b6 3824 return FALSE;
252b5132
RH
3825 }
3826 }
3827
b34976b6 3828 return TRUE;
252b5132
RH
3829}
3830
3765b1be
RH
3831/* The number of dynamic relocations required by a static relocation. */
3832
3833static int
3834alpha_dynamic_entries_for_reloc (r_type, dynamic, shared)
3835 int r_type, dynamic, shared;
3836{
3837 switch (r_type)
3838 {
3839 /* May appear in GOT entries. */
3840 case R_ALPHA_TLSGD:
3841 return (dynamic ? 2 : shared ? 1 : 0);
3842 case R_ALPHA_TLSLDM:
3843 return shared;
3844 case R_ALPHA_LITERAL:
3845 return dynamic || shared;
3846 case R_ALPHA_GOTDTPREL:
3847 case R_ALPHA_GOTTPREL:
3848 return dynamic;
3849
3850 /* May appear in data sections. */
3851 case R_ALPHA_REFLONG:
3852 case R_ALPHA_REFQUAD:
3853 return dynamic || shared;
3854 case R_ALPHA_SREL64:
3855 case R_ALPHA_TPREL64:
3856 return dynamic;
3857
3858 /* Everything else is illegal. We'll issue an error during
3859 relocate_section. */
3860 default:
3861 return 0;
3862 }
3863}
3864
252b5132
RH
3865/* Work out the sizes of the dynamic relocation entries. */
3866
b34976b6 3867static bfd_boolean
252b5132
RH
3868elf64_alpha_calc_dynrel_sizes (h, info)
3869 struct alpha_elf_link_hash_entry *h;
3870 struct bfd_link_info *info;
3871{
b34976b6 3872 bfd_boolean dynamic;
3765b1be 3873 struct alpha_elf_reloc_entry *relent;
f44f99a5 3874 unsigned long entries;
3765b1be 3875
e92d460e
AM
3876 if (h->root.root.type == bfd_link_hash_warning)
3877 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
3878
252b5132
RH
3879 /* If the symbol was defined as a common symbol in a regular object
3880 file, and there was no definition in any dynamic object, then the
3881 linker will have allocated space for the symbol in a common
3882 section but the ELF_LINK_HASH_DEF_REGULAR flag will not have been
3883 set. This is done for dynamic symbols in
3884 elf_adjust_dynamic_symbol but this is not done for non-dynamic
3885 symbols, somehow. */
3886 if (((h->root.elf_link_hash_flags
3887 & (ELF_LINK_HASH_DEF_REGULAR
3888 | ELF_LINK_HASH_REF_REGULAR
3889 | ELF_LINK_HASH_DEF_DYNAMIC))
3890 == ELF_LINK_HASH_REF_REGULAR)
3891 && (h->root.root.type == bfd_link_hash_defined
3892 || h->root.root.type == bfd_link_hash_defweak)
3893 && !(h->root.root.u.def.section->owner->flags & DYNAMIC))
f44f99a5 3894 h->root.elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
252b5132
RH
3895
3896 /* If the symbol is dynamic, we'll need all the relocations in their
3897 natural form. If this is a shared object, and it has been forced
3898 local, we'll need the same number of RELATIVE relocations. */
3899
3765b1be 3900 dynamic = alpha_elf_dynamic_symbol_p (&h->root, info);
252b5132 3901
3765b1be
RH
3902 for (relent = h->reloc_entries; relent; relent = relent->next)
3903 {
3904 entries = alpha_dynamic_entries_for_reloc (relent->rtype, dynamic,
3905 info->shared);
3906 if (entries)
3907 {
3908 relent->srel->_raw_size +=
3909 entries * sizeof (Elf64_External_Rela) * relent->count;
3910 if (relent->reltext)
3911 info->flags |= DT_TEXTREL;
3912 }
3913 }
252b5132 3914
b34976b6 3915 return TRUE;
f44f99a5
RH
3916}
3917
3918/* Set the sizes of the dynamic relocation sections. */
3919
b34976b6 3920static bfd_boolean
f44f99a5
RH
3921elf64_alpha_size_rela_got_section (info)
3922 struct bfd_link_info *info;
3923{
3924 unsigned long entries;
3925 bfd *i, *dynobj;
3926 asection *srel;
3927
3928 /* Shared libraries often require RELATIVE relocs, and some relocs
3929 require attention for the main application as well. */
cedb70c5 3930
f44f99a5
RH
3931 entries = 0;
3932 for (i = alpha_elf_hash_table(info)->got_list;
3933 i ; i = alpha_elf_tdata(i)->got_link_next)
3934 {
3935 bfd *j;
3936
3937 for (j = i; j ; j = alpha_elf_tdata(j)->in_got_link_next)
3938 {
3939 struct alpha_elf_got_entry **local_got_entries, *gotent;
3940 int k, n;
3941
3942 local_got_entries = alpha_elf_tdata(j)->local_got_entries;
3943 if (!local_got_entries)
3944 continue;
3945
3946 for (k = 0, n = elf_tdata(j)->symtab_hdr.sh_info; k < n; ++k)
3947 for (gotent = local_got_entries[k];
3948 gotent ; gotent = gotent->next)
3949 if (gotent->use_count > 0)
3950 entries += (alpha_dynamic_entries_for_reloc
3951 (gotent->reloc_type, 0, info->shared));
3952 }
3953 }
3954
3955 dynobj = elf_hash_table(info)->dynobj;
3956 srel = bfd_get_section_by_name (dynobj, ".rela.got");
3957 if (!srel)
3958 {
3959 BFD_ASSERT (entries == 0);
b34976b6 3960 return TRUE;
f44f99a5
RH
3961 }
3962 srel->_raw_size = sizeof (Elf64_External_Rela) * entries;
3963
3964 /* Now do the non-local symbols. */
3965 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
3966 elf64_alpha_size_rela_got_1, info);
3967
3968 srel->_cooked_size = srel->_raw_size;
3969
b34976b6 3970 return TRUE;
f44f99a5
RH
3971}
3972
3973/* Subroutine of elf64_alpha_size_rela_got_section for doing the
3974 global symbols. */
3975
b34976b6 3976static bfd_boolean
f44f99a5
RH
3977elf64_alpha_size_rela_got_1 (h, info)
3978 struct alpha_elf_link_hash_entry *h;
3979 struct bfd_link_info *info;
3980{
b34976b6 3981 bfd_boolean dynamic;
f44f99a5
RH
3982 struct alpha_elf_got_entry *gotent;
3983 unsigned long entries;
3984
3985 if (h->root.root.type == bfd_link_hash_warning)
3986 h = (struct alpha_elf_link_hash_entry *) h->root.root.u.i.link;
3987
3988 /* If the symbol is dynamic, we'll need all the relocations in their
3989 natural form. If this is a shared object, and it has been forced
3990 local, we'll need the same number of RELATIVE relocations. */
3991
3992 dynamic = alpha_elf_dynamic_symbol_p (&h->root, info);
3993
3765b1be
RH
3994 entries = 0;
3995 for (gotent = h->got_entries; gotent ; gotent = gotent->next)
f44f99a5
RH
3996 if (gotent->use_count > 0)
3997 entries += alpha_dynamic_entries_for_reloc (gotent->reloc_type,
3998 dynamic, info->shared);
252b5132 3999
3765b1be
RH
4000 /* If we are using a .plt entry, subtract one, as the first
4001 reference uses a .rela.plt entry instead. */
4002 if (h->root.plt.offset != MINUS_ONE)
4003 entries--;
252b5132 4004
3765b1be
RH
4005 if (entries > 0)
4006 {
4007 bfd *dynobj = elf_hash_table(info)->dynobj;
4008 asection *srel = bfd_get_section_by_name (dynobj, ".rela.got");
4009 BFD_ASSERT (srel != NULL);
4010 srel->_raw_size += sizeof (Elf64_External_Rela) * entries;
252b5132
RH
4011 }
4012
b34976b6 4013 return TRUE;
252b5132
RH
4014}
4015
4016/* Set the sizes of the dynamic sections. */
4017
b34976b6 4018static bfd_boolean
252b5132 4019elf64_alpha_size_dynamic_sections (output_bfd, info)
24a35864 4020 bfd *output_bfd ATTRIBUTE_UNUSED;
252b5132
RH
4021 struct bfd_link_info *info;
4022{
4023 bfd *dynobj;
4024 asection *s;
b34976b6 4025 bfd_boolean relplt;
252b5132
RH
4026
4027 dynobj = elf_hash_table(info)->dynobj;
4028 BFD_ASSERT(dynobj != NULL);
4029
4030 if (elf_hash_table (info)->dynamic_sections_created)
4031 {
4032 /* Set the contents of the .interp section to the interpreter. */
4033 if (!info->shared)
4034 {
4035 s = bfd_get_section_by_name (dynobj, ".interp");
4036 BFD_ASSERT (s != NULL);
4037 s->_raw_size = sizeof ELF_DYNAMIC_INTERPRETER;
4038 s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
4039 }
4040
4041 /* Now that we've seen all of the input files, we can decide which
4042 symbols need dynamic relocation entries and which don't. We've
4043 collected information in check_relocs that we can now apply to
4044 size the dynamic relocation sections. */
4045 alpha_elf_link_hash_traverse (alpha_elf_hash_table (info),
f44f99a5 4046 elf64_alpha_calc_dynrel_sizes, info);
252b5132 4047
f44f99a5 4048 elf64_alpha_size_rela_got_section (info);
252b5132
RH
4049 }
4050 /* else we're not dynamic and by definition we don't need such things. */
4051
4052 /* The check_relocs and adjust_dynamic_symbol entry points have
4053 determined the sizes of the various dynamic sections. Allocate
4054 memory for them. */
b34976b6 4055 relplt = FALSE;
252b5132
RH
4056 for (s = dynobj->sections; s != NULL; s = s->next)
4057 {
4058 const char *name;
b34976b6 4059 bfd_boolean strip;
252b5132
RH
4060
4061 if (!(s->flags & SEC_LINKER_CREATED))
4062 continue;
4063
4064 /* It's OK to base decisions on the section name, because none
4065 of the dynobj section names depend upon the input files. */
4066 name = bfd_get_section_name (dynobj, s);
4067
4068 /* If we don't need this section, strip it from the output file.
4069 This is to handle .rela.bss and .rela.plt. We must create it
4070 in create_dynamic_sections, because it must be created before
4071 the linker maps input sections to output sections. The
4072 linker does that before adjust_dynamic_symbol is called, and
4073 it is that function which decides whether anything needs to
4074 go into these sections. */
4075
b34976b6 4076 strip = FALSE;
252b5132
RH
4077
4078 if (strncmp (name, ".rela", 5) == 0)
4079 {
4080 strip = (s->_raw_size == 0);
4081
4082 if (!strip)
4083 {
252b5132 4084 if (strcmp(name, ".rela.plt") == 0)
b34976b6 4085 relplt = TRUE;
252b5132
RH
4086
4087 /* We use the reloc_count field as a counter if we need
4088 to copy relocs into the output file. */
4089 s->reloc_count = 0;
4090 }
4091 }
4092 else if (strcmp (name, ".plt") != 0)
4093 {
4094 /* It's not one of our dynamic sections, so don't allocate space. */
4095 continue;
4096 }
4097
4098 if (strip)
7f8d5fc9 4099 _bfd_strip_section_from_output (info, s);
252b5132
RH
4100 else
4101 {
4102 /* Allocate memory for the section contents. */
dc810e39 4103 s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->_raw_size);
252b5132 4104 if (s->contents == NULL && s->_raw_size != 0)
b34976b6 4105 return FALSE;
252b5132
RH
4106 }
4107 }
4108
252b5132
RH
4109 if (elf_hash_table (info)->dynamic_sections_created)
4110 {
4111 /* Add some entries to the .dynamic section. We fill in the
4112 values later, in elf64_alpha_finish_dynamic_sections, but we
4113 must add the entries now so that we get the correct size for
4114 the .dynamic section. The DT_DEBUG entry is filled in by the
4115 dynamic linker and used by the debugger. */
dc810e39
AM
4116#define add_dynamic_entry(TAG, VAL) \
4117 bfd_elf64_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL))
4118
252b5132
RH
4119 if (!info->shared)
4120 {
dc810e39 4121 if (!add_dynamic_entry (DT_DEBUG, 0))
b34976b6 4122 return FALSE;
252b5132
RH
4123 }
4124
252b5132
RH
4125 if (relplt)
4126 {
c0647bfc
JT
4127 if (!add_dynamic_entry (DT_PLTGOT, 0)
4128 || !add_dynamic_entry (DT_PLTRELSZ, 0)
dc810e39
AM
4129 || !add_dynamic_entry (DT_PLTREL, DT_RELA)
4130 || !add_dynamic_entry (DT_JMPREL, 0))
b34976b6 4131 return FALSE;
252b5132
RH
4132 }
4133
dc810e39
AM
4134 if (!add_dynamic_entry (DT_RELA, 0)
4135 || !add_dynamic_entry (DT_RELASZ, 0)
4136 || !add_dynamic_entry (DT_RELAENT, sizeof (Elf64_External_Rela)))
b34976b6 4137 return FALSE;
252b5132 4138
fcfbdf31 4139 if (info->flags & DF_TEXTREL)
252b5132 4140 {
dc810e39 4141 if (!add_dynamic_entry (DT_TEXTREL, 0))
b34976b6 4142 return FALSE;
252b5132
RH
4143 }
4144 }
dc810e39 4145#undef add_dynamic_entry
252b5132 4146
b34976b6 4147 return TRUE;
252b5132
RH
4148}
4149
4a67a098
RH
4150/* Relocate an Alpha ELF section for a relocatable link.
4151
4152 We don't have to change anything unless the reloc is against a section
4153 symbol, in which case we have to adjust according to where the section
4154 symbol winds up in the output section. */
4155
b34976b6 4156static bfd_boolean
4a67a098
RH
4157elf64_alpha_relocate_section_r (output_bfd, info, input_bfd, input_section,
4158 contents, relocs, local_syms, local_sections)
4159 bfd *output_bfd ATTRIBUTE_UNUSED;
4160 struct bfd_link_info *info ATTRIBUTE_UNUSED;
4161 bfd *input_bfd;
4162 asection *input_section;
4163 bfd_byte *contents ATTRIBUTE_UNUSED;
4164 Elf_Internal_Rela *relocs;
4165 Elf_Internal_Sym *local_syms;
4166 asection **local_sections;
4167{
4168 unsigned long symtab_hdr_sh_info;
4169 Elf_Internal_Rela *rel;
4170 Elf_Internal_Rela *relend;
b34976b6 4171 bfd_boolean ret_val = TRUE;
4a67a098
RH
4172
4173 symtab_hdr_sh_info = elf_tdata (input_bfd)->symtab_hdr.sh_info;
4174
4175 relend = relocs + input_section->reloc_count;
4176 for (rel = relocs; rel < relend; rel++)
4177 {
4178 unsigned long r_symndx;
4179 Elf_Internal_Sym *sym;
4180 asection *sec;
4181 unsigned long r_type;
4182
4183 r_type = ELF64_R_TYPE(rel->r_info);
4184 if (r_type >= R_ALPHA_max)
4185 {
4186 (*_bfd_error_handler)
4187 (_("%s: unknown relocation type %d"),
4188 bfd_archive_filename (input_bfd), (int)r_type);
4189 bfd_set_error (bfd_error_bad_value);
b34976b6 4190 ret_val = FALSE;
4a67a098
RH
4191 continue;
4192 }
4193
4194 r_symndx = ELF64_R_SYM(rel->r_info);
4195
4196 /* The symbol associated with GPDISP and LITUSE is
4197 immaterial. Only the addend is significant. */
4198 if (r_type == R_ALPHA_GPDISP || r_type == R_ALPHA_LITUSE)
4199 continue;
4200
4201 if (r_symndx < symtab_hdr_sh_info)
4202 {
4203 sym = local_syms + r_symndx;
4204 if (ELF_ST_TYPE(sym->st_info) == STT_SECTION)
4205 {
4206 sec = local_sections[r_symndx];
4207 rel->r_addend += sec->output_offset + sym->st_value;
4208 }
4209 }
4210 }
4211
4212 return ret_val;
4213}
4214
252b5132
RH
4215/* Relocate an Alpha ELF section. */
4216
b34976b6 4217static bfd_boolean
252b5132
RH
4218elf64_alpha_relocate_section (output_bfd, info, input_bfd, input_section,
4219 contents, relocs, local_syms, local_sections)
4220 bfd *output_bfd;
4221 struct bfd_link_info *info;
4222 bfd *input_bfd;
4223 asection *input_section;
4224 bfd_byte *contents;
4225 Elf_Internal_Rela *relocs;
4226 Elf_Internal_Sym *local_syms;
4227 asection **local_sections;
4228{
4a67a098 4229 Elf_Internal_Shdr *symtab_hdr;
252b5132
RH
4230 Elf_Internal_Rela *rel;
4231 Elf_Internal_Rela *relend;
4a67a098
RH
4232 struct elf_link_tls_segment *tls_segment;
4233 asection *sgot, *srel, *srelgot;
4234 bfd *dynobj, *gotobj;
4235 bfd_vma gp, tp_base, dtp_base;
4236 struct alpha_elf_got_entry **local_got_entries;
b34976b6 4237 bfd_boolean ret_val;
4a67a098 4238 const char *section_name;
252b5132 4239
4a67a098
RH
4240 /* Handle relocatable links with a smaller loop. */
4241 if (info->relocateable)
4242 return elf64_alpha_relocate_section_r (output_bfd, info, input_bfd,
4243 input_section, contents, relocs,
4244 local_syms, local_sections);
4245
4246 /* This is a final link. */
4247
b34976b6 4248 ret_val = TRUE;
252b5132 4249
4a67a098 4250 symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
3765b1be 4251
4a67a098
RH
4252 dynobj = elf_hash_table (info)->dynobj;
4253 if (dynobj)
4254 srelgot = bfd_get_section_by_name (dynobj, ".rela.got");
4255 else
4256 srelgot = NULL;
4257
4258 section_name = (bfd_elf_string_from_elf_section
4259 (input_bfd, elf_elfheader(input_bfd)->e_shstrndx,
4260 elf_section_data(input_section)->rel_hdr.sh_name));
4261 BFD_ASSERT(section_name != NULL);
4262 srel = bfd_get_section_by_name (dynobj, section_name);
3765b1be 4263
4a67a098
RH
4264 /* Find the gp value for this input bfd. */
4265 gotobj = alpha_elf_tdata (input_bfd)->gotobj;
4266 if (gotobj)
4267 {
4268 sgot = alpha_elf_tdata (gotobj)->got;
4269 gp = _bfd_get_gp_value (gotobj);
4270 if (gp == 0)
252b5132 4271 {
4a67a098
RH
4272 gp = (sgot->output_section->vma
4273 + sgot->output_offset
4274 + 0x8000);
4275 _bfd_set_gp_value (gotobj, gp);
4276 }
4277 }
4278 else
4279 {
4280 sgot = NULL;
4281 gp = 0;
4282 }
3765b1be 4283
4a67a098
RH
4284 local_got_entries = alpha_elf_tdata(input_bfd)->local_got_entries;
4285
4286 tls_segment = elf_hash_table (info)->tls_segment;
4287 if (tls_segment)
4288 {
4289 dtp_base = alpha_get_dtprel_base (tls_segment);
4290 tp_base = alpha_get_tprel_base (tls_segment);
252b5132 4291 }
4a67a098
RH
4292 else
4293 dtp_base = tp_base = 0;
252b5132 4294
252b5132 4295 relend = relocs + input_section->reloc_count;
4a67a098 4296 for (rel = relocs; rel < relend; rel++)
252b5132 4297 {
4a67a098 4298 struct alpha_elf_link_hash_entry *h = NULL;
3765b1be
RH
4299 struct alpha_elf_got_entry *gotent;
4300 bfd_reloc_status_type r;
252b5132
RH
4301 reloc_howto_type *howto;
4302 unsigned long r_symndx;
4a67a098
RH
4303 Elf_Internal_Sym *sym = NULL;
4304 asection *sec = NULL;
3765b1be 4305 bfd_vma value;
dc810e39 4306 bfd_vma addend;
b34976b6
AM
4307 bfd_boolean dynamic_symbol_p;
4308 bfd_boolean undef_weak_ref = FALSE;
3765b1be 4309 unsigned long r_type;
252b5132
RH
4310
4311 r_type = ELF64_R_TYPE(rel->r_info);
3765b1be 4312 if (r_type >= R_ALPHA_max)
252b5132 4313 {
3765b1be
RH
4314 (*_bfd_error_handler)
4315 (_("%s: unknown relocation type %d"),
4316 bfd_archive_filename (input_bfd), (int)r_type);
252b5132 4317 bfd_set_error (bfd_error_bad_value);
b34976b6 4318 ret_val = FALSE;
3765b1be 4319 continue;
252b5132 4320 }
252b5132 4321
3765b1be 4322 howto = elf64_alpha_howto_table + r_type;
252b5132
RH
4323 r_symndx = ELF64_R_SYM(rel->r_info);
4324
252b5132
RH
4325 if (r_symndx < symtab_hdr->sh_info)
4326 {
4327 sym = local_syms + r_symndx;
4328 sec = local_sections[r_symndx];
3765b1be
RH
4329 value = _bfd_elf_rela_local_sym (output_bfd, sym, sec, rel);
4330
4a67a098
RH
4331 if (local_got_entries)
4332 gotent = local_got_entries[r_symndx];
4333 else
4334 gotent = NULL;
3765b1be
RH
4335
4336 /* Need to adjust local GOT entries' addends for SEC_MERGE
4337 unless it has been done already. */
4338 if ((sec->flags & SEC_MERGE)
048d873d
RH
4339 && ELF_ST_TYPE (sym->st_info) == STT_SECTION
4340 && (elf_section_data (sec)->sec_info_type
4341 == ELF_INFO_TYPE_MERGE)
4342 && gotent
4343 && !gotent->reloc_xlated)
3765b1be
RH
4344 {
4345 struct alpha_elf_got_entry *ent;
4346 asection *msec;
4347
4348 for (ent = gotent; ent; ent = ent->next)
4349 {
4350 ent->reloc_xlated = 1;
4351 if (ent->use_count == 0)
4352 continue;
4353 msec = sec;
4354 ent->addend =
4355 _bfd_merged_section_offset (output_bfd, &msec,
4356 elf_section_data (sec)->
4357 sec_info,
4358 sym->st_value + ent->addend,
4359 (bfd_vma) 0);
4360 ent->addend -= sym->st_value;
4361 ent->addend += msec->output_section->vma
4362 + msec->output_offset
4363 - sec->output_section->vma
4364 - sec->output_offset;
4365 }
4366 }
4367
b34976b6 4368 dynamic_symbol_p = FALSE;
252b5132
RH
4369 }
4370 else
4371 {
4372 h = alpha_elf_sym_hashes (input_bfd)[r_symndx - symtab_hdr->sh_info];
4373
4374 while (h->root.root.type == bfd_link_hash_indirect
4375 || h->root.root.type == bfd_link_hash_warning)
4376 h = (struct alpha_elf_link_hash_entry *)h->root.root.u.i.link;
4377
3765b1be 4378 value = 0;
252b5132
RH
4379 if (h->root.root.type == bfd_link_hash_defined
4380 || h->root.root.type == bfd_link_hash_defweak)
4381 {
4382 sec = h->root.root.u.def.section;
4383
3765b1be
RH
4384 /* Detect the cases that sym_sec->output_section is
4385 expected to be NULL -- all cases in which the symbol
4386 is defined in another shared module. This includes
4387 PLT relocs for which we've created a PLT entry and
4388 other relocs for which we're prepared to create
4389 dynamic relocations. */
4390 /* ??? Just accept it NULL and continue. */
4391
4392 if (sec->output_section != NULL)
4393 value = (h->root.root.u.def.value
4394 + sec->output_section->vma
4395 + sec->output_offset);
252b5132
RH
4396 }
4397 else if (h->root.root.type == bfd_link_hash_undefweak)
b34976b6 4398 undef_weak_ref = TRUE;
671bae9c
NC
4399 else if (info->shared
4400 && (!info->symbolic || info->allow_shlib_undefined)
3a27a730 4401 && !info->no_undefined
edb72b3b 4402 && ELF_ST_VISIBILITY (h->root.other) == STV_DEFAULT)
3765b1be 4403 ;
252b5132
RH
4404 else
4405 {
4406 if (!((*info->callbacks->undefined_symbol)
4407 (info, h->root.root.root.string, input_bfd,
5cc7c785 4408 input_section, rel->r_offset,
3a27a730 4409 (!info->shared || info->no_undefined
edb72b3b 4410 || ELF_ST_VISIBILITY (h->root.other)))))
b34976b6
AM
4411 return FALSE;
4412 ret_val = FALSE;
3765b1be 4413 continue;
252b5132 4414 }
3765b1be
RH
4415
4416 dynamic_symbol_p = alpha_elf_dynamic_symbol_p (&h->root, info);
4417 gotent = h->got_entries;
252b5132 4418 }
3765b1be 4419
252b5132 4420 addend = rel->r_addend;
3765b1be
RH
4421 value += addend;
4422
4423 /* Search for the proper got entry. */
4424 for (; gotent ; gotent = gotent->next)
4425 if (gotent->gotobj == gotobj
4426 && gotent->reloc_type == r_type
4427 && gotent->addend == addend)
4428 break;
252b5132
RH
4429
4430 switch (r_type)
4431 {
4432 case R_ALPHA_GPDISP:
4433 {
4434 bfd_byte *p_ldah, *p_lda;
4435
4436 BFD_ASSERT(gp != 0);
4437
3765b1be
RH
4438 value = (input_section->output_section->vma
4439 + input_section->output_offset
4440 + rel->r_offset);
252b5132 4441
3765b1be 4442 p_ldah = contents + rel->r_offset;
252b5132
RH
4443 p_lda = p_ldah + rel->r_addend;
4444
3765b1be 4445 r = elf64_alpha_do_reloc_gpdisp (input_bfd, gp - value,
252b5132
RH
4446 p_ldah, p_lda);
4447 }
4448 break;
4449
252b5132 4450 case R_ALPHA_LITERAL:
3765b1be
RH
4451 BFD_ASSERT(sgot != NULL);
4452 BFD_ASSERT(gp != 0);
4453 BFD_ASSERT(gotent != NULL);
4454 BFD_ASSERT(gotent->use_count >= 1);
f7460f5f 4455
3765b1be
RH
4456 if (!gotent->reloc_done)
4457 {
4458 gotent->reloc_done = 1;
252b5132 4459
3765b1be
RH
4460 bfd_put_64 (output_bfd, value,
4461 sgot->contents + gotent->got_offset);
252b5132 4462
3765b1be
RH
4463 /* If the symbol has been forced local, output a
4464 RELATIVE reloc, otherwise it will be handled in
4465 finish_dynamic_symbol. */
4466 if (info->shared && !dynamic_symbol_p)
4467 {
4468 Elf_Internal_Rela outrel;
947216bf 4469 bfd_byte *loc;
252b5132 4470
3765b1be 4471 BFD_ASSERT(srelgot != NULL);
252b5132 4472
3765b1be
RH
4473 outrel.r_offset = (sgot->output_section->vma
4474 + sgot->output_offset
4475 + gotent->got_offset);
4476 outrel.r_info = ELF64_R_INFO (0, R_ALPHA_RELATIVE);
4477 outrel.r_addend = value;
252b5132 4478
947216bf
AM
4479 loc = srelgot->contents;
4480 loc += srelgot->reloc_count++ * sizeof (Elf64_External_Rela);
4481 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
3765b1be
RH
4482 BFD_ASSERT (sizeof (Elf64_External_Rela)
4483 * srelgot->reloc_count
4484 <= srelgot->_cooked_size);
4485 }
4486 }
252b5132 4487
3765b1be
RH
4488 value = (sgot->output_section->vma
4489 + sgot->output_offset
4490 + gotent->got_offset);
4491 value -= gp;
252b5132
RH
4492 goto default_reloc;
4493
dfe57ca0 4494 case R_ALPHA_GPREL16:
252b5132
RH
4495 case R_ALPHA_GPREL32:
4496 case R_ALPHA_GPRELLOW:
3765b1be 4497 if (dynamic_symbol_p)
f16fbd61
RH
4498 {
4499 (*_bfd_error_handler)
4500 (_("%s: gp-relative relocation against dynamic symbol %s"),
8f615d07 4501 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4502 ret_val = FALSE;
f16fbd61 4503 }
252b5132 4504 BFD_ASSERT(gp != 0);
3765b1be 4505 value -= gp;
252b5132
RH
4506 goto default_reloc;
4507
4508 case R_ALPHA_GPRELHIGH:
3765b1be 4509 if (dynamic_symbol_p)
f16fbd61
RH
4510 {
4511 (*_bfd_error_handler)
4512 (_("%s: gp-relative relocation against dynamic symbol %s"),
8f615d07 4513 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4514 ret_val = FALSE;
f16fbd61 4515 }
252b5132 4516 BFD_ASSERT(gp != 0);
3765b1be
RH
4517 value -= gp;
4518 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
252b5132
RH
4519 goto default_reloc;
4520
252b5132 4521 case R_ALPHA_HINT:
f94952df
RH
4522 /* A call to a dynamic symbol is definitely out of range of
4523 the 16-bit displacement. Don't bother writing anything. */
3765b1be 4524 if (dynamic_symbol_p)
f94952df
RH
4525 {
4526 r = bfd_reloc_ok;
4527 break;
4528 }
3765b1be
RH
4529 /* The regular PC-relative stuff measures from the start of
4530 the instruction rather than the end. */
4531 value -= 4;
4532 goto default_reloc;
f94952df
RH
4533
4534 case R_ALPHA_BRADDR:
3765b1be
RH
4535 if (dynamic_symbol_p)
4536 {
4537 (*_bfd_error_handler)
4538 (_("%s: pc-relative relocation against dynamic symbol %s"),
4539 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4540 ret_val = FALSE;
3765b1be 4541 }
252b5132
RH
4542 /* The regular PC-relative stuff measures from the start of
4543 the instruction rather than the end. */
3765b1be 4544 value -= 4;
252b5132
RH
4545 goto default_reloc;
4546
7793f4d0
RH
4547 case R_ALPHA_BRSGP:
4548 {
4549 int other;
4550 const char *name;
4551
4552 /* The regular PC-relative stuff measures from the start of
4553 the instruction rather than the end. */
3765b1be 4554 value -= 4;
7793f4d0 4555
ccf00ab6
RH
4556 /* The source and destination gp must be the same. Note that
4557 the source will always have an assigned gp, since we forced
4558 one in check_relocs, but that the destination may not, as
cedb70c5 4559 it might not have had any relocations at all. Also take
ccf00ab6
RH
4560 care not to crash if H is an undefined symbol. */
4561 if (h != NULL && sec != NULL
4562 && alpha_elf_tdata (sec->owner)->gotobj
7793f4d0
RH
4563 && gotobj != alpha_elf_tdata (sec->owner)->gotobj)
4564 {
7793f4d0
RH
4565 (*_bfd_error_handler)
4566 (_("%s: change in gp: BRSGP %s"),
ccf00ab6 4567 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4568 ret_val = FALSE;
7793f4d0
RH
4569 }
4570
4571 /* The symbol should be marked either NOPV or STD_GPLOAD. */
4572 if (h != NULL)
4573 other = h->root.other;
4574 else
4575 other = sym->st_other;
4576 switch (other & STO_ALPHA_STD_GPLOAD)
4577 {
4578 case STO_ALPHA_NOPV:
4579 break;
4580 case STO_ALPHA_STD_GPLOAD:
64e04ecd 4581 value += 8;
7793f4d0
RH
4582 break;
4583 default:
4584 if (h != NULL)
4585 name = h->root.root.root.string;
4586 else
4587 {
4588 name = (bfd_elf_string_from_elf_section
4589 (input_bfd, symtab_hdr->sh_link, sym->st_name));
4590 if (name == NULL)
4591 name = _("<unknown>");
4592 else if (name[0] == 0)
4593 name = bfd_section_name (input_bfd, sec);
4594 }
4595 (*_bfd_error_handler)
4596 (_("%s: !samegp reloc against symbol without .prologue: %s"),
4597 bfd_archive_filename (input_bfd), name);
b34976b6 4598 ret_val = FALSE;
7793f4d0
RH
4599 break;
4600 }
4601
4602 goto default_reloc;
4603 }
4604
252b5132
RH
4605 case R_ALPHA_REFLONG:
4606 case R_ALPHA_REFQUAD:
3765b1be
RH
4607 case R_ALPHA_DTPREL64:
4608 case R_ALPHA_TPREL64:
252b5132
RH
4609 {
4610 Elf_Internal_Rela outrel;
947216bf 4611 bfd_byte *loc;
252b5132
RH
4612
4613 /* Careful here to remember RELATIVE relocations for global
4614 variables for symbolic shared objects. */
4615
3765b1be 4616 if (dynamic_symbol_p)
252b5132
RH
4617 {
4618 BFD_ASSERT(h->root.dynindx != -1);
3765b1be 4619 outrel.r_info = ELF64_R_INFO (h->root.dynindx, r_type);
252b5132 4620 outrel.r_addend = addend;
3765b1be
RH
4621 addend = 0, value = 0;
4622 }
4623 else if (r_type == R_ALPHA_DTPREL64)
4624 {
4625 BFD_ASSERT(tls_segment != NULL);
4626 value -= dtp_base;
4627 goto default_reloc;
4628 }
4629 else if (r_type == R_ALPHA_TPREL64)
4630 {
4631 BFD_ASSERT(tls_segment != NULL);
4632 value -= dtp_base;
4633 goto default_reloc;
252b5132 4634 }
ec338859
AM
4635 else if (info->shared
4636 && r_symndx != 0
4637 && (input_section->flags & SEC_ALLOC))
252b5132 4638 {
3765b1be
RH
4639 if (r_type == R_ALPHA_REFLONG)
4640 {
4641 (*_bfd_error_handler)
4642 (_("%s: unhandled dynamic relocation against %s"),
4643 bfd_archive_filename (input_bfd),
4644 h->root.root.root.string);
b34976b6 4645 ret_val = FALSE;
3765b1be
RH
4646 }
4647 outrel.r_info = ELF64_R_INFO (0, R_ALPHA_RELATIVE);
4648 outrel.r_addend = value;
252b5132
RH
4649 }
4650 else
4651 goto default_reloc;
4652
3765b1be 4653 BFD_ASSERT(srel != NULL);
252b5132 4654
c629eae0
JJ
4655 outrel.r_offset =
4656 _bfd_elf_section_offset (output_bfd, info, input_section,
4657 rel->r_offset);
0bb2d96a 4658 if ((outrel.r_offset | 1) != (bfd_vma) -1)
252b5132
RH
4659 outrel.r_offset += (input_section->output_section->vma
4660 + input_section->output_offset);
4661 else
4662 memset (&outrel, 0, sizeof outrel);
4663
947216bf
AM
4664 loc = srel->contents;
4665 loc += srel->reloc_count++ * sizeof (Elf64_External_Rela);
4666 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
fe8bc63d 4667 BFD_ASSERT (sizeof (Elf64_External_Rela) * srel->reloc_count
252b5132
RH
4668 <= srel->_cooked_size);
4669 }
4670 goto default_reloc;
4671
3765b1be 4672 case R_ALPHA_SREL16:
84de6048
RH
4673 case R_ALPHA_SREL32:
4674 case R_ALPHA_SREL64:
3765b1be
RH
4675 if (dynamic_symbol_p)
4676 {
4677 (*_bfd_error_handler)
4678 (_("%s: pc-relative relocation against dynamic symbol %s"),
4679 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4680 ret_val = FALSE;
3765b1be
RH
4681 }
4682
84de6048
RH
4683 /* ??? .eh_frame references to discarded sections will be smashed
4684 to relocations against SHN_UNDEF. The .eh_frame format allows
4685 NULL to be encoded as 0 in any format, so this works here. */
4686 if (r_symndx == 0)
4687 howto = (elf64_alpha_howto_table
4688 + (r_type - R_ALPHA_SREL32 + R_ALPHA_REFLONG));
4689 goto default_reloc;
4690
3765b1be
RH
4691 case R_ALPHA_TLSLDM:
4692 /* Ignore the symbol for the relocation. The result is always
4693 the current module. */
4694 dynamic_symbol_p = 0;
4695 /* FALLTHRU */
4696
4697 case R_ALPHA_TLSGD:
4698 if (!gotent->reloc_done)
4699 {
4700 gotent->reloc_done = 1;
4701
4702 /* Note that the module index for the main program is 1. */
4703 bfd_put_64 (output_bfd, !info->shared && !dynamic_symbol_p,
4704 sgot->contents + gotent->got_offset);
4705
4706 /* If the symbol has been forced local, output a
4707 DTPMOD64 reloc, otherwise it will be handled in
4708 finish_dynamic_symbol. */
4709 if (info->shared && !dynamic_symbol_p)
4710 {
4711 Elf_Internal_Rela outrel;
947216bf 4712 bfd_byte *loc;
3765b1be
RH
4713
4714 BFD_ASSERT(srelgot != NULL);
4715
4716 outrel.r_offset = (sgot->output_section->vma
4717 + sgot->output_offset
4718 + gotent->got_offset);
4719 /* ??? Proper dynindx here. */
4720 outrel.r_info = ELF64_R_INFO (0, R_ALPHA_DTPMOD64);
4721 outrel.r_addend = 0;
4722
947216bf
AM
4723 loc = srelgot->contents;
4724 loc += srelgot->reloc_count++ * sizeof (Elf64_External_Rela);
4725 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
3765b1be
RH
4726 BFD_ASSERT (sizeof (Elf64_External_Rela)
4727 * srelgot->reloc_count
4728 <= srelgot->_cooked_size);
4729 }
4730
4731 if (dynamic_symbol_p || r_type == R_ALPHA_TLSLDM)
4732 value = 0;
4733 else
4734 {
4735 BFD_ASSERT(tls_segment != NULL);
4736 value -= dtp_base;
4737 }
4738 bfd_put_64 (output_bfd, value,
4739 sgot->contents + gotent->got_offset + 8);
4740 }
4741
4742 value = (sgot->output_section->vma
4743 + sgot->output_offset
4744 + gotent->got_offset);
4745 value -= gp;
4746 goto default_reloc;
4747
4748 case R_ALPHA_DTPRELHI:
4749 case R_ALPHA_DTPRELLO:
4750 case R_ALPHA_DTPREL16:
4751 if (dynamic_symbol_p)
4752 {
4753 (*_bfd_error_handler)
4754 (_("%s: dtp-relative relocation against dynamic symbol %s"),
4755 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4756 ret_val = FALSE;
3765b1be
RH
4757 }
4758 BFD_ASSERT(tls_segment != NULL);
4759 value -= dtp_base;
9e756d64
RH
4760 if (r_type == R_ALPHA_DTPRELHI)
4761 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
3765b1be
RH
4762 goto default_reloc;
4763
4764 case R_ALPHA_TPRELHI:
4765 case R_ALPHA_TPRELLO:
4766 case R_ALPHA_TPREL16:
9e756d64
RH
4767 if (info->shared)
4768 {
4769 (*_bfd_error_handler)
4770 (_("%s: TLS local exec code cannot be linked into shared objects"),
4771 bfd_archive_filename (input_bfd));
b34976b6 4772 ret_val = FALSE;
9e756d64
RH
4773 }
4774 else if (dynamic_symbol_p)
3765b1be
RH
4775 {
4776 (*_bfd_error_handler)
4777 (_("%s: tp-relative relocation against dynamic symbol %s"),
4778 bfd_archive_filename (input_bfd), h->root.root.root.string);
b34976b6 4779 ret_val = FALSE;
3765b1be
RH
4780 }
4781 BFD_ASSERT(tls_segment != NULL);
4782 value -= tp_base;
9e756d64
RH
4783 if (r_type == R_ALPHA_TPRELHI)
4784 value = ((bfd_signed_vma) value >> 16) + ((value >> 15) & 1);
3765b1be
RH
4785 goto default_reloc;
4786
4787 case R_ALPHA_GOTDTPREL:
4788 case R_ALPHA_GOTTPREL:
4789 BFD_ASSERT(sgot != NULL);
4790 BFD_ASSERT(gp != 0);
4791 BFD_ASSERT(gotent != NULL);
4792 BFD_ASSERT(gotent->use_count >= 1);
4793
4794 if (!gotent->reloc_done)
4795 {
4796 gotent->reloc_done = 1;
4797
4798 if (dynamic_symbol_p)
4799 value = 0;
4800 else
4801 {
4802 BFD_ASSERT(tls_segment != NULL);
4803 value -= (r_type == R_ALPHA_GOTDTPREL ? dtp_base : tp_base);
4804 }
4805 bfd_put_64 (output_bfd, value,
4806 sgot->contents + gotent->got_offset);
4807 }
4808
4809 value = (sgot->output_section->vma
4810 + sgot->output_offset
4811 + gotent->got_offset);
4812 value -= gp;
4813 goto default_reloc;
4814
252b5132
RH
4815 default:
4816 default_reloc:
4817 r = _bfd_final_link_relocate (howto, input_bfd, input_section,
3765b1be 4818 contents, rel->r_offset, value, 0);
252b5132
RH
4819 break;
4820 }
4821
4822 switch (r)
4823 {
4824 case bfd_reloc_ok:
4825 break;
4826
4827 case bfd_reloc_overflow:
4828 {
4829 const char *name;
4830
ed4de5e2
JJ
4831 /* Don't warn if the overflow is due to pc relative reloc
4832 against discarded section. Section optimization code should
4833 handle it. */
4834
4835 if (r_symndx < symtab_hdr->sh_info
4836 && sec != NULL && howto->pc_relative
4837 && elf_discarded_section (sec))
4838 break;
4839
252b5132
RH
4840 if (h != NULL)
4841 name = h->root.root.root.string;
4842 else
4843 {
4844 name = (bfd_elf_string_from_elf_section
4845 (input_bfd, symtab_hdr->sh_link, sym->st_name));
4846 if (name == NULL)
b34976b6 4847 return FALSE;
252b5132
RH
4848 if (*name == '\0')
4849 name = bfd_section_name (input_bfd, sec);
4850 }
4851 if (! ((*info->callbacks->reloc_overflow)
4852 (info, name, howto->name, (bfd_vma) 0,
4853 input_bfd, input_section, rel->r_offset)))
b34976b6 4854 ret_val = FALSE;
252b5132
RH
4855 }
4856 break;
4857
4858 default:
4859 case bfd_reloc_outofrange:
4860 abort ();
4861 }
4862 }
4863
f16fbd61 4864 return ret_val;
252b5132
RH
4865}
4866
4867/* Finish up dynamic symbol handling. We set the contents of various
4868 dynamic sections here. */
4869
b34976b6 4870static bfd_boolean
252b5132
RH
4871elf64_alpha_finish_dynamic_symbol (output_bfd, info, h, sym)
4872 bfd *output_bfd;
4873 struct bfd_link_info *info;
4874 struct elf_link_hash_entry *h;
4875 Elf_Internal_Sym *sym;
4876{
4877 bfd *dynobj = elf_hash_table(info)->dynobj;
4878
4879 if (h->plt.offset != MINUS_ONE)
4880 {
4881 /* Fill in the .plt entry for this symbol. */
4882 asection *splt, *sgot, *srel;
4883 Elf_Internal_Rela outrel;
947216bf 4884 bfd_byte *loc;
252b5132
RH
4885 bfd_vma got_addr, plt_addr;
4886 bfd_vma plt_index;
4887 struct alpha_elf_got_entry *gotent;
4888
4889 BFD_ASSERT (h->dynindx != -1);
4890
4891 /* The first .got entry will be updated by the .plt with the
4892 address of the target function. */
4893 gotent = ((struct alpha_elf_link_hash_entry *) h)->got_entries;
4894 BFD_ASSERT (gotent && gotent->addend == 0);
4895
4896 splt = bfd_get_section_by_name (dynobj, ".plt");
4897 BFD_ASSERT (splt != NULL);
4898 srel = bfd_get_section_by_name (dynobj, ".rela.plt");
4899 BFD_ASSERT (srel != NULL);
4900 sgot = alpha_elf_tdata (gotent->gotobj)->got;
4901 BFD_ASSERT (sgot != NULL);
4902
4903 got_addr = (sgot->output_section->vma
4904 + sgot->output_offset
4905 + gotent->got_offset);
4906 plt_addr = (splt->output_section->vma
4907 + splt->output_offset
4908 + h->plt.offset);
4909
4910 plt_index = (h->plt.offset - PLT_HEADER_SIZE) / PLT_ENTRY_SIZE;
4911
4912 /* Fill in the entry in the procedure linkage table. */
4913 {
dc810e39 4914 bfd_vma insn1, insn2, insn3;
252b5132
RH
4915
4916 insn1 = PLT_ENTRY_WORD1 | ((-(h->plt.offset + 4) >> 2) & 0x1fffff);
4917 insn2 = PLT_ENTRY_WORD2;
4918 insn3 = PLT_ENTRY_WORD3;
4919
4920 bfd_put_32 (output_bfd, insn1, splt->contents + h->plt.offset);
4921 bfd_put_32 (output_bfd, insn2, splt->contents + h->plt.offset + 4);
4922 bfd_put_32 (output_bfd, insn3, splt->contents + h->plt.offset + 8);
4923 }
4924
4925 /* Fill in the entry in the .rela.plt section. */
4926 outrel.r_offset = got_addr;
4927 outrel.r_info = ELF64_R_INFO(h->dynindx, R_ALPHA_JMP_SLOT);
4928 outrel.r_addend = 0;
4929
947216bf
AM
4930 loc = srel->contents + plt_index * sizeof (Elf64_External_Rela);
4931 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
252b5132
RH
4932
4933 if (!(h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR))
4934 {
4935 /* Mark the symbol as undefined, rather than as defined in the
4936 .plt section. Leave the value alone. */
4937 sym->st_shndx = SHN_UNDEF;
4938 }
4939
4940 /* Fill in the entries in the .got. */
4941 bfd_put_64 (output_bfd, plt_addr, sgot->contents + gotent->got_offset);
4942
4943 /* Subsequent .got entries will continue to bounce through the .plt. */
4944 if (gotent->next)
4945 {
4946 srel = bfd_get_section_by_name (dynobj, ".rela.got");
4947 BFD_ASSERT (! info->shared || srel != NULL);
4948
4949 gotent = gotent->next;
4950 do
4951 {
4952 sgot = alpha_elf_tdata(gotent->gotobj)->got;
4953 BFD_ASSERT(sgot != NULL);
4954 BFD_ASSERT(gotent->addend == 0);
4955
4956 bfd_put_64 (output_bfd, plt_addr,
4957 sgot->contents + gotent->got_offset);
4958
4959 if (info->shared)
4960 {
4961 outrel.r_offset = (sgot->output_section->vma
4962 + sgot->output_offset
4963 + gotent->got_offset);
4964 outrel.r_info = ELF64_R_INFO(0, R_ALPHA_RELATIVE);
28cfee26 4965 outrel.r_addend = plt_addr;
252b5132 4966
947216bf
AM
4967 loc = srel->contents;
4968 loc += srel->reloc_count++ * sizeof (Elf64_External_Rela);
4969 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
fe8bc63d 4970 BFD_ASSERT (sizeof (Elf64_External_Rela) * srel->reloc_count
252b5132
RH
4971 <= srel->_cooked_size);
4972 }
4973
4974 gotent = gotent->next;
4975 }
4976 while (gotent != NULL);
4977 }
4978 }
4979 else if (alpha_elf_dynamic_symbol_p (h, info))
4980 {
4981 /* Fill in the dynamic relocations for this symbol's .got entries. */
4982 asection *srel;
4983 Elf_Internal_Rela outrel;
947216bf 4984 bfd_byte *loc;
252b5132
RH
4985 struct alpha_elf_got_entry *gotent;
4986
4987 srel = bfd_get_section_by_name (dynobj, ".rela.got");
4988 BFD_ASSERT (srel != NULL);
4989
252b5132
RH
4990 for (gotent = ((struct alpha_elf_link_hash_entry *) h)->got_entries;
4991 gotent != NULL;
4992 gotent = gotent->next)
4993 {
f44f99a5 4994 asection *sgot;
3765b1be
RH
4995 int r_type;
4996
f44f99a5
RH
4997 if (gotent->use_count == 0)
4998 continue;
4999
5000 sgot = alpha_elf_tdata (gotent->gotobj)->got;
252b5132
RH
5001 outrel.r_offset = (sgot->output_section->vma
5002 + sgot->output_offset
5003 + gotent->got_offset);
3765b1be
RH
5004
5005 r_type = gotent->reloc_type;
5006 switch (r_type)
5007 {
5008 case R_ALPHA_LITERAL:
5009 r_type = R_ALPHA_GLOB_DAT;
5010 break;
5011 case R_ALPHA_TLSGD:
5012 r_type = R_ALPHA_DTPMOD64;
5013 break;
5014 case R_ALPHA_GOTDTPREL:
5015 r_type = R_ALPHA_DTPREL64;
5016 break;
5017 case R_ALPHA_GOTTPREL:
5018 r_type = R_ALPHA_TPREL64;
5019 break;
5020 case R_ALPHA_TLSLDM:
5021 default:
5022 abort ();
5023 }
5024
5025 outrel.r_info = ELF64_R_INFO (h->dynindx, r_type);
252b5132
RH
5026 outrel.r_addend = gotent->addend;
5027
947216bf
AM
5028 loc = srel->contents;
5029 loc += srel->reloc_count++ * sizeof (Elf64_External_Rela);
5030 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
3765b1be
RH
5031
5032 if (gotent->reloc_type == R_ALPHA_TLSGD)
5033 {
5034 outrel.r_offset += 8;
5035 outrel.r_info = ELF64_R_INFO (h->dynindx, R_ALPHA_DTPREL64);
5036
947216bf
AM
5037 loc = srel->contents;
5038 loc += srel->reloc_count++ * sizeof (Elf64_External_Rela);
5039 bfd_elf64_swap_reloca_out (output_bfd, &outrel, loc);
3765b1be
RH
5040 }
5041
fe8bc63d 5042 BFD_ASSERT (sizeof (Elf64_External_Rela) * srel->reloc_count
252b5132
RH
5043 <= srel->_cooked_size);
5044 }
5045 }
5046
5047 /* Mark some specially defined symbols as absolute. */
5048 if (strcmp (h->root.root.string, "_DYNAMIC") == 0
5049 || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0
5050 || strcmp (h->root.root.string, "_PROCEDURE_LINKAGE_TABLE_") == 0)
5051 sym->st_shndx = SHN_ABS;
5052
b34976b6 5053 return TRUE;
252b5132
RH
5054}
5055
5056/* Finish up the dynamic sections. */
5057
b34976b6 5058static bfd_boolean
252b5132
RH
5059elf64_alpha_finish_dynamic_sections (output_bfd, info)
5060 bfd *output_bfd;
5061 struct bfd_link_info *info;
5062{
5063 bfd *dynobj;
5064 asection *sdyn;
5065
5066 dynobj = elf_hash_table (info)->dynobj;
5067 sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
5068
5069 if (elf_hash_table (info)->dynamic_sections_created)
5070 {
5071 asection *splt;
5072 Elf64_External_Dyn *dyncon, *dynconend;
5073
5074 splt = bfd_get_section_by_name (dynobj, ".plt");
5075 BFD_ASSERT (splt != NULL && sdyn != NULL);
5076
5077 dyncon = (Elf64_External_Dyn *) sdyn->contents;
5078 dynconend = (Elf64_External_Dyn *) (sdyn->contents + sdyn->_raw_size);
5079 for (; dyncon < dynconend; dyncon++)
5080 {
5081 Elf_Internal_Dyn dyn;
5082 const char *name;
5083 asection *s;
5084
5085 bfd_elf64_swap_dyn_in (dynobj, dyncon, &dyn);
5086
5087 switch (dyn.d_tag)
5088 {
5089 case DT_PLTGOT:
5090 name = ".plt";
5091 goto get_vma;
5092 case DT_PLTRELSZ:
5093 name = ".rela.plt";
5094 goto get_size;
5095 case DT_JMPREL:
5096 name = ".rela.plt";
5097 goto get_vma;
5098
5099 case DT_RELASZ:
5100 /* My interpretation of the TIS v1.1 ELF document indicates
5101 that RELASZ should not include JMPREL. This is not what
5102 the rest of the BFD does. It is, however, what the
5103 glibc ld.so wants. Do this fixup here until we found
5104 out who is right. */
5105 s = bfd_get_section_by_name (output_bfd, ".rela.plt");
5106 if (s)
5107 {
5108 dyn.d_un.d_val -=
5109 (s->_cooked_size ? s->_cooked_size : s->_raw_size);
5110 }
5111 break;
5112
5113 get_vma:
5114 s = bfd_get_section_by_name (output_bfd, name);
5115 dyn.d_un.d_ptr = (s ? s->vma : 0);
5116 break;
5117
5118 get_size:
5119 s = bfd_get_section_by_name (output_bfd, name);
5120 dyn.d_un.d_val =
5121 (s->_cooked_size ? s->_cooked_size : s->_raw_size);
5122 break;
5123 }
5124
5125 bfd_elf64_swap_dyn_out (output_bfd, &dyn, dyncon);
5126 }
5127
5128 /* Initialize the PLT0 entry */
5129 if (splt->_raw_size > 0)
5130 {
5131 bfd_put_32 (output_bfd, PLT_HEADER_WORD1, splt->contents);
5132 bfd_put_32 (output_bfd, PLT_HEADER_WORD2, splt->contents + 4);
5133 bfd_put_32 (output_bfd, PLT_HEADER_WORD3, splt->contents + 8);
5134 bfd_put_32 (output_bfd, PLT_HEADER_WORD4, splt->contents + 12);
5135
5136 /* The next two words will be filled in by ld.so */
dc810e39
AM
5137 bfd_put_64 (output_bfd, (bfd_vma) 0, splt->contents + 16);
5138 bfd_put_64 (output_bfd, (bfd_vma) 0, splt->contents + 24);
252b5132 5139
eecdbe52 5140 elf_section_data (splt->output_section)->this_hdr.sh_entsize = 0;
252b5132
RH
5141 }
5142 }
5143
b34976b6 5144 return TRUE;
252b5132
RH
5145}
5146
96e2734b
RH
5147/* We need to use a special link routine to handle the .mdebug section.
5148 We need to merge all instances of these sections together, not write
5149 them all out sequentially. */
252b5132 5150
b34976b6 5151static bfd_boolean
252b5132
RH
5152elf64_alpha_final_link (abfd, info)
5153 bfd *abfd;
5154 struct bfd_link_info *info;
5155{
5156 asection *o;
5157 struct bfd_link_order *p;
96e2734b 5158 asection *mdebug_sec;
252b5132
RH
5159 struct ecoff_debug_info debug;
5160 const struct ecoff_debug_swap *swap
5161 = get_elf_backend_data (abfd)->elf_backend_ecoff_debug_swap;
5162 HDRR *symhdr = &debug.symbolic_header;
5163 PTR mdebug_handle = NULL;
5164
96e2734b 5165 /* Go through the sections and collect the mdebug information. */
252b5132 5166 mdebug_sec = NULL;
252b5132
RH
5167 for (o = abfd->sections; o != (asection *) NULL; o = o->next)
5168 {
252b5132
RH
5169 if (strcmp (o->name, ".mdebug") == 0)
5170 {
5171 struct extsym_info einfo;
5172
5173 /* We have found the .mdebug section in the output file.
5174 Look through all the link_orders comprising it and merge
5175 the information together. */
5176 symhdr->magic = swap->sym_magic;
5177 /* FIXME: What should the version stamp be? */
5178 symhdr->vstamp = 0;
5179 symhdr->ilineMax = 0;
5180 symhdr->cbLine = 0;
5181 symhdr->idnMax = 0;
5182 symhdr->ipdMax = 0;
5183 symhdr->isymMax = 0;
5184 symhdr->ioptMax = 0;
5185 symhdr->iauxMax = 0;
5186 symhdr->issMax = 0;
5187 symhdr->issExtMax = 0;
5188 symhdr->ifdMax = 0;
5189 symhdr->crfd = 0;
5190 symhdr->iextMax = 0;
5191
5192 /* We accumulate the debugging information itself in the
5193 debug_info structure. */
5194 debug.line = NULL;
5195 debug.external_dnr = NULL;
5196 debug.external_pdr = NULL;
5197 debug.external_sym = NULL;
5198 debug.external_opt = NULL;
5199 debug.external_aux = NULL;
5200 debug.ss = NULL;
5201 debug.ssext = debug.ssext_end = NULL;
5202 debug.external_fdr = NULL;
5203 debug.external_rfd = NULL;
5204 debug.external_ext = debug.external_ext_end = NULL;
5205
5206 mdebug_handle = bfd_ecoff_debug_init (abfd, &debug, swap, info);
5207 if (mdebug_handle == (PTR) NULL)
b34976b6 5208 return FALSE;
252b5132
RH
5209
5210 if (1)
5211 {
5212 asection *s;
5213 EXTR esym;
52b9d213 5214 bfd_vma last = 0;
252b5132
RH
5215 unsigned int i;
5216 static const char * const name[] =
5217 {
5218 ".text", ".init", ".fini", ".data",
5219 ".rodata", ".sdata", ".sbss", ".bss"
5220 };
5221 static const int sc[] = { scText, scInit, scFini, scData,
5222 scRData, scSData, scSBss, scBss };
5223
5224 esym.jmptbl = 0;
5225 esym.cobol_main = 0;
5226 esym.weakext = 0;
5227 esym.reserved = 0;
5228 esym.ifd = ifdNil;
5229 esym.asym.iss = issNil;
5230 esym.asym.st = stLocal;
5231 esym.asym.reserved = 0;
5232 esym.asym.index = indexNil;
5233 for (i = 0; i < 8; i++)
5234 {
5235 esym.asym.sc = sc[i];
5236 s = bfd_get_section_by_name (abfd, name[i]);
5237 if (s != NULL)
5238 {
5239 esym.asym.value = s->vma;
5240 last = s->vma + s->_raw_size;
5241 }
5242 else
5243 esym.asym.value = last;
5244
5245 if (! bfd_ecoff_debug_one_external (abfd, &debug, swap,
5246 name[i], &esym))
b34976b6 5247 return FALSE;
252b5132
RH
5248 }
5249 }
5250
5251 for (p = o->link_order_head;
5252 p != (struct bfd_link_order *) NULL;
5253 p = p->next)
5254 {
5255 asection *input_section;
5256 bfd *input_bfd;
5257 const struct ecoff_debug_swap *input_swap;
5258 struct ecoff_debug_info input_debug;
5259 char *eraw_src;
5260 char *eraw_end;
5261
5262 if (p->type != bfd_indirect_link_order)
5263 {
fd96f80f 5264 if (p->type == bfd_data_link_order)
252b5132
RH
5265 continue;
5266 abort ();
5267 }
5268
5269 input_section = p->u.indirect.section;
5270 input_bfd = input_section->owner;
5271
5272 if (bfd_get_flavour (input_bfd) != bfd_target_elf_flavour
5273 || (get_elf_backend_data (input_bfd)
5274 ->elf_backend_ecoff_debug_swap) == NULL)
5275 {
5276 /* I don't know what a non ALPHA ELF bfd would be
5277 doing with a .mdebug section, but I don't really
5278 want to deal with it. */
5279 continue;
5280 }
5281
5282 input_swap = (get_elf_backend_data (input_bfd)
5283 ->elf_backend_ecoff_debug_swap);
5284
5285 BFD_ASSERT (p->size == input_section->_raw_size);
5286
5287 /* The ECOFF linking code expects that we have already
5288 read in the debugging information and set up an
5289 ecoff_debug_info structure, so we do that now. */
5290 if (!elf64_alpha_read_ecoff_info (input_bfd, input_section,
5291 &input_debug))
b34976b6 5292 return FALSE;
252b5132
RH
5293
5294 if (! (bfd_ecoff_debug_accumulate
5295 (mdebug_handle, abfd, &debug, swap, input_bfd,
5296 &input_debug, input_swap, info)))
b34976b6 5297 return FALSE;
252b5132
RH
5298
5299 /* Loop through the external symbols. For each one with
5300 interesting information, try to find the symbol in
5301 the linker global hash table and save the information
5302 for the output external symbols. */
5303 eraw_src = input_debug.external_ext;
5304 eraw_end = (eraw_src
5305 + (input_debug.symbolic_header.iextMax
5306 * input_swap->external_ext_size));
5307 for (;
5308 eraw_src < eraw_end;
5309 eraw_src += input_swap->external_ext_size)
5310 {
5311 EXTR ext;
5312 const char *name;
5313 struct alpha_elf_link_hash_entry *h;
5314
5315 (*input_swap->swap_ext_in) (input_bfd, (PTR) eraw_src, &ext);
5316 if (ext.asym.sc == scNil
5317 || ext.asym.sc == scUndefined
5318 || ext.asym.sc == scSUndefined)
5319 continue;
5320
5321 name = input_debug.ssext + ext.asym.iss;
5322 h = alpha_elf_link_hash_lookup (alpha_elf_hash_table (info),
b34976b6 5323 name, FALSE, FALSE, TRUE);
252b5132
RH
5324 if (h == NULL || h->esym.ifd != -2)
5325 continue;
5326
5327 if (ext.ifd != -1)
5328 {
5329 BFD_ASSERT (ext.ifd
5330 < input_debug.symbolic_header.ifdMax);
5331 ext.ifd = input_debug.ifdmap[ext.ifd];
5332 }
5333
5334 h->esym = ext;
5335 }
5336
5337 /* Free up the information we just read. */
5338 free (input_debug.line);
5339 free (input_debug.external_dnr);
5340 free (input_debug.external_pdr);
5341 free (input_debug.external_sym);
5342 free (input_debug.external_opt);
5343 free (input_debug.external_aux);
5344 free (input_debug.ss);
5345 free (input_debug.ssext);
5346 free (input_debug.external_fdr);
5347 free (input_debug.external_rfd);
5348 free (input_debug.external_ext);
5349
5350 /* Hack: reset the SEC_HAS_CONTENTS flag so that
5351 elf_link_input_bfd ignores this section. */
5352 input_section->flags &=~ SEC_HAS_CONTENTS;
5353 }
5354
252b5132
RH
5355 /* Build the external symbol information. */
5356 einfo.abfd = abfd;
5357 einfo.info = info;
5358 einfo.debug = &debug;
5359 einfo.swap = swap;
b34976b6 5360 einfo.failed = FALSE;
252b5132
RH
5361 elf_link_hash_traverse (elf_hash_table (info),
5362 elf64_alpha_output_extsym,
5363 (PTR) &einfo);
5364 if (einfo.failed)
b34976b6 5365 return FALSE;
252b5132
RH
5366
5367 /* Set the size of the .mdebug section. */
5368 o->_raw_size = bfd_ecoff_debug_size (abfd, &debug, swap);
5369
5370 /* Skip this section later on (I don't think this currently
5371 matters, but someday it might). */
5372 o->link_order_head = (struct bfd_link_order *) NULL;
5373
5374 mdebug_sec = o;
5375 }
252b5132
RH
5376 }
5377
5378 /* Invoke the regular ELF backend linker to do all the work. */
5379 if (! bfd_elf64_bfd_final_link (abfd, info))
b34976b6 5380 return FALSE;
252b5132
RH
5381
5382 /* Now write out the computed sections. */
5383
5384 /* The .got subsections... */
5385 {
5386 bfd *i, *dynobj = elf_hash_table(info)->dynobj;
5387 for (i = alpha_elf_hash_table(info)->got_list;
5388 i != NULL;
5389 i = alpha_elf_tdata(i)->got_link_next)
5390 {
5391 asection *sgot;
5392
5393 /* elf_bfd_final_link already did everything in dynobj. */
5394 if (i == dynobj)
5395 continue;
5396
5397 sgot = alpha_elf_tdata(i)->got;
5398 if (! bfd_set_section_contents (abfd, sgot->output_section,
dc810e39
AM
5399 sgot->contents,
5400 (file_ptr) sgot->output_offset,
252b5132 5401 sgot->_raw_size))
b34976b6 5402 return FALSE;
252b5132
RH
5403 }
5404 }
5405
252b5132
RH
5406 if (mdebug_sec != (asection *) NULL)
5407 {
5408 BFD_ASSERT (abfd->output_has_begun);
5409 if (! bfd_ecoff_write_accumulated_debug (mdebug_handle, abfd, &debug,
5410 swap, info,
5411 mdebug_sec->filepos))
b34976b6 5412 return FALSE;
252b5132
RH
5413
5414 bfd_ecoff_debug_free (mdebug_handle, abfd, &debug, swap, info);
5415 }
5416
b34976b6 5417 return TRUE;
252b5132 5418}
fcfbdf31
JJ
5419
5420static enum elf_reloc_type_class
f51e552e
AM
5421elf64_alpha_reloc_type_class (rela)
5422 const Elf_Internal_Rela *rela;
fcfbdf31 5423{
f51e552e 5424 switch ((int) ELF64_R_TYPE (rela->r_info))
fcfbdf31
JJ
5425 {
5426 case R_ALPHA_RELATIVE:
5427 return reloc_class_relative;
5428 case R_ALPHA_JMP_SLOT:
5429 return reloc_class_plt;
5430 case R_ALPHA_COPY:
5431 return reloc_class_copy;
5432 default:
5433 return reloc_class_normal;
5434 }
5435}
252b5132
RH
5436\f
5437/* ECOFF swapping routines. These are used when dealing with the
5438 .mdebug section, which is in the ECOFF debugging format. Copied
fe8bc63d 5439 from elf32-mips.c. */
252b5132
RH
5440static const struct ecoff_debug_swap
5441elf64_alpha_ecoff_debug_swap =
5442{
5443 /* Symbol table magic number. */
5444 magicSym2,
5445 /* Alignment of debugging information. E.g., 4. */
5446 8,
5447 /* Sizes of external symbolic information. */
5448 sizeof (struct hdr_ext),
5449 sizeof (struct dnr_ext),
5450 sizeof (struct pdr_ext),
5451 sizeof (struct sym_ext),
5452 sizeof (struct opt_ext),
5453 sizeof (struct fdr_ext),
5454 sizeof (struct rfd_ext),
5455 sizeof (struct ext_ext),
5456 /* Functions to swap in external symbolic data. */
5457 ecoff_swap_hdr_in,
5458 ecoff_swap_dnr_in,
5459 ecoff_swap_pdr_in,
5460 ecoff_swap_sym_in,
5461 ecoff_swap_opt_in,
5462 ecoff_swap_fdr_in,
5463 ecoff_swap_rfd_in,
5464 ecoff_swap_ext_in,
5465 _bfd_ecoff_swap_tir_in,
5466 _bfd_ecoff_swap_rndx_in,
5467 /* Functions to swap out external symbolic data. */
5468 ecoff_swap_hdr_out,
5469 ecoff_swap_dnr_out,
5470 ecoff_swap_pdr_out,
5471 ecoff_swap_sym_out,
5472 ecoff_swap_opt_out,
5473 ecoff_swap_fdr_out,
5474 ecoff_swap_rfd_out,
5475 ecoff_swap_ext_out,
5476 _bfd_ecoff_swap_tir_out,
5477 _bfd_ecoff_swap_rndx_out,
5478 /* Function to read in symbolic data. */
5479 elf64_alpha_read_ecoff_info
5480};
5481\f
70bcb145
JW
5482/* Use a non-standard hash bucket size of 8. */
5483
562ace6b 5484static const struct elf_size_info alpha_elf_size_info =
70bcb145
JW
5485{
5486 sizeof (Elf64_External_Ehdr),
5487 sizeof (Elf64_External_Phdr),
5488 sizeof (Elf64_External_Shdr),
5489 sizeof (Elf64_External_Rel),
5490 sizeof (Elf64_External_Rela),
5491 sizeof (Elf64_External_Sym),
5492 sizeof (Elf64_External_Dyn),
5493 sizeof (Elf_External_Note),
5494 8,
5495 1,
5496 64, 8,
5497 ELFCLASS64, EV_CURRENT,
5498 bfd_elf64_write_out_phdrs,
5499 bfd_elf64_write_shdrs_and_ehdr,
5500 bfd_elf64_write_relocs,
73ff0d56 5501 bfd_elf64_swap_symbol_in,
70bcb145
JW
5502 bfd_elf64_swap_symbol_out,
5503 bfd_elf64_slurp_reloc_table,
5504 bfd_elf64_slurp_symbol_table,
5505 bfd_elf64_swap_dyn_in,
5506 bfd_elf64_swap_dyn_out,
947216bf
AM
5507 bfd_elf64_swap_reloc_in,
5508 bfd_elf64_swap_reloc_out,
5509 bfd_elf64_swap_reloca_in,
5510 bfd_elf64_swap_reloca_out
70bcb145
JW
5511};
5512
252b5132
RH
5513#define TARGET_LITTLE_SYM bfd_elf64_alpha_vec
5514#define TARGET_LITTLE_NAME "elf64-alpha"
5515#define ELF_ARCH bfd_arch_alpha
56fc028e
AJ
5516#define ELF_MACHINE_CODE EM_ALPHA
5517#define ELF_MAXPAGESIZE 0x10000
252b5132
RH
5518
5519#define bfd_elf64_bfd_link_hash_table_create \
5520 elf64_alpha_bfd_link_hash_table_create
5521
5522#define bfd_elf64_bfd_reloc_type_lookup \
5523 elf64_alpha_bfd_reloc_type_lookup
5524#define elf_info_to_howto \
5525 elf64_alpha_info_to_howto
5526
5527#define bfd_elf64_mkobject \
5528 elf64_alpha_mkobject
5529#define elf_backend_object_p \
5530 elf64_alpha_object_p
5531
5532#define elf_backend_section_from_shdr \
5533 elf64_alpha_section_from_shdr
204692d7
RH
5534#define elf_backend_section_flags \
5535 elf64_alpha_section_flags
252b5132
RH
5536#define elf_backend_fake_sections \
5537 elf64_alpha_fake_sections
5538
5539#define bfd_elf64_bfd_is_local_label_name \
5540 elf64_alpha_is_local_label_name
5541#define bfd_elf64_find_nearest_line \
5542 elf64_alpha_find_nearest_line
5543#define bfd_elf64_bfd_relax_section \
5544 elf64_alpha_relax_section
5545
5546#define elf_backend_add_symbol_hook \
5547 elf64_alpha_add_symbol_hook
5548#define elf_backend_check_relocs \
5549 elf64_alpha_check_relocs
5550#define elf_backend_create_dynamic_sections \
5551 elf64_alpha_create_dynamic_sections
5552#define elf_backend_adjust_dynamic_symbol \
5553 elf64_alpha_adjust_dynamic_symbol
5554#define elf_backend_always_size_sections \
5555 elf64_alpha_always_size_sections
5556#define elf_backend_size_dynamic_sections \
5557 elf64_alpha_size_dynamic_sections
5558#define elf_backend_relocate_section \
5559 elf64_alpha_relocate_section
5560#define elf_backend_finish_dynamic_symbol \
5561 elf64_alpha_finish_dynamic_symbol
5562#define elf_backend_finish_dynamic_sections \
5563 elf64_alpha_finish_dynamic_sections
5564#define bfd_elf64_bfd_final_link \
5565 elf64_alpha_final_link
fcfbdf31
JJ
5566#define elf_backend_reloc_type_class \
5567 elf64_alpha_reloc_type_class
252b5132
RH
5568
5569#define elf_backend_ecoff_debug_swap \
5570 &elf64_alpha_ecoff_debug_swap
5571
70bcb145
JW
5572#define elf_backend_size_info \
5573 alpha_elf_size_info
5574
38b1a46c 5575/* A few constants that determine how the .plt section is set up. */
252b5132
RH
5576#define elf_backend_want_got_plt 0
5577#define elf_backend_plt_readonly 0
5578#define elf_backend_want_plt_sym 1
5579#define elf_backend_got_header_size 0
5580#define elf_backend_plt_header_size PLT_HEADER_SIZE
5581
5582#include "elf64-target.h"
2238051f
RH
5583\f
5584/* FreeBSD support. */
5585
5586#undef TARGET_LITTLE_SYM
5587#define TARGET_LITTLE_SYM bfd_elf64_alpha_freebsd_vec
5588#undef TARGET_LITTLE_NAME
5589#define TARGET_LITTLE_NAME "elf64-alpha-freebsd"
5590
5591/* The kernel recognizes executables as valid only if they carry a
5592 "FreeBSD" label in the ELF header. So we put this label on all
5593 executables and (for simplicity) also all other object files. */
5594
5595static void elf64_alpha_fbsd_post_process_headers
5596 PARAMS ((bfd *, struct bfd_link_info *));
5597
5598static void
5599elf64_alpha_fbsd_post_process_headers (abfd, link_info)
5600 bfd * abfd;
5601 struct bfd_link_info * link_info ATTRIBUTE_UNUSED;
5602{
5603 Elf_Internal_Ehdr * i_ehdrp; /* ELF file header, internal form. */
5604
5605 i_ehdrp = elf_elfheader (abfd);
5606
5607 /* Put an ABI label supported by FreeBSD >= 4.1. */
5608 i_ehdrp->e_ident[EI_OSABI] = ELFOSABI_FREEBSD;
5609#ifdef OLD_FREEBSD_ABI_LABEL
5610 /* The ABI label supported by FreeBSD <= 4.0 is quite nonstandard. */
5611 memcpy (&i_ehdrp->e_ident[EI_ABIVERSION], "FreeBSD", 8);
5612#endif
5613}
5614
5615#undef elf_backend_post_process_headers
5616#define elf_backend_post_process_headers \
5617 elf64_alpha_fbsd_post_process_headers
5618
571fe01f 5619#undef elf64_bed
2238051f
RH
5620#define elf64_bed elf64_alpha_fbsd_bed
5621
5622#include "elf64-target.h"