2000-12-01 Fernando Nasser <fnasser@redhat.com>
[deliverable/binutils-gdb.git] / bfd / elf64-ia64.c
CommitLineData
8d88c4ca
NC
1/* IA-64 support for 64-bit ELF
2 Copyright 1998, 1999, 2000 Free Software Foundation, Inc.
3 Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
4
5This file is part of BFD, the Binary File Descriptor library.
6
7This program is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2 of the License, or
10(at your option) any later version.
11
12This program is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with this program; if not, write to the Free Software
19Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
20
21#include "bfd.h"
22#include "sysdep.h"
23#include "libbfd.h"
24#include "elf-bfd.h"
25#include "opcode/ia64.h"
26#include "elf/ia64.h"
27
28
29/*
30 * THE RULES for all the stuff the linker creates --
31 *
32 * GOT Entries created in response to LTOFF or LTOFF_FPTR
33 * relocations. Dynamic relocs created for dynamic
34 * symbols in an application; REL relocs for locals
35 * in a shared library.
36 *
37 * FPTR The canonical function descriptor. Created for local
38 * symbols in applications. Descriptors for dynamic symbols
39 * and local symbols in shared libraries are created by
40 * ld.so. Thus there are no dynamic relocs against these
41 * objects. The FPTR relocs for such _are_ passed through
42 * to the dynamic relocation tables.
43 *
44 * FULL_PLT Created for a PCREL21B relocation against a dynamic symbol.
45 * Requires the creation of a PLTOFF entry. This does not
46 * require any dynamic relocations.
47 *
48 * PLTOFF Created by PLTOFF relocations. For local symbols, this
49 * is an alternate function descriptor, and in shared libraries
50 * requires two REL relocations. Note that this cannot be
51 * transformed into an FPTR relocation, since it must be in
52 * range of the GP. For dynamic symbols, this is a function
53 * descriptor for a MIN_PLT entry, and requires one IPLT reloc.
54 *
55 * MIN_PLT Created by PLTOFF entries against dynamic symbols. This
56 * does not reqire dynamic relocations.
57 */
58
59#define USE_RELA /* we want RELA relocs, not REL */
60
61#define NELEMS(a) ((int) (sizeof (a) / sizeof ((a)[0])))
62
63typedef struct bfd_hash_entry *(*new_hash_entry_func)
64 PARAMS ((struct bfd_hash_entry *, struct bfd_hash_table *, const char *));
65
66/* In dynamically (linker-) created sections, we generally need to keep track
67 of the place a symbol or expression got allocated to. This is done via hash
68 tables that store entries of the following type. */
69
70struct elf64_ia64_dyn_sym_info
71{
72 /* The addend for which this entry is relevant. */
73 bfd_vma addend;
74
75 /* Next addend in the list. */
76 struct elf64_ia64_dyn_sym_info *next;
77
78 bfd_vma got_offset;
79 bfd_vma fptr_offset;
80 bfd_vma pltoff_offset;
81 bfd_vma plt_offset;
82 bfd_vma plt2_offset;
83
84 /* The symbol table entry, if any, that this was derrived from. */
85 struct elf_link_hash_entry *h;
86
87 /* Used to count non-got, non-plt relocations for delayed sizing
88 of relocation sections. */
89 struct elf64_ia64_dyn_reloc_entry
90 {
91 struct elf64_ia64_dyn_reloc_entry *next;
92 asection *srel;
93 int type;
94 int count;
95 } *reloc_entries;
96
97 /* True when the section contents have been updated. */
98 unsigned got_done : 1;
99 unsigned fptr_done : 1;
100 unsigned pltoff_done : 1;
101
102 /* True for the different kinds of linker data we want created. */
103 unsigned want_got : 1;
104 unsigned want_fptr : 1;
105 unsigned want_ltoff_fptr : 1;
106 unsigned want_plt : 1;
107 unsigned want_plt2 : 1;
108 unsigned want_pltoff : 1;
109};
110
111struct elf64_ia64_local_hash_entry
112{
113 struct bfd_hash_entry root;
114 struct elf64_ia64_dyn_sym_info *info;
115};
116
117struct elf64_ia64_local_hash_table
118{
119 struct bfd_hash_table root;
120 /* No additional fields for now. */
121};
122
123struct elf64_ia64_link_hash_entry
124{
125 struct elf_link_hash_entry root;
126 struct elf64_ia64_dyn_sym_info *info;
127};
128
129struct elf64_ia64_link_hash_table
130{
131 /* The main hash table */
132 struct elf_link_hash_table root;
133
134 asection *got_sec; /* the linkage table section (or NULL) */
135 asection *rel_got_sec; /* dynamic relocation section for same */
136 asection *fptr_sec; /* function descriptor table (or NULL) */
137 asection *plt_sec; /* the primary plt section (or NULL) */
138 asection *pltoff_sec; /* private descriptors for plt (or NULL) */
139 asection *rel_pltoff_sec; /* dynamic relocation section for same */
140
141 bfd_size_type minplt_entries; /* number of minplt entries */
142
143 struct elf64_ia64_local_hash_table loc_hash_table;
144};
145
146#define elf64_ia64_hash_table(p) \
147 ((struct elf64_ia64_link_hash_table *) ((p)->hash))
148
149static bfd_reloc_status_type elf64_ia64_reloc
150 PARAMS ((bfd *abfd, arelent *reloc, asymbol *sym, PTR data,
151 asection *input_section, bfd *output_bfd, char **error_message));
152static reloc_howto_type * lookup_howto
153 PARAMS ((unsigned int rtype));
154static reloc_howto_type *elf64_ia64_reloc_type_lookup
155 PARAMS ((bfd *abfd, bfd_reloc_code_real_type bfd_code));
156static void elf64_ia64_info_to_howto
157 PARAMS ((bfd *abfd, arelent *bfd_reloc, Elf64_Internal_Rela *elf_reloc));
158static boolean elf64_ia64_relax_section
159 PARAMS((bfd *abfd, asection *sec, struct bfd_link_info *link_info,
160 boolean *again));
161static boolean elf64_ia64_section_from_shdr
162 PARAMS ((bfd *, Elf64_Internal_Shdr *, char *));
163static boolean elf64_ia64_fake_sections
164 PARAMS ((bfd *abfd, Elf64_Internal_Shdr *hdr, asection *sec));
165static boolean elf64_ia64_add_symbol_hook
166 PARAMS ((bfd *abfd, struct bfd_link_info *info, const Elf_Internal_Sym *sym,
167 const char **namep, flagword *flagsp, asection **secp,
168 bfd_vma *valp));
169static int elf64_ia64_additional_program_headers
170 PARAMS ((bfd *abfd));
171static boolean elf64_ia64_is_local_label_name
172 PARAMS ((bfd *abfd, const char *name));
173static boolean elf64_ia64_dynamic_symbol_p
174 PARAMS ((struct elf_link_hash_entry *h, struct bfd_link_info *info));
175static boolean elf64_ia64_local_hash_table_init
176 PARAMS ((struct elf64_ia64_local_hash_table *ht, bfd *abfd,
177 new_hash_entry_func new));
178static struct bfd_hash_entry *elf64_ia64_new_loc_hash_entry
179 PARAMS ((struct bfd_hash_entry *entry, struct bfd_hash_table *table,
180 const char *string));
181static struct bfd_hash_entry *elf64_ia64_new_elf_hash_entry
182 PARAMS ((struct bfd_hash_entry *entry, struct bfd_hash_table *table,
183 const char *string));
184static struct bfd_link_hash_table *elf64_ia64_hash_table_create
185 PARAMS ((bfd *abfd));
186static struct elf64_ia64_local_hash_entry *elf64_ia64_local_hash_lookup
187 PARAMS ((struct elf64_ia64_local_hash_table *table, const char *string,
188 boolean create, boolean copy));
189static void elf64_ia64_dyn_sym_traverse
190 PARAMS ((struct elf64_ia64_link_hash_table *ia64_info,
191 boolean (*func)(struct elf64_ia64_dyn_sym_info *, PTR),
192 PTR info));
193static boolean elf64_ia64_create_dynamic_sections
194 PARAMS ((bfd *abfd, struct bfd_link_info *info));
195static struct elf64_ia64_dyn_sym_info * get_dyn_sym_info
196 PARAMS ((struct elf64_ia64_link_hash_table *ia64_info,
197 struct elf_link_hash_entry *h,
198 bfd *abfd, const Elf_Internal_Rela *rel, boolean create));
199static asection *get_got
200 PARAMS ((bfd *abfd, struct bfd_link_info *info,
201 struct elf64_ia64_link_hash_table *ia64_info));
202static asection *get_fptr
203 PARAMS ((bfd *abfd, struct bfd_link_info *info,
204 struct elf64_ia64_link_hash_table *ia64_info));
205static asection *get_pltoff
206 PARAMS ((bfd *abfd, struct bfd_link_info *info,
207 struct elf64_ia64_link_hash_table *ia64_info));
208static asection *get_reloc_section
209 PARAMS ((bfd *abfd, struct elf64_ia64_link_hash_table *ia64_info,
210 asection *sec, boolean create));
211static boolean count_dyn_reloc
212 PARAMS ((bfd *abfd, struct elf64_ia64_dyn_sym_info *dyn_i,
213 asection *srel, int type));
214static boolean elf64_ia64_check_relocs
215 PARAMS ((bfd *abfd, struct bfd_link_info *info, asection *sec,
216 const Elf_Internal_Rela *relocs));
217static boolean elf64_ia64_adjust_dynamic_symbol
218 PARAMS ((struct bfd_link_info *info, struct elf_link_hash_entry *h));
219static unsigned long global_sym_index
220 PARAMS ((struct elf_link_hash_entry *h));
221static boolean allocate_fptr
222 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
223static boolean allocate_global_data_got
224 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
225static boolean allocate_global_fptr_got
226 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
227static boolean allocate_local_got
228 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
229static boolean allocate_pltoff_entries
230 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
231static boolean allocate_plt_entries
232 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
233static boolean allocate_plt2_entries
234 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
235static boolean allocate_dynrel_entries
236 PARAMS ((struct elf64_ia64_dyn_sym_info *dyn_i, PTR data));
237static boolean elf64_ia64_size_dynamic_sections
238 PARAMS ((bfd *output_bfd, struct bfd_link_info *info));
239static bfd_reloc_status_type elf64_ia64_install_value
240 PARAMS ((bfd *abfd, bfd_byte *hit_addr, bfd_vma val, unsigned int r_type));
241static void elf64_ia64_install_dyn_reloc
242 PARAMS ((bfd *abfd, struct bfd_link_info *info, asection *sec,
243 asection *srel, bfd_vma offset, unsigned int type,
244 long dynindx, bfd_vma addend));
245static bfd_vma set_got_entry
246 PARAMS ((bfd *abfd, struct bfd_link_info *info,
247 struct elf64_ia64_dyn_sym_info *dyn_i, long dynindx,
248 bfd_vma addend, bfd_vma value, unsigned int dyn_r_type));
249static bfd_vma set_fptr_entry
250 PARAMS ((bfd *abfd, struct bfd_link_info *info,
251 struct elf64_ia64_dyn_sym_info *dyn_i,
252 bfd_vma value));
253static bfd_vma set_pltoff_entry
254 PARAMS ((bfd *abfd, struct bfd_link_info *info,
255 struct elf64_ia64_dyn_sym_info *dyn_i,
256 bfd_vma value, boolean));
257static boolean elf64_ia64_final_link
258 PARAMS ((bfd *abfd, struct bfd_link_info *info));
259static boolean elf64_ia64_relocate_section
260 PARAMS ((bfd *output_bfd, struct bfd_link_info *info, bfd *input_bfd,
261 asection *input_section, bfd_byte *contents,
262 Elf_Internal_Rela *relocs, Elf_Internal_Sym *local_syms,
263 asection **local_sections));
264static boolean elf64_ia64_finish_dynamic_symbol
265 PARAMS ((bfd *output_bfd, struct bfd_link_info *info,
266 struct elf_link_hash_entry *h, Elf_Internal_Sym *sym));
267static boolean elf64_ia64_finish_dynamic_sections
268 PARAMS ((bfd *abfd, struct bfd_link_info *info));
269static boolean elf64_ia64_set_private_flags
270 PARAMS ((bfd *abfd, flagword flags));
271static boolean elf64_ia64_copy_private_bfd_data
272 PARAMS ((bfd *ibfd, bfd *obfd));
273static boolean elf64_ia64_merge_private_bfd_data
274 PARAMS ((bfd *ibfd, bfd *obfd));
275static boolean elf64_ia64_print_private_bfd_data
276 PARAMS ((bfd *abfd, PTR ptr));
277
278\f
279/* ia64-specific relocation */
280
281/* Perform a relocation. Not much to do here as all the hard work is
282 done in elf64_ia64_final_link_relocate. */
283static bfd_reloc_status_type
284elf64_ia64_reloc (abfd, reloc, sym, data, input_section,
285 output_bfd, error_message)
286 bfd *abfd;
287 arelent *reloc;
288 asymbol *sym;
289 PTR data;
290 asection *input_section;
291 bfd *output_bfd;
292 char **error_message;
293{
294 if (output_bfd)
295 {
296 reloc->address += input_section->output_offset;
297 return bfd_reloc_ok;
298 }
299 *error_message = "Unsupported call to elf64_ia64_reloc";
300 return bfd_reloc_notsupported;
301}
302
303#define IA64_HOWTO(TYPE, NAME, SIZE, PCREL, IN) \
304 HOWTO (TYPE, 0, SIZE, 0, PCREL, 0, complain_overflow_signed, \
305 elf64_ia64_reloc, NAME, false, 0, 0, IN)
306
307/* This table has to be sorted according to increasing number of the
308 TYPE field. */
309static reloc_howto_type ia64_howto_table[] =
310 {
311 IA64_HOWTO (R_IA64_NONE, "NONE", 0, false, true),
312
313 IA64_HOWTO (R_IA64_IMM14, "IMM14", 0, false, true),
314 IA64_HOWTO (R_IA64_IMM22, "IMM22", 0, false, true),
315 IA64_HOWTO (R_IA64_IMM64, "IMM64", 0, false, true),
316 IA64_HOWTO (R_IA64_DIR32MSB, "DIR32MSB", 2, false, true),
317 IA64_HOWTO (R_IA64_DIR32LSB, "DIR32LSB", 2, false, true),
318 IA64_HOWTO (R_IA64_DIR64MSB, "DIR64MSB", 4, false, true),
319 IA64_HOWTO (R_IA64_DIR64LSB, "DIR64LSB", 4, false, true),
320
321 IA64_HOWTO (R_IA64_GPREL22, "GPREL22", 0, false, true),
322 IA64_HOWTO (R_IA64_GPREL64I, "GPREL64I", 0, false, true),
323 IA64_HOWTO (R_IA64_GPREL32MSB, "GPREL32MSB", 2, false, true),
324 IA64_HOWTO (R_IA64_GPREL32LSB, "GPREL32LSB", 2, false, true),
325 IA64_HOWTO (R_IA64_GPREL64MSB, "GPREL64MSB", 4, false, true),
326 IA64_HOWTO (R_IA64_GPREL64LSB, "GPREL64LSB", 4, false, true),
327
328 IA64_HOWTO (R_IA64_LTOFF22, "LTOFF22", 0, false, true),
329 IA64_HOWTO (R_IA64_LTOFF64I, "LTOFF64I", 0, false, true),
330
331 IA64_HOWTO (R_IA64_PLTOFF22, "PLTOFF22", 0, false, true),
332 IA64_HOWTO (R_IA64_PLTOFF64I, "PLTOFF64I", 0, false, true),
333 IA64_HOWTO (R_IA64_PLTOFF64MSB, "PLTOFF64MSB", 4, false, true),
334 IA64_HOWTO (R_IA64_PLTOFF64LSB, "PLTOFF64LSB", 4, false, true),
335
336 IA64_HOWTO (R_IA64_FPTR64I, "FPTR64I", 0, false, true),
337 IA64_HOWTO (R_IA64_FPTR32MSB, "FPTR32MSB", 2, false, true),
338 IA64_HOWTO (R_IA64_FPTR32LSB, "FPTR32LSB", 2, false, true),
339 IA64_HOWTO (R_IA64_FPTR64MSB, "FPTR64MSB", 4, false, true),
340 IA64_HOWTO (R_IA64_FPTR64LSB, "FPTR64LSB", 4, false, true),
341
342 IA64_HOWTO (R_IA64_PCREL60B, "PCREL60B", 0, true, true),
343 IA64_HOWTO (R_IA64_PCREL21B, "PCREL21B", 0, true, true),
344 IA64_HOWTO (R_IA64_PCREL21M, "PCREL21M", 0, true, true),
345 IA64_HOWTO (R_IA64_PCREL21F, "PCREL21F", 0, true, true),
346 IA64_HOWTO (R_IA64_PCREL32MSB, "PCREL32MSB", 2, true, true),
347 IA64_HOWTO (R_IA64_PCREL32LSB, "PCREL32LSB", 2, true, true),
348 IA64_HOWTO (R_IA64_PCREL64MSB, "PCREL64MSB", 4, true, true),
349 IA64_HOWTO (R_IA64_PCREL64LSB, "PCREL64LSB", 4, true, true),
350
351 IA64_HOWTO (R_IA64_LTOFF_FPTR22, "LTOFF_FPTR22", 0, false, true),
352 IA64_HOWTO (R_IA64_LTOFF_FPTR64I, "LTOFF_FPTR64I", 0, false, true),
353 IA64_HOWTO (R_IA64_LTOFF_FPTR64MSB, "LTOFF_FPTR64MSB", 4, false, true),
354 IA64_HOWTO (R_IA64_LTOFF_FPTR64LSB, "LTOFF_FPTR64LSB", 4, false, true),
355
356 IA64_HOWTO (R_IA64_SEGBASE, "SEGBASE", 4, false, true),
357 IA64_HOWTO (R_IA64_SEGREL32MSB, "SEGREL32MSB", 2, false, true),
358 IA64_HOWTO (R_IA64_SEGREL32LSB, "SEGREL32LSB", 2, false, true),
359 IA64_HOWTO (R_IA64_SEGREL64MSB, "SEGREL64MSB", 4, false, true),
360 IA64_HOWTO (R_IA64_SEGREL64LSB, "SEGREL64LSB", 4, false, true),
361
362 IA64_HOWTO (R_IA64_SECREL32MSB, "SECREL32MSB", 2, false, true),
363 IA64_HOWTO (R_IA64_SECREL32LSB, "SECREL32LSB", 2, false, true),
364 IA64_HOWTO (R_IA64_SECREL64MSB, "SECREL64MSB", 4, false, true),
365 IA64_HOWTO (R_IA64_SECREL64LSB, "SECREL64LSB", 4, false, true),
366
367 IA64_HOWTO (R_IA64_REL32MSB, "REL32MSB", 2, false, true),
368 IA64_HOWTO (R_IA64_REL32LSB, "REL32LSB", 2, false, true),
369 IA64_HOWTO (R_IA64_REL64MSB, "REL64MSB", 4, false, true),
370 IA64_HOWTO (R_IA64_REL64LSB, "REL64LSB", 4, false, true),
371
372 IA64_HOWTO (R_IA64_LTV32MSB, "LTV32MSB", 2, false, true),
373 IA64_HOWTO (R_IA64_LTV32LSB, "LTV32LSB", 2, false, true),
374 IA64_HOWTO (R_IA64_LTV64MSB, "LTV64MSB", 4, false, true),
375 IA64_HOWTO (R_IA64_LTV64LSB, "LTV64LSB", 4, false, true),
376
377 IA64_HOWTO (R_IA64_PCREL21BI, "PCREL21BI", 0, true, true),
378 IA64_HOWTO (R_IA64_PCREL22, "PCREL22", 0, true, true),
379 IA64_HOWTO (R_IA64_PCREL64I, "PCREL64I", 0, true, true),
380
381 IA64_HOWTO (R_IA64_IPLTMSB, "IPLTMSB", 4, false, true),
382 IA64_HOWTO (R_IA64_IPLTLSB, "IPLTLSB", 4, false, true),
383 IA64_HOWTO (R_IA64_EPLTMSB, "EPLTMSB", 4, false, true),
384 IA64_HOWTO (R_IA64_EPLTLSB, "EPLTLSB", 4, false, true),
385 IA64_HOWTO (R_IA64_COPY, "COPY", 4, false, true),
386 IA64_HOWTO (R_IA64_LTOFF22X, "LTOFF22X", 0, false, true),
387 IA64_HOWTO (R_IA64_LDXMOV, "LDXMOV", 0, false, true),
388
389 IA64_HOWTO (R_IA64_TPREL22, "TPREL22", 0, false, false),
390 IA64_HOWTO (R_IA64_TPREL64MSB, "TPREL64MSB", 8, false, false),
391 IA64_HOWTO (R_IA64_TPREL64LSB, "TPREL64LSB", 8, false, false),
392 IA64_HOWTO (R_IA64_LTOFF_TP22, "LTOFF_TP22", 0, false, false),
393 };
394
395static unsigned char elf_code_to_howto_index[R_IA64_MAX_RELOC_CODE + 1];
396
397/* Given a BFD reloc type, return the matching HOWTO structure. */
398
399static reloc_howto_type*
400lookup_howto (rtype)
401 unsigned int rtype;
402{
403 static int inited = 0;
404 int i;
405
406 if (!inited)
407 {
408 inited = 1;
409
410 memset (elf_code_to_howto_index, 0xff, sizeof (elf_code_to_howto_index));
411 for (i = 0; i < NELEMS (ia64_howto_table); ++i)
412 elf_code_to_howto_index[ia64_howto_table[i].type] = i;
413 }
414
415 BFD_ASSERT (rtype <= R_IA64_MAX_RELOC_CODE);
416 i = elf_code_to_howto_index[rtype];
417 if (i >= NELEMS (ia64_howto_table))
418 return 0;
419 return ia64_howto_table + i;
420}
421
422static reloc_howto_type*
423elf64_ia64_reloc_type_lookup (abfd, bfd_code)
424 bfd *abfd;
425 bfd_reloc_code_real_type bfd_code;
426{
427 unsigned int rtype;
428
429 switch (bfd_code)
430 {
431 case BFD_RELOC_NONE: rtype = R_IA64_NONE; break;
432
433 case BFD_RELOC_IA64_IMM14: rtype = R_IA64_IMM14; break;
434 case BFD_RELOC_IA64_IMM22: rtype = R_IA64_IMM22; break;
435 case BFD_RELOC_IA64_IMM64: rtype = R_IA64_IMM64; break;
436
437 case BFD_RELOC_IA64_DIR32MSB: rtype = R_IA64_DIR32MSB; break;
438 case BFD_RELOC_IA64_DIR32LSB: rtype = R_IA64_DIR32LSB; break;
439 case BFD_RELOC_IA64_DIR64MSB: rtype = R_IA64_DIR64MSB; break;
440 case BFD_RELOC_IA64_DIR64LSB: rtype = R_IA64_DIR64LSB; break;
441
442 case BFD_RELOC_IA64_GPREL22: rtype = R_IA64_GPREL22; break;
443 case BFD_RELOC_IA64_GPREL64I: rtype = R_IA64_GPREL64I; break;
444 case BFD_RELOC_IA64_GPREL32MSB: rtype = R_IA64_GPREL32MSB; break;
445 case BFD_RELOC_IA64_GPREL32LSB: rtype = R_IA64_GPREL32LSB; break;
446 case BFD_RELOC_IA64_GPREL64MSB: rtype = R_IA64_GPREL64MSB; break;
447 case BFD_RELOC_IA64_GPREL64LSB: rtype = R_IA64_GPREL64LSB; break;
448
449 case BFD_RELOC_IA64_LTOFF22: rtype = R_IA64_LTOFF22; break;
450 case BFD_RELOC_IA64_LTOFF64I: rtype = R_IA64_LTOFF64I; break;
451
452 case BFD_RELOC_IA64_PLTOFF22: rtype = R_IA64_PLTOFF22; break;
453 case BFD_RELOC_IA64_PLTOFF64I: rtype = R_IA64_PLTOFF64I; break;
454 case BFD_RELOC_IA64_PLTOFF64MSB: rtype = R_IA64_PLTOFF64MSB; break;
455 case BFD_RELOC_IA64_PLTOFF64LSB: rtype = R_IA64_PLTOFF64LSB; break;
456 case BFD_RELOC_IA64_FPTR64I: rtype = R_IA64_FPTR64I; break;
457 case BFD_RELOC_IA64_FPTR32MSB: rtype = R_IA64_FPTR32MSB; break;
458 case BFD_RELOC_IA64_FPTR32LSB: rtype = R_IA64_FPTR32LSB; break;
459 case BFD_RELOC_IA64_FPTR64MSB: rtype = R_IA64_FPTR64MSB; break;
460 case BFD_RELOC_IA64_FPTR64LSB: rtype = R_IA64_FPTR64LSB; break;
461
462 case BFD_RELOC_IA64_PCREL21B: rtype = R_IA64_PCREL21B; break;
463 case BFD_RELOC_IA64_PCREL21BI: rtype = R_IA64_PCREL21BI; break;
464 case BFD_RELOC_IA64_PCREL21M: rtype = R_IA64_PCREL21M; break;
465 case BFD_RELOC_IA64_PCREL21F: rtype = R_IA64_PCREL21F; break;
466 case BFD_RELOC_IA64_PCREL22: rtype = R_IA64_PCREL22; break;
467 case BFD_RELOC_IA64_PCREL60B: rtype = R_IA64_PCREL60B; break;
468 case BFD_RELOC_IA64_PCREL64I: rtype = R_IA64_PCREL64I; break;
469 case BFD_RELOC_IA64_PCREL32MSB: rtype = R_IA64_PCREL32MSB; break;
470 case BFD_RELOC_IA64_PCREL32LSB: rtype = R_IA64_PCREL32LSB; break;
471 case BFD_RELOC_IA64_PCREL64MSB: rtype = R_IA64_PCREL64MSB; break;
472 case BFD_RELOC_IA64_PCREL64LSB: rtype = R_IA64_PCREL64LSB; break;
473
474 case BFD_RELOC_IA64_LTOFF_FPTR22: rtype = R_IA64_LTOFF_FPTR22; break;
475 case BFD_RELOC_IA64_LTOFF_FPTR64I: rtype = R_IA64_LTOFF_FPTR64I; break;
476 case BFD_RELOC_IA64_LTOFF_FPTR64MSB: rtype = R_IA64_LTOFF_FPTR64MSB; break;
477 case BFD_RELOC_IA64_LTOFF_FPTR64LSB: rtype = R_IA64_LTOFF_FPTR64LSB; break;
478
479 case BFD_RELOC_IA64_SEGBASE: rtype = R_IA64_SEGBASE; break;
480 case BFD_RELOC_IA64_SEGREL32MSB: rtype = R_IA64_SEGREL32MSB; break;
481 case BFD_RELOC_IA64_SEGREL32LSB: rtype = R_IA64_SEGREL32LSB; break;
482 case BFD_RELOC_IA64_SEGREL64MSB: rtype = R_IA64_SEGREL64MSB; break;
483 case BFD_RELOC_IA64_SEGREL64LSB: rtype = R_IA64_SEGREL64LSB; break;
484
485 case BFD_RELOC_IA64_SECREL32MSB: rtype = R_IA64_SECREL32MSB; break;
486 case BFD_RELOC_IA64_SECREL32LSB: rtype = R_IA64_SECREL32LSB; break;
487 case BFD_RELOC_IA64_SECREL64MSB: rtype = R_IA64_SECREL64MSB; break;
488 case BFD_RELOC_IA64_SECREL64LSB: rtype = R_IA64_SECREL64LSB; break;
489
490 case BFD_RELOC_IA64_REL32MSB: rtype = R_IA64_REL32MSB; break;
491 case BFD_RELOC_IA64_REL32LSB: rtype = R_IA64_REL32LSB; break;
492 case BFD_RELOC_IA64_REL64MSB: rtype = R_IA64_REL64MSB; break;
493 case BFD_RELOC_IA64_REL64LSB: rtype = R_IA64_REL64LSB; break;
494
495 case BFD_RELOC_IA64_LTV32MSB: rtype = R_IA64_LTV32MSB; break;
496 case BFD_RELOC_IA64_LTV32LSB: rtype = R_IA64_LTV32LSB; break;
497 case BFD_RELOC_IA64_LTV64MSB: rtype = R_IA64_LTV64MSB; break;
498 case BFD_RELOC_IA64_LTV64LSB: rtype = R_IA64_LTV64LSB; break;
499
500 case BFD_RELOC_IA64_IPLTMSB: rtype = R_IA64_IPLTMSB; break;
501 case BFD_RELOC_IA64_IPLTLSB: rtype = R_IA64_IPLTLSB; break;
502 case BFD_RELOC_IA64_EPLTMSB: rtype = R_IA64_EPLTMSB; break;
503 case BFD_RELOC_IA64_EPLTLSB: rtype = R_IA64_EPLTLSB; break;
504 case BFD_RELOC_IA64_COPY: rtype = R_IA64_COPY; break;
505 case BFD_RELOC_IA64_LTOFF22X: rtype = R_IA64_LTOFF22X; break;
506 case BFD_RELOC_IA64_LDXMOV: rtype = R_IA64_LDXMOV; break;
507
508 case BFD_RELOC_IA64_TPREL22: rtype = R_IA64_TPREL22; break;
509 case BFD_RELOC_IA64_TPREL64MSB: rtype = R_IA64_TPREL64MSB; break;
510 case BFD_RELOC_IA64_TPREL64LSB: rtype = R_IA64_TPREL64LSB; break;
511 case BFD_RELOC_IA64_LTOFF_TP22: rtype = R_IA64_LTOFF_TP22; break;
512
513 default: return 0;
514 }
515 return lookup_howto (rtype);
516}
517
518/* Given a ELF reloc, return the matching HOWTO structure. */
519
520static void
521elf64_ia64_info_to_howto (abfd, bfd_reloc, elf_reloc)
522 bfd *abfd;
523 arelent *bfd_reloc;
524 Elf64_Internal_Rela *elf_reloc;
525{
526 bfd_reloc->howto = lookup_howto (ELF64_R_TYPE (elf_reloc->r_info));
527}
528\f
529#define PLT_HEADER_SIZE (3 * 16)
530#define PLT_MIN_ENTRY_SIZE (1 * 16)
531#define PLT_FULL_ENTRY_SIZE (2 * 16)
532#define PLT_RESERVED_WORDS 3
533
534static const bfd_byte plt_header[PLT_HEADER_SIZE] =
535{
536 0x0b, 0x10, 0x00, 0x1c, 0x00, 0x21, /* [MMI] mov r2=r14;; */
537 0xe0, 0x00, 0x08, 0x00, 0x48, 0x00, /* addl r14=0,r2 */
538 0x00, 0x00, 0x04, 0x00, /* nop.i 0x0;; */
539 0x0b, 0x80, 0x20, 0x1c, 0x18, 0x14, /* [MMI] ld8 r16=[r14],8;; */
540 0x10, 0x41, 0x38, 0x30, 0x28, 0x00, /* ld8 r17=[r14],8 */
541 0x00, 0x00, 0x04, 0x00, /* nop.i 0x0;; */
542 0x11, 0x08, 0x00, 0x1c, 0x18, 0x10, /* [MIB] ld8 r1=[r14] */
543 0x60, 0x88, 0x04, 0x80, 0x03, 0x00, /* mov b6=r17 */
544 0x60, 0x00, 0x80, 0x00 /* br.few b6;; */
545};
546
547static const bfd_byte plt_min_entry[PLT_MIN_ENTRY_SIZE] =
548{
549 0x11, 0x78, 0x00, 0x00, 0x00, 0x24, /* [MIB] mov r15=0 */
550 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, /* nop.i 0x0 */
551 0x00, 0x00, 0x00, 0x40 /* br.few 0 <PLT0>;; */
552};
553
554static const bfd_byte plt_full_entry[PLT_FULL_ENTRY_SIZE] =
555{
556 0x0b, 0x78, 0x00, 0x02, 0x00, 0x24, /* [MMI] addl r15=0,r1;; */
557 0x00, 0x41, 0x3c, 0x30, 0x28, 0xc0, /* ld8 r16=[r15],8 */
558 0x01, 0x08, 0x00, 0x84, /* mov r14=r1;; */
559 0x11, 0x08, 0x00, 0x1e, 0x18, 0x10, /* [MIB] ld8 r1=[r15] */
560 0x60, 0x80, 0x04, 0x80, 0x03, 0x00, /* mov b6=r16 */
561 0x60, 0x00, 0x80, 0x00 /* br.few b6;; */
562};
563
564#define ELF_DYNAMIC_INTERPRETER "/usr/lib/ld.so.1"
565
566/* Select out of range branch fixup type. Note that Itanium does
567 not support brl, and so it gets emulated by the kernel. */
568#undef USE_BRL
569
570static const bfd_byte oor_brl[16] =
571{
572 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MLX] nop.m 0 */
573 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* brl.sptk.few tgt;; */
574 0x00, 0x00, 0x00, 0xc0
575};
576
577static const bfd_byte oor_ip[48] =
578{
579 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MLX] nop.m 0 */
580 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, /* movl r15=0 */
581 0x01, 0x00, 0x00, 0x60,
582 0x03, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MII] nop.m 0 */
583 0x00, 0x01, 0x00, 0x60, 0x00, 0x00, /* mov r16=ip;; */
584 0xf2, 0x80, 0x00, 0x80, /* add r16=r15,r16;; */
585 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MIB] nop.m 0 */
586 0x60, 0x80, 0x04, 0x80, 0x03, 0x00, /* mov b6=r16 */
587 0x60, 0x00, 0x80, 0x00 /* br b6;; */
588};
589\f
590/* These functions do relaxation for IA-64 ELF.
591
592 This is primarily to support branches to targets out of range;
593 relaxation of R_IA64_LTOFF22X and R_IA64_LDXMOV not yet supported. */
594
595static boolean
596elf64_ia64_relax_section (abfd, sec, link_info, again)
597 bfd *abfd;
598 asection *sec;
599 struct bfd_link_info *link_info;
600 boolean *again;
601{
602 struct one_fixup
603 {
604 struct one_fixup *next;
605 asection *tsec;
606 bfd_vma toff;
607 bfd_vma trampoff;
608 };
609
610 Elf_Internal_Shdr *symtab_hdr;
611 Elf_Internal_Rela *internal_relocs;
612 Elf_Internal_Rela *free_relocs;
613 Elf_Internal_Rela *irel, *irelend;
614 bfd_byte *contents;
615 bfd_byte *free_contents;
616 Elf64_External_Sym *extsyms;
617 Elf64_External_Sym *free_extsyms;
618 struct elf64_ia64_link_hash_table *ia64_info;
619 struct one_fixup *fixups = NULL;
620 boolean changed_contents = false;
621 boolean changed_relocs = false;
622
623 /* Assume we're not going to change any sizes, and we'll only need
624 one pass. */
625 *again = false;
626
627 /* Nothing to do if there are no relocations. */
628 if ((sec->flags & SEC_RELOC) == 0
629 || sec->reloc_count == 0)
630 return true;
631
632 /* If this is the first time we have been called for this section,
633 initialize the cooked size. */
634 if (sec->_cooked_size == 0)
635 sec->_cooked_size = sec->_raw_size;
636
637 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
638
639 /* Load the relocations for this section. */
640 internal_relocs = (_bfd_elf64_link_read_relocs
641 (abfd, sec, (PTR) NULL, (Elf_Internal_Rela *) NULL,
642 link_info->keep_memory));
643 if (internal_relocs == NULL)
644 goto error_return;
645 free_relocs = NULL;
646 if (! link_info->keep_memory)
647 free_relocs = internal_relocs;
648
649 ia64_info = elf64_ia64_hash_table (link_info);
650 irelend = internal_relocs + sec->reloc_count;
651
652 for (irel = internal_relocs; irel < irelend; irel++)
653 if (ELF64_R_TYPE (irel->r_info) == (int) R_IA64_PCREL21B)
654 break;
655
656 /* No branch-type relocations. */
657 if (irel == irelend)
658 {
659 if (free_relocs != NULL)
660 free (free_relocs);
661 return true;
662 }
663
664 /* Get the section contents. */
665 free_contents = NULL;
666 if (elf_section_data (sec)->this_hdr.contents != NULL)
667 contents = elf_section_data (sec)->this_hdr.contents;
668 else
669 {
670 contents = (bfd_byte *) bfd_malloc (sec->_raw_size);
671 if (contents == NULL)
672 goto error_return;
673 free_contents = contents;
674
675 if (! bfd_get_section_contents (abfd, sec, contents,
676 (file_ptr) 0, sec->_raw_size))
677 goto error_return;
678 }
679
680 /* Read this BFD's symbols. */
681 free_extsyms = NULL;
682 if (symtab_hdr->contents != NULL)
683 extsyms = (Elf64_External_Sym *) symtab_hdr->contents;
684 else
685 {
686 extsyms = (Elf64_External_Sym *) bfd_malloc (symtab_hdr->sh_size);
687 if (extsyms == NULL)
688 goto error_return;
689 free_extsyms = extsyms;
690 if (bfd_seek (abfd, symtab_hdr->sh_offset, SEEK_SET) != 0
691 || (bfd_read (extsyms, 1, symtab_hdr->sh_size, abfd)
692 != symtab_hdr->sh_size))
693 goto error_return;
694 }
695
696 for (; irel < irelend; irel++)
697 {
698 bfd_vma symaddr, reladdr, trampoff, toff, roff;
699 Elf_Internal_Sym isym;
700 asection *tsec;
701 struct one_fixup *f;
702
703 if (ELF64_R_TYPE (irel->r_info) != (int) R_IA64_PCREL21B)
704 continue;
705
706 /* Get the value of the symbol referred to by the reloc. */
707 if (ELF64_R_SYM (irel->r_info) < symtab_hdr->sh_info)
708 {
709 /* A local symbol. */
710 bfd_elf64_swap_symbol_in (abfd,
711 extsyms + ELF64_R_SYM (irel->r_info),
712 &isym);
713 if (isym.st_shndx == SHN_UNDEF)
714 continue; /* We can't do anthing with undefined symbols. */
715 else if (isym.st_shndx == SHN_ABS)
716 tsec = bfd_abs_section_ptr;
717 else if (isym.st_shndx == SHN_COMMON)
718 tsec = bfd_com_section_ptr;
719 else if (isym.st_shndx > 0 && isym.st_shndx < SHN_LORESERVE)
720 tsec = bfd_section_from_elf_index (abfd, isym.st_shndx);
721 else
722 continue; /* who knows. */
723
724 toff = isym.st_value;
725 }
726 else
727 {
728 unsigned long indx;
729 struct elf_link_hash_entry *h;
730 struct elf64_ia64_dyn_sym_info *dyn_i;
731
732 indx = ELF64_R_SYM (irel->r_info) - symtab_hdr->sh_info;
733 h = elf_sym_hashes (abfd)[indx];
734 BFD_ASSERT (h != NULL);
735
736 while (h->root.type == bfd_link_hash_indirect
737 || h->root.type == bfd_link_hash_warning)
738 h = (struct elf_link_hash_entry *) h->root.u.i.link;
739
740 dyn_i = get_dyn_sym_info (ia64_info, h, abfd, irel, false);
741
742 /* For branches to dynamic symbols, we're interested instead
743 in a branch to the PLT entry. */
744 if (dyn_i && dyn_i->want_plt2)
745 {
746 tsec = ia64_info->plt_sec;
747 toff = dyn_i->plt2_offset;
748 }
749 else
750 {
751 /* We can't do anthing with undefined symbols. */
752 if (h->root.type == bfd_link_hash_undefined
753 || h->root.type == bfd_link_hash_undefweak)
754 continue;
755
756 tsec = h->root.u.def.section;
757 toff = h->root.u.def.value;
758 }
759 }
760
761 symaddr = (tsec->output_section->vma
762 + tsec->output_offset
763 + toff
764 + irel->r_addend);
765
766 roff = irel->r_offset;
767 reladdr = (sec->output_section->vma
768 + sec->output_offset
769 + roff) & -4;
770
771 /* If the branch is in range, no need to do anything. */
772 if ((bfd_signed_vma) (symaddr - reladdr) >= -0x1000000
773 && (bfd_signed_vma) (symaddr - reladdr) <= 0x0FFFFF0)
774 continue;
775
776 /* If the branch and target are in the same section, you've
777 got one honking big section and we can't help you. You'll
778 get an error message later. */
779 if (tsec == sec)
780 continue;
781
782 /* Look for an existing fixup to this address. */
783 for (f = fixups; f ; f = f->next)
784 if (f->tsec == tsec && f->toff == toff)
785 break;
786
787 if (f == NULL)
788 {
789 /* Two alternatives: If it's a branch to a PLT entry, we can
790 make a copy of the FULL_PLT entry. Otherwise, we'll have
791 to use a `brl' insn to get where we're going. */
792
793 int size;
794
795 if (tsec == ia64_info->plt_sec)
796 size = sizeof (plt_full_entry);
797 else
798 {
799#ifdef USE_BRL
800 size = sizeof (oor_brl);
801#else
802 size = sizeof (oor_ip);
803#endif
804 }
805
806 /* Resize the current section to make room for the new branch. */
807 trampoff = (sec->_cooked_size + 15) & -16;
808 contents = (bfd_byte *) bfd_realloc (contents, trampoff + size);
809 if (contents == NULL)
810 goto error_return;
811 sec->_cooked_size = trampoff + size;
812
813 if (tsec == ia64_info->plt_sec)
814 {
815 memcpy (contents + trampoff, plt_full_entry, size);
816
817 /* Hijack the old relocation for use as the PLTOFF reloc. */
818 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
819 R_IA64_PLTOFF22);
820 irel->r_offset = trampoff;
821 }
822 else
823 {
824#ifdef USE_BRL
825 memcpy (contents + trampoff, oor_brl, size);
826 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
827 R_IA64_PCREL60B);
828 irel->r_offset = trampoff + 2;
829#else
830 memcpy (contents + trampoff, oor_ip, size);
831 irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
832 R_IA64_PCREL64I);
833 irel->r_addend -= 16;
834 irel->r_offset = trampoff + 2;
835#endif
836 }
837
838 /* Record the fixup so we don't do it again this section. */
839 f = (struct one_fixup *) bfd_malloc (sizeof (*f));
840 f->next = fixups;
841 f->tsec = tsec;
842 f->toff = toff;
843 f->trampoff = trampoff;
844 fixups = f;
845 }
846 else
847 {
848 /* Nop out the reloc, since we're finalizing things here. */
849 irel->r_info = ELF64_R_INFO (0, R_IA64_NONE);
850 }
851
852 /* Fix up the existing branch to hit the trampoline. Hope like
853 hell this doesn't overflow too. */
854 if (elf64_ia64_install_value (abfd, contents + roff,
855 f->trampoff - (roff & -4),
856 R_IA64_PCREL21B) != bfd_reloc_ok)
857 goto error_return;
858
859 changed_contents = true;
860 changed_relocs = true;
861 }
862
863 /* Clean up and go home. */
864 while (fixups)
865 {
866 struct one_fixup *f = fixups;
867 fixups = fixups->next;
868 free (f);
869 }
870
871 if (changed_relocs)
872 elf_section_data (sec)->relocs = internal_relocs;
873 else if (free_relocs != NULL)
874 free (free_relocs);
875
876 if (changed_contents)
877 elf_section_data (sec)->this_hdr.contents = contents;
878 else if (free_contents != NULL)
879 {
880 if (! link_info->keep_memory)
881 free (free_contents);
882 else
883 {
884 /* Cache the section contents for elf_link_input_bfd. */
885 elf_section_data (sec)->this_hdr.contents = contents;
886 }
887 }
888
889 if (free_extsyms != NULL)
890 {
891 if (! link_info->keep_memory)
892 free (free_extsyms);
893 else
894 {
895 /* Cache the symbols for elf_link_input_bfd. */
896 symtab_hdr->contents = extsyms;
897 }
898 }
899
900 *again = changed_contents || changed_relocs;
901 return true;
902
903 error_return:
904 if (free_relocs != NULL)
905 free (free_relocs);
906 if (free_contents != NULL)
907 free (free_contents);
908 if (free_extsyms != NULL)
909 free (free_extsyms);
910 return false;
911}
912\f
913/* Handle an IA-64 specific section when reading an object file. This
914 is called when elfcode.h finds a section with an unknown type. */
915
916static boolean
917elf64_ia64_section_from_shdr (abfd, hdr, name)
918 bfd *abfd;
919 Elf64_Internal_Shdr *hdr;
920 char *name;
921{
922 asection *newsect;
923
924 /* There ought to be a place to keep ELF backend specific flags, but
925 at the moment there isn't one. We just keep track of the
926 sections by their name, instead. Fortunately, the ABI gives
927 suggested names for all the MIPS specific sections, so we will
928 probably get away with this. */
929 switch (hdr->sh_type)
930 {
931 case SHT_IA_64_UNWIND:
932 if (strcmp (name, ELF_STRING_ia64_unwind) != 0)
933 return false;
934 break;
935
936 case SHT_IA_64_EXT:
937 if (strcmp (name, ELF_STRING_ia64_archext) != 0)
938 return false;
939 break;
940
941 default:
942 return false;
943 }
944
945 if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name))
946 return false;
947 newsect = hdr->bfd_section;
948
949 return true;
950}
951
952/* Convert IA-64 specific section flags to bfd internal section flags. */
953
954/* ??? There is no bfd internal flag equivalent to the SHF_IA_64_NORECOV
955 flag. */
956
957static boolean
958elf64_ia64_section_flags (flags, hdr)
959 flagword *flags;
960 Elf64_Internal_Shdr *hdr;
961{
962 if (hdr->sh_flags & SHF_IA_64_SHORT)
963 *flags |= SEC_SMALL_DATA;
964
965 return true;
966}
967
968/* Set the correct type for an IA-64 ELF section. We do this by the
969 section name, which is a hack, but ought to work. */
970
971static boolean
972elf64_ia64_fake_sections (abfd, hdr, sec)
973 bfd *abfd;
974 Elf64_Internal_Shdr *hdr;
975 asection *sec;
976{
977 register const char *name;
978
979 name = bfd_get_section_name (abfd, sec);
980
981 if (strcmp (name, ELF_STRING_ia64_unwind) == 0)
982 hdr->sh_type = SHT_IA_64_UNWIND;
983 else if (strcmp (name, ELF_STRING_ia64_archext) == 0)
984 hdr->sh_type = SHT_IA_64_EXT;
985 else if (strcmp (name, ".reloc") == 0)
986 /*
987 * This is an ugly, but unfortunately necessary hack that is
988 * needed when producing EFI binaries on IA-64. It tells
989 * elf.c:elf_fake_sections() not to consider ".reloc" as a section
990 * containing ELF relocation info. We need this hack in order to
991 * be able to generate ELF binaries that can be translated into
992 * EFI applications (which are essentially COFF objects). Those
993 * files contain a COFF ".reloc" section inside an ELF64 object,
994 * which would normally cause BFD to segfault because it would
995 * attempt to interpret this section as containing relocation
996 * entries for section "oc". With this hack enabled, ".reloc"
997 * will be treated as a normal data section, which will avoid the
998 * segfault. However, you won't be able to create an ELF64 binary
999 * with a section named "oc" that needs relocations, but that's
1000 * the kind of ugly side-effects you get when detecting section
1001 * types based on their names... In practice, this limitation is
1002 * unlikely to bite.
1003 */
1004 hdr->sh_type = SHT_PROGBITS;
1005
1006 if (sec->flags & SEC_SMALL_DATA)
1007 hdr->sh_flags |= SHF_IA_64_SHORT;
1008
1009 return true;
1010}
1011
1012/* Hook called by the linker routine which adds symbols from an object
1013 file. We use it to put .comm items in .sbss, and not .bss. */
1014
1015static boolean
1016elf64_ia64_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
1017 bfd *abfd;
1018 struct bfd_link_info *info;
1019 const Elf_Internal_Sym *sym;
1020 const char **namep;
1021 flagword *flagsp;
1022 asection **secp;
1023 bfd_vma *valp;
1024{
1025 if (sym->st_shndx == SHN_COMMON
1026 && !info->relocateable
1027 && sym->st_size <= bfd_get_gp_size (abfd))
1028 {
1029 /* Common symbols less than or equal to -G nn bytes are
1030 automatically put into .sbss. */
1031
1032 asection *scomm = bfd_get_section_by_name (abfd, ".scommon");
1033
1034 if (scomm == NULL)
1035 {
1036 scomm = bfd_make_section (abfd, ".scommon");
1037 if (scomm == NULL
1038 || !bfd_set_section_flags (abfd, scomm, (SEC_ALLOC
1039 | SEC_IS_COMMON
1040 | SEC_LINKER_CREATED)))
1041 return false;
1042 }
1043
1044 *secp = scomm;
1045 *valp = sym->st_size;
1046 }
1047
1048 return true;
1049}
1050
1051/* Return the number of additional phdrs we will need. */
1052
1053static int
1054elf64_ia64_additional_program_headers (abfd)
1055 bfd *abfd;
1056{
1057 asection *s;
1058 int ret = 0;
1059
1060 /* See if we need a PT_IA_64_ARCHEXT segment. */
1061 s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_archext);
1062 if (s && (s->flags & SEC_LOAD))
1063 ++ret;
1064
1065 /* See if we need a PT_IA_64_UNWIND segment. */
1066 s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_unwind);
1067 if (s && (s->flags & SEC_LOAD))
1068 ++ret;
1069
1070 return ret;
1071}
1072
1073static boolean
1074elf64_ia64_modify_segment_map (abfd)
1075 bfd *abfd;
1076{
1077 struct elf_segment_map *m, **pm;
1078 asection *s;
1079
1080 /* If we need a PT_IA_64_ARCHEXT segment, it must come before
1081 all PT_LOAD segments. */
1082 s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_archext);
1083 if (s && (s->flags & SEC_LOAD))
1084 {
1085 for (m = elf_tdata (abfd)->segment_map; m != NULL; m = m->next)
1086 if (m->p_type == PT_IA_64_ARCHEXT)
1087 break;
1088 if (m == NULL)
1089 {
1090 m = (struct elf_segment_map *) bfd_zalloc (abfd, sizeof *m);
1091 if (m == NULL)
1092 return false;
1093
1094 m->p_type = PT_IA_64_ARCHEXT;
1095 m->count = 1;
1096 m->sections[0] = s;
1097
1098 /* We want to put it after the PHDR and INTERP segments. */
1099 pm = &elf_tdata (abfd)->segment_map;
1100 while (*pm != NULL
1101 && ((*pm)->p_type == PT_PHDR
1102 || (*pm)->p_type == PT_INTERP))
1103 pm = &(*pm)->next;
1104
1105 m->next = *pm;
1106 *pm = m;
1107 }
1108 }
1109
1110 /* Install the PT_IA_64_UNWIND segment, if needed. */
1111 s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_unwind);
1112 if (s && (s->flags & SEC_LOAD))
1113 {
1114 for (m = elf_tdata (abfd)->segment_map; m != NULL; m = m->next)
1115 if (m->p_type == PT_IA_64_UNWIND)
1116 break;
1117 if (m == NULL)
1118 {
1119 m = (struct elf_segment_map *) bfd_zalloc (abfd, sizeof *m);
1120 if (m == NULL)
1121 return false;
1122
1123 m->p_type = PT_IA_64_UNWIND;
1124 m->count = 1;
1125 m->sections[0] = s;
1126 m->next = NULL;
1127
1128 /* We want to put it last. */
1129 pm = &elf_tdata (abfd)->segment_map;
1130 while (*pm != NULL)
1131 pm = &(*pm)->next;
1132 *pm = m;
1133 }
1134 }
1135
1136 /* Turn on PF_IA_64_NORECOV if needed. This involves traversing all of
1137 the input sections for each output section in the segment and testing
1138 for SHF_IA_64_NORECOV on each. */
1139 for (m = elf_tdata (abfd)->segment_map; m != NULL; m = m->next)
1140 if (m->p_type == PT_LOAD)
1141 {
1142 int i;
1143 for (i = m->count - 1; i >= 0; --i)
1144 {
1145 struct bfd_link_order *order = m->sections[i]->link_order_head;
1146 while (order)
1147 {
1148 if (order->type == bfd_indirect_link_order)
1149 {
1150 asection *is = order->u.indirect.section;
1151 bfd_vma flags = elf_section_data(is)->this_hdr.sh_flags;
1152 if (flags & SHF_IA_64_NORECOV)
1153 {
1154 m->p_flags |= PF_IA_64_NORECOV;
1155 goto found;
1156 }
1157 }
1158 order = order->next;
1159 }
1160 }
1161 found:;
1162 }
1163
1164 return true;
1165}
1166
1167
1168/* According to the Tahoe assembler spec, all labels starting with a
1169 '.' are local. */
1170
1171static boolean
1172elf64_ia64_is_local_label_name (abfd, name)
1173 bfd *abfd;
1174 const char *name;
1175{
1176 return name[0] == '.';
1177}
1178
1179/* Should we do dynamic things to this symbol? */
1180
1181static boolean
1182elf64_ia64_dynamic_symbol_p (h, info)
1183 struct elf_link_hash_entry *h;
1184 struct bfd_link_info *info;
1185{
1186 if (h == NULL)
1187 return false;
1188
1189 while (h->root.type == bfd_link_hash_indirect
1190 || h->root.type == bfd_link_hash_warning)
1191 h = (struct elf_link_hash_entry *) h->root.u.i.link;
1192
1193 if (h->dynindx == -1)
1194 return false;
1195
1196 if (h->root.type == bfd_link_hash_undefweak
1197 || h->root.type == bfd_link_hash_defweak)
1198 return true;
1199
1200 if ((info->shared && !info->symbolic)
1201 || ((h->elf_link_hash_flags
1202 & (ELF_LINK_HASH_DEF_DYNAMIC | ELF_LINK_HASH_REF_REGULAR))
1203 == (ELF_LINK_HASH_DEF_DYNAMIC | ELF_LINK_HASH_REF_REGULAR)))
1204 return true;
1205
1206 return false;
1207}
1208\f
1209static boolean
1210elf64_ia64_local_hash_table_init (ht, abfd, new)
1211 struct elf64_ia64_local_hash_table *ht;
1212 bfd *abfd;
1213 new_hash_entry_func new;
1214{
1215 memset (ht, 0, sizeof(*ht));
1216 return bfd_hash_table_init (&ht->root, new);
1217}
1218
1219static struct bfd_hash_entry*
1220elf64_ia64_new_loc_hash_entry (entry, table, string)
1221 struct bfd_hash_entry *entry;
1222 struct bfd_hash_table *table;
1223 const char *string;
1224{
1225 struct elf64_ia64_local_hash_entry *ret;
1226 ret = (struct elf64_ia64_local_hash_entry *) entry;
1227
1228 /* Allocate the structure if it has not already been allocated by a
1229 subclass. */
1230 if (!ret)
1231 ret = bfd_hash_allocate (table, sizeof (*ret));
1232
1233 if (!ret)
1234 return 0;
1235
1236 /* Initialize our local data. All zeros, and definitely easier
1237 than setting a handful of bit fields. */
1238 memset (ret, 0, sizeof(*ret));
1239
1240 /* Call the allocation method of the superclass. */
1241 ret = ((struct elf64_ia64_local_hash_entry *)
1242 bfd_hash_newfunc ((struct bfd_hash_entry *) ret, table, string));
1243
1244 return (struct bfd_hash_entry *) ret;
1245}
1246
1247static struct bfd_hash_entry*
1248elf64_ia64_new_elf_hash_entry (entry, table, string)
1249 struct bfd_hash_entry *entry;
1250 struct bfd_hash_table *table;
1251 const char *string;
1252{
1253 struct elf64_ia64_link_hash_entry *ret;
1254 ret = (struct elf64_ia64_link_hash_entry *) entry;
1255
1256 /* Allocate the structure if it has not already been allocated by a
1257 subclass. */
1258 if (!ret)
1259 ret = bfd_hash_allocate (table, sizeof (*ret));
1260
1261 if (!ret)
1262 return 0;
1263
1264 /* Initialize our local data. All zeros, and definitely easier
1265 than setting a handful of bit fields. */
1266 memset (ret, 0, sizeof(*ret));
1267
1268 /* Call the allocation method of the superclass. */
1269 ret = ((struct elf64_ia64_link_hash_entry *)
1270 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
1271 table, string));
1272
1273 return (struct bfd_hash_entry *) ret;
1274}
1275
1276static void
1277elf64_ia64_hash_copy_indirect (xdir, xind)
1278 struct elf_link_hash_entry *xdir, *xind;
1279{
1280 struct elf64_ia64_link_hash_entry *dir, *ind;
1281
1282 dir = (struct elf64_ia64_link_hash_entry *)xdir;
1283 ind = (struct elf64_ia64_link_hash_entry *)xind;
1284
1285 /* Copy down any references that we may have already seen to the
1286 symbol which just became indirect. */
1287
1288 dir->root.elf_link_hash_flags |=
1289 (ind->root.elf_link_hash_flags
1290 & (ELF_LINK_HASH_REF_DYNAMIC
1291 | ELF_LINK_HASH_REF_REGULAR
1292 | ELF_LINK_HASH_REF_REGULAR_NONWEAK));
1293
1294 /* Copy over the got and plt data. This would have been done
1295 by check_relocs. */
1296
1297 if (dir->info == NULL)
1298 {
1299 struct elf64_ia64_dyn_sym_info *dyn_i;
1300
1301 dir->info = dyn_i = ind->info;
1302 ind->info = NULL;
1303
1304 /* Fix up the dyn_sym_info pointers to the global symbol. */
1305 for (; dyn_i; dyn_i = dyn_i->next)
1306 dyn_i->h = &dir->root;
1307 }
1308 BFD_ASSERT (ind->info == NULL);
1309
1310 /* Copy over the dynindx. */
1311
1312 if (dir->root.dynindx == -1)
1313 {
1314 dir->root.dynindx = ind->root.dynindx;
1315 dir->root.dynstr_index = ind->root.dynstr_index;
1316 ind->root.dynindx = -1;
1317 ind->root.dynstr_index = 0;
1318 }
1319 BFD_ASSERT (ind->root.dynindx == -1);
1320}
1321
1322static void
1323elf64_ia64_hash_hide_symbol (info, xh)
1324 struct bfd_link_info *info ATTRIBUTE_UNUSED;
1325 struct elf_link_hash_entry *xh;
1326{
1327 struct elf64_ia64_link_hash_entry *h;
1328 struct elf64_ia64_dyn_sym_info *dyn_i;
1329
1330 h = (struct elf64_ia64_link_hash_entry *)xh;
1331
1332 h->root.elf_link_hash_flags &= ~ELF_LINK_HASH_NEEDS_PLT;
1333 h->root.dynindx = -1;
1334
1335 for (dyn_i = h->info; dyn_i; dyn_i = dyn_i->next)
1336 dyn_i->want_plt2 = 0;
1337}
1338
1339/* Create the derived linker hash table. The IA-64 ELF port uses this
1340 derived hash table to keep information specific to the IA-64 ElF
1341 linker (without using static variables). */
1342
1343static struct bfd_link_hash_table*
1344elf64_ia64_hash_table_create (abfd)
1345 bfd *abfd;
1346{
1347 struct elf64_ia64_link_hash_table *ret;
1348
1349 ret = bfd_alloc (abfd, sizeof (*ret));
1350 if (!ret)
1351 return 0;
1352 if (!_bfd_elf_link_hash_table_init (&ret->root, abfd,
1353 elf64_ia64_new_elf_hash_entry))
1354 {
1355 bfd_release (abfd, ret);
1356 return 0;
1357 }
1358
1359 if (!elf64_ia64_local_hash_table_init (&ret->loc_hash_table, abfd,
1360 elf64_ia64_new_loc_hash_entry))
1361 return 0;
1362 return &ret->root.root;
1363}
1364
1365/* Look up an entry in a Alpha ELF linker hash table. */
1366
1367static INLINE struct elf64_ia64_local_hash_entry *
1368elf64_ia64_local_hash_lookup(table, string, create, copy)
1369 struct elf64_ia64_local_hash_table *table;
1370 const char *string;
1371 boolean create, copy;
1372{
1373 return ((struct elf64_ia64_local_hash_entry *)
1374 bfd_hash_lookup (&table->root, string, create, copy));
1375}
1376
1377/* Traverse both local and global hash tables. */
1378
1379struct elf64_ia64_dyn_sym_traverse_data
1380{
1381 boolean (*func) PARAMS ((struct elf64_ia64_dyn_sym_info *, PTR));
1382 PTR data;
1383};
1384
1385static boolean
1386elf64_ia64_global_dyn_sym_thunk (xentry, xdata)
1387 struct bfd_hash_entry *xentry;
1388 PTR xdata;
1389{
1390 struct elf64_ia64_link_hash_entry *entry
1391 = (struct elf64_ia64_link_hash_entry *) xentry;
1392 struct elf64_ia64_dyn_sym_traverse_data *data
1393 = (struct elf64_ia64_dyn_sym_traverse_data *) xdata;
1394 struct elf64_ia64_dyn_sym_info *dyn_i;
1395
1396 for (dyn_i = entry->info; dyn_i; dyn_i = dyn_i->next)
1397 if (! (*data->func) (dyn_i, data->data))
1398 return false;
1399 return true;
1400}
1401
1402static boolean
1403elf64_ia64_local_dyn_sym_thunk (xentry, xdata)
1404 struct bfd_hash_entry *xentry;
1405 PTR xdata;
1406{
1407 struct elf64_ia64_local_hash_entry *entry
1408 = (struct elf64_ia64_local_hash_entry *) xentry;
1409 struct elf64_ia64_dyn_sym_traverse_data *data
1410 = (struct elf64_ia64_dyn_sym_traverse_data *) xdata;
1411 struct elf64_ia64_dyn_sym_info *dyn_i;
1412
1413 for (dyn_i = entry->info; dyn_i; dyn_i = dyn_i->next)
1414 if (! (*data->func) (dyn_i, data->data))
1415 return false;
1416 return true;
1417}
1418
1419static void
1420elf64_ia64_dyn_sym_traverse (ia64_info, func, data)
1421 struct elf64_ia64_link_hash_table *ia64_info;
1422 boolean (*func) PARAMS ((struct elf64_ia64_dyn_sym_info *, PTR));
1423 PTR data;
1424{
1425 struct elf64_ia64_dyn_sym_traverse_data xdata;
1426
1427 xdata.func = func;
1428 xdata.data = data;
1429
1430 elf_link_hash_traverse (&ia64_info->root,
1431 elf64_ia64_global_dyn_sym_thunk, &xdata);
1432 bfd_hash_traverse (&ia64_info->loc_hash_table.root,
1433 elf64_ia64_local_dyn_sym_thunk, &xdata);
1434}
1435\f
1436static boolean
1437elf64_ia64_create_dynamic_sections (abfd, info)
1438 bfd *abfd;
1439 struct bfd_link_info *info;
1440{
1441 struct elf64_ia64_link_hash_table *ia64_info;
1442 struct elf_link_hash_entry *h;
1443 asection *s;
1444
1445 if (! _bfd_elf_create_dynamic_sections (abfd, info))
1446 return false;
1447
1448 ia64_info = elf64_ia64_hash_table (info);
1449
1450 ia64_info->plt_sec = bfd_get_section_by_name (abfd, ".plt");
1451 ia64_info->got_sec = bfd_get_section_by_name (abfd, ".got");
1452
1453 {
1454 flagword flags = bfd_get_section_flags (abfd, ia64_info->got_sec);
1455 bfd_set_section_flags (abfd, ia64_info->got_sec, SEC_SMALL_DATA | flags);
1456 }
1457
1458 if (!get_pltoff (abfd, info, ia64_info))
1459 return false;
1460
1461 s = bfd_make_section(abfd, ".rela.IA_64.pltoff");
1462 if (s == NULL
1463 || !bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
1464 | SEC_HAS_CONTENTS
1465 | SEC_IN_MEMORY
1466 | SEC_LINKER_CREATED
1467 | SEC_READONLY))
1468 || !bfd_set_section_alignment (abfd, s, 3))
1469 return false;
1470 ia64_info->rel_pltoff_sec = s;
1471
1472 s = bfd_make_section(abfd, ".rela.got");
1473 if (s == NULL
1474 || !bfd_set_section_flags (abfd, s, (SEC_ALLOC | SEC_LOAD
1475 | SEC_HAS_CONTENTS
1476 | SEC_IN_MEMORY
1477 | SEC_LINKER_CREATED
1478 | SEC_READONLY))
1479 || !bfd_set_section_alignment (abfd, s, 3))
1480 return false;
1481 ia64_info->rel_got_sec = s;
1482
1483 return true;
1484}
1485
1486/* Find and/or create a descriptor for dynamic symbol info. This will
1487 vary based on global or local symbol, and the addend to the reloc. */
1488
1489static struct elf64_ia64_dyn_sym_info *
1490get_dyn_sym_info (ia64_info, h, abfd, rel, create)
1491 struct elf64_ia64_link_hash_table *ia64_info;
1492 struct elf_link_hash_entry *h;
1493 bfd *abfd;
1494 const Elf_Internal_Rela *rel;
1495 boolean create;
1496{
1497 struct elf64_ia64_dyn_sym_info **pp;
1498 struct elf64_ia64_dyn_sym_info *dyn_i;
1499 bfd_vma addend = rel ? rel->r_addend : 0;
1500
1501 if (h)
1502 pp = &((struct elf64_ia64_link_hash_entry *)h)->info;
1503 else
1504 {
1505 struct elf64_ia64_local_hash_entry *loc_h;
1506 char *addr_name;
1507 size_t len;
1508
1509 /* Construct a string for use in the elf64_ia64_local_hash_table.
1510 The name describes what was once anonymous memory. */
1511
1512 len = sizeof(void*)*2 + 1 + sizeof(bfd_vma)*4 + 1 + 1;
1513 len += 10; /* %p slop */
1514
1515 addr_name = alloca (len);
1516 sprintf (addr_name, "%p:%lx", abfd, ELF64_R_SYM (rel->r_info));
1517
1518 /* Collect the canonical entry data for this address. */
1519 loc_h = elf64_ia64_local_hash_lookup (&ia64_info->loc_hash_table,
1520 addr_name, create, create);
1521 BFD_ASSERT (loc_h);
1522
1523 pp = &loc_h->info;
1524 }
1525
1526 for (dyn_i = *pp; dyn_i && dyn_i->addend != addend; dyn_i = *pp)
1527 pp = &dyn_i->next;
1528
1529 if (dyn_i == NULL && create)
1530 {
1531 dyn_i = (struct elf64_ia64_dyn_sym_info *)
1532 bfd_zalloc (abfd, sizeof *dyn_i);
1533 *pp = dyn_i;
1534 dyn_i->addend = addend;
1535 }
1536
1537 return dyn_i;
1538}
1539
1540static asection *
1541get_got (abfd, info, ia64_info)
1542 bfd *abfd;
1543 struct bfd_link_info *info;
1544 struct elf64_ia64_link_hash_table *ia64_info;
1545{
1546 asection *got, *srel;
1547 bfd *dynobj;
1548
1549 got = ia64_info->got_sec;
1550 if (!got)
1551 {
1552 flagword flags;
1553
1554 dynobj = ia64_info->root.dynobj;
1555 if (!dynobj)
1556 ia64_info->root.dynobj = dynobj = abfd;
1557 if (!_bfd_elf_create_got_section (dynobj, info))
1558 return 0;
1559
1560 got = bfd_get_section_by_name (dynobj, ".got");
1561 BFD_ASSERT (got);
1562 ia64_info->got_sec = got;
1563
1564 flags = bfd_get_section_flags (abfd, got);
1565 bfd_set_section_flags (abfd, got, SEC_SMALL_DATA | flags);
1566 }
1567
1568 return got;
1569}
1570
1571/* Create function descriptor section (.opd). This section is called .opd
1572 because it contains "official prodecure descriptors". The "official"
1573 refers to the fact that these descriptors are used when taking the address
1574 of a procedure, thus ensuring a unique address for each procedure. */
1575
1576static asection *
1577get_fptr (abfd, info, ia64_info)
1578 bfd *abfd;
1579 struct bfd_link_info *info;
1580 struct elf64_ia64_link_hash_table *ia64_info;
1581{
1582 asection *fptr;
1583 bfd *dynobj;
1584
1585 fptr = ia64_info->fptr_sec;
1586 if (!fptr)
1587 {
1588 dynobj = ia64_info->root.dynobj;
1589 if (!dynobj)
1590 ia64_info->root.dynobj = dynobj = abfd;
1591
1592 fptr = bfd_make_section (dynobj, ".opd");
1593 if (!fptr
1594 || !bfd_set_section_flags (dynobj, fptr,
1595 (SEC_ALLOC
1596 | SEC_LOAD
1597 | SEC_HAS_CONTENTS
1598 | SEC_IN_MEMORY
1599 | SEC_READONLY
1600 | SEC_LINKER_CREATED))
1601 || !bfd_set_section_alignment (abfd, fptr, 4))
1602 {
1603 BFD_ASSERT (0);
1604 return NULL;
1605 }
1606
1607 ia64_info->fptr_sec = fptr;
1608 }
1609
1610 return fptr;
1611}
1612
1613static asection *
1614get_pltoff (abfd, info, ia64_info)
1615 bfd *abfd;
1616 struct bfd_link_info *info;
1617 struct elf64_ia64_link_hash_table *ia64_info;
1618{
1619 asection *pltoff;
1620 bfd *dynobj;
1621
1622 pltoff = ia64_info->pltoff_sec;
1623 if (!pltoff)
1624 {
1625 dynobj = ia64_info->root.dynobj;
1626 if (!dynobj)
1627 ia64_info->root.dynobj = dynobj = abfd;
1628
1629 pltoff = bfd_make_section (dynobj, ELF_STRING_ia64_pltoff);
1630 if (!pltoff
1631 || !bfd_set_section_flags (dynobj, pltoff,
1632 (SEC_ALLOC
1633 | SEC_LOAD
1634 | SEC_HAS_CONTENTS
1635 | SEC_IN_MEMORY
1636 | SEC_SMALL_DATA
1637 | SEC_LINKER_CREATED))
1638 || !bfd_set_section_alignment (abfd, pltoff, 4))
1639 {
1640 BFD_ASSERT (0);
1641 return NULL;
1642 }
1643
1644 ia64_info->pltoff_sec = pltoff;
1645 }
1646
1647 return pltoff;
1648}
1649
1650static asection *
1651get_reloc_section (abfd, ia64_info, sec, create)
1652 bfd *abfd;
1653 struct elf64_ia64_link_hash_table *ia64_info;
1654 asection *sec;
1655 boolean create;
1656{
1657 const char *srel_name;
1658 asection *srel;
1659 bfd *dynobj;
1660
1661 srel_name = (bfd_elf_string_from_elf_section
1662 (abfd, elf_elfheader(abfd)->e_shstrndx,
1663 elf_section_data(sec)->rel_hdr.sh_name));
1664 if (srel_name == NULL)
1665 return NULL;
1666
1667 BFD_ASSERT ((strncmp (srel_name, ".rela", 5) == 0
1668 && strcmp (bfd_get_section_name (abfd, sec),
1669 srel_name+5) == 0)
1670 || (strncmp (srel_name, ".rel", 4) == 0
1671 && strcmp (bfd_get_section_name (abfd, sec),
1672 srel_name+4) == 0));
1673
1674 dynobj = ia64_info->root.dynobj;
1675 if (!dynobj)
1676 ia64_info->root.dynobj = dynobj = abfd;
1677
1678 srel = bfd_get_section_by_name (dynobj, srel_name);
1679 if (srel == NULL && create)
1680 {
1681 srel = bfd_make_section (dynobj, srel_name);
1682 if (srel == NULL
1683 || !bfd_set_section_flags (dynobj, srel,
1684 (SEC_ALLOC
1685 | SEC_LOAD
1686 | SEC_HAS_CONTENTS
1687 | SEC_IN_MEMORY
1688 | SEC_LINKER_CREATED
1689 | SEC_READONLY))
1690 || !bfd_set_section_alignment (dynobj, srel, 3))
1691 return NULL;
1692 }
1693
1694 return srel;
1695}
1696
1697static boolean
1698count_dyn_reloc (abfd, dyn_i, srel, type)
1699 bfd *abfd;
1700 struct elf64_ia64_dyn_sym_info *dyn_i;
1701 asection *srel;
1702 int type;
1703{
1704 struct elf64_ia64_dyn_reloc_entry *rent;
1705
1706 for (rent = dyn_i->reloc_entries; rent; rent = rent->next)
1707 if (rent->srel == srel && rent->type == type)
1708 break;
1709
1710 if (!rent)
1711 {
1712 rent = (struct elf64_ia64_dyn_reloc_entry *)
1713 bfd_alloc (abfd, sizeof (*rent));
1714 if (!rent)
1715 return false;
1716
1717 rent->next = dyn_i->reloc_entries;
1718 rent->srel = srel;
1719 rent->type = type;
1720 rent->count = 0;
1721 dyn_i->reloc_entries = rent;
1722 }
1723 rent->count++;
1724
1725 return true;
1726}
1727
1728static boolean
1729elf64_ia64_check_relocs (abfd, info, sec, relocs)
1730 bfd *abfd;
1731 struct bfd_link_info *info;
1732 asection *sec;
1733 const Elf_Internal_Rela *relocs;
1734{
1735 struct elf64_ia64_link_hash_table *ia64_info;
1736 const Elf_Internal_Rela *relend;
1737 Elf_Internal_Shdr *symtab_hdr;
1738 const Elf_Internal_Rela *rel;
1739 asection *got, *fptr, *srel;
1740
1741 if (info->relocateable)
1742 return true;
1743
1744 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
1745 ia64_info = elf64_ia64_hash_table (info);
1746
1747 got = fptr = srel = NULL;
1748
1749 relend = relocs + sec->reloc_count;
1750 for (rel = relocs; rel < relend; ++rel)
1751 {
1752 enum {
1753 NEED_GOT = 1,
1754 NEED_FPTR = 2,
1755 NEED_PLTOFF = 4,
1756 NEED_MIN_PLT = 8,
1757 NEED_FULL_PLT = 16,
1758 NEED_DYNREL = 32,
1759 NEED_LTOFF_FPTR = 64,
1760 };
1761
1762 struct elf_link_hash_entry *h = NULL;
1763 unsigned long r_symndx = ELF64_R_SYM (rel->r_info);
1764 struct elf64_ia64_dyn_sym_info *dyn_i;
1765 int need_entry;
1766 boolean maybe_dynamic;
1767 int dynrel_type;
1768
1769 if (r_symndx >= symtab_hdr->sh_info)
1770 {
1771 /* We're dealing with a global symbol -- find its hash entry
1772 and mark it as being referenced. */
1773 long indx = r_symndx - symtab_hdr->sh_info;
1774 h = elf_sym_hashes (abfd)[indx];
1775 while (h->root.type == bfd_link_hash_indirect
1776 || h->root.type == bfd_link_hash_warning)
1777 h = (struct elf_link_hash_entry *) h->root.u.i.link;
1778
1779 h->elf_link_hash_flags |= ELF_LINK_HASH_REF_REGULAR;
1780 }
1781
1782 /* We can only get preliminary data on whether a symbol is
1783 locally or externally defined, as not all of the input files
1784 have yet been processed. Do something with what we know, as
1785 this may help reduce memory usage and processing time later. */
1786 maybe_dynamic = false;
1787 if (h && ((info->shared && ! info->symbolic)
1788 || ! (h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR)
1789 || h->root.type == bfd_link_hash_defweak))
1790 maybe_dynamic = true;
1791
1792 need_entry = 0;
1793 switch (ELF64_R_TYPE (rel->r_info))
1794 {
1795 case R_IA64_TPREL22:
1796 case R_IA64_TPREL64MSB:
1797 case R_IA64_TPREL64LSB:
1798 case R_IA64_LTOFF_TP22:
1799 return false;
1800
1801 case R_IA64_LTOFF_FPTR22:
1802 case R_IA64_LTOFF_FPTR64I:
1803 case R_IA64_LTOFF_FPTR64MSB:
1804 case R_IA64_LTOFF_FPTR64LSB:
1805 need_entry = NEED_FPTR | NEED_GOT | NEED_LTOFF_FPTR;
1806 break;
1807
1808 case R_IA64_FPTR64I:
1809 case R_IA64_FPTR32MSB:
1810 case R_IA64_FPTR32LSB:
1811 case R_IA64_FPTR64MSB:
1812 case R_IA64_FPTR64LSB:
1813 if (info->shared || h)
1814 need_entry = NEED_FPTR | NEED_DYNREL;
1815 else
1816 need_entry = NEED_FPTR;
1817 dynrel_type = R_IA64_FPTR64LSB;
1818 break;
1819
1820 case R_IA64_LTOFF22:
1821 case R_IA64_LTOFF22X:
1822 case R_IA64_LTOFF64I:
1823 need_entry = NEED_GOT;
1824 break;
1825
1826 case R_IA64_PLTOFF22:
1827 case R_IA64_PLTOFF64I:
1828 case R_IA64_PLTOFF64MSB:
1829 case R_IA64_PLTOFF64LSB:
1830 need_entry = NEED_PLTOFF;
1831 if (h)
1832 {
1833 if (maybe_dynamic)
1834 need_entry |= NEED_MIN_PLT;
1835 }
1836 else
1837 {
1838 (*info->callbacks->warning)
1839 (info, _("@pltoff reloc against local symbol"), 0,
1840 abfd, 0, 0);
1841 }
1842 break;
1843
1844 case R_IA64_PCREL21B:
1845 case R_IA64_PCREL60B:
1846 /* Depending on where this symbol is defined, we may or may not
1847 need a full plt entry. Only skip if we know we'll not need
1848 the entry -- static or symbolic, and the symbol definition
1849 has already been seen. */
1850 if (maybe_dynamic && rel->r_addend == 0)
1851 need_entry = NEED_FULL_PLT;
1852 break;
1853
1854 case R_IA64_IMM14:
1855 case R_IA64_IMM22:
1856 case R_IA64_IMM64:
1857 case R_IA64_DIR32MSB:
1858 case R_IA64_DIR32LSB:
1859 case R_IA64_DIR64MSB:
1860 case R_IA64_DIR64LSB:
1861 /* Shared objects will always need at least a REL relocation. */
1862 if (info->shared || maybe_dynamic)
1863 need_entry = NEED_DYNREL;
1864 dynrel_type = R_IA64_DIR64LSB;
1865 break;
1866
1867 case R_IA64_PCREL22:
1868 case R_IA64_PCREL64I:
1869 case R_IA64_PCREL32MSB:
1870 case R_IA64_PCREL32LSB:
1871 case R_IA64_PCREL64MSB:
1872 case R_IA64_PCREL64LSB:
1873 if (maybe_dynamic)
1874 need_entry = NEED_DYNREL;
1875 dynrel_type = R_IA64_PCREL64LSB;
1876 break;
1877 }
1878
1879 if (!need_entry)
1880 continue;
1881
1882 if ((need_entry & NEED_FPTR) != 0
1883 && rel->r_addend)
1884 {
1885 (*info->callbacks->warning)
1886 (info, _("non-zero addend in @fptr reloc"), 0,
1887 abfd, 0, 0);
1888 }
1889
1890 dyn_i = get_dyn_sym_info (ia64_info, h, abfd, rel, true);
1891
1892 /* Record whether or not this is a local symbol. */
1893 dyn_i->h = h;
1894
1895 /* Create what's needed. */
1896 if (need_entry & NEED_GOT)
1897 {
1898 if (!got)
1899 {
1900 got = get_got (abfd, info, ia64_info);
1901 if (!got)
1902 return false;
1903 }
1904 dyn_i->want_got = 1;
1905 }
1906 if (need_entry & NEED_FPTR)
1907 {
1908 if (!fptr)
1909 {
1910 fptr = get_fptr (abfd, info, ia64_info);
1911 if (!fptr)
1912 return false;
1913 }
1914
1915 /* FPTRs for shared libraries are allocated by the dynamic
1916 linker. Make sure this local symbol will appear in the
1917 dynamic symbol table. */
1918 if (!h && (info->shared
1919 ))
1920 {
1921 if (! (_bfd_elf64_link_record_local_dynamic_symbol
1922 (info, abfd, r_symndx)))
1923 return false;
1924 }
1925
1926 dyn_i->want_fptr = 1;
1927 }
1928 if (need_entry & NEED_LTOFF_FPTR)
1929 dyn_i->want_ltoff_fptr = 1;
1930 if (need_entry & (NEED_MIN_PLT | NEED_FULL_PLT))
1931 {
1932 if (!ia64_info->root.dynobj)
1933 ia64_info->root.dynobj = abfd;
1934 h->elf_link_hash_flags |= ELF_LINK_HASH_NEEDS_PLT;
1935 dyn_i->want_plt = 1;
1936 }
1937 if (need_entry & NEED_FULL_PLT)
1938 dyn_i->want_plt2 = 1;
1939 if (need_entry & NEED_PLTOFF)
1940 dyn_i->want_pltoff = 1;
1941 if ((need_entry & NEED_DYNREL) && (sec->flags & SEC_ALLOC))
1942 {
1943 if (!srel)
1944 {
1945 srel = get_reloc_section (abfd, ia64_info, sec, true);
1946 if (!srel)
1947 return false;
1948 }
1949 if (!count_dyn_reloc (abfd, dyn_i, srel, dynrel_type))
1950 return false;
1951 }
1952 }
1953
1954 return true;
1955}
1956
1957struct elf64_ia64_allocate_data
1958{
1959 struct bfd_link_info *info;
1960 bfd_size_type ofs;
1961};
1962
1963/* For cleanliness, and potentially faster dynamic loading, allocate
1964 external GOT entries first. */
1965
1966static boolean
1967allocate_global_data_got (dyn_i, data)
1968 struct elf64_ia64_dyn_sym_info *dyn_i;
1969 PTR data;
1970{
1971 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
1972
1973 if (dyn_i->want_got
1974 && ! dyn_i->want_fptr
1975 && (elf64_ia64_dynamic_symbol_p (dyn_i->h, x->info)
1976 ))
1977 {
1978 dyn_i->got_offset = x->ofs;
1979 x->ofs += 8;
1980 }
1981 return true;
1982}
1983
1984/* Next, allocate all the GOT entries used by LTOFF_FPTR relocs. */
1985
1986static boolean
1987allocate_global_fptr_got (dyn_i, data)
1988 struct elf64_ia64_dyn_sym_info *dyn_i;
1989 PTR data;
1990{
1991 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
1992
1993 if (dyn_i->want_got
1994 && dyn_i->want_fptr
1995 && (elf64_ia64_dynamic_symbol_p (dyn_i->h, x->info)
1996 ))
1997 {
1998 dyn_i->got_offset = x->ofs;
1999 x->ofs += 8;
2000 }
2001 return true;
2002}
2003
2004/* Lastly, allocate all the GOT entries for local data. */
2005
2006static boolean
2007allocate_local_got (dyn_i, data)
2008 struct elf64_ia64_dyn_sym_info *dyn_i;
2009 PTR data;
2010{
2011 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2012
2013 if (dyn_i->want_got
2014 && ! (elf64_ia64_dynamic_symbol_p (dyn_i->h, x->info)
2015 ))
2016 {
2017 dyn_i->got_offset = x->ofs;
2018 x->ofs += 8;
2019 }
2020 return true;
2021}
2022
2023/* Search for the index of a global symbol in it's defining object file. */
2024
2025static unsigned long
2026global_sym_index (h)
2027 struct elf_link_hash_entry *h;
2028{
2029 struct elf_link_hash_entry **p;
2030 bfd *obj;
2031
2032 BFD_ASSERT (h->root.type == bfd_link_hash_defined
2033 || h->root.type == bfd_link_hash_defweak);
2034
2035 obj = h->root.u.def.section->owner;
2036 for (p = elf_sym_hashes (obj); *p != h; ++p)
2037 continue;
2038
2039 return p - elf_sym_hashes (obj) + elf_tdata (obj)->symtab_hdr.sh_info;
2040}
2041
2042/* Allocate function descriptors. We can do these for every function
2043 in a main executable that is not exported. */
2044
2045static boolean
2046allocate_fptr (dyn_i, data)
2047 struct elf64_ia64_dyn_sym_info *dyn_i;
2048 PTR data;
2049{
2050 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2051
2052 if (dyn_i->want_fptr)
2053 {
2054 struct elf_link_hash_entry *h = dyn_i->h;
2055
2056 if (h)
2057 while (h->root.type == bfd_link_hash_indirect
2058 || h->root.type == bfd_link_hash_warning)
2059 h = (struct elf_link_hash_entry *) h->root.u.i.link;
2060
2061 if (x->info->shared
2062 )
2063 {
2064 if (h && h->dynindx == -1)
2065 {
2066 BFD_ASSERT ((h->root.type == bfd_link_hash_defined)
2067 || (h->root.type == bfd_link_hash_defweak));
2068
2069 if (!_bfd_elf64_link_record_local_dynamic_symbol
2070 (x->info, h->root.u.def.section->owner,
2071 global_sym_index (h)))
2072 return false;
2073 }
2074
2075 dyn_i->want_fptr = 0;
2076 }
2077 else if (h == NULL || h->dynindx == -1)
2078 {
2079 dyn_i->fptr_offset = x->ofs;
2080 x->ofs += 16;
2081 }
2082 else
2083 dyn_i->want_fptr = 0;
2084 }
2085 return true;
2086}
2087
2088/* Allocate all the minimal PLT entries. */
2089
2090static boolean
2091allocate_plt_entries (dyn_i, data)
2092 struct elf64_ia64_dyn_sym_info *dyn_i;
2093 PTR data;
2094{
2095 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2096
2097 if (dyn_i->want_plt)
2098 {
2099 struct elf_link_hash_entry *h = dyn_i->h;
2100
2101 if (h)
2102 while (h->root.type == bfd_link_hash_indirect
2103 || h->root.type == bfd_link_hash_warning)
2104 h = (struct elf_link_hash_entry *) h->root.u.i.link;
2105
2106 /* ??? Versioned symbols seem to lose ELF_LINK_HASH_NEEDS_PLT. */
2107 if (elf64_ia64_dynamic_symbol_p (h, x->info))
2108 {
2109 bfd_size_type offset = x->ofs;
2110 if (offset == 0)
2111 offset = PLT_HEADER_SIZE;
2112 dyn_i->plt_offset = offset;
2113 x->ofs = offset + PLT_MIN_ENTRY_SIZE;
2114
2115 dyn_i->want_pltoff = 1;
2116 }
2117 else
2118 {
2119 dyn_i->want_plt = 0;
2120 dyn_i->want_plt2 = 0;
2121 }
2122 }
2123 return true;
2124}
2125
2126/* Allocate all the full PLT entries. */
2127
2128static boolean
2129allocate_plt2_entries (dyn_i, data)
2130 struct elf64_ia64_dyn_sym_info *dyn_i;
2131 PTR data;
2132{
2133 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2134
2135 if (dyn_i->want_plt2)
2136 {
2137 struct elf_link_hash_entry *h = dyn_i->h;
2138 bfd_size_type ofs = x->ofs;
2139
2140 dyn_i->plt2_offset = ofs;
2141 x->ofs = ofs + PLT_FULL_ENTRY_SIZE;
2142
2143 while (h->root.type == bfd_link_hash_indirect
2144 || h->root.type == bfd_link_hash_warning)
2145 h = (struct elf_link_hash_entry *) h->root.u.i.link;
2146 dyn_i->h->plt.offset = ofs;
2147 }
2148 return true;
2149}
2150
2151/* Allocate all the PLTOFF entries requested by relocations and
2152 plt entries. We can't share space with allocated FPTR entries,
2153 because the latter are not necessarily addressable by the GP.
2154 ??? Relaxation might be able to determine that they are. */
2155
2156static boolean
2157allocate_pltoff_entries (dyn_i, data)
2158 struct elf64_ia64_dyn_sym_info *dyn_i;
2159 PTR data;
2160{
2161 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2162
2163 if (dyn_i->want_pltoff)
2164 {
2165 dyn_i->pltoff_offset = x->ofs;
2166 x->ofs += 16;
2167 }
2168 return true;
2169}
2170
2171/* Allocate dynamic relocations for those symbols that turned out
2172 to be dynamic. */
2173
2174static boolean
2175allocate_dynrel_entries (dyn_i, data)
2176 struct elf64_ia64_dyn_sym_info *dyn_i;
2177 PTR data;
2178{
2179 struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2180 struct elf64_ia64_link_hash_table *ia64_info;
2181 struct elf64_ia64_dyn_reloc_entry *rent;
2182 boolean dynamic_symbol, shared;
2183
2184 ia64_info = elf64_ia64_hash_table (x->info);
2185 dynamic_symbol = elf64_ia64_dynamic_symbol_p (dyn_i->h, x->info);
2186 shared = x->info->shared;
2187
2188 /* Take care of the normal data relocations. */
2189
2190 for (rent = dyn_i->reloc_entries; rent; rent = rent->next)
2191 {
2192 switch (rent->type)
2193 {
2194 case R_IA64_FPTR64LSB:
2195 /* Allocate one iff !want_fptr, which by this point will
2196 be true only if we're actually allocating one statically
2197 in the main executable. */
2198 if (dyn_i->want_fptr)
2199 continue;
2200 break;
2201 case R_IA64_PCREL64LSB:
2202 if (!dynamic_symbol
2203 )
2204 continue;
2205 break;
2206 case R_IA64_DIR64LSB:
2207 if (!dynamic_symbol
2208 && !shared)
2209 continue;
2210 break;
2211 }
2212 rent->srel->_raw_size += sizeof (Elf64_External_Rela) * rent->count;
2213 }
2214
2215 /* Take care of the GOT and PLT relocations. */
2216
2217 if (((dynamic_symbol
2218 || shared)
2219 && dyn_i->want_got)
2220 || (dyn_i->want_ltoff_fptr && dyn_i->h && dyn_i->h->dynindx != -1))
2221 ia64_info->rel_got_sec->_raw_size += sizeof (Elf64_External_Rela);
2222
2223 if (dyn_i->want_pltoff)
2224 {
2225 bfd_size_type t = 0;
2226
2227 /* Dynamic symbols get one IPLT relocation. Local symbols in
2228 shared libraries get two REL relocations. Local symbols in
2229 main applications get nothing. */
2230 if (dynamic_symbol)
2231 t = sizeof (Elf64_External_Rela);
2232 else if (shared
2233 )
2234 t = 2 * sizeof (Elf64_External_Rela);
2235
2236 ia64_info->rel_pltoff_sec->_raw_size += t;
2237 }
2238
2239 return true;
2240}
2241
2242static boolean
2243elf64_ia64_adjust_dynamic_symbol (info, h)
2244 struct bfd_link_info *info;
2245 struct elf_link_hash_entry *h;
2246{
2247 /* ??? Undefined symbols with PLT entries should be re-defined
2248 to be the PLT entry. */
2249
2250 /* If this is a weak symbol, and there is a real definition, the
2251 processor independent code will have arranged for us to see the
2252 real definition first, and we can just use the same value. */
2253 if (h->weakdef != NULL)
2254 {
2255 BFD_ASSERT (h->weakdef->root.type == bfd_link_hash_defined
2256 || h->weakdef->root.type == bfd_link_hash_defweak);
2257 h->root.u.def.section = h->weakdef->root.u.def.section;
2258 h->root.u.def.value = h->weakdef->root.u.def.value;
2259 return true;
2260 }
2261
2262 /* If this is a reference to a symbol defined by a dynamic object which
2263 is not a function, we might allocate the symbol in our .dynbss section
2264 and allocate a COPY dynamic relocation.
2265
2266 But IA-64 code is canonically PIC, so as a rule we can avoid this sort
2267 of hackery. */
2268
2269 return true;
2270}
2271
2272static boolean
2273elf64_ia64_size_dynamic_sections (output_bfd, info)
2274 bfd *output_bfd;
2275 struct bfd_link_info *info;
2276{
2277 struct elf64_ia64_allocate_data data;
2278 struct elf64_ia64_link_hash_table *ia64_info;
2279 asection *sec;
2280 bfd *dynobj;
2281 boolean reltext = false;
2282 boolean relplt = false;
2283
2284 dynobj = elf_hash_table(info)->dynobj;
2285 ia64_info = elf64_ia64_hash_table (info);
2286 BFD_ASSERT(dynobj != NULL);
2287 data.info = info;
2288
2289 /* Set the contents of the .interp section to the interpreter. */
2290 if (ia64_info->root.dynamic_sections_created
2291 && !info->shared)
2292 {
2293 sec = bfd_get_section_by_name (dynobj, ".interp");
2294 BFD_ASSERT (sec != NULL);
2295 sec->contents = (bfd_byte *) ELF_DYNAMIC_INTERPRETER;
2296 sec->_raw_size = strlen (ELF_DYNAMIC_INTERPRETER) + 1;
2297 }
2298
2299 /* DT_INIT and DT_FINI get function descriptors not raw code addresses.
2300 Force their symbols to have pltoff entries so we can use those. */
2301 if (ia64_info->root.dynamic_sections_created)
2302 {
2303 struct elf_link_hash_entry *h;
2304 struct elf64_ia64_dyn_sym_info *dyn_i;
2305
2306 if (info->init_function
2307 && (h = elf_link_hash_lookup (elf_hash_table (info),
2308 info->init_function, false,
2309 false, false))
2310 && (h->elf_link_hash_flags & (ELF_LINK_HASH_REF_REGULAR
2311 | ELF_LINK_HASH_DEF_REGULAR)) != 0)
2312 {
2313 dyn_i = get_dyn_sym_info (ia64_info, h, output_bfd, NULL, true);
2314 dyn_i->want_pltoff = 1;
2315 }
2316
2317 if (info->fini_function
2318 && (h = elf_link_hash_lookup (elf_hash_table (info),
2319 info->fini_function, false,
2320 false, false))
2321 && (h->elf_link_hash_flags & (ELF_LINK_HASH_REF_REGULAR
2322 | ELF_LINK_HASH_DEF_REGULAR)) != 0)
2323 {
2324 dyn_i = get_dyn_sym_info (ia64_info, h, output_bfd, NULL, true);
2325 dyn_i->want_pltoff = 1;
2326 }
2327 }
2328
2329 /* Allocate the GOT entries. */
2330
2331 if (ia64_info->got_sec)
2332 {
2333 data.ofs = 0;
2334 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_global_data_got, &data);
2335 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_global_fptr_got, &data);
2336 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_local_got, &data);
2337 ia64_info->got_sec->_raw_size = data.ofs;
2338 }
2339
2340 /* Allocate the FPTR entries. */
2341
2342 if (ia64_info->fptr_sec)
2343 {
2344 data.ofs = 0;
2345 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_fptr, &data);
2346 ia64_info->fptr_sec->_raw_size = data.ofs;
2347 }
2348
2349 /* Now that we've seen all of the input files, we can decide which
2350 symbols need plt entries. Allocate the minimal PLT entries first.
2351 We do this even though dynamic_sections_created may be false, because
2352 this has the side-effect of clearing want_plt and want_plt2. */
2353
2354 data.ofs = 0;
2355 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_plt_entries, &data);
2356
2357 ia64_info->minplt_entries = 0;
2358 if (data.ofs)
2359 {
2360 ia64_info->minplt_entries
2361 = (data.ofs - PLT_HEADER_SIZE) / PLT_MIN_ENTRY_SIZE;
2362 }
2363
2364 /* Align the pointer for the plt2 entries. */
2365 data.ofs = (data.ofs + 31) & -32;
2366
2367 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_plt2_entries, &data);
2368 if (data.ofs != 0)
2369 {
2370 BFD_ASSERT (ia64_info->root.dynamic_sections_created);
2371
2372 ia64_info->plt_sec->_raw_size = data.ofs;
2373
2374 /* If we've got a .plt, we need some extra memory for the dynamic
2375 linker. We stuff these in .got.plt. */
2376 sec = bfd_get_section_by_name (dynobj, ".got.plt");
2377 sec->_raw_size = 8 * PLT_RESERVED_WORDS;
2378 }
2379
2380 /* Allocate the PLTOFF entries. */
2381
2382 if (ia64_info->pltoff_sec)
2383 {
2384 data.ofs = 0;
2385 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_pltoff_entries, &data);
2386 ia64_info->pltoff_sec->_raw_size = data.ofs;
2387 }
2388
2389 if (ia64_info->root.dynamic_sections_created)
2390 {
2391 /* Allocate space for the dynamic relocations that turned out to be
2392 required. */
2393
2394 elf64_ia64_dyn_sym_traverse (ia64_info, allocate_dynrel_entries, &data);
2395 }
2396
2397 /* We have now determined the sizes of the various dynamic sections.
2398 Allocate memory for them. */
2399 for (sec = dynobj->sections; sec != NULL; sec = sec->next)
2400 {
2401 boolean strip;
2402
2403 if (!(sec->flags & SEC_LINKER_CREATED))
2404 continue;
2405
2406 /* If we don't need this section, strip it from the output file.
2407 There were several sections primarily related to dynamic
2408 linking that must be create before the linker maps input
2409 sections to output sections. The linker does that before
2410 bfd_elf_size_dynamic_sections is called, and it is that
2411 function which decides whether anything needs to go into
2412 these sections. */
2413
2414 strip = (sec->_raw_size == 0);
2415
2416 if (sec == ia64_info->got_sec)
2417 strip = false;
2418 else if (sec == ia64_info->rel_got_sec)
2419 {
2420 if (strip)
2421 ia64_info->rel_got_sec = NULL;
2422 else
2423 /* We use the reloc_count field as a counter if we need to
2424 copy relocs into the output file. */
2425 sec->reloc_count = 0;
2426 }
2427 else if (sec == ia64_info->fptr_sec)
2428 {
2429 if (strip)
2430 ia64_info->fptr_sec = NULL;
2431 }
2432 else if (sec == ia64_info->plt_sec)
2433 {
2434 if (strip)
2435 ia64_info->plt_sec = NULL;
2436 }
2437 else if (sec == ia64_info->pltoff_sec)
2438 {
2439 if (strip)
2440 ia64_info->pltoff_sec = NULL;
2441 }
2442 else if (sec == ia64_info->rel_pltoff_sec)
2443 {
2444 if (strip)
2445 ia64_info->rel_pltoff_sec = NULL;
2446 else
2447 {
2448 relplt = true;
2449 /* We use the reloc_count field as a counter if we need to
2450 copy relocs into the output file. */
2451 sec->reloc_count = 0;
2452 }
2453 }
2454 else
2455 {
2456 const char *name;
2457
2458 /* It's OK to base decisions on the section name, because none
2459 of the dynobj section names depend upon the input files. */
2460 name = bfd_get_section_name (dynobj, sec);
2461
2462 if (strcmp (name, ".got.plt") == 0)
2463 strip = false;
2464 else if (strncmp (name, ".rel", 4) == 0)
2465 {
2466 if (!strip)
2467 {
2468 const char *outname;
2469 asection *target;
2470
2471 /* If this relocation section applies to a read only
2472 section, then we probably need a DT_TEXTREL entry. */
2473 outname = bfd_get_section_name (output_bfd,
2474 sec->output_section);
2475 if (outname[4] == 'a')
2476 outname += 5;
2477 else
2478 outname += 4;
2479
2480 target = bfd_get_section_by_name (output_bfd, outname);
2481 if (target != NULL
2482 && (target->flags & SEC_READONLY) != 0
2483 && (target->flags & SEC_ALLOC) != 0)
2484 reltext = true;
2485
2486 /* We use the reloc_count field as a counter if we need to
2487 copy relocs into the output file. */
2488 sec->reloc_count = 0;
2489 }
2490 }
2491 else
2492 continue;
2493 }
2494
2495 if (strip)
2496 _bfd_strip_section_from_output (info, sec);
2497 else
2498 {
2499 /* Allocate memory for the section contents. */
2500 sec->contents = (bfd_byte *) bfd_zalloc(dynobj, sec->_raw_size);
2501 if (sec->contents == NULL && sec->_raw_size != 0)
2502 return false;
2503 }
2504 }
2505
2506 if (elf_hash_table (info)->dynamic_sections_created)
2507 {
2508 /* Add some entries to the .dynamic section. We fill in the values
2509 later (in finish_dynamic_sections) but we must add the entries now
2510 so that we get the correct size for the .dynamic section. */
2511
2512 if (!info->shared)
2513 {
2514 /* The DT_DEBUG entry is filled in by the dynamic linker and used
2515 by the debugger. */
2516 if (!bfd_elf64_add_dynamic_entry (info, DT_DEBUG, 0))
2517 return false;
2518 }
2519
2520 if (! bfd_elf64_add_dynamic_entry (info, DT_IA_64_PLT_RESERVE, 0))
2521 return false;
2522 if (! bfd_elf64_add_dynamic_entry (info, DT_PLTGOT, 0))
2523 return false;
2524
2525 if (relplt)
2526 {
2527 if (! bfd_elf64_add_dynamic_entry (info, DT_PLTRELSZ, 0)
2528 || ! bfd_elf64_add_dynamic_entry (info, DT_PLTREL, DT_RELA)
2529 || ! bfd_elf64_add_dynamic_entry (info, DT_JMPREL, 0))
2530 return false;
2531 }
2532
2533 if (! bfd_elf64_add_dynamic_entry (info, DT_RELA, 0)
2534 || ! bfd_elf64_add_dynamic_entry (info, DT_RELASZ, 0)
2535 || ! bfd_elf64_add_dynamic_entry (info, DT_RELAENT,
2536 sizeof(Elf64_External_Rela)))
2537 return false;
2538
2539 if (reltext)
2540 {
2541 if (! bfd_elf64_add_dynamic_entry (info, DT_TEXTREL, 0))
2542 return false;
2543 info->flags |= DF_TEXTREL;
2544 }
2545 }
2546
2547 /* ??? Perhaps force __gp local. */
2548
2549 return true;
2550}
2551
2552static bfd_reloc_status_type
2553elf64_ia64_install_value (abfd, hit_addr, val, r_type)
2554 bfd *abfd;
2555 bfd_byte *hit_addr;
2556 bfd_vma val;
2557 unsigned int r_type;
2558{
2559 const struct ia64_operand *op;
2560 int bigendian = 0, shift = 0;
2561 bfd_vma t0, t1, insn, dword;
2562 enum ia64_opnd opnd;
2563 const char *err;
2564 size_t size = 8;
2565
2566 opnd = IA64_OPND_NIL;
2567 switch (r_type)
2568 {
2569 case R_IA64_NONE:
2570 case R_IA64_LDXMOV:
2571 return bfd_reloc_ok;
2572
2573 /* Instruction relocations. */
2574
2575 case R_IA64_IMM14: opnd = IA64_OPND_IMM14; break;
2576
2577 case R_IA64_PCREL21F: opnd = IA64_OPND_TGT25; break;
2578 case R_IA64_PCREL21M: opnd = IA64_OPND_TGT25b; break;
2579 case R_IA64_PCREL60B: opnd = IA64_OPND_TGT64; break;
2580 case R_IA64_PCREL21B:
2581 case R_IA64_PCREL21BI:
2582 opnd = IA64_OPND_TGT25c;
2583 break;
2584
2585 case R_IA64_IMM22:
2586 case R_IA64_GPREL22:
2587 case R_IA64_LTOFF22:
2588 case R_IA64_LTOFF22X:
2589 case R_IA64_PLTOFF22:
2590 case R_IA64_PCREL22:
2591 case R_IA64_LTOFF_FPTR22:
2592 opnd = IA64_OPND_IMM22;
2593 break;
2594
2595 case R_IA64_IMM64:
2596 case R_IA64_GPREL64I:
2597 case R_IA64_LTOFF64I:
2598 case R_IA64_PLTOFF64I:
2599 case R_IA64_PCREL64I:
2600 case R_IA64_FPTR64I:
2601 case R_IA64_LTOFF_FPTR64I:
2602 opnd = IA64_OPND_IMMU64;
2603 break;
2604
2605 /* Data relocations. */
2606
2607 case R_IA64_DIR32MSB:
2608 case R_IA64_GPREL32MSB:
2609 case R_IA64_FPTR32MSB:
2610 case R_IA64_PCREL32MSB:
2611 case R_IA64_SEGREL32MSB:
2612 case R_IA64_SECREL32MSB:
2613 case R_IA64_LTV32MSB:
2614 size = 4; bigendian = 1;
2615 break;
2616
2617 case R_IA64_DIR32LSB:
2618 case R_IA64_GPREL32LSB:
2619 case R_IA64_FPTR32LSB:
2620 case R_IA64_PCREL32LSB:
2621 case R_IA64_SEGREL32LSB:
2622 case R_IA64_SECREL32LSB:
2623 case R_IA64_LTV32LSB:
2624 size = 4; bigendian = 0;
2625 break;
2626
2627 case R_IA64_DIR64MSB:
2628 case R_IA64_GPREL64MSB:
2629 case R_IA64_PLTOFF64MSB:
2630 case R_IA64_FPTR64MSB:
2631 case R_IA64_PCREL64MSB:
2632 case R_IA64_LTOFF_FPTR64MSB:
2633 case R_IA64_SEGREL64MSB:
2634 case R_IA64_SECREL64MSB:
2635 case R_IA64_LTV64MSB:
2636 size = 8; bigendian = 1;
2637 break;
2638
2639 case R_IA64_DIR64LSB:
2640 case R_IA64_GPREL64LSB:
2641 case R_IA64_PLTOFF64LSB:
2642 case R_IA64_FPTR64LSB:
2643 case R_IA64_PCREL64LSB:
2644 case R_IA64_LTOFF_FPTR64LSB:
2645 case R_IA64_SEGREL64LSB:
2646 case R_IA64_SECREL64LSB:
2647 case R_IA64_LTV64LSB:
2648 size = 8; bigendian = 0;
2649 break;
2650
2651 /* Unsupported / Dynamic relocations. */
2652
2653 case R_IA64_REL32MSB:
2654 case R_IA64_REL32LSB:
2655 case R_IA64_REL64MSB:
2656 case R_IA64_REL64LSB:
2657
2658 case R_IA64_IPLTMSB:
2659 case R_IA64_IPLTLSB:
2660 case R_IA64_EPLTMSB:
2661 case R_IA64_EPLTLSB:
2662 case R_IA64_COPY:
2663
2664 case R_IA64_SEGBASE:
2665
2666 case R_IA64_TPREL22:
2667 case R_IA64_TPREL64MSB:
2668 case R_IA64_TPREL64LSB:
2669 case R_IA64_LTOFF_TP22:
2670
2671 default:
2672 return bfd_reloc_notsupported;
2673 }
2674
2675 switch (opnd)
2676 {
2677 case IA64_OPND_IMMU64:
2678 hit_addr -= (long) hit_addr & 0x3;
2679 t0 = bfd_get_64 (abfd, hit_addr);
2680 t1 = bfd_get_64 (abfd, hit_addr + 8);
2681
2682 /* tmpl/s: bits 0.. 5 in t0
2683 slot 0: bits 5..45 in t0
2684 slot 1: bits 46..63 in t0, bits 0..22 in t1
2685 slot 2: bits 23..63 in t1 */
2686
2687 /* First, clear the bits that form the 64 bit constant. */
2688 t0 &= ~(0x3ffffLL << 46);
2689 t1 &= ~(0x7fffffLL
2690 | (( (0x07fLL << 13) | (0x1ffLL << 27)
2691 | (0x01fLL << 22) | (0x001LL << 21)
2692 | (0x001LL << 36)) << 23));
2693
2694 t0 |= ((val >> 22) & 0x03ffffLL) << 46; /* 18 lsbs of imm41 */
2695 t1 |= ((val >> 40) & 0x7fffffLL) << 0; /* 23 msbs of imm41 */
2696 t1 |= ( (((val >> 0) & 0x07f) << 13) /* imm7b */
2697 | (((val >> 7) & 0x1ff) << 27) /* imm9d */
2698 | (((val >> 16) & 0x01f) << 22) /* imm5c */
2699 | (((val >> 21) & 0x001) << 21) /* ic */
2700 | (((val >> 63) & 0x001) << 36)) << 23; /* i */
2701
2702 bfd_put_64 (abfd, t0, hit_addr);
2703 bfd_put_64 (abfd, t1, hit_addr + 8);
2704 break;
2705
2706 case IA64_OPND_TGT64:
2707 hit_addr -= (long) hit_addr & 0x3;
2708 t0 = bfd_get_64 (abfd, hit_addr);
2709 t1 = bfd_get_64 (abfd, hit_addr + 8);
2710
2711 /* tmpl/s: bits 0.. 5 in t0
2712 slot 0: bits 5..45 in t0
2713 slot 1: bits 46..63 in t0, bits 0..22 in t1
2714 slot 2: bits 23..63 in t1 */
2715
2716 /* First, clear the bits that form the 64 bit constant. */
2717 t0 &= ~(0x3ffffLL << 46);
2718 t1 &= ~(0x7fffffLL
2719 | ((1LL << 36 | 0xfffffLL << 13) << 23));
2720
2721 val >>= 4;
2722 t0 |= ((val >> 20) & 0xffffLL) << 2 << 46; /* 16 lsbs of imm39 */
2723 t1 |= ((val >> 36) & 0x7fffffLL) << 0; /* 23 msbs of imm39 */
2724 t1 |= ((((val >> 0) & 0xfffffLL) << 13) /* imm20b */
2725 | (((val >> 59) & 0x1LL) << 36)) << 23; /* i */
2726
2727 bfd_put_64 (abfd, t0, hit_addr);
2728 bfd_put_64 (abfd, t1, hit_addr + 8);
2729 break;
2730
2731 default:
2732 switch ((long) hit_addr & 0x3)
2733 {
2734 case 0: shift = 5; break;
2735 case 1: shift = 14; hit_addr += 3; break;
2736 case 2: shift = 23; hit_addr += 6; break;
2737 case 3: return bfd_reloc_notsupported; /* shouldn't happen... */
2738 }
2739 dword = bfd_get_64 (abfd, hit_addr);
2740 insn = (dword >> shift) & 0x1ffffffffffLL;
2741
2742 op = elf64_ia64_operands + opnd;
2743 err = (*op->insert) (op, val, &insn);
2744 if (err)
2745 return bfd_reloc_overflow;
2746
2747 dword &= ~(0x1ffffffffffLL << shift);
2748 dword |= (insn << shift);
2749 bfd_put_64 (abfd, dword, hit_addr);
2750 break;
2751
2752 case IA64_OPND_NIL:
2753 /* A data relocation. */
2754 if (bigendian)
2755 if (size == 4)
2756 bfd_putb32 (val, hit_addr);
2757 else
2758 bfd_putb64 (val, hit_addr);
2759 else
2760 if (size == 4)
2761 bfd_putl32 (val, hit_addr);
2762 else
2763 bfd_putl64 (val, hit_addr);
2764 break;
2765 }
2766
2767 return bfd_reloc_ok;
2768}
2769
2770static void
2771elf64_ia64_install_dyn_reloc (abfd, info, sec, srel, offset, type,
2772 dynindx, addend)
2773 bfd *abfd;
2774 struct bfd_link_info *info;
2775 asection *sec;
2776 asection *srel;
2777 bfd_vma offset;
2778 unsigned int type;
2779 long dynindx;
2780 bfd_vma addend;
2781{
2782 Elf_Internal_Rela outrel;
2783
2784 outrel.r_offset = (sec->output_section->vma
2785 + sec->output_offset
2786 + offset);
2787
2788 BFD_ASSERT (dynindx != -1);
2789 outrel.r_info = ELF64_R_INFO (dynindx, type);
2790 outrel.r_addend = addend;
2791
2792 if (elf_section_data (sec)->stab_info != NULL)
2793 {
2794 /* This may be NULL for linker-generated relocations, as it is
2795 inconvenient to pass all the bits around. And this shouldn't
2796 happen. */
2797 BFD_ASSERT (info != NULL);
2798
2799 offset = (_bfd_stab_section_offset
2800 (abfd, &elf_hash_table (info)->stab_info, sec,
2801 &elf_section_data (sec)->stab_info, offset));
2802 if (offset == (bfd_vma) -1)
2803 {
2804 /* Run for the hills. We shouldn't be outputting a relocation
2805 for this. So do what everyone else does and output a no-op. */
2806 outrel.r_info = ELF64_R_INFO (0, R_IA64_NONE);
2807 outrel.r_addend = 0;
2808 offset = 0;
2809 }
2810 outrel.r_offset = offset;
2811 }
2812
2813 bfd_elf64_swap_reloca_out (abfd, &outrel,
2814 ((Elf64_External_Rela *) srel->contents
2815 + srel->reloc_count++));
2816 BFD_ASSERT (sizeof(Elf64_External_Rela) * srel->reloc_count
2817 <= srel->_cooked_size);
2818}
2819
2820/* Store an entry for target address TARGET_ADDR in the linkage table
2821 and return the gp-relative address of the linkage table entry. */
2822
2823static bfd_vma
2824set_got_entry (abfd, info, dyn_i, dynindx, addend, value, dyn_r_type)
2825 bfd *abfd;
2826 struct bfd_link_info *info;
2827 struct elf64_ia64_dyn_sym_info *dyn_i;
2828 long dynindx;
2829 bfd_vma addend;
2830 bfd_vma value;
2831 unsigned int dyn_r_type;
2832{
2833 struct elf64_ia64_link_hash_table *ia64_info;
2834 asection *got_sec;
2835
2836 ia64_info = elf64_ia64_hash_table (info);
2837 got_sec = ia64_info->got_sec;
2838
2839 BFD_ASSERT ((dyn_i->got_offset & 7) == 0);
2840
2841 if (! dyn_i->got_done)
2842 {
2843 dyn_i->got_done = true;
2844
2845 /* Store the target address in the linkage table entry. */
2846 bfd_put_64 (abfd, value, got_sec->contents + dyn_i->got_offset);
2847
2848 /* Install a dynamic relocation if needed. */
2849 if (info->shared
2850 || elf64_ia64_dynamic_symbol_p (dyn_i->h, info)
2851 || (dynindx != -1 && dyn_r_type == R_IA64_FPTR64LSB))
2852 {
2853 if (dynindx == -1)
2854 {
2855 dyn_r_type = R_IA64_REL64LSB;
2856 dynindx = 0;
2857 addend = value;
2858 }
2859
2860 if (bfd_big_endian (abfd))
2861 {
2862 switch (dyn_r_type)
2863 {
2864 case R_IA64_REL64LSB:
2865 dyn_r_type = R_IA64_REL64MSB;
2866 break;
2867 case R_IA64_DIR64LSB:
2868 dyn_r_type = R_IA64_DIR64MSB;
2869 break;
2870 case R_IA64_FPTR64LSB:
2871 dyn_r_type = R_IA64_FPTR64MSB;
2872 break;
2873 default:
2874 BFD_ASSERT (false);
2875 break;
2876 }
2877 }
2878
2879 elf64_ia64_install_dyn_reloc (abfd, NULL, got_sec,
2880 ia64_info->rel_got_sec,
2881 dyn_i->got_offset, dyn_r_type,
2882 dynindx, addend);
2883 }
2884 }
2885
2886 /* Return the address of the linkage table entry. */
2887 value = (got_sec->output_section->vma
2888 + got_sec->output_offset
2889 + dyn_i->got_offset);
2890
2891 return value;
2892}
2893
2894/* Fill in a function descriptor consisting of the function's code
2895 address and its global pointer. Return the descriptor's address. */
2896
2897static bfd_vma
2898set_fptr_entry (abfd, info, dyn_i, value)
2899 bfd *abfd;
2900 struct bfd_link_info *info;
2901 struct elf64_ia64_dyn_sym_info *dyn_i;
2902 bfd_vma value;
2903{
2904 struct elf64_ia64_link_hash_table *ia64_info;
2905 asection *fptr_sec;
2906
2907 ia64_info = elf64_ia64_hash_table (info);
2908 fptr_sec = ia64_info->fptr_sec;
2909
2910 if (!dyn_i->fptr_done)
2911 {
2912 dyn_i->fptr_done = 1;
2913
2914 /* Fill in the function descriptor. */
2915 bfd_put_64 (abfd, value, fptr_sec->contents + dyn_i->fptr_offset);
2916 bfd_put_64 (abfd, _bfd_get_gp_value (abfd),
2917 fptr_sec->contents + dyn_i->fptr_offset + 8);
2918 }
2919
2920 /* Return the descriptor's address. */
2921 value = (fptr_sec->output_section->vma
2922 + fptr_sec->output_offset
2923 + dyn_i->fptr_offset);
2924
2925 return value;
2926}
2927
2928/* Fill in a PLTOFF entry consisting of the function's code address
2929 and its global pointer. Return the descriptor's address. */
2930
2931static bfd_vma
2932set_pltoff_entry (abfd, info, dyn_i, value, is_plt)
2933 bfd *abfd;
2934 struct bfd_link_info *info;
2935 struct elf64_ia64_dyn_sym_info *dyn_i;
2936 bfd_vma value;
2937 boolean is_plt;
2938{
2939 struct elf64_ia64_link_hash_table *ia64_info;
2940 asection *pltoff_sec;
2941
2942 ia64_info = elf64_ia64_hash_table (info);
2943 pltoff_sec = ia64_info->pltoff_sec;
2944
2945 /* Don't do anything if this symbol uses a real PLT entry. In
2946 that case, we'll fill this in during finish_dynamic_symbol. */
2947 if ((! dyn_i->want_plt || is_plt)
2948 && !dyn_i->pltoff_done)
2949 {
2950 /* Fill in the function descriptor. */
2951 bfd_put_64 (abfd, value, pltoff_sec->contents + dyn_i->pltoff_offset);
2952 bfd_put_64 (abfd, _bfd_get_gp_value (abfd),
2953 pltoff_sec->contents + dyn_i->pltoff_offset + 8);
2954
2955 /* Install dynamic relocations if needed. */
2956 if (!is_plt && info->shared)
2957 {
2958 unsigned int dyn_r_type;
2959
2960 if (bfd_big_endian (abfd))
2961 dyn_r_type = R_IA64_REL64MSB;
2962 else
2963 dyn_r_type = R_IA64_REL64LSB;
2964
2965 elf64_ia64_install_dyn_reloc (abfd, NULL, pltoff_sec,
2966 ia64_info->rel_pltoff_sec,
2967 dyn_i->pltoff_offset,
2968 dyn_r_type, 0, 0);
2969 elf64_ia64_install_dyn_reloc (abfd, NULL, pltoff_sec,
2970 ia64_info->rel_pltoff_sec,
2971 dyn_i->pltoff_offset + 8,
2972 dyn_r_type, 0, 0);
2973 }
2974
2975 dyn_i->pltoff_done = 1;
2976 }
2977
2978 /* Return the descriptor's address. */
2979 value = (pltoff_sec->output_section->vma
2980 + pltoff_sec->output_offset
2981 + dyn_i->pltoff_offset);
2982
2983 return value;
2984}
2985
2986/* Called through qsort to sort the .IA_64.unwind section during a
2987 non-relocatable link. Set elf64_ia64_unwind_entry_compare_bfd
2988 to the output bfd so we can do proper endianness frobbing. */
2989
2990static bfd *elf64_ia64_unwind_entry_compare_bfd;
2991
2992static int
2993elf64_ia64_unwind_entry_compare (a, b)
2994 PTR a;
2995 PTR b;
2996{
2997 bfd_vma av, bv;
2998
2999 av = bfd_get_64 (elf64_ia64_unwind_entry_compare_bfd, a);
3000 bv = bfd_get_64 (elf64_ia64_unwind_entry_compare_bfd, b);
3001
3002 return (av < bv ? -1 : av > bv ? 1 : 0);
3003}
3004
3005static boolean
3006elf64_ia64_final_link (abfd, info)
3007 bfd *abfd;
3008 struct bfd_link_info *info;
3009{
3010 struct elf64_ia64_link_hash_table *ia64_info;
3011 ia64_info = elf64_ia64_hash_table (info);
3012
3013 /* Make sure we've got ourselves a nice fat __gp value. */
3014 if (!info->relocateable)
3015 {
3016 bfd_vma min_vma = (bfd_vma) -1, max_vma = 0;
3017 bfd_vma min_short_vma = min_vma, max_short_vma = 0;
3018 struct elf_link_hash_entry *gp;
3019 bfd_vma gp_val;
3020 asection *os;
3021
3022 /* Find the min and max vma of all sections marked short. Also
3023 collect min and max vma of any type, for use in selecting a
3024 nice gp. */
3025 for (os = abfd->sections; os ; os = os->next)
3026 {
3027 bfd_vma lo, hi;
3028
3029 if ((os->flags & SEC_ALLOC) == 0)
3030 continue;
3031
3032 lo = os->vma;
3033 hi = os->vma + os->_raw_size;
3034 if (hi < lo)
3035 hi = (bfd_vma) -1;
3036
3037 if (min_vma > lo)
3038 min_vma = lo;
3039 if (max_vma < hi)
3040 max_vma = hi;
3041 if (os->flags & SEC_SMALL_DATA)
3042 {
3043 if (min_short_vma > lo)
3044 min_short_vma = lo;
3045 if (max_short_vma < hi)
3046 max_short_vma = hi;
3047 }
3048 }
3049
3050 /* See if the user wants to force a value. */
3051 gp = elf_link_hash_lookup (elf_hash_table (info), "__gp", false,
3052 false, false);
3053
3054 if (gp
3055 && (gp->root.type == bfd_link_hash_defined
3056 || gp->root.type == bfd_link_hash_defweak))
3057 {
3058 asection *gp_sec = gp->root.u.def.section;
3059 gp_val = (gp->root.u.def.value
3060 + gp_sec->output_section->vma
3061 + gp_sec->output_offset);
3062 }
3063 else
3064 {
3065 /* Pick a sensible value. */
3066
3067 asection *got_sec = ia64_info->got_sec;
3068
3069 /* Start with just the address of the .got. */
3070 if (got_sec)
3071 gp_val = got_sec->output_section->vma;
3072 else if (max_short_vma != 0)
3073 gp_val = min_short_vma;
3074 else
3075 gp_val = min_vma;
3076
3077 /* If it is possible to address the entire image, but we
3078 don't with the choice above, adjust. */
3079 if (max_vma - min_vma < 0x400000
3080 && max_vma - gp_val <= 0x200000
3081 && gp_val - min_vma > 0x200000)
3082 gp_val = min_vma + 0x200000;
3083 else if (max_short_vma != 0)
3084 {
3085 /* If we don't cover all the short data, adjust. */
3086 if (max_short_vma - gp_val >= 0x200000)
3087 gp_val = min_short_vma + 0x200000;
3088
3089 /* If we're addressing stuff past the end, adjust back. */
3090 if (gp_val > max_vma)
3091 gp_val = max_vma - 0x200000 + 8;
3092 }
3093 }
3094
3095 /* Validate whether all SHF_IA_64_SHORT sections are within
3096 range of the chosen GP. */
3097
3098 if (max_short_vma != 0)
3099 {
3100 if (max_short_vma - min_short_vma >= 0x400000)
3101 {
3102 (*_bfd_error_handler)
3103 (_("%s: short data segment overflowed (0x%lx >= 0x400000)"),
3104 bfd_get_filename (abfd),
3105 (unsigned long)(max_short_vma - min_short_vma));
3106 return false;
3107 }
3108 else if ((gp_val > min_short_vma
3109 && gp_val - min_short_vma > 0x200000)
3110 || (gp_val < max_short_vma
3111 && max_short_vma - gp_val >= 0x200000))
3112 {
3113 (*_bfd_error_handler)
3114 (_("%s: __gp does not cover short data segment"),
3115 bfd_get_filename (abfd));
3116 return false;
3117 }
3118 }
3119
3120 _bfd_set_gp_value (abfd, gp_val);
3121 }
3122
3123 /* Tricky bits. DT_INIT and DT_FINI use a pltoff entry, which is
3124 normally initialized in finish_dynamic_sections. Except that
3125 we need all non-plt pltoff entries to be initialized before
3126 finish_dynamic_symbols. This because the array of relocations
3127 used for plt entries (aka DT_JMPREL) begins after all the
3128 non-plt pltoff relocations. If the order gets confused, we
3129 munge either the array or the array base. */
3130 if (ia64_info->root.dynamic_sections_created)
3131 {
3132 struct elf_link_hash_entry *h;
3133 struct elf64_ia64_dyn_sym_info *dyn_i;
3134 bfd_vma addr;
3135
3136 if (info->init_function
3137 && (h = elf_link_hash_lookup (elf_hash_table (info),
3138 info->init_function, false,
3139 false, false))
3140 && (h->elf_link_hash_flags & (ELF_LINK_HASH_REF_REGULAR
3141 | ELF_LINK_HASH_DEF_REGULAR)) != 0)
3142 {
3143 dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, false);
3144 addr = (h->root.u.def.section->output_section->vma
3145 + h->root.u.def.section->output_offset
3146 + h->root.u.def.value);
3147 (void) set_pltoff_entry (abfd, info, dyn_i, addr, false);
3148 }
3149
3150 if (info->fini_function
3151 && (h = elf_link_hash_lookup (elf_hash_table (info),
3152 info->fini_function, false,
3153 false, false))
3154 && (h->elf_link_hash_flags & (ELF_LINK_HASH_REF_REGULAR
3155 | ELF_LINK_HASH_DEF_REGULAR)) != 0)
3156 {
3157 dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, false);
3158 addr = (h->root.u.def.section->output_section->vma
3159 + h->root.u.def.section->output_offset
3160 + h->root.u.def.value);
3161 (void) set_pltoff_entry (abfd, info, dyn_i, addr, false);
3162 }
3163 }
3164
3165 /* Invoke the regular ELF backend linker to do all the work. */
3166 if (!bfd_elf64_bfd_final_link (abfd, info))
3167 return false;
3168
3169 /* If we're producing a final executable, we need to sort the contents
3170 of the .IA_64.unwind section. */
3171 if (!info->relocateable)
3172 {
3173 asection *s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_unwind);
3174 if (s)
3175 {
3176 bfd_size_type size = s->output_section->_raw_size;
3177 char *contents = bfd_malloc (size);
3178
3179 if (contents == NULL)
3180 return false;
3181 if (! bfd_get_section_contents (abfd, s->output_section,
3182 contents, (file_ptr) 0, size))
3183 return false;
3184
3185 elf64_ia64_unwind_entry_compare_bfd = abfd;
3186 qsort (contents, size / 24, 24, elf64_ia64_unwind_entry_compare);
3187
3188 if (! bfd_set_section_contents (abfd, s->output_section,
3189 contents, (file_ptr) 0, size))
3190 return false;
3191 }
3192 }
3193
3194 return true;
3195}
3196
3197static boolean
3198elf64_ia64_relocate_section (output_bfd, info, input_bfd, input_section,
3199 contents, relocs, local_syms, local_sections)
3200 bfd *output_bfd;
3201 struct bfd_link_info *info;
3202 bfd *input_bfd;
3203 asection *input_section;
3204 bfd_byte *contents;
3205 Elf_Internal_Rela *relocs;
3206 Elf_Internal_Sym *local_syms;
3207 asection **local_sections;
3208{
3209 struct elf64_ia64_link_hash_table *ia64_info;
3210 Elf_Internal_Shdr *symtab_hdr;
3211 Elf_Internal_Rela *rel;
3212 Elf_Internal_Rela *relend;
3213 asection *srel;
3214 boolean ret_val = true; /* for non-fatal errors */
3215 bfd_vma gp_val;
3216
3217 symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
3218 ia64_info = elf64_ia64_hash_table (info);
3219
3220 /* Infect various flags from the input section to the output section. */
3221 if (info->relocateable)
3222 {
3223 bfd_vma flags;
3224
3225 flags = elf_section_data(input_section)->this_hdr.sh_flags;
3226 flags &= SHF_IA_64_NORECOV;
3227
3228 elf_section_data(input_section->output_section)
3229 ->this_hdr.sh_flags |= flags;
3230 }
3231
3232 gp_val = _bfd_get_gp_value (output_bfd);
3233 srel = get_reloc_section (input_bfd, ia64_info, input_section, false);
3234
3235 rel = relocs;
3236 relend = relocs + input_section->reloc_count;
3237 for (; rel < relend; ++rel)
3238 {
3239 struct elf_link_hash_entry *h;
3240 struct elf64_ia64_dyn_sym_info *dyn_i;
3241 bfd_reloc_status_type r;
3242 reloc_howto_type *howto;
3243 unsigned long r_symndx;
3244 Elf_Internal_Sym *sym;
3245 unsigned int r_type;
3246 bfd_vma value;
3247 asection *sym_sec;
3248 bfd_byte *hit_addr;
3249 boolean dynamic_symbol_p;
3250 boolean undef_weak_ref;
3251
3252 r_type = ELF64_R_TYPE (rel->r_info);
3253 if (r_type > R_IA64_MAX_RELOC_CODE)
3254 {
3255 (*_bfd_error_handler)
3256 (_("%s: unknown relocation type %d"),
3257 bfd_get_filename (input_bfd), (int)r_type);
3258 bfd_set_error (bfd_error_bad_value);
3259 ret_val = false;
3260 continue;
3261 }
3262 howto = lookup_howto (r_type);
3263 r_symndx = ELF64_R_SYM (rel->r_info);
3264
3265 if (info->relocateable)
3266 {
3267 /* This is a relocateable link. We don't have to change
3268 anything, unless the reloc is against a section symbol,
3269 in which case we have to adjust according to where the
3270 section symbol winds up in the output section. */
3271 if (r_symndx < symtab_hdr->sh_info)
3272 {
3273 sym = local_syms + r_symndx;
3274 if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
3275 {
3276 sym_sec = local_sections[r_symndx];
3277 rel->r_addend += sym_sec->output_offset;
3278 }
3279 }
3280 continue;
3281 }
3282
3283 /* This is a final link. */
3284
3285 h = NULL;
3286 sym = NULL;
3287 sym_sec = NULL;
3288 undef_weak_ref = false;
3289
3290 if (r_symndx < symtab_hdr->sh_info)
3291 {
3292 /* Reloc against local symbol. */
3293 sym = local_syms + r_symndx;
3294 sym_sec = local_sections[r_symndx];
3295 value = (sym_sec->output_section->vma
3296 + sym_sec->output_offset
3297 + sym->st_value);
3298 }
3299 else
3300 {
3301 long indx;
3302
3303 /* Reloc against global symbol. */
3304 indx = r_symndx - symtab_hdr->sh_info;
3305 h = elf_sym_hashes (input_bfd)[indx];
3306 while (h->root.type == bfd_link_hash_indirect
3307 || h->root.type == bfd_link_hash_warning)
3308 h = (struct elf_link_hash_entry *) h->root.u.i.link;
3309
3310 value = 0;
3311 if (h->root.type == bfd_link_hash_defined
3312 || h->root.type == bfd_link_hash_defweak)
3313 {
3314 sym_sec = h->root.u.def.section;
3315
3316 /* Detect the cases that sym_sec->output_section is
3317 expected to be NULL -- all cases in which the symbol
3318 is defined in another shared module. This includes
3319 PLT relocs for which we've created a PLT entry and
3320 other relocs for which we're prepared to create
3321 dynamic relocations. */
3322 /* ??? Just accept it NULL and continue. */
3323
3324 if (sym_sec->output_section != NULL)
3325 {
3326 value = (h->root.u.def.value
3327 + sym_sec->output_section->vma
3328 + sym_sec->output_offset);
3329 }
3330 }
3331 else if (h->root.type == bfd_link_hash_undefweak)
3332 undef_weak_ref = true;
3333 else if (info->shared && !info->symbolic
3334 && !info->no_undefined
3335 && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
3336 ;
3337 else
3338 {
3339 if (! ((*info->callbacks->undefined_symbol)
3340 (info, h->root.root.string, input_bfd,
3341 input_section, rel->r_offset,
3342 (!info->shared || info->no_undefined
3343 || ELF_ST_VISIBILITY (h->other)))))
3344 return false;
3345 ret_val = false;
3346 continue;
3347 }
3348 }
3349
3350 hit_addr = contents + rel->r_offset;
3351 value += rel->r_addend;
3352 dynamic_symbol_p = elf64_ia64_dynamic_symbol_p (h, info);
3353
3354 switch (r_type)
3355 {
3356 case R_IA64_NONE:
3357 case R_IA64_LDXMOV:
3358 continue;
3359
3360 case R_IA64_IMM14:
3361 case R_IA64_IMM22:
3362 case R_IA64_IMM64:
3363 case R_IA64_DIR32MSB:
3364 case R_IA64_DIR32LSB:
3365 case R_IA64_DIR64MSB:
3366 case R_IA64_DIR64LSB:
3367 /* Install a dynamic relocation for this reloc. */
3368 if ((dynamic_symbol_p
3369 || info->shared)
3370 && (input_section->flags & SEC_ALLOC) != 0)
3371 {
3372 unsigned int dyn_r_type;
3373 long dynindx;
3374
3375 BFD_ASSERT (srel != NULL);
3376
3377 /* If we don't need dynamic symbol lookup, find a
3378 matching RELATIVE relocation. */
3379 dyn_r_type = r_type;
3380 if (dynamic_symbol_p)
3381 dynindx = h->dynindx;
3382 else
3383 {
3384 switch (r_type)
3385 {
3386 case R_IA64_DIR32MSB:
3387 dyn_r_type = R_IA64_REL32MSB;
3388 break;
3389 case R_IA64_DIR32LSB:
3390 dyn_r_type = R_IA64_REL32LSB;
3391 break;
3392 case R_IA64_DIR64MSB:
3393 dyn_r_type = R_IA64_REL64MSB;
3394 break;
3395 case R_IA64_DIR64LSB:
3396 dyn_r_type = R_IA64_REL64LSB;
3397 break;
3398
3399 default:
3400 /* We can't represent this without a dynamic symbol.
3401 Adjust the relocation to be against an output
3402 section symbol, which are always present in the
3403 dynamic symbol table. */
3404 /* ??? People shouldn't be doing non-pic code in
3405 shared libraries. Hork. */
3406 (*_bfd_error_handler)
3407 (_("%s: linking non-pic code in a shared library"),
3408 bfd_get_filename (input_bfd));
3409 ret_val = false;
3410 continue;
3411 }
3412 dynindx = 0;
3413 }
3414
3415 elf64_ia64_install_dyn_reloc (output_bfd, info, input_section,
3416 srel, rel->r_offset, dyn_r_type,
3417 dynindx, rel->r_addend);
3418 }
3419 /* FALLTHRU */
3420
3421 case R_IA64_LTV32MSB:
3422 case R_IA64_LTV32LSB:
3423 case R_IA64_LTV64MSB:
3424 case R_IA64_LTV64LSB:
3425 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3426 break;
3427
3428 case R_IA64_GPREL22:
3429 case R_IA64_GPREL64I:
3430 case R_IA64_GPREL32MSB:
3431 case R_IA64_GPREL32LSB:
3432 case R_IA64_GPREL64MSB:
3433 case R_IA64_GPREL64LSB:
3434 if (dynamic_symbol_p)
3435 {
3436 (*_bfd_error_handler)
3437 (_("%s: @gprel relocation against dynamic symbol %s"),
3438 bfd_get_filename (input_bfd), h->root.root.string);
3439 ret_val = false;
3440 continue;
3441 }
3442 value -= gp_val;
3443 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3444 break;
3445
3446 case R_IA64_LTOFF22:
3447 case R_IA64_LTOFF22X:
3448 case R_IA64_LTOFF64I:
3449 dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, false);
3450 value = set_got_entry (input_bfd, info, dyn_i, (h ? h->dynindx : -1),
3451 rel->r_addend, value, R_IA64_DIR64LSB);
3452 value -= gp_val;
3453 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3454 break;
3455
3456 case R_IA64_PLTOFF22:
3457 case R_IA64_PLTOFF64I:
3458 case R_IA64_PLTOFF64MSB:
3459 case R_IA64_PLTOFF64LSB:
3460 dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, false);
3461 value = set_pltoff_entry (output_bfd, info, dyn_i, value, false);
3462 value -= gp_val;
3463 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3464 break;
3465
3466 case R_IA64_FPTR64I:
3467 case R_IA64_FPTR32MSB:
3468 case R_IA64_FPTR32LSB:
3469 case R_IA64_FPTR64MSB:
3470 case R_IA64_FPTR64LSB:
3471 dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, false);
3472 if (dyn_i->want_fptr)
3473 {
3474 if (!undef_weak_ref)
3475 value = set_fptr_entry (output_bfd, info, dyn_i, value);
3476 }
3477 else
3478 {
3479 long dynindx;
3480
3481 /* Otherwise, we expect the dynamic linker to create
3482 the entry. */
3483
3484 if (h)
3485 {
3486 if (h->dynindx != -1)
3487 dynindx = h->dynindx;
3488 else
3489 dynindx = (_bfd_elf_link_lookup_local_dynindx
3490 (info, h->root.u.def.section->owner,
3491 global_sym_index (h)));
3492 }
3493 else
3494 {
3495 dynindx = (_bfd_elf_link_lookup_local_dynindx
3496 (info, input_bfd, r_symndx));
3497 }
3498
3499 elf64_ia64_install_dyn_reloc (output_bfd, info, input_section,
3500 srel, rel->r_offset, r_type,
3501 dynindx, rel->r_addend);
3502 value = 0;
3503 }
3504
3505 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3506 break;
3507
3508 case R_IA64_LTOFF_FPTR22:
3509 case R_IA64_LTOFF_FPTR64I:
3510 case R_IA64_LTOFF_FPTR64MSB:
3511 case R_IA64_LTOFF_FPTR64LSB:
3512 {
3513 long dynindx;
3514
3515 dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, false);
3516 if (dyn_i->want_fptr)
3517 {
3518 BFD_ASSERT (h == NULL || h->dynindx == -1)
3519 if (!undef_weak_ref)
3520 value = set_fptr_entry (output_bfd, info, dyn_i, value);
3521 dynindx = -1;
3522 }
3523 else
3524 {
3525 /* Otherwise, we expect the dynamic linker to create
3526 the entry. */
3527 if (h)
3528 {
3529 if (h->dynindx != -1)
3530 dynindx = h->dynindx;
3531 else
3532 dynindx = (_bfd_elf_link_lookup_local_dynindx
3533 (info, h->root.u.def.section->owner,
3534 global_sym_index (h)));
3535 }
3536 else
3537 dynindx = (_bfd_elf_link_lookup_local_dynindx
3538 (info, input_bfd, r_symndx));
3539 value = 0;
3540 }
3541
3542 value = set_got_entry (output_bfd, info, dyn_i, dynindx,
3543 rel->r_addend, value, R_IA64_FPTR64LSB);
3544 value -= gp_val;
3545 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3546 }
3547 break;
3548
3549 case R_IA64_PCREL32MSB:
3550 case R_IA64_PCREL32LSB:
3551 case R_IA64_PCREL64MSB:
3552 case R_IA64_PCREL64LSB:
3553 /* Install a dynamic relocation for this reloc. */
3554 if (dynamic_symbol_p
3555 )
3556 {
3557 BFD_ASSERT (srel != NULL);
3558
3559 elf64_ia64_install_dyn_reloc (output_bfd, info, input_section,
3560 srel, rel->r_offset, r_type,
3561 h->dynindx, rel->r_addend);
3562 }
3563 goto finish_pcrel;
3564
3565 case R_IA64_PCREL21BI:
3566 case R_IA64_PCREL21F:
3567 case R_IA64_PCREL21M:
3568 /* ??? These two are only used for speculation fixup code.
3569 They should never be dynamic. */
3570 if (dynamic_symbol_p)
3571 {
3572 (*_bfd_error_handler)
3573 (_("%s: dynamic relocation against speculation fixup"),
3574 bfd_get_filename (input_bfd));
3575 ret_val = false;
3576 continue;
3577 }
3578 if (undef_weak_ref)
3579 {
3580 (*_bfd_error_handler)
3581 (_("%s: speculation fixup against undefined weak symbol"),
3582 bfd_get_filename (input_bfd));
3583 ret_val = false;
3584 continue;
3585 }
3586 goto finish_pcrel;
3587
3588 case R_IA64_PCREL21B:
3589 case R_IA64_PCREL60B:
3590 /* We should have created a PLT entry for any dynamic symbol. */
3591 dyn_i = NULL;
3592 if (h)
3593 dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, false);
3594
3595 if (dyn_i && dyn_i->want_plt2)
3596 {
3597 /* Should have caught this earlier. */
3598 BFD_ASSERT (rel->r_addend == 0);
3599
3600 value = (ia64_info->plt_sec->output_section->vma
3601 + ia64_info->plt_sec->output_offset
3602 + dyn_i->plt2_offset);
3603 }
3604 else
3605 {
3606 /* Since there's no PLT entry, Validate that this is
3607 locally defined. */
3608 BFD_ASSERT (undef_weak_ref || sym_sec->output_section != NULL);
3609
3610 /* If the symbol is undef_weak, we shouldn't be trying
3611 to call it. There's every chance that we'd wind up
3612 with an out-of-range fixup here. Don't bother setting
3613 any value at all. */
3614 if (undef_weak_ref)
3615 continue;
3616 }
3617 goto finish_pcrel;
3618
3619 case R_IA64_PCREL22:
3620 case R_IA64_PCREL64I:
3621 finish_pcrel:
3622 /* Make pc-relative. */
3623 value -= (input_section->output_section->vma
3624 + input_section->output_offset
3625 + rel->r_offset) & ~ (bfd_vma) 0x3;
3626 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3627 break;
3628
3629 case R_IA64_SEGREL32MSB:
3630 case R_IA64_SEGREL32LSB:
3631 case R_IA64_SEGREL64MSB:
3632 case R_IA64_SEGREL64LSB:
3633 {
3634 struct elf_segment_map *m;
3635 Elf_Internal_Phdr *p;
3636
3637 /* Find the segment that contains the output_section. */
3638 for (m = elf_tdata (output_bfd)->segment_map,
3639 p = elf_tdata (output_bfd)->phdr;
3640 m != NULL;
3641 m = m->next, p++)
3642 {
3643 int i;
3644 for (i = m->count - 1; i >= 0; i--)
3645 if (m->sections[i] == sym_sec->output_section)
3646 break;
3647 if (i >= 0)
3648 break;
3649 }
3650
3651 if (m == NULL)
3652 {
3653 /* If the input section was discarded from the output, then
3654 do nothing. */
3655
3656 if (bfd_is_abs_section (sym_sec->output_section))
3657 r = bfd_reloc_ok;
3658 else
3659 r = bfd_reloc_notsupported;
3660 }
3661 else
3662 {
3663 /* The VMA of the segment is the vaddr of the associated
3664 program header. */
3665 if (value > p->p_vaddr)
3666 value -= p->p_vaddr;
3667 else
3668 value = 0;
3669 r = elf64_ia64_install_value (output_bfd, hit_addr, value,
3670 r_type);
3671 }
3672 break;
3673 }
3674
3675 case R_IA64_SECREL32MSB:
3676 case R_IA64_SECREL32LSB:
3677 case R_IA64_SECREL64MSB:
3678 case R_IA64_SECREL64LSB:
3679 /* Make output-section relative. */
3680 if (value > input_section->output_section->vma)
3681 value -= input_section->output_section->vma;
3682 else
3683 value = 0;
3684 r = elf64_ia64_install_value (output_bfd, hit_addr, value, r_type);
3685 break;
3686
3687 case R_IA64_SEGBASE:
3688
3689 case R_IA64_REL32MSB:
3690 case R_IA64_REL32LSB:
3691 case R_IA64_REL64MSB:
3692 case R_IA64_REL64LSB:
3693
3694 case R_IA64_IPLTMSB:
3695 case R_IA64_IPLTLSB:
3696 case R_IA64_EPLTMSB:
3697 case R_IA64_EPLTLSB:
3698 case R_IA64_COPY:
3699
3700 case R_IA64_TPREL22:
3701 case R_IA64_TPREL64MSB:
3702 case R_IA64_TPREL64LSB:
3703 case R_IA64_LTOFF_TP22:
3704 default:
3705 r = bfd_reloc_notsupported;
3706 break;
3707 }
3708
3709 switch (r)
3710 {
3711 case bfd_reloc_ok:
3712 break;
3713
3714 case bfd_reloc_undefined:
3715 /* This can happen for global table relative relocs if
3716 __gp is undefined. This is a panic situation so we
3717 don't try to continue. */
3718 (*info->callbacks->undefined_symbol)
3719 (info, "__gp", input_bfd, input_section, rel->r_offset, 1);
3720 return false;
3721
3722 case bfd_reloc_notsupported:
3723 {
3724 const char *name;
3725
3726 if (h)
3727 name = h->root.root.string;
3728 else
3729 {
3730 name = bfd_elf_string_from_elf_section (input_bfd,
3731 symtab_hdr->sh_link,
3732 sym->st_name);
3733 if (name == NULL)
3734 return false;
3735 if (*name == '\0')
3736 name = bfd_section_name (input_bfd, input_section);
3737 }
3738 if (!(*info->callbacks->warning) (info, _("unsupported reloc"),
3739 name, input_bfd,
3740 input_section, rel->r_offset))
3741 return false;
3742 ret_val = false;
3743 }
3744 break;
3745
3746 case bfd_reloc_dangerous:
3747 case bfd_reloc_outofrange:
3748 case bfd_reloc_overflow:
3749 default:
3750 {
3751 const char *name;
3752
3753 if (h)
3754 name = h->root.root.string;
3755 else
3756 {
3757 name = bfd_elf_string_from_elf_section (input_bfd,
3758 symtab_hdr->sh_link,
3759 sym->st_name);
3760 if (name == NULL)
3761 return false;
3762 if (*name == '\0')
3763 name = bfd_section_name (input_bfd, input_section);
3764 }
3765 if (!(*info->callbacks->reloc_overflow) (info, name,
3766 howto->name, 0,
3767 input_bfd,
3768 input_section,
3769 rel->r_offset))
3770 return false;
3771 ret_val = false;
3772 }
3773 break;
3774 }
3775 }
3776
3777 return ret_val;
3778}
3779
3780static boolean
3781elf64_ia64_finish_dynamic_symbol (output_bfd, info, h, sym)
3782 bfd *output_bfd;
3783 struct bfd_link_info *info;
3784 struct elf_link_hash_entry *h;
3785 Elf_Internal_Sym *sym;
3786{
3787 struct elf64_ia64_link_hash_table *ia64_info;
3788 struct elf64_ia64_dyn_sym_info *dyn_i;
3789
3790 ia64_info = elf64_ia64_hash_table (info);
3791 dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, false);
3792
3793 /* Fill in the PLT data, if required. */
3794 if (dyn_i && dyn_i->want_plt)
3795 {
3796 Elf_Internal_Rela outrel;
3797 bfd_byte *loc;
3798 asection *plt_sec;
3799 bfd_vma plt_addr, pltoff_addr, gp_val, index;
3800 Elf64_External_Rela *rel;
3801
3802 gp_val = _bfd_get_gp_value (output_bfd);
3803
3804 /* Initialize the minimal PLT entry. */
3805
3806 index = (dyn_i->plt_offset - PLT_HEADER_SIZE) / PLT_MIN_ENTRY_SIZE;
3807 plt_sec = ia64_info->plt_sec;
3808 loc = plt_sec->contents + dyn_i->plt_offset;
3809
3810 memcpy (loc, plt_min_entry, PLT_MIN_ENTRY_SIZE);
3811 elf64_ia64_install_value (output_bfd, loc, index, R_IA64_IMM22);
3812 elf64_ia64_install_value (output_bfd, loc+2, -dyn_i->plt_offset,
3813 R_IA64_PCREL21B);
3814
3815 plt_addr = (plt_sec->output_section->vma
3816 + plt_sec->output_offset
3817 + dyn_i->plt_offset);
3818 pltoff_addr = set_pltoff_entry (output_bfd, info, dyn_i, plt_addr, true);
3819
3820 /* Initialize the FULL PLT entry, if needed. */
3821 if (dyn_i->want_plt2)
3822 {
3823 loc = plt_sec->contents + dyn_i->plt2_offset;
3824
3825 memcpy (loc, plt_full_entry, PLT_FULL_ENTRY_SIZE);
3826 elf64_ia64_install_value (output_bfd, loc, pltoff_addr - gp_val,
3827 R_IA64_IMM22);
3828
3829 /* Mark the symbol as undefined, rather than as defined in the
3830 plt section. Leave the value alone. */
3831 /* ??? We didn't redefine it in adjust_dynamic_symbol in the
3832 first place. But perhaps elflink.h did some for us. */
3833 if ((h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR) == 0)
3834 sym->st_shndx = SHN_UNDEF;
3835 }
3836
3837 /* Create the dynamic relocation. */
3838 outrel.r_offset = pltoff_addr;
3839 if (bfd_little_endian (output_bfd))
3840 outrel.r_info = ELF64_R_INFO (h->dynindx, R_IA64_IPLTLSB);
3841 else
3842 outrel.r_info = ELF64_R_INFO (h->dynindx, R_IA64_IPLTMSB);
3843 outrel.r_addend = 0;
3844
3845 /* This is fun. In the .IA_64.pltoff section, we've got entries
3846 that correspond both to real PLT entries, and those that
3847 happened to resolve to local symbols but need to be created
3848 to satisfy @pltoff relocations. The .rela.IA_64.pltoff
3849 relocations for the real PLT should come at the end of the
3850 section, so that they can be indexed by plt entry at runtime.
3851
3852 We emitted all of the relocations for the non-PLT @pltoff
3853 entries during relocate_section. So we can consider the
3854 existing sec->reloc_count to be the base of the array of
3855 PLT relocations. */
3856
3857 rel = (Elf64_External_Rela *)ia64_info->rel_pltoff_sec->contents;
3858 rel += ia64_info->rel_pltoff_sec->reloc_count;
3859
3860 bfd_elf64_swap_reloca_out (output_bfd, &outrel, rel + index);
3861 }
3862
3863 /* Mark some specially defined symbols as absolute. */
3864 if (strcmp (h->root.root.string, "_DYNAMIC") == 0
3865 || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0
3866 || strcmp (h->root.root.string, "_PROCEDURE_LINKAGE_TABLE_") == 0)
3867 sym->st_shndx = SHN_ABS;
3868
3869 return true;
3870}
3871
3872static boolean
3873elf64_ia64_finish_dynamic_sections (abfd, info)
3874 bfd *abfd;
3875 struct bfd_link_info *info;
3876{
3877 struct elf64_ia64_link_hash_table *ia64_info;
3878 bfd *dynobj;
3879
3880 ia64_info = elf64_ia64_hash_table (info);
3881 dynobj = ia64_info->root.dynobj;
3882
3883 if (elf_hash_table (info)->dynamic_sections_created)
3884 {
3885 Elf64_External_Dyn *dyncon, *dynconend;
3886 asection *sdyn, *sgotplt;
3887 bfd_vma gp_val;
3888
3889 sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
3890 sgotplt = bfd_get_section_by_name (dynobj, ".got.plt");
3891 BFD_ASSERT (sdyn != NULL);
3892 dyncon = (Elf64_External_Dyn *) sdyn->contents;
3893 dynconend = (Elf64_External_Dyn *) (sdyn->contents + sdyn->_raw_size);
3894
3895 gp_val = _bfd_get_gp_value (abfd);
3896
3897 for (; dyncon < dynconend; dyncon++)
3898 {
3899 Elf_Internal_Dyn dyn;
3900 const char *name;
3901 asection *s;
3902
3903 bfd_elf64_swap_dyn_in (dynobj, dyncon, &dyn);
3904
3905 switch (dyn.d_tag)
3906 {
3907 case DT_PLTGOT:
3908 dyn.d_un.d_ptr = gp_val;
3909 break;
3910
3911 case DT_PLTRELSZ:
3912 dyn.d_un.d_val = (ia64_info->minplt_entries
3913 * sizeof (Elf64_External_Rela));
3914 break;
3915
3916 case DT_JMPREL:
3917 /* See the comment above in finish_dynamic_symbol. */
3918 dyn.d_un.d_ptr = (ia64_info->rel_pltoff_sec->output_section->vma
3919 + ia64_info->rel_pltoff_sec->output_offset
3920 + (ia64_info->rel_pltoff_sec->reloc_count
3921 * sizeof (Elf64_External_Rela)));
3922 break;
3923
3924 case DT_IA_64_PLT_RESERVE:
3925 dyn.d_un.d_ptr = (sgotplt->output_section->vma
3926 + sgotplt->output_offset);
3927 break;
3928
3929 case DT_RELASZ:
3930 /* Do not have RELASZ include JMPREL. This makes things
3931 easier on ld.so. This is not what the rest of BFD set up. */
3932 dyn.d_un.d_val -= (ia64_info->minplt_entries
3933 * sizeof (Elf64_External_Rela));
3934 break;
3935
3936 case DT_INIT:
3937 case DT_FINI:
3938 {
3939 struct elf_link_hash_entry *h;
3940 struct elf64_ia64_dyn_sym_info *dyn_i;
3941 const char *which;
3942
3943 if (dyn.d_tag == DT_INIT)
3944 which = info->init_function;
3945 else
3946 which = info->fini_function;
3947
3948 h = elf_link_hash_lookup (elf_hash_table (info), which,
3949 false, false, false);
3950 dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, false);
3951 dyn.d_un.d_ptr = set_pltoff_entry (abfd, info, dyn_i,
3952 dyn.d_un.d_ptr, 0);
3953 }
3954 }
3955
3956 bfd_elf64_swap_dyn_out (abfd, &dyn, dyncon);
3957 }
3958
3959 /* Initialize the PLT0 entry */
3960 if (ia64_info->plt_sec)
3961 {
3962 bfd_byte *loc = ia64_info->plt_sec->contents;
3963 bfd_vma pltres;
3964
3965 memcpy (loc, plt_header, PLT_HEADER_SIZE);
3966
3967 pltres = (sgotplt->output_section->vma
3968 + sgotplt->output_offset
3969 - gp_val);
3970
3971 elf64_ia64_install_value (abfd, loc+1, pltres, R_IA64_GPREL22);
3972 }
3973 }
3974
3975 return true;
3976}
3977\f
3978/* ELF file flag handling: */
3979
3980/* Function to keep IA-64 specific file flags. */
3981static boolean
3982elf64_ia64_set_private_flags (abfd, flags)
3983 bfd *abfd;
3984 flagword flags;
3985{
3986 BFD_ASSERT (!elf_flags_init (abfd)
3987 || elf_elfheader (abfd)->e_flags == flags);
3988
3989 elf_elfheader (abfd)->e_flags = flags;
3990 elf_flags_init (abfd) = true;
3991 return true;
3992}
3993
3994/* Copy backend specific data from one object module to another */
3995static boolean
3996elf64_ia64_copy_private_bfd_data (ibfd, obfd)
3997 bfd *ibfd, *obfd;
3998{
3999 if ( bfd_get_flavour (ibfd) != bfd_target_elf_flavour
4000 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
4001 return true;
4002
4003 BFD_ASSERT (!elf_flags_init (obfd)
4004 || (elf_elfheader (obfd)->e_flags
4005 == elf_elfheader (ibfd)->e_flags));
4006
4007 elf_elfheader (obfd)->e_flags = elf_elfheader (ibfd)->e_flags;
4008 elf_flags_init (obfd) = true;
4009 return true;
4010}
4011
4012/* Merge backend specific data from an object file to the output
4013 object file when linking. */
4014static boolean
4015elf64_ia64_merge_private_bfd_data (ibfd, obfd)
4016 bfd *ibfd, *obfd;
4017{
4018 flagword out_flags;
4019 flagword in_flags;
4020 boolean ok = true;
4021
4022 /* Don't even pretend to support mixed-format linking. */
4023 if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
4024 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
4025 return false;
4026
4027 in_flags = elf_elfheader (ibfd)->e_flags;
4028 out_flags = elf_elfheader (obfd)->e_flags;
4029
4030 if (! elf_flags_init (obfd))
4031 {
4032 elf_flags_init (obfd) = true;
4033 elf_elfheader (obfd)->e_flags = in_flags;
4034
4035 if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
4036 && bfd_get_arch_info (obfd)->the_default)
4037 {
4038 return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd),
4039 bfd_get_mach (ibfd));
4040 }
4041
4042 return true;
4043 }
4044
4045 /* Check flag compatibility. */
4046 if (in_flags == out_flags)
4047 return true;
4048
4049 /* Output has EF_IA_64_REDUCEDFP set only if all inputs have it set. */
4050 if (!(in_flags & EF_IA_64_REDUCEDFP) && (out_flags & EF_IA_64_REDUCEDFP))
4051 elf_elfheader (obfd)->e_flags &= ~EF_IA_64_REDUCEDFP;
4052
4053 if ((in_flags & EF_IA_64_TRAPNIL) != (out_flags & EF_IA_64_TRAPNIL))
4054 {
4055 (*_bfd_error_handler)
4056 (_("%s: linking trap-on-NULL-dereference with non-trapping files"),
4057 bfd_get_filename (ibfd));
4058
4059 bfd_set_error (bfd_error_bad_value);
4060 ok = false;
4061 }
4062 if ((in_flags & EF_IA_64_BE) != (out_flags & EF_IA_64_BE))
4063 {
4064 (*_bfd_error_handler)
4065 (_("%s: linking big-endian files with little-endian files"),
4066 bfd_get_filename (ibfd));
4067
4068 bfd_set_error (bfd_error_bad_value);
4069 ok = false;
4070 }
4071 if ((in_flags & EF_IA_64_ABI64) != (out_flags & EF_IA_64_ABI64))
4072 {
4073 (*_bfd_error_handler)
4074 (_("%s: linking 64-bit files with 32-bit files"),
4075 bfd_get_filename (ibfd));
4076
4077 bfd_set_error (bfd_error_bad_value);
4078 ok = false;
4079 }
4080 if ((in_flags & EF_IA_64_CONS_GP) != (out_flags & EF_IA_64_CONS_GP))
4081 {
4082 (*_bfd_error_handler)
4083 (_("%s: linking constant-gp files with non-constant-gp files"),
4084 bfd_get_filename (ibfd));
4085
4086 bfd_set_error (bfd_error_bad_value);
4087 ok = false;
4088 }
4089 if ((in_flags & EF_IA_64_NOFUNCDESC_CONS_GP)
4090 != (out_flags & EF_IA_64_NOFUNCDESC_CONS_GP))
4091 {
4092 (*_bfd_error_handler)
4093 (_("%s: linking auto-pic files with non-auto-pic files"),
4094 bfd_get_filename (ibfd));
4095
4096 bfd_set_error (bfd_error_bad_value);
4097 ok = false;
4098 }
4099
4100 return ok;
4101}
4102
4103static boolean
4104elf64_ia64_print_private_bfd_data (abfd, ptr)
4105 bfd *abfd;
4106 PTR ptr;
4107{
4108 FILE *file = (FILE *) ptr;
4109 flagword flags = elf_elfheader (abfd)->e_flags;
4110
4111 BFD_ASSERT (abfd != NULL && ptr != NULL);
4112
4113 fprintf (file, "private flags = %s%s%s%s%s%s%s%s\n",
4114 (flags & EF_IA_64_TRAPNIL) ? "TRAPNIL, " : "",
4115 (flags & EF_IA_64_EXT) ? "EXT, " : "",
4116 (flags & EF_IA_64_BE) ? "BE, " : "LE, ",
4117 (flags & EF_IA_64_REDUCEDFP) ? "REDUCEDFP, " : "",
4118 (flags & EF_IA_64_CONS_GP) ? "CONS_GP, " : "",
4119 (flags & EF_IA_64_NOFUNCDESC_CONS_GP) ? "NOFUNCDESC_CONS_GP, " : "",
4120 (flags & EF_IA_64_ABSOLUTE) ? "ABSOLUTE, " : "",
4121 (flags & EF_IA_64_ABI64) ? "ABI64" : "ABI32");
4122
4123 _bfd_elf_print_private_bfd_data (abfd, ptr);
4124 return true;
4125}
4126\f
4127#define TARGET_LITTLE_SYM bfd_elf64_ia64_little_vec
4128#define TARGET_LITTLE_NAME "elf64-ia64-little"
4129#define TARGET_BIG_SYM bfd_elf64_ia64_big_vec
4130#define TARGET_BIG_NAME "elf64-ia64-big"
4131#define ELF_ARCH bfd_arch_ia64
4132#define ELF_MACHINE_CODE EM_IA_64
4133#define ELF_MACHINE_ALT1 1999 /* EAS2.3 */
4134#define ELF_MACHINE_ALT2 1998 /* EAS2.2 */
4135#define ELF_MAXPAGESIZE 0x10000 /* 64KB */
4136
4137#define elf_backend_section_from_shdr \
4138 elf64_ia64_section_from_shdr
4139#define elf_backend_section_flags \
4140 elf64_ia64_section_flags
4141#define elf_backend_fake_sections \
4142 elf64_ia64_fake_sections
4143#define elf_backend_add_symbol_hook \
4144 elf64_ia64_add_symbol_hook
4145#define elf_backend_additional_program_headers \
4146 elf64_ia64_additional_program_headers
4147#define elf_backend_modify_segment_map \
4148 elf64_ia64_modify_segment_map
4149#define elf_info_to_howto \
4150 elf64_ia64_info_to_howto
4151
4152#define bfd_elf64_bfd_reloc_type_lookup \
4153 elf64_ia64_reloc_type_lookup
4154#define bfd_elf64_bfd_is_local_label_name \
4155 elf64_ia64_is_local_label_name
4156#define bfd_elf64_bfd_relax_section \
4157 elf64_ia64_relax_section
4158
4159/* Stuff for the BFD linker: */
4160#define bfd_elf64_bfd_link_hash_table_create \
4161 elf64_ia64_hash_table_create
4162#define elf_backend_create_dynamic_sections \
4163 elf64_ia64_create_dynamic_sections
4164#define elf_backend_check_relocs \
4165 elf64_ia64_check_relocs
4166#define elf_backend_adjust_dynamic_symbol \
4167 elf64_ia64_adjust_dynamic_symbol
4168#define elf_backend_size_dynamic_sections \
4169 elf64_ia64_size_dynamic_sections
4170#define elf_backend_relocate_section \
4171 elf64_ia64_relocate_section
4172#define elf_backend_finish_dynamic_symbol \
4173 elf64_ia64_finish_dynamic_symbol
4174#define elf_backend_finish_dynamic_sections \
4175 elf64_ia64_finish_dynamic_sections
4176#define bfd_elf64_bfd_final_link \
4177 elf64_ia64_final_link
4178
4179#define bfd_elf64_bfd_copy_private_bfd_data \
4180 elf64_ia64_copy_private_bfd_data
4181#define bfd_elf64_bfd_merge_private_bfd_data \
4182 elf64_ia64_merge_private_bfd_data
4183#define bfd_elf64_bfd_set_private_flags \
4184 elf64_ia64_set_private_flags
4185#define bfd_elf64_bfd_print_private_bfd_data \
4186 elf64_ia64_print_private_bfd_data
4187
4188#define elf_backend_plt_readonly 1
4189#define elf_backend_want_plt_sym 0
4190#define elf_backend_plt_alignment 5
4191#define elf_backend_got_header_size 0
4192#define elf_backend_plt_header_size PLT_HEADER_SIZE
4193#define elf_backend_want_got_plt 1
4194#define elf_backend_may_use_rel_p 1
4195#define elf_backend_may_use_rela_p 1
4196#define elf_backend_default_use_rela_p 1
4197#define elf_backend_want_dynbss 0
4198#define elf_backend_copy_indirect_symbol elf64_ia64_hash_copy_indirect
4199#define elf_backend_hide_symbol elf64_ia64_hash_hide_symbol
4200
4201#include "elf64-target.h"
This page took 0.175858 seconds and 4 git commands to generate.