1 /* IA-64 support for 64-bit ELF
2 Copyright 1998, 1999, 2000, 2001, 2002 Free Software Foundation, Inc.
3 Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
5 This file is part of BFD, the Binary File Descriptor library.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
25 #include "opcode/ia64.h"
28 /* THE RULES for all the stuff the linker creates --
30 GOT Entries created in response to LTOFF or LTOFF_FPTR
31 relocations. Dynamic relocs created for dynamic
32 symbols in an application; REL relocs for locals
35 FPTR The canonical function descriptor. Created for local
36 symbols in applications. Descriptors for dynamic symbols
37 and local symbols in shared libraries are created by
38 ld.so. Thus there are no dynamic relocs against these
39 objects. The FPTR relocs for such _are_ passed through
40 to the dynamic relocation tables.
42 FULL_PLT Created for a PCREL21B relocation against a dynamic symbol.
43 Requires the creation of a PLTOFF entry. This does not
44 require any dynamic relocations.
46 PLTOFF Created by PLTOFF relocations. For local symbols, this
47 is an alternate function descriptor, and in shared libraries
48 requires two REL relocations. Note that this cannot be
49 transformed into an FPTR relocation, since it must be in
50 range of the GP. For dynamic symbols, this is a function
51 descriptor for a MIN_PLT entry, and requires one IPLT reloc.
53 MIN_PLT Created by PLTOFF entries against dynamic symbols. This
54 does not reqire dynamic relocations. */
56 #define NELEMS(a) ((int) (sizeof (a) / sizeof ((a)[0])))
58 typedef struct bfd_hash_entry
*(*new_hash_entry_func
)
59 PARAMS ((struct bfd_hash_entry
*, struct bfd_hash_table
*, const char *));
61 /* In dynamically (linker-) created sections, we generally need to keep track
62 of the place a symbol or expression got allocated to. This is done via hash
63 tables that store entries of the following type. */
65 struct elfNN_ia64_dyn_sym_info
67 /* The addend for which this entry is relevant. */
70 /* Next addend in the list. */
71 struct elfNN_ia64_dyn_sym_info
*next
;
75 bfd_vma pltoff_offset
;
79 bfd_vma dtpmod_offset
;
80 bfd_vma dtprel_offset
;
82 /* The symbol table entry, if any, that this was derrived from. */
83 struct elf_link_hash_entry
*h
;
85 /* Used to count non-got, non-plt relocations for delayed sizing
86 of relocation sections. */
87 struct elfNN_ia64_dyn_reloc_entry
89 struct elfNN_ia64_dyn_reloc_entry
*next
;
95 /* True when the section contents have been updated. */
96 unsigned got_done
: 1;
97 unsigned fptr_done
: 1;
98 unsigned pltoff_done
: 1;
99 unsigned tprel_done
: 1;
100 unsigned dtpmod_done
: 1;
101 unsigned dtprel_done
: 1;
103 /* True for the different kinds of linker data we want created. */
104 unsigned want_got
: 1;
105 unsigned want_fptr
: 1;
106 unsigned want_ltoff_fptr
: 1;
107 unsigned want_plt
: 1;
108 unsigned want_plt2
: 1;
109 unsigned want_pltoff
: 1;
110 unsigned want_tprel
: 1;
111 unsigned want_dtpmod
: 1;
112 unsigned want_dtprel
: 1;
115 struct elfNN_ia64_local_hash_entry
117 struct bfd_hash_entry root
;
118 struct elfNN_ia64_dyn_sym_info
*info
;
120 /* True if this hash entry's addends was translated for
121 SHF_MERGE optimization. */
122 unsigned sec_merge_done
: 1;
125 struct elfNN_ia64_local_hash_table
127 struct bfd_hash_table root
;
128 /* No additional fields for now. */
131 struct elfNN_ia64_link_hash_entry
133 struct elf_link_hash_entry root
;
134 struct elfNN_ia64_dyn_sym_info
*info
;
137 struct elfNN_ia64_link_hash_table
139 /* The main hash table. */
140 struct elf_link_hash_table root
;
142 asection
*got_sec
; /* the linkage table section (or NULL) */
143 asection
*rel_got_sec
; /* dynamic relocation section for same */
144 asection
*fptr_sec
; /* function descriptor table (or NULL) */
145 asection
*plt_sec
; /* the primary plt section (or NULL) */
146 asection
*pltoff_sec
; /* private descriptors for plt (or NULL) */
147 asection
*rel_pltoff_sec
; /* dynamic relocation section for same */
149 bfd_size_type minplt_entries
; /* number of minplt entries */
150 unsigned reltext
: 1; /* are there relocs against readonly sections? */
152 struct elfNN_ia64_local_hash_table loc_hash_table
;
155 #define elfNN_ia64_hash_table(p) \
156 ((struct elfNN_ia64_link_hash_table *) ((p)->hash))
158 static bfd_reloc_status_type elfNN_ia64_reloc
159 PARAMS ((bfd
*abfd
, arelent
*reloc
, asymbol
*sym
, PTR data
,
160 asection
*input_section
, bfd
*output_bfd
, char **error_message
));
161 static reloc_howto_type
* lookup_howto
162 PARAMS ((unsigned int rtype
));
163 static reloc_howto_type
*elfNN_ia64_reloc_type_lookup
164 PARAMS ((bfd
*abfd
, bfd_reloc_code_real_type bfd_code
));
165 static void elfNN_ia64_info_to_howto
166 PARAMS ((bfd
*abfd
, arelent
*bfd_reloc
, ElfNN_Internal_Rela
*elf_reloc
));
167 static boolean elfNN_ia64_relax_section
168 PARAMS((bfd
*abfd
, asection
*sec
, struct bfd_link_info
*link_info
,
170 static boolean is_unwind_section_name
171 PARAMS ((bfd
*abfd
, const char *));
172 static boolean elfNN_ia64_section_from_shdr
173 PARAMS ((bfd
*, ElfNN_Internal_Shdr
*, const char *));
174 static boolean elfNN_ia64_section_flags
175 PARAMS ((flagword
*, ElfNN_Internal_Shdr
*));
176 static boolean elfNN_ia64_fake_sections
177 PARAMS ((bfd
*abfd
, ElfNN_Internal_Shdr
*hdr
, asection
*sec
));
178 static void elfNN_ia64_final_write_processing
179 PARAMS ((bfd
*abfd
, boolean linker
));
180 static boolean elfNN_ia64_add_symbol_hook
181 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
, const Elf_Internal_Sym
*sym
,
182 const char **namep
, flagword
*flagsp
, asection
**secp
,
184 static boolean elfNN_ia64_aix_vec
185 PARAMS ((const bfd_target
*vec
));
186 static boolean elfNN_ia64_aix_add_symbol_hook
187 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
, const Elf_Internal_Sym
*sym
,
188 const char **namep
, flagword
*flagsp
, asection
**secp
,
190 static boolean elfNN_ia64_aix_link_add_symbols
191 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
));
192 static int elfNN_ia64_additional_program_headers
193 PARAMS ((bfd
*abfd
));
194 static boolean elfNN_ia64_modify_segment_map
196 static boolean elfNN_ia64_is_local_label_name
197 PARAMS ((bfd
*abfd
, const char *name
));
198 static boolean elfNN_ia64_dynamic_symbol_p
199 PARAMS ((struct elf_link_hash_entry
*h
, struct bfd_link_info
*info
));
200 static boolean elfNN_ia64_local_hash_table_init
201 PARAMS ((struct elfNN_ia64_local_hash_table
*ht
, bfd
*abfd
,
202 new_hash_entry_func
new));
203 static struct bfd_hash_entry
*elfNN_ia64_new_loc_hash_entry
204 PARAMS ((struct bfd_hash_entry
*entry
, struct bfd_hash_table
*table
,
205 const char *string
));
206 static struct bfd_hash_entry
*elfNN_ia64_new_elf_hash_entry
207 PARAMS ((struct bfd_hash_entry
*entry
, struct bfd_hash_table
*table
,
208 const char *string
));
209 static void elfNN_ia64_hash_copy_indirect
210 PARAMS ((struct elf_link_hash_entry
*, struct elf_link_hash_entry
*));
211 static void elfNN_ia64_hash_hide_symbol
212 PARAMS ((struct bfd_link_info
*, struct elf_link_hash_entry
*, boolean
));
213 static struct bfd_link_hash_table
*elfNN_ia64_hash_table_create
214 PARAMS ((bfd
*abfd
));
215 static struct elfNN_ia64_local_hash_entry
*elfNN_ia64_local_hash_lookup
216 PARAMS ((struct elfNN_ia64_local_hash_table
*table
, const char *string
,
217 boolean create
, boolean copy
));
218 static boolean elfNN_ia64_global_dyn_sym_thunk
219 PARAMS ((struct bfd_hash_entry
*, PTR
));
220 static boolean elfNN_ia64_local_dyn_sym_thunk
221 PARAMS ((struct bfd_hash_entry
*, PTR
));
222 static void elfNN_ia64_dyn_sym_traverse
223 PARAMS ((struct elfNN_ia64_link_hash_table
*ia64_info
,
224 boolean (*func
) (struct elfNN_ia64_dyn_sym_info
*, PTR
),
226 static boolean elfNN_ia64_create_dynamic_sections
227 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
));
228 static struct elfNN_ia64_local_hash_entry
* get_local_sym_hash
229 PARAMS ((struct elfNN_ia64_link_hash_table
*ia64_info
,
230 bfd
*abfd
, const Elf_Internal_Rela
*rel
, boolean create
));
231 static struct elfNN_ia64_dyn_sym_info
* get_dyn_sym_info
232 PARAMS ((struct elfNN_ia64_link_hash_table
*ia64_info
,
233 struct elf_link_hash_entry
*h
,
234 bfd
*abfd
, const Elf_Internal_Rela
*rel
, boolean create
));
235 static asection
*get_got
236 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
237 struct elfNN_ia64_link_hash_table
*ia64_info
));
238 static asection
*get_fptr
239 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
240 struct elfNN_ia64_link_hash_table
*ia64_info
));
241 static asection
*get_pltoff
242 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
243 struct elfNN_ia64_link_hash_table
*ia64_info
));
244 static asection
*get_reloc_section
245 PARAMS ((bfd
*abfd
, struct elfNN_ia64_link_hash_table
*ia64_info
,
246 asection
*sec
, boolean create
));
247 static boolean count_dyn_reloc
248 PARAMS ((bfd
*abfd
, struct elfNN_ia64_dyn_sym_info
*dyn_i
,
249 asection
*srel
, int type
));
250 static boolean elfNN_ia64_check_relocs
251 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
, asection
*sec
,
252 const Elf_Internal_Rela
*relocs
));
253 static boolean elfNN_ia64_adjust_dynamic_symbol
254 PARAMS ((struct bfd_link_info
*info
, struct elf_link_hash_entry
*h
));
255 static long global_sym_index
256 PARAMS ((struct elf_link_hash_entry
*h
));
257 static boolean allocate_fptr
258 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
259 static boolean allocate_global_data_got
260 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
261 static boolean allocate_global_fptr_got
262 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
263 static boolean allocate_local_got
264 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
265 static boolean allocate_pltoff_entries
266 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
267 static boolean allocate_plt_entries
268 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
269 static boolean allocate_plt2_entries
270 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
271 static boolean allocate_dynrel_entries
272 PARAMS ((struct elfNN_ia64_dyn_sym_info
*dyn_i
, PTR data
));
273 static boolean elfNN_ia64_size_dynamic_sections
274 PARAMS ((bfd
*output_bfd
, struct bfd_link_info
*info
));
275 static bfd_reloc_status_type elfNN_ia64_install_value
276 PARAMS ((bfd
*abfd
, bfd_byte
*hit_addr
, bfd_vma val
, unsigned int r_type
));
277 static void elfNN_ia64_install_dyn_reloc
278 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
, asection
*sec
,
279 asection
*srel
, bfd_vma offset
, unsigned int type
,
280 long dynindx
, bfd_vma addend
));
281 static bfd_vma set_got_entry
282 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
283 struct elfNN_ia64_dyn_sym_info
*dyn_i
, long dynindx
,
284 bfd_vma addend
, bfd_vma value
, unsigned int dyn_r_type
));
285 static bfd_vma set_fptr_entry
286 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
287 struct elfNN_ia64_dyn_sym_info
*dyn_i
,
289 static bfd_vma set_pltoff_entry
290 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
,
291 struct elfNN_ia64_dyn_sym_info
*dyn_i
,
292 bfd_vma value
, boolean
));
293 static bfd_vma elfNN_ia64_tprel_base
294 PARAMS ((struct bfd_link_info
*info
));
295 static bfd_vma elfNN_ia64_dtprel_base
296 PARAMS ((struct bfd_link_info
*info
));
297 static int elfNN_ia64_unwind_entry_compare
298 PARAMS ((const PTR
, const PTR
));
299 static boolean elfNN_ia64_final_link
300 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
));
301 static boolean elfNN_ia64_relocate_section
302 PARAMS ((bfd
*output_bfd
, struct bfd_link_info
*info
, bfd
*input_bfd
,
303 asection
*input_section
, bfd_byte
*contents
,
304 Elf_Internal_Rela
*relocs
, Elf_Internal_Sym
*local_syms
,
305 asection
**local_sections
));
306 static boolean elfNN_ia64_finish_dynamic_symbol
307 PARAMS ((bfd
*output_bfd
, struct bfd_link_info
*info
,
308 struct elf_link_hash_entry
*h
, Elf_Internal_Sym
*sym
));
309 static boolean elfNN_ia64_finish_dynamic_sections
310 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
));
311 static boolean elfNN_ia64_set_private_flags
312 PARAMS ((bfd
*abfd
, flagword flags
));
313 static boolean elfNN_ia64_merge_private_bfd_data
314 PARAMS ((bfd
*ibfd
, bfd
*obfd
));
315 static boolean elfNN_ia64_print_private_bfd_data
316 PARAMS ((bfd
*abfd
, PTR ptr
));
317 static enum elf_reloc_type_class elfNN_ia64_reloc_type_class
318 PARAMS ((const Elf_Internal_Rela
*));
319 static boolean elfNN_ia64_hpux_vec
320 PARAMS ((const bfd_target
*vec
));
321 static void elfNN_hpux_post_process_headers
322 PARAMS ((bfd
*abfd
, struct bfd_link_info
*info
));
323 boolean elfNN_hpux_backend_section_from_bfd_section
324 PARAMS ((bfd
*abfd
, asection
*sec
, int *retval
));
326 /* ia64-specific relocation. */
328 /* Perform a relocation. Not much to do here as all the hard work is
329 done in elfNN_ia64_final_link_relocate. */
330 static bfd_reloc_status_type
331 elfNN_ia64_reloc (abfd
, reloc
, sym
, data
, input_section
,
332 output_bfd
, error_message
)
333 bfd
*abfd ATTRIBUTE_UNUSED
;
335 asymbol
*sym ATTRIBUTE_UNUSED
;
336 PTR data ATTRIBUTE_UNUSED
;
337 asection
*input_section
;
339 char **error_message
;
343 reloc
->address
+= input_section
->output_offset
;
346 *error_message
= "Unsupported call to elfNN_ia64_reloc";
347 return bfd_reloc_notsupported
;
350 #define IA64_HOWTO(TYPE, NAME, SIZE, PCREL, IN) \
351 HOWTO (TYPE, 0, SIZE, 0, PCREL, 0, complain_overflow_signed, \
352 elfNN_ia64_reloc, NAME, false, 0, 0, IN)
354 /* This table has to be sorted according to increasing number of the
356 static reloc_howto_type ia64_howto_table
[] =
358 IA64_HOWTO (R_IA64_NONE
, "NONE", 0, false, true),
360 IA64_HOWTO (R_IA64_IMM14
, "IMM14", 0, false, true),
361 IA64_HOWTO (R_IA64_IMM22
, "IMM22", 0, false, true),
362 IA64_HOWTO (R_IA64_IMM64
, "IMM64", 0, false, true),
363 IA64_HOWTO (R_IA64_DIR32MSB
, "DIR32MSB", 2, false, true),
364 IA64_HOWTO (R_IA64_DIR32LSB
, "DIR32LSB", 2, false, true),
365 IA64_HOWTO (R_IA64_DIR64MSB
, "DIR64MSB", 4, false, true),
366 IA64_HOWTO (R_IA64_DIR64LSB
, "DIR64LSB", 4, false, true),
368 IA64_HOWTO (R_IA64_GPREL22
, "GPREL22", 0, false, true),
369 IA64_HOWTO (R_IA64_GPREL64I
, "GPREL64I", 0, false, true),
370 IA64_HOWTO (R_IA64_GPREL32MSB
, "GPREL32MSB", 2, false, true),
371 IA64_HOWTO (R_IA64_GPREL32LSB
, "GPREL32LSB", 2, false, true),
372 IA64_HOWTO (R_IA64_GPREL64MSB
, "GPREL64MSB", 4, false, true),
373 IA64_HOWTO (R_IA64_GPREL64LSB
, "GPREL64LSB", 4, false, true),
375 IA64_HOWTO (R_IA64_LTOFF22
, "LTOFF22", 0, false, true),
376 IA64_HOWTO (R_IA64_LTOFF64I
, "LTOFF64I", 0, false, true),
378 IA64_HOWTO (R_IA64_PLTOFF22
, "PLTOFF22", 0, false, true),
379 IA64_HOWTO (R_IA64_PLTOFF64I
, "PLTOFF64I", 0, false, true),
380 IA64_HOWTO (R_IA64_PLTOFF64MSB
, "PLTOFF64MSB", 4, false, true),
381 IA64_HOWTO (R_IA64_PLTOFF64LSB
, "PLTOFF64LSB", 4, false, true),
383 IA64_HOWTO (R_IA64_FPTR64I
, "FPTR64I", 0, false, true),
384 IA64_HOWTO (R_IA64_FPTR32MSB
, "FPTR32MSB", 2, false, true),
385 IA64_HOWTO (R_IA64_FPTR32LSB
, "FPTR32LSB", 2, false, true),
386 IA64_HOWTO (R_IA64_FPTR64MSB
, "FPTR64MSB", 4, false, true),
387 IA64_HOWTO (R_IA64_FPTR64LSB
, "FPTR64LSB", 4, false, true),
389 IA64_HOWTO (R_IA64_PCREL60B
, "PCREL60B", 0, true, true),
390 IA64_HOWTO (R_IA64_PCREL21B
, "PCREL21B", 0, true, true),
391 IA64_HOWTO (R_IA64_PCREL21M
, "PCREL21M", 0, true, true),
392 IA64_HOWTO (R_IA64_PCREL21F
, "PCREL21F", 0, true, true),
393 IA64_HOWTO (R_IA64_PCREL32MSB
, "PCREL32MSB", 2, true, true),
394 IA64_HOWTO (R_IA64_PCREL32LSB
, "PCREL32LSB", 2, true, true),
395 IA64_HOWTO (R_IA64_PCREL64MSB
, "PCREL64MSB", 4, true, true),
396 IA64_HOWTO (R_IA64_PCREL64LSB
, "PCREL64LSB", 4, true, true),
398 IA64_HOWTO (R_IA64_LTOFF_FPTR22
, "LTOFF_FPTR22", 0, false, true),
399 IA64_HOWTO (R_IA64_LTOFF_FPTR64I
, "LTOFF_FPTR64I", 0, false, true),
400 IA64_HOWTO (R_IA64_LTOFF_FPTR32MSB
, "LTOFF_FPTR32MSB", 2, false, true),
401 IA64_HOWTO (R_IA64_LTOFF_FPTR32LSB
, "LTOFF_FPTR32LSB", 2, false, true),
402 IA64_HOWTO (R_IA64_LTOFF_FPTR64MSB
, "LTOFF_FPTR64MSB", 4, false, true),
403 IA64_HOWTO (R_IA64_LTOFF_FPTR64LSB
, "LTOFF_FPTR64LSB", 4, false, true),
405 IA64_HOWTO (R_IA64_SEGREL32MSB
, "SEGREL32MSB", 2, false, true),
406 IA64_HOWTO (R_IA64_SEGREL32LSB
, "SEGREL32LSB", 2, false, true),
407 IA64_HOWTO (R_IA64_SEGREL64MSB
, "SEGREL64MSB", 4, false, true),
408 IA64_HOWTO (R_IA64_SEGREL64LSB
, "SEGREL64LSB", 4, false, true),
410 IA64_HOWTO (R_IA64_SECREL32MSB
, "SECREL32MSB", 2, false, true),
411 IA64_HOWTO (R_IA64_SECREL32LSB
, "SECREL32LSB", 2, false, true),
412 IA64_HOWTO (R_IA64_SECREL64MSB
, "SECREL64MSB", 4, false, true),
413 IA64_HOWTO (R_IA64_SECREL64LSB
, "SECREL64LSB", 4, false, true),
415 IA64_HOWTO (R_IA64_REL32MSB
, "REL32MSB", 2, false, true),
416 IA64_HOWTO (R_IA64_REL32LSB
, "REL32LSB", 2, false, true),
417 IA64_HOWTO (R_IA64_REL64MSB
, "REL64MSB", 4, false, true),
418 IA64_HOWTO (R_IA64_REL64LSB
, "REL64LSB", 4, false, true),
420 IA64_HOWTO (R_IA64_LTV32MSB
, "LTV32MSB", 2, false, true),
421 IA64_HOWTO (R_IA64_LTV32LSB
, "LTV32LSB", 2, false, true),
422 IA64_HOWTO (R_IA64_LTV64MSB
, "LTV64MSB", 4, false, true),
423 IA64_HOWTO (R_IA64_LTV64LSB
, "LTV64LSB", 4, false, true),
425 IA64_HOWTO (R_IA64_PCREL21BI
, "PCREL21BI", 0, true, true),
426 IA64_HOWTO (R_IA64_PCREL22
, "PCREL22", 0, true, true),
427 IA64_HOWTO (R_IA64_PCREL64I
, "PCREL64I", 0, true, true),
429 IA64_HOWTO (R_IA64_IPLTMSB
, "IPLTMSB", 4, false, true),
430 IA64_HOWTO (R_IA64_IPLTLSB
, "IPLTLSB", 4, false, true),
431 IA64_HOWTO (R_IA64_COPY
, "COPY", 4, false, true),
432 IA64_HOWTO (R_IA64_LTOFF22X
, "LTOFF22X", 0, false, true),
433 IA64_HOWTO (R_IA64_LDXMOV
, "LDXMOV", 0, false, true),
435 IA64_HOWTO (R_IA64_TPREL14
, "TPREL14", 0, false, false),
436 IA64_HOWTO (R_IA64_TPREL22
, "TPREL22", 0, false, false),
437 IA64_HOWTO (R_IA64_TPREL64I
, "TPREL64I", 0, false, false),
438 IA64_HOWTO (R_IA64_TPREL64MSB
, "TPREL64MSB", 8, false, false),
439 IA64_HOWTO (R_IA64_TPREL64LSB
, "TPREL64LSB", 8, false, false),
440 IA64_HOWTO (R_IA64_LTOFF_TPREL22
, "LTOFF_TPREL22", 0, false, false),
442 IA64_HOWTO (R_IA64_DTPMOD64MSB
, "TPREL64MSB", 8, false, false),
443 IA64_HOWTO (R_IA64_DTPMOD64LSB
, "TPREL64LSB", 8, false, false),
444 IA64_HOWTO (R_IA64_LTOFF_DTPMOD22
, "LTOFF_DTPMOD22", 0, false, false),
446 IA64_HOWTO (R_IA64_DTPREL14
, "DTPREL14", 0, false, false),
447 IA64_HOWTO (R_IA64_DTPREL22
, "DTPREL22", 0, false, false),
448 IA64_HOWTO (R_IA64_DTPREL64I
, "DTPREL64I", 0, false, false),
449 IA64_HOWTO (R_IA64_DTPREL32MSB
, "DTPREL32MSB", 4, false, false),
450 IA64_HOWTO (R_IA64_DTPREL32LSB
, "DTPREL32LSB", 4, false, false),
451 IA64_HOWTO (R_IA64_DTPREL64MSB
, "DTPREL64MSB", 8, false, false),
452 IA64_HOWTO (R_IA64_DTPREL64LSB
, "DTPREL64LSB", 8, false, false),
453 IA64_HOWTO (R_IA64_LTOFF_DTPREL22
, "LTOFF_DTPREL22", 0, false, false),
456 static unsigned char elf_code_to_howto_index
[R_IA64_MAX_RELOC_CODE
+ 1];
458 /* Given a BFD reloc type, return the matching HOWTO structure. */
460 static reloc_howto_type
*
464 static int inited
= 0;
471 memset (elf_code_to_howto_index
, 0xff, sizeof (elf_code_to_howto_index
));
472 for (i
= 0; i
< NELEMS (ia64_howto_table
); ++i
)
473 elf_code_to_howto_index
[ia64_howto_table
[i
].type
] = i
;
476 BFD_ASSERT (rtype
<= R_IA64_MAX_RELOC_CODE
);
477 i
= elf_code_to_howto_index
[rtype
];
478 if (i
>= NELEMS (ia64_howto_table
))
480 return ia64_howto_table
+ i
;
483 static reloc_howto_type
*
484 elfNN_ia64_reloc_type_lookup (abfd
, bfd_code
)
485 bfd
*abfd ATTRIBUTE_UNUSED
;
486 bfd_reloc_code_real_type bfd_code
;
492 case BFD_RELOC_NONE
: rtype
= R_IA64_NONE
; break;
494 case BFD_RELOC_IA64_IMM14
: rtype
= R_IA64_IMM14
; break;
495 case BFD_RELOC_IA64_IMM22
: rtype
= R_IA64_IMM22
; break;
496 case BFD_RELOC_IA64_IMM64
: rtype
= R_IA64_IMM64
; break;
498 case BFD_RELOC_IA64_DIR32MSB
: rtype
= R_IA64_DIR32MSB
; break;
499 case BFD_RELOC_IA64_DIR32LSB
: rtype
= R_IA64_DIR32LSB
; break;
500 case BFD_RELOC_IA64_DIR64MSB
: rtype
= R_IA64_DIR64MSB
; break;
501 case BFD_RELOC_IA64_DIR64LSB
: rtype
= R_IA64_DIR64LSB
; break;
503 case BFD_RELOC_IA64_GPREL22
: rtype
= R_IA64_GPREL22
; break;
504 case BFD_RELOC_IA64_GPREL64I
: rtype
= R_IA64_GPREL64I
; break;
505 case BFD_RELOC_IA64_GPREL32MSB
: rtype
= R_IA64_GPREL32MSB
; break;
506 case BFD_RELOC_IA64_GPREL32LSB
: rtype
= R_IA64_GPREL32LSB
; break;
507 case BFD_RELOC_IA64_GPREL64MSB
: rtype
= R_IA64_GPREL64MSB
; break;
508 case BFD_RELOC_IA64_GPREL64LSB
: rtype
= R_IA64_GPREL64LSB
; break;
510 case BFD_RELOC_IA64_LTOFF22
: rtype
= R_IA64_LTOFF22
; break;
511 case BFD_RELOC_IA64_LTOFF64I
: rtype
= R_IA64_LTOFF64I
; break;
513 case BFD_RELOC_IA64_PLTOFF22
: rtype
= R_IA64_PLTOFF22
; break;
514 case BFD_RELOC_IA64_PLTOFF64I
: rtype
= R_IA64_PLTOFF64I
; break;
515 case BFD_RELOC_IA64_PLTOFF64MSB
: rtype
= R_IA64_PLTOFF64MSB
; break;
516 case BFD_RELOC_IA64_PLTOFF64LSB
: rtype
= R_IA64_PLTOFF64LSB
; break;
517 case BFD_RELOC_IA64_FPTR64I
: rtype
= R_IA64_FPTR64I
; break;
518 case BFD_RELOC_IA64_FPTR32MSB
: rtype
= R_IA64_FPTR32MSB
; break;
519 case BFD_RELOC_IA64_FPTR32LSB
: rtype
= R_IA64_FPTR32LSB
; break;
520 case BFD_RELOC_IA64_FPTR64MSB
: rtype
= R_IA64_FPTR64MSB
; break;
521 case BFD_RELOC_IA64_FPTR64LSB
: rtype
= R_IA64_FPTR64LSB
; break;
523 case BFD_RELOC_IA64_PCREL21B
: rtype
= R_IA64_PCREL21B
; break;
524 case BFD_RELOC_IA64_PCREL21BI
: rtype
= R_IA64_PCREL21BI
; break;
525 case BFD_RELOC_IA64_PCREL21M
: rtype
= R_IA64_PCREL21M
; break;
526 case BFD_RELOC_IA64_PCREL21F
: rtype
= R_IA64_PCREL21F
; break;
527 case BFD_RELOC_IA64_PCREL22
: rtype
= R_IA64_PCREL22
; break;
528 case BFD_RELOC_IA64_PCREL60B
: rtype
= R_IA64_PCREL60B
; break;
529 case BFD_RELOC_IA64_PCREL64I
: rtype
= R_IA64_PCREL64I
; break;
530 case BFD_RELOC_IA64_PCREL32MSB
: rtype
= R_IA64_PCREL32MSB
; break;
531 case BFD_RELOC_IA64_PCREL32LSB
: rtype
= R_IA64_PCREL32LSB
; break;
532 case BFD_RELOC_IA64_PCREL64MSB
: rtype
= R_IA64_PCREL64MSB
; break;
533 case BFD_RELOC_IA64_PCREL64LSB
: rtype
= R_IA64_PCREL64LSB
; break;
535 case BFD_RELOC_IA64_LTOFF_FPTR22
: rtype
= R_IA64_LTOFF_FPTR22
; break;
536 case BFD_RELOC_IA64_LTOFF_FPTR64I
: rtype
= R_IA64_LTOFF_FPTR64I
; break;
537 case BFD_RELOC_IA64_LTOFF_FPTR32MSB
: rtype
= R_IA64_LTOFF_FPTR32MSB
; break;
538 case BFD_RELOC_IA64_LTOFF_FPTR32LSB
: rtype
= R_IA64_LTOFF_FPTR32LSB
; break;
539 case BFD_RELOC_IA64_LTOFF_FPTR64MSB
: rtype
= R_IA64_LTOFF_FPTR64MSB
; break;
540 case BFD_RELOC_IA64_LTOFF_FPTR64LSB
: rtype
= R_IA64_LTOFF_FPTR64LSB
; break;
542 case BFD_RELOC_IA64_SEGREL32MSB
: rtype
= R_IA64_SEGREL32MSB
; break;
543 case BFD_RELOC_IA64_SEGREL32LSB
: rtype
= R_IA64_SEGREL32LSB
; break;
544 case BFD_RELOC_IA64_SEGREL64MSB
: rtype
= R_IA64_SEGREL64MSB
; break;
545 case BFD_RELOC_IA64_SEGREL64LSB
: rtype
= R_IA64_SEGREL64LSB
; break;
547 case BFD_RELOC_IA64_SECREL32MSB
: rtype
= R_IA64_SECREL32MSB
; break;
548 case BFD_RELOC_IA64_SECREL32LSB
: rtype
= R_IA64_SECREL32LSB
; break;
549 case BFD_RELOC_IA64_SECREL64MSB
: rtype
= R_IA64_SECREL64MSB
; break;
550 case BFD_RELOC_IA64_SECREL64LSB
: rtype
= R_IA64_SECREL64LSB
; break;
552 case BFD_RELOC_IA64_REL32MSB
: rtype
= R_IA64_REL32MSB
; break;
553 case BFD_RELOC_IA64_REL32LSB
: rtype
= R_IA64_REL32LSB
; break;
554 case BFD_RELOC_IA64_REL64MSB
: rtype
= R_IA64_REL64MSB
; break;
555 case BFD_RELOC_IA64_REL64LSB
: rtype
= R_IA64_REL64LSB
; break;
557 case BFD_RELOC_IA64_LTV32MSB
: rtype
= R_IA64_LTV32MSB
; break;
558 case BFD_RELOC_IA64_LTV32LSB
: rtype
= R_IA64_LTV32LSB
; break;
559 case BFD_RELOC_IA64_LTV64MSB
: rtype
= R_IA64_LTV64MSB
; break;
560 case BFD_RELOC_IA64_LTV64LSB
: rtype
= R_IA64_LTV64LSB
; break;
562 case BFD_RELOC_IA64_IPLTMSB
: rtype
= R_IA64_IPLTMSB
; break;
563 case BFD_RELOC_IA64_IPLTLSB
: rtype
= R_IA64_IPLTLSB
; break;
564 case BFD_RELOC_IA64_COPY
: rtype
= R_IA64_COPY
; break;
565 case BFD_RELOC_IA64_LTOFF22X
: rtype
= R_IA64_LTOFF22X
; break;
566 case BFD_RELOC_IA64_LDXMOV
: rtype
= R_IA64_LDXMOV
; break;
568 case BFD_RELOC_IA64_TPREL14
: rtype
= R_IA64_TPREL14
; break;
569 case BFD_RELOC_IA64_TPREL22
: rtype
= R_IA64_TPREL22
; break;
570 case BFD_RELOC_IA64_TPREL64I
: rtype
= R_IA64_TPREL64I
; break;
571 case BFD_RELOC_IA64_TPREL64MSB
: rtype
= R_IA64_TPREL64MSB
; break;
572 case BFD_RELOC_IA64_TPREL64LSB
: rtype
= R_IA64_TPREL64LSB
; break;
573 case BFD_RELOC_IA64_LTOFF_TPREL22
: rtype
= R_IA64_LTOFF_TPREL22
; break;
575 case BFD_RELOC_IA64_DTPMOD64MSB
: rtype
= R_IA64_DTPMOD64MSB
; break;
576 case BFD_RELOC_IA64_DTPMOD64LSB
: rtype
= R_IA64_DTPMOD64LSB
; break;
577 case BFD_RELOC_IA64_LTOFF_DTPMOD22
: rtype
= R_IA64_LTOFF_DTPMOD22
; break;
579 case BFD_RELOC_IA64_DTPREL14
: rtype
= R_IA64_DTPREL14
; break;
580 case BFD_RELOC_IA64_DTPREL22
: rtype
= R_IA64_DTPREL22
; break;
581 case BFD_RELOC_IA64_DTPREL64I
: rtype
= R_IA64_DTPREL64I
; break;
582 case BFD_RELOC_IA64_DTPREL32MSB
: rtype
= R_IA64_DTPREL32MSB
; break;
583 case BFD_RELOC_IA64_DTPREL32LSB
: rtype
= R_IA64_DTPREL32LSB
; break;
584 case BFD_RELOC_IA64_DTPREL64MSB
: rtype
= R_IA64_DTPREL64MSB
; break;
585 case BFD_RELOC_IA64_DTPREL64LSB
: rtype
= R_IA64_DTPREL64LSB
; break;
586 case BFD_RELOC_IA64_LTOFF_DTPREL22
: rtype
= R_IA64_LTOFF_DTPREL22
; break;
590 return lookup_howto (rtype
);
593 /* Given a ELF reloc, return the matching HOWTO structure. */
596 elfNN_ia64_info_to_howto (abfd
, bfd_reloc
, elf_reloc
)
597 bfd
*abfd ATTRIBUTE_UNUSED
;
599 ElfNN_Internal_Rela
*elf_reloc
;
602 = lookup_howto ((unsigned int) ELFNN_R_TYPE (elf_reloc
->r_info
));
605 #define PLT_HEADER_SIZE (3 * 16)
606 #define PLT_MIN_ENTRY_SIZE (1 * 16)
607 #define PLT_FULL_ENTRY_SIZE (2 * 16)
608 #define PLT_RESERVED_WORDS 3
610 static const bfd_byte plt_header
[PLT_HEADER_SIZE
] =
612 0x0b, 0x10, 0x00, 0x1c, 0x00, 0x21, /* [MMI] mov r2=r14;; */
613 0xe0, 0x00, 0x08, 0x00, 0x48, 0x00, /* addl r14=0,r2 */
614 0x00, 0x00, 0x04, 0x00, /* nop.i 0x0;; */
615 0x0b, 0x80, 0x20, 0x1c, 0x18, 0x14, /* [MMI] ld8 r16=[r14],8;; */
616 0x10, 0x41, 0x38, 0x30, 0x28, 0x00, /* ld8 r17=[r14],8 */
617 0x00, 0x00, 0x04, 0x00, /* nop.i 0x0;; */
618 0x11, 0x08, 0x00, 0x1c, 0x18, 0x10, /* [MIB] ld8 r1=[r14] */
619 0x60, 0x88, 0x04, 0x80, 0x03, 0x00, /* mov b6=r17 */
620 0x60, 0x00, 0x80, 0x00 /* br.few b6;; */
623 static const bfd_byte plt_min_entry
[PLT_MIN_ENTRY_SIZE
] =
625 0x11, 0x78, 0x00, 0x00, 0x00, 0x24, /* [MIB] mov r15=0 */
626 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, /* nop.i 0x0 */
627 0x00, 0x00, 0x00, 0x40 /* br.few 0 <PLT0>;; */
630 static const bfd_byte plt_full_entry
[PLT_FULL_ENTRY_SIZE
] =
632 0x0b, 0x78, 0x00, 0x02, 0x00, 0x24, /* [MMI] addl r15=0,r1;; */
633 0x00, 0x41, 0x3c, 0x30, 0x28, 0xc0, /* ld8 r16=[r15],8 */
634 0x01, 0x08, 0x00, 0x84, /* mov r14=r1;; */
635 0x11, 0x08, 0x00, 0x1e, 0x18, 0x10, /* [MIB] ld8 r1=[r15] */
636 0x60, 0x80, 0x04, 0x80, 0x03, 0x00, /* mov b6=r16 */
637 0x60, 0x00, 0x80, 0x00 /* br.few b6;; */
640 #define ELF_DYNAMIC_INTERPRETER "/usr/lib/ld.so.1"
641 #define AIX_DYNAMIC_INTERPRETER "/usr/lib/ia64l64/libc.so.1"
642 #define DYNAMIC_INTERPRETER(abfd) \
643 (elfNN_ia64_aix_vec (abfd->xvec) ? AIX_DYNAMIC_INTERPRETER : ELF_DYNAMIC_INTERPRETER)
645 /* Select out of range branch fixup type. Note that Itanium does
646 not support brl, and so it gets emulated by the kernel. */
649 static const bfd_byte oor_brl
[16] =
651 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MLX] nop.m 0 */
652 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* brl.sptk.few tgt;; */
653 0x00, 0x00, 0x00, 0xc0
656 static const bfd_byte oor_ip
[48] =
658 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MLX] nop.m 0 */
659 0x00, 0x00, 0x00, 0x00, 0x00, 0xe0, /* movl r15=0 */
660 0x01, 0x00, 0x00, 0x60,
661 0x03, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MII] nop.m 0 */
662 0x00, 0x01, 0x00, 0x60, 0x00, 0x00, /* mov r16=ip;; */
663 0xf2, 0x80, 0x00, 0x80, /* add r16=r15,r16;; */
664 0x11, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MIB] nop.m 0 */
665 0x60, 0x80, 0x04, 0x80, 0x03, 0x00, /* mov b6=r16 */
666 0x60, 0x00, 0x80, 0x00 /* br b6;; */
669 /* These functions do relaxation for IA-64 ELF.
671 This is primarily to support branches to targets out of range;
672 relaxation of R_IA64_LTOFF22X and R_IA64_LDXMOV not yet supported. */
675 elfNN_ia64_relax_section (abfd
, sec
, link_info
, again
)
678 struct bfd_link_info
*link_info
;
683 struct one_fixup
*next
;
689 Elf_Internal_Shdr
*symtab_hdr
;
690 Elf_Internal_Rela
*internal_relocs
;
691 Elf_Internal_Rela
*irel
, *irelend
;
693 Elf_Internal_Sym
*isymbuf
= NULL
;
694 struct elfNN_ia64_link_hash_table
*ia64_info
;
695 struct one_fixup
*fixups
= NULL
;
696 boolean changed_contents
= false;
697 boolean changed_relocs
= false;
699 /* Assume we're not going to change any sizes, and we'll only need
703 /* Nothing to do if there are no relocations. */
704 if ((sec
->flags
& SEC_RELOC
) == 0
705 || sec
->reloc_count
== 0)
708 /* If this is the first time we have been called for this section,
709 initialize the cooked size. */
710 if (sec
->_cooked_size
== 0)
711 sec
->_cooked_size
= sec
->_raw_size
;
713 symtab_hdr
= &elf_tdata (abfd
)->symtab_hdr
;
715 /* Load the relocations for this section. */
716 internal_relocs
= (_bfd_elfNN_link_read_relocs
717 (abfd
, sec
, (PTR
) NULL
, (Elf_Internal_Rela
*) NULL
,
718 link_info
->keep_memory
));
719 if (internal_relocs
== NULL
)
722 ia64_info
= elfNN_ia64_hash_table (link_info
);
723 irelend
= internal_relocs
+ sec
->reloc_count
;
725 for (irel
= internal_relocs
; irel
< irelend
; irel
++)
726 if (ELFNN_R_TYPE (irel
->r_info
) == (int) R_IA64_PCREL21B
)
729 /* No branch-type relocations. */
732 if (elf_section_data (sec
)->relocs
!= internal_relocs
)
733 free (internal_relocs
);
737 /* Get the section contents. */
738 if (elf_section_data (sec
)->this_hdr
.contents
!= NULL
)
739 contents
= elf_section_data (sec
)->this_hdr
.contents
;
742 contents
= (bfd_byte
*) bfd_malloc (sec
->_raw_size
);
743 if (contents
== NULL
)
746 if (! bfd_get_section_contents (abfd
, sec
, contents
,
747 (file_ptr
) 0, sec
->_raw_size
))
751 for (; irel
< irelend
; irel
++)
753 bfd_vma symaddr
, reladdr
, trampoff
, toff
, roff
;
758 if (ELFNN_R_TYPE (irel
->r_info
) != (int) R_IA64_PCREL21B
)
761 /* Get the value of the symbol referred to by the reloc. */
762 if (ELFNN_R_SYM (irel
->r_info
) < symtab_hdr
->sh_info
)
764 /* A local symbol. */
765 Elf_Internal_Sym
*isym
;
767 /* Read this BFD's local symbols. */
770 isymbuf
= (Elf_Internal_Sym
*) symtab_hdr
->contents
;
772 isymbuf
= bfd_elf_get_elf_syms (abfd
, symtab_hdr
,
773 symtab_hdr
->sh_info
, 0,
779 isym
= isymbuf
+ ELF64_R_SYM (irel
->r_info
);
780 if (isym
->st_shndx
== SHN_UNDEF
)
781 continue; /* We can't do anthing with undefined symbols. */
782 else if (isym
->st_shndx
== SHN_ABS
)
783 tsec
= bfd_abs_section_ptr
;
784 else if (isym
->st_shndx
== SHN_COMMON
)
785 tsec
= bfd_com_section_ptr
;
786 else if (isym
->st_shndx
== SHN_IA_64_ANSI_COMMON
)
787 tsec
= bfd_com_section_ptr
;
789 tsec
= bfd_section_from_elf_index (abfd
, isym
->st_shndx
);
791 toff
= isym
->st_value
;
796 struct elf_link_hash_entry
*h
;
797 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
799 indx
= ELFNN_R_SYM (irel
->r_info
) - symtab_hdr
->sh_info
;
800 h
= elf_sym_hashes (abfd
)[indx
];
801 BFD_ASSERT (h
!= NULL
);
803 while (h
->root
.type
== bfd_link_hash_indirect
804 || h
->root
.type
== bfd_link_hash_warning
)
805 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
807 dyn_i
= get_dyn_sym_info (ia64_info
, h
, abfd
, irel
, false);
809 /* For branches to dynamic symbols, we're interested instead
810 in a branch to the PLT entry. */
811 if (dyn_i
&& dyn_i
->want_plt2
)
813 tsec
= ia64_info
->plt_sec
;
814 toff
= dyn_i
->plt2_offset
;
818 /* We can't do anthing with undefined symbols. */
819 if (h
->root
.type
== bfd_link_hash_undefined
820 || h
->root
.type
== bfd_link_hash_undefweak
)
823 tsec
= h
->root
.u
.def
.section
;
824 toff
= h
->root
.u
.def
.value
;
828 symaddr
= (tsec
->output_section
->vma
829 + tsec
->output_offset
833 roff
= irel
->r_offset
;
834 reladdr
= (sec
->output_section
->vma
836 + roff
) & (bfd_vma
) -4;
838 /* If the branch is in range, no need to do anything. */
839 if ((bfd_signed_vma
) (symaddr
- reladdr
) >= -0x1000000
840 && (bfd_signed_vma
) (symaddr
- reladdr
) <= 0x0FFFFF0)
843 /* If the branch and target are in the same section, you've
844 got one honking big section and we can't help you. You'll
845 get an error message later. */
849 /* Look for an existing fixup to this address. */
850 for (f
= fixups
; f
; f
= f
->next
)
851 if (f
->tsec
== tsec
&& f
->toff
== toff
)
856 /* Two alternatives: If it's a branch to a PLT entry, we can
857 make a copy of the FULL_PLT entry. Otherwise, we'll have
858 to use a `brl' insn to get where we're going. */
862 if (tsec
== ia64_info
->plt_sec
)
863 size
= sizeof (plt_full_entry
);
867 size
= sizeof (oor_brl
);
869 size
= sizeof (oor_ip
);
873 /* Resize the current section to make room for the new branch. */
874 trampoff
= (sec
->_cooked_size
+ 15) & (bfd_vma
) -16;
875 amt
= trampoff
+ size
;
876 contents
= (bfd_byte
*) bfd_realloc (contents
, amt
);
877 if (contents
== NULL
)
879 sec
->_cooked_size
= amt
;
881 if (tsec
== ia64_info
->plt_sec
)
883 memcpy (contents
+ trampoff
, plt_full_entry
, size
);
885 /* Hijack the old relocation for use as the PLTOFF reloc. */
886 irel
->r_info
= ELFNN_R_INFO (ELFNN_R_SYM (irel
->r_info
),
888 irel
->r_offset
= trampoff
;
893 memcpy (contents
+ trampoff
, oor_brl
, size
);
894 irel
->r_info
= ELFNN_R_INFO (ELFNN_R_SYM (irel
->r_info
),
896 irel
->r_offset
= trampoff
+ 2;
898 memcpy (contents
+ trampoff
, oor_ip
, size
);
899 irel
->r_info
= ELFNN_R_INFO (ELFNN_R_SYM (irel
->r_info
),
901 irel
->r_addend
-= 16;
902 irel
->r_offset
= trampoff
+ 2;
906 /* Record the fixup so we don't do it again this section. */
907 f
= (struct one_fixup
*) bfd_malloc ((bfd_size_type
) sizeof (*f
));
911 f
->trampoff
= trampoff
;
916 /* Nop out the reloc, since we're finalizing things here. */
917 irel
->r_info
= ELFNN_R_INFO (0, R_IA64_NONE
);
920 /* Fix up the existing branch to hit the trampoline. Hope like
921 hell this doesn't overflow too. */
922 if (elfNN_ia64_install_value (abfd
, contents
+ roff
,
923 f
->trampoff
- (roff
& (bfd_vma
) -4),
924 R_IA64_PCREL21B
) != bfd_reloc_ok
)
927 changed_contents
= true;
928 changed_relocs
= true;
931 /* Clean up and go home. */
934 struct one_fixup
*f
= fixups
;
935 fixups
= fixups
->next
;
940 && symtab_hdr
->contents
!= (unsigned char *) isymbuf
)
942 if (! link_info
->keep_memory
)
946 /* Cache the symbols for elf_link_input_bfd. */
947 symtab_hdr
->contents
= (unsigned char *) isymbuf
;
952 && elf_section_data (sec
)->this_hdr
.contents
!= contents
)
954 if (!changed_contents
&& !link_info
->keep_memory
)
958 /* Cache the section contents for elf_link_input_bfd. */
959 elf_section_data (sec
)->this_hdr
.contents
= contents
;
963 if (elf_section_data (sec
)->relocs
!= internal_relocs
)
966 free (internal_relocs
);
968 elf_section_data (sec
)->relocs
= internal_relocs
;
971 *again
= changed_contents
|| changed_relocs
;
975 if (isymbuf
!= NULL
&& (unsigned char *) isymbuf
!= symtab_hdr
->contents
)
978 && elf_section_data (sec
)->this_hdr
.contents
!= contents
)
980 if (internal_relocs
!= NULL
981 && elf_section_data (sec
)->relocs
!= internal_relocs
)
982 free (internal_relocs
);
986 /* Return true if NAME is an unwind table section name. */
988 static inline boolean
989 is_unwind_section_name (abfd
, name
)
993 size_t len1
, len2
, len3
;
995 if (elfNN_ia64_hpux_vec (abfd
->xvec
)
996 && !strcmp (name
, ELF_STRING_ia64_unwind_hdr
))
999 len1
= sizeof (ELF_STRING_ia64_unwind
) - 1;
1000 len2
= sizeof (ELF_STRING_ia64_unwind_info
) - 1;
1001 len3
= sizeof (ELF_STRING_ia64_unwind_once
) - 1;
1002 return ((strncmp (name
, ELF_STRING_ia64_unwind
, len1
) == 0
1003 && strncmp (name
, ELF_STRING_ia64_unwind_info
, len2
) != 0)
1004 || strncmp (name
, ELF_STRING_ia64_unwind_once
, len3
) == 0);
1007 /* Handle an IA-64 specific section when reading an object file. This
1008 is called when elfcode.h finds a section with an unknown type. */
1011 elfNN_ia64_section_from_shdr (abfd
, hdr
, name
)
1013 ElfNN_Internal_Shdr
*hdr
;
1018 /* There ought to be a place to keep ELF backend specific flags, but
1019 at the moment there isn't one. We just keep track of the
1020 sections by their name, instead. Fortunately, the ABI gives
1021 suggested names for all the MIPS specific sections, so we will
1022 probably get away with this. */
1023 switch (hdr
->sh_type
)
1025 case SHT_IA_64_UNWIND
:
1026 case SHT_IA_64_HP_OPT_ANOT
:
1030 if (strcmp (name
, ELF_STRING_ia64_archext
) != 0)
1038 if (! _bfd_elf_make_section_from_shdr (abfd
, hdr
, name
))
1040 newsect
= hdr
->bfd_section
;
1045 /* Convert IA-64 specific section flags to bfd internal section flags. */
1047 /* ??? There is no bfd internal flag equivalent to the SHF_IA_64_NORECOV
1051 elfNN_ia64_section_flags (flags
, hdr
)
1053 ElfNN_Internal_Shdr
*hdr
;
1055 if (hdr
->sh_flags
& SHF_IA_64_SHORT
)
1056 *flags
|= SEC_SMALL_DATA
;
1061 /* Set the correct type for an IA-64 ELF section. We do this by the
1062 section name, which is a hack, but ought to work. */
1065 elfNN_ia64_fake_sections (abfd
, hdr
, sec
)
1066 bfd
*abfd ATTRIBUTE_UNUSED
;
1067 ElfNN_Internal_Shdr
*hdr
;
1070 register const char *name
;
1072 name
= bfd_get_section_name (abfd
, sec
);
1074 if (is_unwind_section_name (abfd
, name
))
1076 /* We don't have the sections numbered at this point, so sh_info
1077 is set later, in elfNN_ia64_final_write_processing. */
1078 hdr
->sh_type
= SHT_IA_64_UNWIND
;
1079 hdr
->sh_flags
|= SHF_LINK_ORDER
;
1081 else if (strcmp (name
, ELF_STRING_ia64_archext
) == 0)
1082 hdr
->sh_type
= SHT_IA_64_EXT
;
1083 else if (strcmp (name
, ".HP.opt_annot") == 0)
1084 hdr
->sh_type
= SHT_IA_64_HP_OPT_ANOT
;
1085 else if (strcmp (name
, ".reloc") == 0)
1086 /* This is an ugly, but unfortunately necessary hack that is
1087 needed when producing EFI binaries on IA-64. It tells
1088 elf.c:elf_fake_sections() not to consider ".reloc" as a section
1089 containing ELF relocation info. We need this hack in order to
1090 be able to generate ELF binaries that can be translated into
1091 EFI applications (which are essentially COFF objects). Those
1092 files contain a COFF ".reloc" section inside an ELFNN object,
1093 which would normally cause BFD to segfault because it would
1094 attempt to interpret this section as containing relocation
1095 entries for section "oc". With this hack enabled, ".reloc"
1096 will be treated as a normal data section, which will avoid the
1097 segfault. However, you won't be able to create an ELFNN binary
1098 with a section named "oc" that needs relocations, but that's
1099 the kind of ugly side-effects you get when detecting section
1100 types based on their names... In practice, this limitation is
1101 unlikely to bite. */
1102 hdr
->sh_type
= SHT_PROGBITS
;
1104 if (sec
->flags
& SEC_SMALL_DATA
)
1105 hdr
->sh_flags
|= SHF_IA_64_SHORT
;
1110 /* The final processing done just before writing out an IA-64 ELF
1114 elfNN_ia64_final_write_processing (abfd
, linker
)
1116 boolean linker ATTRIBUTE_UNUSED
;
1118 Elf_Internal_Shdr
*hdr
;
1120 asection
*text_sect
, *s
;
1123 for (s
= abfd
->sections
; s
; s
= s
->next
)
1125 hdr
= &elf_section_data (s
)->this_hdr
;
1126 switch (hdr
->sh_type
)
1128 case SHT_IA_64_UNWIND
:
1129 /* See comments in gas/config/tc-ia64.c:dot_endp on why we
1131 sname
= bfd_get_section_name (abfd
, s
);
1132 len
= sizeof (ELF_STRING_ia64_unwind
) - 1;
1133 if (sname
&& strncmp (sname
, ELF_STRING_ia64_unwind
, len
) == 0)
1137 if (sname
[0] == '\0')
1138 /* .IA_64.unwind -> .text */
1139 text_sect
= bfd_get_section_by_name (abfd
, ".text");
1141 /* .IA_64.unwindFOO -> FOO */
1142 text_sect
= bfd_get_section_by_name (abfd
, sname
);
1145 && (len
= sizeof (ELF_STRING_ia64_unwind_once
) - 1,
1146 strncmp (sname
, ELF_STRING_ia64_unwind_once
, len
)) == 0)
1148 /* .gnu.linkonce.ia64unw.FOO -> .gnu.linkonce.t.FOO */
1149 size_t len2
= sizeof (".gnu.linkonce.t.") - 1;
1150 char *once_name
= bfd_malloc (len2
+ strlen (sname
+ len
) + 1);
1152 if (once_name
!= NULL
)
1154 memcpy (once_name
, ".gnu.linkonce.t.", len2
);
1155 strcpy (once_name
+ len2
, sname
+ len
);
1156 text_sect
= bfd_get_section_by_name (abfd
, once_name
);
1160 /* Should only happen if we run out of memory, in
1161 which case we're probably toast anyway. Try to
1162 cope by finding the section the slow way. */
1163 for (text_sect
= abfd
->sections
;
1165 text_sect
= text_sect
->next
)
1167 if (strncmp (bfd_section_name (abfd
, text_sect
),
1168 ".gnu.linkonce.t.", len2
) == 0
1169 && strcmp (bfd_section_name (abfd
, text_sect
) + len2
,
1175 /* last resort: fall back on .text */
1176 text_sect
= bfd_get_section_by_name (abfd
, ".text");
1180 /* The IA-64 processor-specific ABI requires setting
1181 sh_link to the unwind section, whereas HP-UX requires
1182 sh_info to do so. For maximum compatibility, we'll
1183 set both for now... */
1184 hdr
->sh_link
= elf_section_data (text_sect
)->this_idx
;
1185 hdr
->sh_info
= elf_section_data (text_sect
)->this_idx
;
1191 if (! elf_flags_init (abfd
))
1193 unsigned long flags
= 0;
1195 if (abfd
->xvec
->byteorder
== BFD_ENDIAN_BIG
)
1196 flags
|= EF_IA_64_BE
;
1197 if (bfd_get_mach (abfd
) == bfd_mach_ia64_elf64
)
1198 flags
|= EF_IA_64_ABI64
;
1200 elf_elfheader(abfd
)->e_flags
= flags
;
1201 elf_flags_init (abfd
) = true;
1205 /* Hook called by the linker routine which adds symbols from an object
1206 file. We use it to put .comm items in .sbss, and not .bss. */
1209 elfNN_ia64_add_symbol_hook (abfd
, info
, sym
, namep
, flagsp
, secp
, valp
)
1211 struct bfd_link_info
*info
;
1212 const Elf_Internal_Sym
*sym
;
1213 const char **namep ATTRIBUTE_UNUSED
;
1214 flagword
*flagsp ATTRIBUTE_UNUSED
;
1218 if (sym
->st_shndx
== SHN_COMMON
1219 && !info
->relocateable
1220 && sym
->st_size
<= elf_gp_size (abfd
))
1222 /* Common symbols less than or equal to -G nn bytes are
1223 automatically put into .sbss. */
1225 asection
*scomm
= bfd_get_section_by_name (abfd
, ".scommon");
1229 scomm
= bfd_make_section (abfd
, ".scommon");
1231 || !bfd_set_section_flags (abfd
, scomm
, (SEC_ALLOC
1233 | SEC_LINKER_CREATED
)))
1238 *valp
= sym
->st_size
;
1245 elfNN_ia64_aix_vec (const bfd_target
*vec
)
1247 extern const bfd_target bfd_elfNN_ia64_aix_little_vec
;
1248 extern const bfd_target bfd_elfNN_ia64_aix_big_vec
;
1250 return (/**/vec
== & bfd_elfNN_ia64_aix_little_vec
1251 || vec
== & bfd_elfNN_ia64_aix_big_vec
);
1254 /* Hook called by the linker routine which adds symbols from an object
1255 file. We use it to handle OS-specific symbols. */
1258 elfNN_ia64_aix_add_symbol_hook (abfd
, info
, sym
, namep
, flagsp
, secp
, valp
)
1260 struct bfd_link_info
*info
;
1261 const Elf_Internal_Sym
*sym
;
1267 if (strcmp (*namep
, "__GLOB_DATA_PTR") == 0)
1269 /* Define __GLOB_DATA_PTR when it is encountered. This is expected to
1270 be a linker-defined symbol by the Aix C runtime startup code. IBM sez
1271 no one else should use it b/c it is undocumented. */
1272 struct elf_link_hash_entry
*h
;
1274 h
= elf_link_hash_lookup (elf_hash_table (info
), *namep
,
1275 false, false, false);
1278 struct elf_backend_data
*bed
;
1279 struct elfNN_ia64_link_hash_table
*ia64_info
;
1281 bed
= get_elf_backend_data (abfd
);
1282 ia64_info
= elfNN_ia64_hash_table (info
);
1284 if (!(_bfd_generic_link_add_one_symbol
1285 (info
, abfd
, *namep
, BSF_GLOBAL
,
1286 bfd_get_section_by_name (abfd
, ".bss"),
1287 bed
->got_symbol_offset
, (const char *) NULL
, false,
1288 bed
->collect
, (struct bfd_link_hash_entry
**) &h
)))
1291 h
->elf_link_hash_flags
|= ELF_LINK_HASH_DEF_REGULAR
;
1292 h
->type
= STT_OBJECT
;
1294 if (! _bfd_elf_link_record_dynamic_symbol (info
, h
))
1300 else if (sym
->st_shndx
== SHN_LOOS
)
1304 /* SHN_AIX_SYSCALL: Treat this as any other symbol. The special symbol
1305 is only relevant when compiling code for extended system calls.
1306 Replace the "special" section with .text, if possible.
1307 Note that these symbols are always assumed to be in .text. */
1308 for (i
= 1; i
< elf_numsections (abfd
); i
++)
1310 asection
* sec
= bfd_section_from_elf_index (abfd
, i
);
1312 if (sec
&& strcmp (sec
->name
, ".text") == 0)
1320 *secp
= bfd_abs_section_ptr
;
1322 *valp
= sym
->st_size
;
1328 return elfNN_ia64_add_symbol_hook (abfd
, info
, sym
,
1329 namep
, flagsp
, secp
, valp
);
1334 elfNN_ia64_aix_link_add_symbols (abfd
, info
)
1336 struct bfd_link_info
*info
;
1338 /* Make sure dynamic sections are always created. */
1339 if (! elf_hash_table (info
)->dynamic_sections_created
1340 && abfd
->xvec
== info
->hash
->creator
)
1342 if (! bfd_elfNN_link_create_dynamic_sections (abfd
, info
))
1346 /* Now do the standard call. */
1347 return bfd_elfNN_bfd_link_add_symbols (abfd
, info
);
1350 /* Return the number of additional phdrs we will need. */
1353 elfNN_ia64_additional_program_headers (abfd
)
1359 /* See if we need a PT_IA_64_ARCHEXT segment. */
1360 s
= bfd_get_section_by_name (abfd
, ELF_STRING_ia64_archext
);
1361 if (s
&& (s
->flags
& SEC_LOAD
))
1364 /* Count how many PT_IA_64_UNWIND segments we need. */
1365 for (s
= abfd
->sections
; s
; s
= s
->next
)
1366 if (is_unwind_section_name (abfd
, s
->name
) && (s
->flags
& SEC_LOAD
))
1373 elfNN_ia64_modify_segment_map (abfd
)
1376 struct elf_segment_map
*m
, **pm
;
1377 Elf_Internal_Shdr
*hdr
;
1380 /* If we need a PT_IA_64_ARCHEXT segment, it must come before
1381 all PT_LOAD segments. */
1382 s
= bfd_get_section_by_name (abfd
, ELF_STRING_ia64_archext
);
1383 if (s
&& (s
->flags
& SEC_LOAD
))
1385 for (m
= elf_tdata (abfd
)->segment_map
; m
!= NULL
; m
= m
->next
)
1386 if (m
->p_type
== PT_IA_64_ARCHEXT
)
1390 m
= ((struct elf_segment_map
*)
1391 bfd_zalloc (abfd
, (bfd_size_type
) sizeof *m
));
1395 m
->p_type
= PT_IA_64_ARCHEXT
;
1399 /* We want to put it after the PHDR and INTERP segments. */
1400 pm
= &elf_tdata (abfd
)->segment_map
;
1402 && ((*pm
)->p_type
== PT_PHDR
1403 || (*pm
)->p_type
== PT_INTERP
))
1411 /* Install PT_IA_64_UNWIND segments, if needed. */
1412 for (s
= abfd
->sections
; s
; s
= s
->next
)
1414 hdr
= &elf_section_data (s
)->this_hdr
;
1415 if (hdr
->sh_type
!= SHT_IA_64_UNWIND
)
1418 if (s
&& (s
->flags
& SEC_LOAD
))
1420 for (m
= elf_tdata (abfd
)->segment_map
; m
!= NULL
; m
= m
->next
)
1421 if (m
->p_type
== PT_IA_64_UNWIND
)
1425 /* Look through all sections in the unwind segment
1426 for a match since there may be multiple sections
1428 for (i
= m
->count
- 1; i
>= 0; --i
)
1429 if (m
->sections
[i
] == s
)
1438 m
= ((struct elf_segment_map
*)
1439 bfd_zalloc (abfd
, (bfd_size_type
) sizeof *m
));
1443 m
->p_type
= PT_IA_64_UNWIND
;
1448 /* We want to put it last. */
1449 pm
= &elf_tdata (abfd
)->segment_map
;
1457 /* Turn on PF_IA_64_NORECOV if needed. This involves traversing all of
1458 the input sections for each output section in the segment and testing
1459 for SHF_IA_64_NORECOV on each. */
1460 for (m
= elf_tdata (abfd
)->segment_map
; m
!= NULL
; m
= m
->next
)
1461 if (m
->p_type
== PT_LOAD
)
1464 for (i
= m
->count
- 1; i
>= 0; --i
)
1466 struct bfd_link_order
*order
= m
->sections
[i
]->link_order_head
;
1469 if (order
->type
== bfd_indirect_link_order
)
1471 asection
*is
= order
->u
.indirect
.section
;
1472 bfd_vma flags
= elf_section_data(is
)->this_hdr
.sh_flags
;
1473 if (flags
& SHF_IA_64_NORECOV
)
1475 m
->p_flags
|= PF_IA_64_NORECOV
;
1479 order
= order
->next
;
1488 /* According to the Tahoe assembler spec, all labels starting with a
1492 elfNN_ia64_is_local_label_name (abfd
, name
)
1493 bfd
*abfd ATTRIBUTE_UNUSED
;
1496 return name
[0] == '.';
1499 /* Should we do dynamic things to this symbol? */
1502 elfNN_ia64_dynamic_symbol_p (h
, info
)
1503 struct elf_link_hash_entry
*h
;
1504 struct bfd_link_info
*info
;
1509 while (h
->root
.type
== bfd_link_hash_indirect
1510 || h
->root
.type
== bfd_link_hash_warning
)
1511 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
1513 if (h
->dynindx
== -1)
1515 switch (ELF_ST_VISIBILITY (h
->other
))
1524 if (h
->root
.type
== bfd_link_hash_undefweak
1525 || h
->root
.type
== bfd_link_hash_defweak
)
1528 if ((info
->shared
&& (!info
->symbolic
|| info
->allow_shlib_undefined
))
1529 || ((h
->elf_link_hash_flags
1530 & (ELF_LINK_HASH_DEF_DYNAMIC
| ELF_LINK_HASH_REF_REGULAR
))
1531 == (ELF_LINK_HASH_DEF_DYNAMIC
| ELF_LINK_HASH_REF_REGULAR
)))
1538 elfNN_ia64_local_hash_table_init (ht
, abfd
, new)
1539 struct elfNN_ia64_local_hash_table
*ht
;
1540 bfd
*abfd ATTRIBUTE_UNUSED
;
1541 new_hash_entry_func
new;
1543 memset (ht
, 0, sizeof (*ht
));
1544 return bfd_hash_table_init (&ht
->root
, new);
1547 static struct bfd_hash_entry
*
1548 elfNN_ia64_new_loc_hash_entry (entry
, table
, string
)
1549 struct bfd_hash_entry
*entry
;
1550 struct bfd_hash_table
*table
;
1553 struct elfNN_ia64_local_hash_entry
*ret
;
1554 ret
= (struct elfNN_ia64_local_hash_entry
*) entry
;
1556 /* Allocate the structure if it has not already been allocated by a
1559 ret
= bfd_hash_allocate (table
, sizeof (*ret
));
1564 /* Initialize our local data. All zeros, and definitely easier
1565 than setting a handful of bit fields. */
1566 memset (ret
, 0, sizeof (*ret
));
1568 /* Call the allocation method of the superclass. */
1569 ret
= ((struct elfNN_ia64_local_hash_entry
*)
1570 bfd_hash_newfunc ((struct bfd_hash_entry
*) ret
, table
, string
));
1572 return (struct bfd_hash_entry
*) ret
;
1575 static struct bfd_hash_entry
*
1576 elfNN_ia64_new_elf_hash_entry (entry
, table
, string
)
1577 struct bfd_hash_entry
*entry
;
1578 struct bfd_hash_table
*table
;
1581 struct elfNN_ia64_link_hash_entry
*ret
;
1582 ret
= (struct elfNN_ia64_link_hash_entry
*) entry
;
1584 /* Allocate the structure if it has not already been allocated by a
1587 ret
= bfd_hash_allocate (table
, sizeof (*ret
));
1592 /* Initialize our local data. All zeros, and definitely easier
1593 than setting a handful of bit fields. */
1594 memset (ret
, 0, sizeof (*ret
));
1596 /* Call the allocation method of the superclass. */
1597 ret
= ((struct elfNN_ia64_link_hash_entry
*)
1598 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry
*) ret
,
1601 return (struct bfd_hash_entry
*) ret
;
1605 elfNN_ia64_hash_copy_indirect (xdir
, xind
)
1606 struct elf_link_hash_entry
*xdir
, *xind
;
1608 struct elfNN_ia64_link_hash_entry
*dir
, *ind
;
1610 dir
= (struct elfNN_ia64_link_hash_entry
*) xdir
;
1611 ind
= (struct elfNN_ia64_link_hash_entry
*) xind
;
1613 /* Copy down any references that we may have already seen to the
1614 symbol which just became indirect. */
1616 dir
->root
.elf_link_hash_flags
|=
1617 (ind
->root
.elf_link_hash_flags
1618 & (ELF_LINK_HASH_REF_DYNAMIC
1619 | ELF_LINK_HASH_REF_REGULAR
1620 | ELF_LINK_HASH_REF_REGULAR_NONWEAK
));
1622 if (ind
->root
.root
.type
!= bfd_link_hash_indirect
)
1625 /* Copy over the got and plt data. This would have been done
1628 if (dir
->info
== NULL
)
1630 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
1632 dir
->info
= dyn_i
= ind
->info
;
1635 /* Fix up the dyn_sym_info pointers to the global symbol. */
1636 for (; dyn_i
; dyn_i
= dyn_i
->next
)
1637 dyn_i
->h
= &dir
->root
;
1639 BFD_ASSERT (ind
->info
== NULL
);
1641 /* Copy over the dynindx. */
1643 if (dir
->root
.dynindx
== -1)
1645 dir
->root
.dynindx
= ind
->root
.dynindx
;
1646 dir
->root
.dynstr_index
= ind
->root
.dynstr_index
;
1647 ind
->root
.dynindx
= -1;
1648 ind
->root
.dynstr_index
= 0;
1650 BFD_ASSERT (ind
->root
.dynindx
== -1);
1654 elfNN_ia64_hash_hide_symbol (info
, xh
, force_local
)
1655 struct bfd_link_info
*info
;
1656 struct elf_link_hash_entry
*xh
;
1657 boolean force_local
;
1659 struct elfNN_ia64_link_hash_entry
*h
;
1660 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
1662 h
= (struct elfNN_ia64_link_hash_entry
*)xh
;
1664 _bfd_elf_link_hash_hide_symbol (info
, &h
->root
, force_local
);
1666 for (dyn_i
= h
->info
; dyn_i
; dyn_i
= dyn_i
->next
)
1667 dyn_i
->want_plt2
= 0;
1670 /* Create the derived linker hash table. The IA-64 ELF port uses this
1671 derived hash table to keep information specific to the IA-64 ElF
1672 linker (without using static variables). */
1674 static struct bfd_link_hash_table
*
1675 elfNN_ia64_hash_table_create (abfd
)
1678 struct elfNN_ia64_link_hash_table
*ret
;
1680 ret
= bfd_zalloc (abfd
, (bfd_size_type
) sizeof (*ret
));
1683 if (!_bfd_elf_link_hash_table_init (&ret
->root
, abfd
,
1684 elfNN_ia64_new_elf_hash_entry
))
1686 bfd_release (abfd
, ret
);
1690 if (!elfNN_ia64_local_hash_table_init (&ret
->loc_hash_table
, abfd
,
1691 elfNN_ia64_new_loc_hash_entry
))
1693 return &ret
->root
.root
;
1696 /* Look up an entry in a Alpha ELF linker hash table. */
1698 static INLINE
struct elfNN_ia64_local_hash_entry
*
1699 elfNN_ia64_local_hash_lookup(table
, string
, create
, copy
)
1700 struct elfNN_ia64_local_hash_table
*table
;
1702 boolean create
, copy
;
1704 return ((struct elfNN_ia64_local_hash_entry
*)
1705 bfd_hash_lookup (&table
->root
, string
, create
, copy
));
1708 /* Traverse both local and global hash tables. */
1710 struct elfNN_ia64_dyn_sym_traverse_data
1712 boolean (*func
) PARAMS ((struct elfNN_ia64_dyn_sym_info
*, PTR
));
1717 elfNN_ia64_global_dyn_sym_thunk (xentry
, xdata
)
1718 struct bfd_hash_entry
*xentry
;
1721 struct elfNN_ia64_link_hash_entry
*entry
1722 = (struct elfNN_ia64_link_hash_entry
*) xentry
;
1723 struct elfNN_ia64_dyn_sym_traverse_data
*data
1724 = (struct elfNN_ia64_dyn_sym_traverse_data
*) xdata
;
1725 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
1727 if (entry
->root
.root
.type
== bfd_link_hash_warning
)
1728 entry
= (struct elfNN_ia64_link_hash_entry
*) entry
->root
.root
.u
.i
.link
;
1730 for (dyn_i
= entry
->info
; dyn_i
; dyn_i
= dyn_i
->next
)
1731 if (! (*data
->func
) (dyn_i
, data
->data
))
1737 elfNN_ia64_local_dyn_sym_thunk (xentry
, xdata
)
1738 struct bfd_hash_entry
*xentry
;
1741 struct elfNN_ia64_local_hash_entry
*entry
1742 = (struct elfNN_ia64_local_hash_entry
*) xentry
;
1743 struct elfNN_ia64_dyn_sym_traverse_data
*data
1744 = (struct elfNN_ia64_dyn_sym_traverse_data
*) xdata
;
1745 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
1747 for (dyn_i
= entry
->info
; dyn_i
; dyn_i
= dyn_i
->next
)
1748 if (! (*data
->func
) (dyn_i
, data
->data
))
1754 elfNN_ia64_dyn_sym_traverse (ia64_info
, func
, data
)
1755 struct elfNN_ia64_link_hash_table
*ia64_info
;
1756 boolean (*func
) PARAMS ((struct elfNN_ia64_dyn_sym_info
*, PTR
));
1759 struct elfNN_ia64_dyn_sym_traverse_data xdata
;
1764 elf_link_hash_traverse (&ia64_info
->root
,
1765 elfNN_ia64_global_dyn_sym_thunk
, &xdata
);
1766 bfd_hash_traverse (&ia64_info
->loc_hash_table
.root
,
1767 elfNN_ia64_local_dyn_sym_thunk
, &xdata
);
1771 elfNN_ia64_create_dynamic_sections (abfd
, info
)
1773 struct bfd_link_info
*info
;
1775 struct elfNN_ia64_link_hash_table
*ia64_info
;
1778 if (! _bfd_elf_create_dynamic_sections (abfd
, info
))
1781 ia64_info
= elfNN_ia64_hash_table (info
);
1783 ia64_info
->plt_sec
= bfd_get_section_by_name (abfd
, ".plt");
1784 ia64_info
->got_sec
= bfd_get_section_by_name (abfd
, ".got");
1787 flagword flags
= bfd_get_section_flags (abfd
, ia64_info
->got_sec
);
1788 bfd_set_section_flags (abfd
, ia64_info
->got_sec
, SEC_SMALL_DATA
| flags
);
1791 if (!get_pltoff (abfd
, info
, ia64_info
))
1794 s
= bfd_make_section(abfd
, ".rela.IA_64.pltoff");
1796 || !bfd_set_section_flags (abfd
, s
, (SEC_ALLOC
| SEC_LOAD
1799 | SEC_LINKER_CREATED
1801 || !bfd_set_section_alignment (abfd
, s
, 3))
1803 ia64_info
->rel_pltoff_sec
= s
;
1805 s
= bfd_make_section(abfd
, ".rela.got");
1807 || !bfd_set_section_flags (abfd
, s
, (SEC_ALLOC
| SEC_LOAD
1810 | SEC_LINKER_CREATED
1812 || !bfd_set_section_alignment (abfd
, s
, 3))
1814 ia64_info
->rel_got_sec
= s
;
1819 /* Find and/or create a hash entry for local symbol. */
1820 static struct elfNN_ia64_local_hash_entry
*
1821 get_local_sym_hash (ia64_info
, abfd
, rel
, create
)
1822 struct elfNN_ia64_link_hash_table
*ia64_info
;
1824 const Elf_Internal_Rela
*rel
;
1829 struct elfNN_ia64_local_hash_entry
*ret
;
1831 /* Construct a string for use in the elfNN_ia64_local_hash_table.
1832 name describes what was once anonymous memory. */
1834 len
= sizeof (void*)*2 + 1 + sizeof (bfd_vma
)*4 + 1 + 1;
1835 len
+= 10; /* %p slop */
1837 addr_name
= bfd_malloc (len
);
1838 if (addr_name
== NULL
)
1840 sprintf (addr_name
, "%p:%lx",
1841 (void *) abfd
, (unsigned long) ELFNN_R_SYM (rel
->r_info
));
1843 /* Collect the canonical entry data for this address. */
1844 ret
= elfNN_ia64_local_hash_lookup (&ia64_info
->loc_hash_table
,
1845 addr_name
, create
, create
);
1850 /* Find and/or create a descriptor for dynamic symbol info. This will
1851 vary based on global or local symbol, and the addend to the reloc. */
1853 static struct elfNN_ia64_dyn_sym_info
*
1854 get_dyn_sym_info (ia64_info
, h
, abfd
, rel
, create
)
1855 struct elfNN_ia64_link_hash_table
*ia64_info
;
1856 struct elf_link_hash_entry
*h
;
1858 const Elf_Internal_Rela
*rel
;
1861 struct elfNN_ia64_dyn_sym_info
**pp
;
1862 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
1863 bfd_vma addend
= rel
? rel
->r_addend
: 0;
1866 pp
= &((struct elfNN_ia64_link_hash_entry
*)h
)->info
;
1869 struct elfNN_ia64_local_hash_entry
*loc_h
;
1871 loc_h
= get_local_sym_hash (ia64_info
, abfd
, rel
, create
);
1877 for (dyn_i
= *pp
; dyn_i
&& dyn_i
->addend
!= addend
; dyn_i
= *pp
)
1880 if (dyn_i
== NULL
&& create
)
1882 dyn_i
= ((struct elfNN_ia64_dyn_sym_info
*)
1883 bfd_zalloc (abfd
, (bfd_size_type
) sizeof *dyn_i
));
1885 dyn_i
->addend
= addend
;
1892 get_got (abfd
, info
, ia64_info
)
1894 struct bfd_link_info
*info
;
1895 struct elfNN_ia64_link_hash_table
*ia64_info
;
1900 got
= ia64_info
->got_sec
;
1905 dynobj
= ia64_info
->root
.dynobj
;
1907 ia64_info
->root
.dynobj
= dynobj
= abfd
;
1908 if (!_bfd_elf_create_got_section (dynobj
, info
))
1911 got
= bfd_get_section_by_name (dynobj
, ".got");
1913 ia64_info
->got_sec
= got
;
1915 flags
= bfd_get_section_flags (abfd
, got
);
1916 bfd_set_section_flags (abfd
, got
, SEC_SMALL_DATA
| flags
);
1922 /* Create function descriptor section (.opd). This section is called .opd
1923 because it contains "official prodecure descriptors". The "official"
1924 refers to the fact that these descriptors are used when taking the address
1925 of a procedure, thus ensuring a unique address for each procedure. */
1928 get_fptr (abfd
, info
, ia64_info
)
1930 struct bfd_link_info
*info ATTRIBUTE_UNUSED
;
1931 struct elfNN_ia64_link_hash_table
*ia64_info
;
1936 fptr
= ia64_info
->fptr_sec
;
1939 dynobj
= ia64_info
->root
.dynobj
;
1941 ia64_info
->root
.dynobj
= dynobj
= abfd
;
1943 fptr
= bfd_make_section (dynobj
, ".opd");
1945 || !bfd_set_section_flags (dynobj
, fptr
,
1951 | SEC_LINKER_CREATED
))
1952 || !bfd_set_section_alignment (abfd
, fptr
, 4))
1958 ia64_info
->fptr_sec
= fptr
;
1965 get_pltoff (abfd
, info
, ia64_info
)
1967 struct bfd_link_info
*info ATTRIBUTE_UNUSED
;
1968 struct elfNN_ia64_link_hash_table
*ia64_info
;
1973 pltoff
= ia64_info
->pltoff_sec
;
1976 dynobj
= ia64_info
->root
.dynobj
;
1978 ia64_info
->root
.dynobj
= dynobj
= abfd
;
1980 pltoff
= bfd_make_section (dynobj
, ELF_STRING_ia64_pltoff
);
1982 || !bfd_set_section_flags (dynobj
, pltoff
,
1988 | SEC_LINKER_CREATED
))
1989 || !bfd_set_section_alignment (abfd
, pltoff
, 4))
1995 ia64_info
->pltoff_sec
= pltoff
;
2002 get_reloc_section (abfd
, ia64_info
, sec
, create
)
2004 struct elfNN_ia64_link_hash_table
*ia64_info
;
2008 const char *srel_name
;
2012 srel_name
= (bfd_elf_string_from_elf_section
2013 (abfd
, elf_elfheader(abfd
)->e_shstrndx
,
2014 elf_section_data(sec
)->rel_hdr
.sh_name
));
2015 if (srel_name
== NULL
)
2018 BFD_ASSERT ((strncmp (srel_name
, ".rela", 5) == 0
2019 && strcmp (bfd_get_section_name (abfd
, sec
),
2021 || (strncmp (srel_name
, ".rel", 4) == 0
2022 && strcmp (bfd_get_section_name (abfd
, sec
),
2023 srel_name
+4) == 0));
2025 dynobj
= ia64_info
->root
.dynobj
;
2027 ia64_info
->root
.dynobj
= dynobj
= abfd
;
2029 srel
= bfd_get_section_by_name (dynobj
, srel_name
);
2030 if (srel
== NULL
&& create
)
2032 srel
= bfd_make_section (dynobj
, srel_name
);
2034 || !bfd_set_section_flags (dynobj
, srel
,
2039 | SEC_LINKER_CREATED
2041 || !bfd_set_section_alignment (dynobj
, srel
, 3))
2045 if (sec
->flags
& SEC_READONLY
)
2046 ia64_info
->reltext
= 1;
2052 count_dyn_reloc (abfd
, dyn_i
, srel
, type
)
2054 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2058 struct elfNN_ia64_dyn_reloc_entry
*rent
;
2060 for (rent
= dyn_i
->reloc_entries
; rent
; rent
= rent
->next
)
2061 if (rent
->srel
== srel
&& rent
->type
== type
)
2066 rent
= ((struct elfNN_ia64_dyn_reloc_entry
*)
2067 bfd_alloc (abfd
, (bfd_size_type
) sizeof (*rent
)));
2071 rent
->next
= dyn_i
->reloc_entries
;
2075 dyn_i
->reloc_entries
= rent
;
2083 elfNN_ia64_check_relocs (abfd
, info
, sec
, relocs
)
2085 struct bfd_link_info
*info
;
2087 const Elf_Internal_Rela
*relocs
;
2089 struct elfNN_ia64_link_hash_table
*ia64_info
;
2090 const Elf_Internal_Rela
*relend
;
2091 Elf_Internal_Shdr
*symtab_hdr
;
2092 const Elf_Internal_Rela
*rel
;
2093 asection
*got
, *fptr
, *srel
;
2095 if (info
->relocateable
)
2098 symtab_hdr
= &elf_tdata (abfd
)->symtab_hdr
;
2099 ia64_info
= elfNN_ia64_hash_table (info
);
2101 got
= fptr
= srel
= NULL
;
2103 relend
= relocs
+ sec
->reloc_count
;
2104 for (rel
= relocs
; rel
< relend
; ++rel
)
2113 NEED_LTOFF_FPTR
= 64,
2119 struct elf_link_hash_entry
*h
= NULL
;
2120 unsigned long r_symndx
= ELFNN_R_SYM (rel
->r_info
);
2121 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2123 boolean maybe_dynamic
;
2124 int dynrel_type
= R_IA64_NONE
;
2126 if (r_symndx
>= symtab_hdr
->sh_info
)
2128 /* We're dealing with a global symbol -- find its hash entry
2129 and mark it as being referenced. */
2130 long indx
= r_symndx
- symtab_hdr
->sh_info
;
2131 h
= elf_sym_hashes (abfd
)[indx
];
2132 while (h
->root
.type
== bfd_link_hash_indirect
2133 || h
->root
.type
== bfd_link_hash_warning
)
2134 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
2136 h
->elf_link_hash_flags
|= ELF_LINK_HASH_REF_REGULAR
;
2139 /* We can only get preliminary data on whether a symbol is
2140 locally or externally defined, as not all of the input files
2141 have yet been processed. Do something with what we know, as
2142 this may help reduce memory usage and processing time later. */
2143 maybe_dynamic
= false;
2144 if (h
&& ((info
->shared
2145 && (!info
->symbolic
|| info
->allow_shlib_undefined
))
2146 || ! (h
->elf_link_hash_flags
& ELF_LINK_HASH_DEF_REGULAR
)
2147 || h
->root
.type
== bfd_link_hash_defweak
2148 || elfNN_ia64_aix_vec (abfd
->xvec
)))
2149 maybe_dynamic
= true;
2152 switch (ELFNN_R_TYPE (rel
->r_info
))
2154 case R_IA64_TPREL64MSB
:
2155 case R_IA64_TPREL64LSB
:
2156 if (info
->shared
|| maybe_dynamic
)
2157 need_entry
= NEED_DYNREL
;
2158 dynrel_type
= R_IA64_TPREL64LSB
;
2160 info
->flags
|= DF_STATIC_TLS
;
2163 case R_IA64_LTOFF_TPREL22
:
2164 need_entry
= NEED_TPREL
;
2166 info
->flags
|= DF_STATIC_TLS
;
2169 case R_IA64_DTPREL64MSB
:
2170 case R_IA64_DTPREL64LSB
:
2171 if (info
->shared
|| maybe_dynamic
)
2172 need_entry
= NEED_DYNREL
;
2173 dynrel_type
= R_IA64_DTPREL64LSB
;
2176 case R_IA64_LTOFF_DTPREL22
:
2177 need_entry
= NEED_DTPREL
;
2180 case R_IA64_DTPMOD64MSB
:
2181 case R_IA64_DTPMOD64LSB
:
2182 if (info
->shared
|| maybe_dynamic
)
2183 need_entry
= NEED_DYNREL
;
2184 dynrel_type
= R_IA64_DTPMOD64LSB
;
2187 case R_IA64_LTOFF_DTPMOD22
:
2188 need_entry
= NEED_DTPMOD
;
2191 case R_IA64_LTOFF_FPTR22
:
2192 case R_IA64_LTOFF_FPTR64I
:
2193 case R_IA64_LTOFF_FPTR32MSB
:
2194 case R_IA64_LTOFF_FPTR32LSB
:
2195 case R_IA64_LTOFF_FPTR64MSB
:
2196 case R_IA64_LTOFF_FPTR64LSB
:
2197 need_entry
= NEED_FPTR
| NEED_GOT
| NEED_LTOFF_FPTR
;
2200 case R_IA64_FPTR64I
:
2201 case R_IA64_FPTR32MSB
:
2202 case R_IA64_FPTR32LSB
:
2203 case R_IA64_FPTR64MSB
:
2204 case R_IA64_FPTR64LSB
:
2205 if (info
->shared
|| h
|| elfNN_ia64_aix_vec (abfd
->xvec
))
2206 need_entry
= NEED_FPTR
| NEED_DYNREL
;
2208 need_entry
= NEED_FPTR
;
2209 dynrel_type
= R_IA64_FPTR64LSB
;
2212 case R_IA64_LTOFF22
:
2213 case R_IA64_LTOFF22X
:
2214 case R_IA64_LTOFF64I
:
2215 need_entry
= NEED_GOT
;
2218 case R_IA64_PLTOFF22
:
2219 case R_IA64_PLTOFF64I
:
2220 case R_IA64_PLTOFF64MSB
:
2221 case R_IA64_PLTOFF64LSB
:
2222 need_entry
= NEED_PLTOFF
;
2226 need_entry
|= NEED_MIN_PLT
;
2230 (*info
->callbacks
->warning
)
2231 (info
, _("@pltoff reloc against local symbol"), 0,
2232 abfd
, 0, (bfd_vma
) 0);
2236 case R_IA64_PCREL21B
:
2237 case R_IA64_PCREL60B
:
2238 /* Depending on where this symbol is defined, we may or may not
2239 need a full plt entry. Only skip if we know we'll not need
2240 the entry -- static or symbolic, and the symbol definition
2241 has already been seen. */
2242 if (maybe_dynamic
&& rel
->r_addend
== 0)
2243 need_entry
= NEED_FULL_PLT
;
2249 case R_IA64_DIR32MSB
:
2250 case R_IA64_DIR32LSB
:
2251 case R_IA64_DIR64MSB
:
2252 case R_IA64_DIR64LSB
:
2253 /* Shared objects will always need at least a REL relocation. */
2254 if (info
->shared
|| maybe_dynamic
2255 || (elfNN_ia64_aix_vec (abfd
->xvec
)
2256 && (!h
|| strcmp (h
->root
.root
.string
,
2257 "__GLOB_DATA_PTR") != 0)))
2258 need_entry
= NEED_DYNREL
;
2259 dynrel_type
= R_IA64_DIR64LSB
;
2262 case R_IA64_IPLTMSB
:
2263 case R_IA64_IPLTLSB
:
2264 /* Shared objects will always need at least a REL relocation. */
2265 if (info
->shared
|| maybe_dynamic
)
2266 need_entry
= NEED_DYNREL
;
2267 dynrel_type
= R_IA64_IPLTLSB
;
2270 case R_IA64_PCREL22
:
2271 case R_IA64_PCREL64I
:
2272 case R_IA64_PCREL32MSB
:
2273 case R_IA64_PCREL32LSB
:
2274 case R_IA64_PCREL64MSB
:
2275 case R_IA64_PCREL64LSB
:
2277 need_entry
= NEED_DYNREL
;
2278 dynrel_type
= R_IA64_PCREL64LSB
;
2285 if ((need_entry
& NEED_FPTR
) != 0
2288 (*info
->callbacks
->warning
)
2289 (info
, _("non-zero addend in @fptr reloc"), 0,
2290 abfd
, 0, (bfd_vma
) 0);
2293 dyn_i
= get_dyn_sym_info (ia64_info
, h
, abfd
, rel
, true);
2295 /* Record whether or not this is a local symbol. */
2298 /* Create what's needed. */
2299 if (need_entry
& (NEED_GOT
| NEED_TPREL
| NEED_DTPMOD
| NEED_DTPREL
))
2303 got
= get_got (abfd
, info
, ia64_info
);
2307 if (need_entry
& NEED_GOT
)
2308 dyn_i
->want_got
= 1;
2309 if (need_entry
& NEED_TPREL
)
2310 dyn_i
->want_tprel
= 1;
2311 if (need_entry
& NEED_DTPMOD
)
2312 dyn_i
->want_dtpmod
= 1;
2313 if (need_entry
& NEED_DTPREL
)
2314 dyn_i
->want_dtprel
= 1;
2316 if (need_entry
& NEED_FPTR
)
2320 fptr
= get_fptr (abfd
, info
, ia64_info
);
2325 /* FPTRs for shared libraries are allocated by the dynamic
2326 linker. Make sure this local symbol will appear in the
2327 dynamic symbol table. */
2328 if (!h
&& (info
->shared
2329 /* AIX also needs one */
2330 || elfNN_ia64_aix_vec (abfd
->xvec
)))
2332 if (! (_bfd_elfNN_link_record_local_dynamic_symbol
2333 (info
, abfd
, (long) r_symndx
)))
2337 dyn_i
->want_fptr
= 1;
2339 if (need_entry
& NEED_LTOFF_FPTR
)
2340 dyn_i
->want_ltoff_fptr
= 1;
2341 if (need_entry
& (NEED_MIN_PLT
| NEED_FULL_PLT
))
2343 if (!ia64_info
->root
.dynobj
)
2344 ia64_info
->root
.dynobj
= abfd
;
2345 h
->elf_link_hash_flags
|= ELF_LINK_HASH_NEEDS_PLT
;
2346 dyn_i
->want_plt
= 1;
2348 if (need_entry
& NEED_FULL_PLT
)
2349 dyn_i
->want_plt2
= 1;
2350 if (need_entry
& NEED_PLTOFF
)
2351 dyn_i
->want_pltoff
= 1;
2352 if ((need_entry
& NEED_DYNREL
) && (sec
->flags
& SEC_ALLOC
))
2356 srel
= get_reloc_section (abfd
, ia64_info
, sec
, true);
2360 if (!count_dyn_reloc (abfd
, dyn_i
, srel
, dynrel_type
))
2368 struct elfNN_ia64_allocate_data
2370 struct bfd_link_info
*info
;
2374 /* For cleanliness, and potentially faster dynamic loading, allocate
2375 external GOT entries first. */
2378 allocate_global_data_got (dyn_i
, data
)
2379 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2382 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2385 && ! dyn_i
->want_fptr
2386 && (elfNN_ia64_dynamic_symbol_p (dyn_i
->h
, x
->info
)
2387 || (elfNN_ia64_aix_vec (x
->info
->hash
->creator
)
2388 && (!dyn_i
->h
|| strcmp (dyn_i
->h
->root
.root
.string
,
2389 "__GLOB_DATA_PTR") != 0))))
2391 dyn_i
->got_offset
= x
->ofs
;
2394 if (dyn_i
->want_tprel
)
2396 dyn_i
->tprel_offset
= x
->ofs
;
2399 if (dyn_i
->want_dtpmod
)
2401 dyn_i
->dtpmod_offset
= x
->ofs
;
2404 if (dyn_i
->want_dtprel
)
2406 dyn_i
->dtprel_offset
= x
->ofs
;
2412 /* Next, allocate all the GOT entries used by LTOFF_FPTR relocs. */
2415 allocate_global_fptr_got (dyn_i
, data
)
2416 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2419 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2423 && (elfNN_ia64_dynamic_symbol_p (dyn_i
->h
, x
->info
)
2424 || elfNN_ia64_aix_vec (x
->info
->hash
->creator
)))
2426 dyn_i
->got_offset
= x
->ofs
;
2432 /* Lastly, allocate all the GOT entries for local data. */
2435 allocate_local_got (dyn_i
, data
)
2436 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2439 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2442 && ! (elfNN_ia64_dynamic_symbol_p (dyn_i
->h
, x
->info
)
2443 || elfNN_ia64_aix_vec (x
->info
->hash
->creator
)))
2445 dyn_i
->got_offset
= x
->ofs
;
2451 /* Search for the index of a global symbol in it's defining object file. */
2454 global_sym_index (h
)
2455 struct elf_link_hash_entry
*h
;
2457 struct elf_link_hash_entry
**p
;
2460 BFD_ASSERT (h
->root
.type
== bfd_link_hash_defined
2461 || h
->root
.type
== bfd_link_hash_defweak
);
2463 obj
= h
->root
.u
.def
.section
->owner
;
2464 for (p
= elf_sym_hashes (obj
); *p
!= h
; ++p
)
2467 return p
- elf_sym_hashes (obj
) + elf_tdata (obj
)->symtab_hdr
.sh_info
;
2470 /* Allocate function descriptors. We can do these for every function
2471 in a main executable that is not exported. */
2474 allocate_fptr (dyn_i
, data
)
2475 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2478 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2480 if (dyn_i
->want_fptr
)
2482 struct elf_link_hash_entry
*h
= dyn_i
->h
;
2485 while (h
->root
.type
== bfd_link_hash_indirect
2486 || h
->root
.type
== bfd_link_hash_warning
)
2487 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
2490 /* AIX needs an FPTR in this case. */
2491 || (elfNN_ia64_aix_vec (x
->info
->hash
->creator
)
2493 || h
->root
.type
== bfd_link_hash_defined
2494 || h
->root
.type
== bfd_link_hash_defweak
)))
2496 if (h
&& h
->dynindx
== -1)
2498 BFD_ASSERT ((h
->root
.type
== bfd_link_hash_defined
)
2499 || (h
->root
.type
== bfd_link_hash_defweak
));
2501 if (!_bfd_elfNN_link_record_local_dynamic_symbol
2502 (x
->info
, h
->root
.u
.def
.section
->owner
,
2503 global_sym_index (h
)))
2507 dyn_i
->want_fptr
= 0;
2509 else if (h
== NULL
|| h
->dynindx
== -1)
2511 dyn_i
->fptr_offset
= x
->ofs
;
2515 dyn_i
->want_fptr
= 0;
2520 /* Allocate all the minimal PLT entries. */
2523 allocate_plt_entries (dyn_i
, data
)
2524 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2527 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2529 if (dyn_i
->want_plt
)
2531 struct elf_link_hash_entry
*h
= dyn_i
->h
;
2534 while (h
->root
.type
== bfd_link_hash_indirect
2535 || h
->root
.type
== bfd_link_hash_warning
)
2536 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
2538 /* ??? Versioned symbols seem to lose ELF_LINK_HASH_NEEDS_PLT. */
2539 if (elfNN_ia64_dynamic_symbol_p (h
, x
->info
))
2541 bfd_size_type offset
= x
->ofs
;
2543 offset
= PLT_HEADER_SIZE
;
2544 dyn_i
->plt_offset
= offset
;
2545 x
->ofs
= offset
+ PLT_MIN_ENTRY_SIZE
;
2547 dyn_i
->want_pltoff
= 1;
2551 dyn_i
->want_plt
= 0;
2552 dyn_i
->want_plt2
= 0;
2558 /* Allocate all the full PLT entries. */
2561 allocate_plt2_entries (dyn_i
, data
)
2562 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2565 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2567 if (dyn_i
->want_plt2
)
2569 struct elf_link_hash_entry
*h
= dyn_i
->h
;
2570 bfd_size_type ofs
= x
->ofs
;
2572 dyn_i
->plt2_offset
= ofs
;
2573 x
->ofs
= ofs
+ PLT_FULL_ENTRY_SIZE
;
2575 while (h
->root
.type
== bfd_link_hash_indirect
2576 || h
->root
.type
== bfd_link_hash_warning
)
2577 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
2578 dyn_i
->h
->plt
.offset
= ofs
;
2583 /* Allocate all the PLTOFF entries requested by relocations and
2584 plt entries. We can't share space with allocated FPTR entries,
2585 because the latter are not necessarily addressable by the GP.
2586 ??? Relaxation might be able to determine that they are. */
2589 allocate_pltoff_entries (dyn_i
, data
)
2590 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2593 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2595 if (dyn_i
->want_pltoff
)
2597 dyn_i
->pltoff_offset
= x
->ofs
;
2603 /* Allocate dynamic relocations for those symbols that turned out
2607 allocate_dynrel_entries (dyn_i
, data
)
2608 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
2611 struct elfNN_ia64_allocate_data
*x
= (struct elfNN_ia64_allocate_data
*)data
;
2612 struct elfNN_ia64_link_hash_table
*ia64_info
;
2613 struct elfNN_ia64_dyn_reloc_entry
*rent
;
2614 boolean dynamic_symbol
, shared
;
2616 ia64_info
= elfNN_ia64_hash_table (x
->info
);
2617 dynamic_symbol
= elfNN_ia64_dynamic_symbol_p (dyn_i
->h
, x
->info
)
2618 || (elfNN_ia64_aix_vec (x
->info
->hash
->creator
)
2619 /* Don't allocate an entry for __GLOB_DATA_PTR */
2620 && (!dyn_i
->h
|| strcmp (dyn_i
->h
->root
.root
.string
,
2621 "__GLOB_DATA_PTR") != 0));
2622 shared
= x
->info
->shared
;
2624 /* Take care of the normal data relocations. */
2626 for (rent
= dyn_i
->reloc_entries
; rent
; rent
= rent
->next
)
2628 int count
= rent
->count
;
2632 case R_IA64_FPTR64LSB
:
2633 /* Allocate one iff !want_fptr, which by this point will
2634 be true only if we're actually allocating one statically
2635 in the main executable. */
2636 if (dyn_i
->want_fptr
)
2639 case R_IA64_PCREL64LSB
:
2640 if (!dynamic_symbol
)
2643 case R_IA64_DIR64LSB
:
2644 if (!dynamic_symbol
&& !shared
)
2647 case R_IA64_IPLTLSB
:
2648 if (!dynamic_symbol
&& !shared
)
2650 /* Use two REL relocations for IPLT relocations
2651 against local symbols. */
2652 if (!dynamic_symbol
)
2655 case R_IA64_TPREL64LSB
:
2656 case R_IA64_DTPREL64LSB
:
2657 case R_IA64_DTPMOD64LSB
:
2662 rent
->srel
->_raw_size
+= sizeof (ElfNN_External_Rela
) * count
;
2665 /* Take care of the GOT and PLT relocations. */
2667 if (((dynamic_symbol
|| shared
) && dyn_i
->want_got
)
2668 || (dyn_i
->want_ltoff_fptr
&& dyn_i
->h
&& dyn_i
->h
->dynindx
!= -1))
2669 ia64_info
->rel_got_sec
->_raw_size
+= sizeof (ElfNN_External_Rela
);
2670 if ((dynamic_symbol
|| shared
) && dyn_i
->want_tprel
)
2671 ia64_info
->rel_got_sec
->_raw_size
+= sizeof (ElfNN_External_Rela
);
2672 if ((dynamic_symbol
|| shared
) && dyn_i
->want_dtpmod
)
2673 ia64_info
->rel_got_sec
->_raw_size
+= sizeof (ElfNN_External_Rela
);
2674 if (dynamic_symbol
&& dyn_i
->want_dtprel
)
2675 ia64_info
->rel_got_sec
->_raw_size
+= sizeof (ElfNN_External_Rela
);
2677 if (dyn_i
->want_pltoff
)
2679 bfd_size_type t
= 0;
2681 /* Dynamic symbols get one IPLT relocation. Local symbols in
2682 shared libraries get two REL relocations. Local symbols in
2683 main applications get nothing. */
2685 t
= sizeof (ElfNN_External_Rela
);
2687 t
= 2 * sizeof (ElfNN_External_Rela
);
2689 ia64_info
->rel_pltoff_sec
->_raw_size
+= t
;
2696 elfNN_ia64_adjust_dynamic_symbol (info
, h
)
2697 struct bfd_link_info
*info ATTRIBUTE_UNUSED
;
2698 struct elf_link_hash_entry
*h
;
2700 /* ??? Undefined symbols with PLT entries should be re-defined
2701 to be the PLT entry. */
2703 /* If this is a weak symbol, and there is a real definition, the
2704 processor independent code will have arranged for us to see the
2705 real definition first, and we can just use the same value. */
2706 if (h
->weakdef
!= NULL
)
2708 BFD_ASSERT (h
->weakdef
->root
.type
== bfd_link_hash_defined
2709 || h
->weakdef
->root
.type
== bfd_link_hash_defweak
);
2710 h
->root
.u
.def
.section
= h
->weakdef
->root
.u
.def
.section
;
2711 h
->root
.u
.def
.value
= h
->weakdef
->root
.u
.def
.value
;
2715 /* If this is a reference to a symbol defined by a dynamic object which
2716 is not a function, we might allocate the symbol in our .dynbss section
2717 and allocate a COPY dynamic relocation.
2719 But IA-64 code is canonically PIC, so as a rule we can avoid this sort
2726 elfNN_ia64_size_dynamic_sections (output_bfd
, info
)
2728 struct bfd_link_info
*info
;
2730 struct elfNN_ia64_allocate_data data
;
2731 struct elfNN_ia64_link_hash_table
*ia64_info
;
2734 boolean relplt
= false;
2736 dynobj
= elf_hash_table(info
)->dynobj
;
2737 ia64_info
= elfNN_ia64_hash_table (info
);
2738 BFD_ASSERT(dynobj
!= NULL
);
2741 /* Set the contents of the .interp section to the interpreter. */
2742 if (ia64_info
->root
.dynamic_sections_created
2745 sec
= bfd_get_section_by_name (dynobj
, ".interp");
2746 BFD_ASSERT (sec
!= NULL
);
2747 sec
->contents
= (bfd_byte
*) DYNAMIC_INTERPRETER (output_bfd
);
2748 sec
->_raw_size
= strlen (DYNAMIC_INTERPRETER (output_bfd
)) + 1;
2751 /* Allocate the GOT entries. */
2753 if (ia64_info
->got_sec
)
2756 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_global_data_got
, &data
);
2757 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_global_fptr_got
, &data
);
2758 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_local_got
, &data
);
2759 ia64_info
->got_sec
->_raw_size
= data
.ofs
;
2762 /* Allocate the FPTR entries. */
2764 if (ia64_info
->fptr_sec
)
2767 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_fptr
, &data
);
2768 ia64_info
->fptr_sec
->_raw_size
= data
.ofs
;
2771 /* Now that we've seen all of the input files, we can decide which
2772 symbols need plt entries. Allocate the minimal PLT entries first.
2773 We do this even though dynamic_sections_created may be false, because
2774 this has the side-effect of clearing want_plt and want_plt2. */
2777 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_plt_entries
, &data
);
2779 ia64_info
->minplt_entries
= 0;
2782 ia64_info
->minplt_entries
2783 = (data
.ofs
- PLT_HEADER_SIZE
) / PLT_MIN_ENTRY_SIZE
;
2786 /* Align the pointer for the plt2 entries. */
2787 data
.ofs
= (data
.ofs
+ 31) & (bfd_vma
) -32;
2789 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_plt2_entries
, &data
);
2792 BFD_ASSERT (ia64_info
->root
.dynamic_sections_created
);
2794 ia64_info
->plt_sec
->_raw_size
= data
.ofs
;
2796 /* If we've got a .plt, we need some extra memory for the dynamic
2797 linker. We stuff these in .got.plt. */
2798 sec
= bfd_get_section_by_name (dynobj
, ".got.plt");
2799 sec
->_raw_size
= 8 * PLT_RESERVED_WORDS
;
2802 /* Allocate the PLTOFF entries. */
2804 if (ia64_info
->pltoff_sec
)
2807 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_pltoff_entries
, &data
);
2808 ia64_info
->pltoff_sec
->_raw_size
= data
.ofs
;
2811 if (ia64_info
->root
.dynamic_sections_created
)
2813 /* Allocate space for the dynamic relocations that turned out to be
2816 elfNN_ia64_dyn_sym_traverse (ia64_info
, allocate_dynrel_entries
, &data
);
2819 /* We have now determined the sizes of the various dynamic sections.
2820 Allocate memory for them. */
2821 for (sec
= dynobj
->sections
; sec
!= NULL
; sec
= sec
->next
)
2825 if (!(sec
->flags
& SEC_LINKER_CREATED
))
2828 /* If we don't need this section, strip it from the output file.
2829 There were several sections primarily related to dynamic
2830 linking that must be create before the linker maps input
2831 sections to output sections. The linker does that before
2832 bfd_elf_size_dynamic_sections is called, and it is that
2833 function which decides whether anything needs to go into
2836 strip
= (sec
->_raw_size
== 0);
2838 if (sec
== ia64_info
->got_sec
)
2840 else if (sec
== ia64_info
->rel_got_sec
)
2843 ia64_info
->rel_got_sec
= NULL
;
2845 /* We use the reloc_count field as a counter if we need to
2846 copy relocs into the output file. */
2847 sec
->reloc_count
= 0;
2849 else if (sec
== ia64_info
->fptr_sec
)
2852 ia64_info
->fptr_sec
= NULL
;
2854 else if (sec
== ia64_info
->plt_sec
)
2857 ia64_info
->plt_sec
= NULL
;
2859 else if (sec
== ia64_info
->pltoff_sec
)
2862 ia64_info
->pltoff_sec
= NULL
;
2864 else if (sec
== ia64_info
->rel_pltoff_sec
)
2867 ia64_info
->rel_pltoff_sec
= NULL
;
2871 /* We use the reloc_count field as a counter if we need to
2872 copy relocs into the output file. */
2873 sec
->reloc_count
= 0;
2880 /* It's OK to base decisions on the section name, because none
2881 of the dynobj section names depend upon the input files. */
2882 name
= bfd_get_section_name (dynobj
, sec
);
2884 if (strcmp (name
, ".got.plt") == 0)
2886 else if (strncmp (name
, ".rel", 4) == 0)
2890 /* We use the reloc_count field as a counter if we need to
2891 copy relocs into the output file. */
2892 sec
->reloc_count
= 0;
2900 _bfd_strip_section_from_output (info
, sec
);
2903 /* Allocate memory for the section contents. */
2904 sec
->contents
= (bfd_byte
*) bfd_zalloc (dynobj
, sec
->_raw_size
);
2905 if (sec
->contents
== NULL
&& sec
->_raw_size
!= 0)
2910 if (elf_hash_table (info
)->dynamic_sections_created
)
2912 /* Add some entries to the .dynamic section. We fill in the values
2913 later (in finish_dynamic_sections) but we must add the entries now
2914 so that we get the correct size for the .dynamic section. */
2918 /* The DT_DEBUG entry is filled in by the dynamic linker and used
2920 #define add_dynamic_entry(TAG, VAL) \
2921 bfd_elfNN_add_dynamic_entry (info, (bfd_vma) (TAG), (bfd_vma) (VAL))
2923 if (!add_dynamic_entry (DT_DEBUG
, 0))
2927 if (!add_dynamic_entry (DT_IA_64_PLT_RESERVE
, 0))
2929 if (!add_dynamic_entry (DT_PLTGOT
, 0))
2934 if (!add_dynamic_entry (DT_PLTRELSZ
, 0)
2935 || !add_dynamic_entry (DT_PLTREL
, DT_RELA
)
2936 || !add_dynamic_entry (DT_JMPREL
, 0))
2940 if (!add_dynamic_entry (DT_RELA
, 0)
2941 || !add_dynamic_entry (DT_RELASZ
, 0)
2942 || !add_dynamic_entry (DT_RELAENT
, sizeof (ElfNN_External_Rela
)))
2945 if (ia64_info
->reltext
)
2947 if (!add_dynamic_entry (DT_TEXTREL
, 0))
2949 info
->flags
|= DF_TEXTREL
;
2953 /* ??? Perhaps force __gp local. */
2958 static bfd_reloc_status_type
2959 elfNN_ia64_install_value (abfd
, hit_addr
, v
, r_type
)
2963 unsigned int r_type
;
2965 const struct ia64_operand
*op
;
2966 int bigendian
= 0, shift
= 0;
2967 bfd_vma t0
, t1
, insn
, dword
;
2968 enum ia64_opnd opnd
;
2971 #ifdef BFD_HOST_U_64_BIT
2972 BFD_HOST_U_64_BIT val
= (BFD_HOST_U_64_BIT
) v
;
2977 opnd
= IA64_OPND_NIL
;
2982 return bfd_reloc_ok
;
2984 /* Instruction relocations. */
2987 case R_IA64_TPREL14
:
2988 case R_IA64_DTPREL14
:
2989 opnd
= IA64_OPND_IMM14
;
2992 case R_IA64_PCREL21F
: opnd
= IA64_OPND_TGT25
; break;
2993 case R_IA64_PCREL21M
: opnd
= IA64_OPND_TGT25b
; break;
2994 case R_IA64_PCREL60B
: opnd
= IA64_OPND_TGT64
; break;
2995 case R_IA64_PCREL21B
:
2996 case R_IA64_PCREL21BI
:
2997 opnd
= IA64_OPND_TGT25c
;
3001 case R_IA64_GPREL22
:
3002 case R_IA64_LTOFF22
:
3003 case R_IA64_LTOFF22X
:
3004 case R_IA64_PLTOFF22
:
3005 case R_IA64_PCREL22
:
3006 case R_IA64_LTOFF_FPTR22
:
3007 case R_IA64_TPREL22
:
3008 case R_IA64_DTPREL22
:
3009 case R_IA64_LTOFF_TPREL22
:
3010 case R_IA64_LTOFF_DTPMOD22
:
3011 case R_IA64_LTOFF_DTPREL22
:
3012 opnd
= IA64_OPND_IMM22
;
3016 case R_IA64_GPREL64I
:
3017 case R_IA64_LTOFF64I
:
3018 case R_IA64_PLTOFF64I
:
3019 case R_IA64_PCREL64I
:
3020 case R_IA64_FPTR64I
:
3021 case R_IA64_LTOFF_FPTR64I
:
3022 case R_IA64_TPREL64I
:
3023 case R_IA64_DTPREL64I
:
3024 opnd
= IA64_OPND_IMMU64
;
3027 /* Data relocations. */
3029 case R_IA64_DIR32MSB
:
3030 case R_IA64_GPREL32MSB
:
3031 case R_IA64_FPTR32MSB
:
3032 case R_IA64_PCREL32MSB
:
3033 case R_IA64_LTOFF_FPTR32MSB
:
3034 case R_IA64_SEGREL32MSB
:
3035 case R_IA64_SECREL32MSB
:
3036 case R_IA64_LTV32MSB
:
3037 case R_IA64_DTPREL32MSB
:
3038 size
= 4; bigendian
= 1;
3041 case R_IA64_DIR32LSB
:
3042 case R_IA64_GPREL32LSB
:
3043 case R_IA64_FPTR32LSB
:
3044 case R_IA64_PCREL32LSB
:
3045 case R_IA64_LTOFF_FPTR32LSB
:
3046 case R_IA64_SEGREL32LSB
:
3047 case R_IA64_SECREL32LSB
:
3048 case R_IA64_LTV32LSB
:
3049 case R_IA64_DTPREL32LSB
:
3050 size
= 4; bigendian
= 0;
3053 case R_IA64_DIR64MSB
:
3054 case R_IA64_GPREL64MSB
:
3055 case R_IA64_PLTOFF64MSB
:
3056 case R_IA64_FPTR64MSB
:
3057 case R_IA64_PCREL64MSB
:
3058 case R_IA64_LTOFF_FPTR64MSB
:
3059 case R_IA64_SEGREL64MSB
:
3060 case R_IA64_SECREL64MSB
:
3061 case R_IA64_LTV64MSB
:
3062 case R_IA64_TPREL64MSB
:
3063 case R_IA64_DTPMOD64MSB
:
3064 case R_IA64_DTPREL64MSB
:
3065 size
= 8; bigendian
= 1;
3068 case R_IA64_DIR64LSB
:
3069 case R_IA64_GPREL64LSB
:
3070 case R_IA64_PLTOFF64LSB
:
3071 case R_IA64_FPTR64LSB
:
3072 case R_IA64_PCREL64LSB
:
3073 case R_IA64_LTOFF_FPTR64LSB
:
3074 case R_IA64_SEGREL64LSB
:
3075 case R_IA64_SECREL64LSB
:
3076 case R_IA64_LTV64LSB
:
3077 case R_IA64_TPREL64LSB
:
3078 case R_IA64_DTPMOD64LSB
:
3079 case R_IA64_DTPREL64LSB
:
3080 size
= 8; bigendian
= 0;
3083 /* Unsupported / Dynamic relocations. */
3085 return bfd_reloc_notsupported
;
3090 case IA64_OPND_IMMU64
:
3091 hit_addr
-= (long) hit_addr
& 0x3;
3092 t0
= bfd_get_64 (abfd
, hit_addr
);
3093 t1
= bfd_get_64 (abfd
, hit_addr
+ 8);
3095 /* tmpl/s: bits 0.. 5 in t0
3096 slot 0: bits 5..45 in t0
3097 slot 1: bits 46..63 in t0, bits 0..22 in t1
3098 slot 2: bits 23..63 in t1 */
3100 /* First, clear the bits that form the 64 bit constant. */
3101 t0
&= ~(0x3ffffLL
<< 46);
3103 | (( (0x07fLL
<< 13) | (0x1ffLL
<< 27)
3104 | (0x01fLL
<< 22) | (0x001LL
<< 21)
3105 | (0x001LL
<< 36)) << 23));
3107 t0
|= ((val
>> 22) & 0x03ffffLL
) << 46; /* 18 lsbs of imm41 */
3108 t1
|= ((val
>> 40) & 0x7fffffLL
) << 0; /* 23 msbs of imm41 */
3109 t1
|= ( (((val
>> 0) & 0x07f) << 13) /* imm7b */
3110 | (((val
>> 7) & 0x1ff) << 27) /* imm9d */
3111 | (((val
>> 16) & 0x01f) << 22) /* imm5c */
3112 | (((val
>> 21) & 0x001) << 21) /* ic */
3113 | (((val
>> 63) & 0x001) << 36)) << 23; /* i */
3115 bfd_put_64 (abfd
, t0
, hit_addr
);
3116 bfd_put_64 (abfd
, t1
, hit_addr
+ 8);
3119 case IA64_OPND_TGT64
:
3120 hit_addr
-= (long) hit_addr
& 0x3;
3121 t0
= bfd_get_64 (abfd
, hit_addr
);
3122 t1
= bfd_get_64 (abfd
, hit_addr
+ 8);
3124 /* tmpl/s: bits 0.. 5 in t0
3125 slot 0: bits 5..45 in t0
3126 slot 1: bits 46..63 in t0, bits 0..22 in t1
3127 slot 2: bits 23..63 in t1 */
3129 /* First, clear the bits that form the 64 bit constant. */
3130 t0
&= ~(0x3ffffLL
<< 46);
3132 | ((1LL << 36 | 0xfffffLL
<< 13) << 23));
3135 t0
|= ((val
>> 20) & 0xffffLL
) << 2 << 46; /* 16 lsbs of imm39 */
3136 t1
|= ((val
>> 36) & 0x7fffffLL
) << 0; /* 23 msbs of imm39 */
3137 t1
|= ((((val
>> 0) & 0xfffffLL
) << 13) /* imm20b */
3138 | (((val
>> 59) & 0x1LL
) << 36)) << 23; /* i */
3140 bfd_put_64 (abfd
, t0
, hit_addr
);
3141 bfd_put_64 (abfd
, t1
, hit_addr
+ 8);
3145 switch ((long) hit_addr
& 0x3)
3147 case 0: shift
= 5; break;
3148 case 1: shift
= 14; hit_addr
+= 3; break;
3149 case 2: shift
= 23; hit_addr
+= 6; break;
3150 case 3: return bfd_reloc_notsupported
; /* shouldn't happen... */
3152 dword
= bfd_get_64 (abfd
, hit_addr
);
3153 insn
= (dword
>> shift
) & 0x1ffffffffffLL
;
3155 op
= elf64_ia64_operands
+ opnd
;
3156 err
= (*op
->insert
) (op
, val
, (ia64_insn
*)& insn
);
3158 return bfd_reloc_overflow
;
3160 dword
&= ~(0x1ffffffffffLL
<< shift
);
3161 dword
|= (insn
<< shift
);
3162 bfd_put_64 (abfd
, dword
, hit_addr
);
3166 /* A data relocation. */
3169 bfd_putb32 (val
, hit_addr
);
3171 bfd_putb64 (val
, hit_addr
);
3174 bfd_putl32 (val
, hit_addr
);
3176 bfd_putl64 (val
, hit_addr
);
3180 return bfd_reloc_ok
;
3184 elfNN_ia64_install_dyn_reloc (abfd
, info
, sec
, srel
, offset
, type
,
3187 struct bfd_link_info
*info
;
3195 Elf_Internal_Rela outrel
;
3197 offset
+= sec
->output_section
->vma
+ sec
->output_offset
;
3199 BFD_ASSERT (dynindx
!= -1);
3200 outrel
.r_info
= ELFNN_R_INFO (dynindx
, type
);
3201 outrel
.r_addend
= addend
;
3202 outrel
.r_offset
= _bfd_elf_section_offset (abfd
, info
, sec
, offset
);
3203 if ((outrel
.r_offset
| 1) == (bfd_vma
) -1)
3205 /* Run for the hills. We shouldn't be outputting a relocation
3206 for this. So do what everyone else does and output a no-op. */
3207 outrel
.r_info
= ELFNN_R_INFO (0, R_IA64_NONE
);
3208 outrel
.r_addend
= 0;
3209 outrel
.r_offset
= 0;
3212 bfd_elfNN_swap_reloca_out (abfd
, &outrel
,
3213 ((ElfNN_External_Rela
*) srel
->contents
3214 + srel
->reloc_count
++));
3215 BFD_ASSERT (sizeof (ElfNN_External_Rela
) * srel
->reloc_count
3216 <= srel
->_cooked_size
);
3219 /* Store an entry for target address TARGET_ADDR in the linkage table
3220 and return the gp-relative address of the linkage table entry. */
3223 set_got_entry (abfd
, info
, dyn_i
, dynindx
, addend
, value
, dyn_r_type
)
3225 struct bfd_link_info
*info
;
3226 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
3230 unsigned int dyn_r_type
;
3232 struct elfNN_ia64_link_hash_table
*ia64_info
;
3237 ia64_info
= elfNN_ia64_hash_table (info
);
3238 got_sec
= ia64_info
->got_sec
;
3242 case R_IA64_TPREL64LSB
:
3243 done
= dyn_i
->tprel_done
;
3244 dyn_i
->tprel_done
= true;
3245 got_offset
= dyn_i
->tprel_offset
;
3247 case R_IA64_DTPMOD64LSB
:
3248 done
= dyn_i
->dtpmod_done
;
3249 dyn_i
->dtpmod_done
= true;
3250 got_offset
= dyn_i
->dtpmod_offset
;
3252 case R_IA64_DTPREL64LSB
:
3253 done
= dyn_i
->dtprel_done
;
3254 dyn_i
->dtprel_done
= true;
3255 got_offset
= dyn_i
->dtprel_offset
;
3258 done
= dyn_i
->got_done
;
3259 dyn_i
->got_done
= true;
3260 got_offset
= dyn_i
->got_offset
;
3264 BFD_ASSERT ((got_offset
& 7) == 0);
3268 /* Store the target address in the linkage table entry. */
3269 bfd_put_64 (abfd
, value
, got_sec
->contents
+ got_offset
);
3271 /* Install a dynamic relocation if needed. */
3272 if ((info
->shared
&& dyn_r_type
!= R_IA64_DTPREL64LSB
)
3273 || elfNN_ia64_dynamic_symbol_p (dyn_i
->h
, info
)
3274 || elfNN_ia64_aix_vec (abfd
->xvec
)
3275 || (dynindx
!= -1 && dyn_r_type
== R_IA64_FPTR64LSB
))
3278 && dyn_r_type
!= R_IA64_TPREL64LSB
3279 && dyn_r_type
!= R_IA64_DTPMOD64LSB
3280 && dyn_r_type
!= R_IA64_DTPREL64LSB
)
3282 dyn_r_type
= R_IA64_REL64LSB
;
3287 if (bfd_big_endian (abfd
))
3291 case R_IA64_REL64LSB
:
3292 dyn_r_type
= R_IA64_REL64MSB
;
3294 case R_IA64_DIR64LSB
:
3295 dyn_r_type
= R_IA64_DIR64MSB
;
3297 case R_IA64_FPTR64LSB
:
3298 dyn_r_type
= R_IA64_FPTR64MSB
;
3300 case R_IA64_TPREL64LSB
:
3301 dyn_r_type
= R_IA64_TPREL64MSB
;
3303 case R_IA64_DTPMOD64LSB
:
3304 dyn_r_type
= R_IA64_DTPMOD64MSB
;
3306 case R_IA64_DTPREL64LSB
:
3307 dyn_r_type
= R_IA64_DTPREL64MSB
;
3315 elfNN_ia64_install_dyn_reloc (abfd
, NULL
, got_sec
,
3316 ia64_info
->rel_got_sec
,
3317 got_offset
, dyn_r_type
,
3322 /* Return the address of the linkage table entry. */
3323 value
= (got_sec
->output_section
->vma
3324 + got_sec
->output_offset
3330 /* Fill in a function descriptor consisting of the function's code
3331 address and its global pointer. Return the descriptor's address. */
3334 set_fptr_entry (abfd
, info
, dyn_i
, value
)
3336 struct bfd_link_info
*info
;
3337 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
3340 struct elfNN_ia64_link_hash_table
*ia64_info
;
3343 ia64_info
= elfNN_ia64_hash_table (info
);
3344 fptr_sec
= ia64_info
->fptr_sec
;
3346 if (!dyn_i
->fptr_done
)
3348 dyn_i
->fptr_done
= 1;
3350 /* Fill in the function descriptor. */
3351 bfd_put_64 (abfd
, value
, fptr_sec
->contents
+ dyn_i
->fptr_offset
);
3352 bfd_put_64 (abfd
, _bfd_get_gp_value (abfd
),
3353 fptr_sec
->contents
+ dyn_i
->fptr_offset
+ 8);
3356 /* Return the descriptor's address. */
3357 value
= (fptr_sec
->output_section
->vma
3358 + fptr_sec
->output_offset
3359 + dyn_i
->fptr_offset
);
3364 /* Fill in a PLTOFF entry consisting of the function's code address
3365 and its global pointer. Return the descriptor's address. */
3368 set_pltoff_entry (abfd
, info
, dyn_i
, value
, is_plt
)
3370 struct bfd_link_info
*info
;
3371 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
3375 struct elfNN_ia64_link_hash_table
*ia64_info
;
3376 asection
*pltoff_sec
;
3378 ia64_info
= elfNN_ia64_hash_table (info
);
3379 pltoff_sec
= ia64_info
->pltoff_sec
;
3381 /* Don't do anything if this symbol uses a real PLT entry. In
3382 that case, we'll fill this in during finish_dynamic_symbol. */
3383 if ((! dyn_i
->want_plt
|| is_plt
)
3384 && !dyn_i
->pltoff_done
)
3386 bfd_vma gp
= _bfd_get_gp_value (abfd
);
3388 /* Fill in the function descriptor. */
3389 bfd_put_64 (abfd
, value
, pltoff_sec
->contents
+ dyn_i
->pltoff_offset
);
3390 bfd_put_64 (abfd
, gp
, pltoff_sec
->contents
+ dyn_i
->pltoff_offset
+ 8);
3392 /* Install dynamic relocations if needed. */
3393 if (!is_plt
&& info
->shared
)
3395 unsigned int dyn_r_type
;
3397 if (bfd_big_endian (abfd
))
3398 dyn_r_type
= R_IA64_REL64MSB
;
3400 dyn_r_type
= R_IA64_REL64LSB
;
3402 elfNN_ia64_install_dyn_reloc (abfd
, NULL
, pltoff_sec
,
3403 ia64_info
->rel_pltoff_sec
,
3404 dyn_i
->pltoff_offset
,
3405 dyn_r_type
, 0, value
);
3406 elfNN_ia64_install_dyn_reloc (abfd
, NULL
, pltoff_sec
,
3407 ia64_info
->rel_pltoff_sec
,
3408 dyn_i
->pltoff_offset
+ 8,
3412 dyn_i
->pltoff_done
= 1;
3415 /* Return the descriptor's address. */
3416 value
= (pltoff_sec
->output_section
->vma
3417 + pltoff_sec
->output_offset
3418 + dyn_i
->pltoff_offset
);
3423 /* Return the base VMA address which should be subtracted from real addresses
3424 when resolving @tprel() relocation.
3425 Main program TLS (whose template starts at PT_TLS p_vaddr)
3426 is assigned offset round(16, PT_TLS p_align). */
3429 elfNN_ia64_tprel_base (info
)
3430 struct bfd_link_info
*info
;
3432 struct elf_link_tls_segment
*tls_segment
3433 = elf_hash_table (info
)->tls_segment
;
3435 BFD_ASSERT (tls_segment
!= NULL
);
3436 return (tls_segment
->start
3437 - align_power ((bfd_vma
) 16, tls_segment
->align
));
3440 /* Return the base VMA address which should be subtracted from real addresses
3441 when resolving @dtprel() relocation.
3442 This is PT_TLS segment p_vaddr. */
3445 elfNN_ia64_dtprel_base (info
)
3446 struct bfd_link_info
*info
;
3448 BFD_ASSERT (elf_hash_table (info
)->tls_segment
!= NULL
);
3449 return elf_hash_table (info
)->tls_segment
->start
;
3452 /* Called through qsort to sort the .IA_64.unwind section during a
3453 non-relocatable link. Set elfNN_ia64_unwind_entry_compare_bfd
3454 to the output bfd so we can do proper endianness frobbing. */
3456 static bfd
*elfNN_ia64_unwind_entry_compare_bfd
;
3459 elfNN_ia64_unwind_entry_compare (a
, b
)
3465 av
= bfd_get_64 (elfNN_ia64_unwind_entry_compare_bfd
, a
);
3466 bv
= bfd_get_64 (elfNN_ia64_unwind_entry_compare_bfd
, b
);
3468 return (av
< bv
? -1 : av
> bv
? 1 : 0);
3472 elfNN_ia64_final_link (abfd
, info
)
3474 struct bfd_link_info
*info
;
3476 struct elfNN_ia64_link_hash_table
*ia64_info
;
3477 asection
*unwind_output_sec
;
3479 ia64_info
= elfNN_ia64_hash_table (info
);
3481 /* Make sure we've got ourselves a nice fat __gp value. */
3482 if (!info
->relocateable
)
3484 bfd_vma min_vma
= (bfd_vma
) -1, max_vma
= 0;
3485 bfd_vma min_short_vma
= min_vma
, max_short_vma
= 0;
3486 struct elf_link_hash_entry
*gp
;
3490 /* Find the min and max vma of all sections marked short. Also
3491 collect min and max vma of any type, for use in selecting a
3493 for (os
= abfd
->sections
; os
; os
= os
->next
)
3497 if ((os
->flags
& SEC_ALLOC
) == 0)
3501 hi
= os
->vma
+ os
->_raw_size
;
3509 if (os
->flags
& SEC_SMALL_DATA
)
3511 if (min_short_vma
> lo
)
3513 if (max_short_vma
< hi
)
3518 /* See if the user wants to force a value. */
3519 gp
= elf_link_hash_lookup (elf_hash_table (info
), "__gp", false,
3523 && (gp
->root
.type
== bfd_link_hash_defined
3524 || gp
->root
.type
== bfd_link_hash_defweak
))
3526 asection
*gp_sec
= gp
->root
.u
.def
.section
;
3527 gp_val
= (gp
->root
.u
.def
.value
3528 + gp_sec
->output_section
->vma
3529 + gp_sec
->output_offset
);
3533 /* Pick a sensible value. */
3535 asection
*got_sec
= ia64_info
->got_sec
;
3537 /* Start with just the address of the .got. */
3539 gp_val
= got_sec
->output_section
->vma
;
3540 else if (max_short_vma
!= 0)
3541 gp_val
= min_short_vma
;
3545 /* If it is possible to address the entire image, but we
3546 don't with the choice above, adjust. */
3547 if (max_vma
- min_vma
< 0x400000
3548 && max_vma
- gp_val
<= 0x200000
3549 && gp_val
- min_vma
> 0x200000)
3550 gp_val
= min_vma
+ 0x200000;
3551 else if (max_short_vma
!= 0)
3553 /* If we don't cover all the short data, adjust. */
3554 if (max_short_vma
- gp_val
>= 0x200000)
3555 gp_val
= min_short_vma
+ 0x200000;
3557 /* If we're addressing stuff past the end, adjust back. */
3558 if (gp_val
> max_vma
)
3559 gp_val
= max_vma
- 0x200000 + 8;
3563 /* Validate whether all SHF_IA_64_SHORT sections are within
3564 range of the chosen GP. */
3566 if (max_short_vma
!= 0)
3568 if (max_short_vma
- min_short_vma
>= 0x400000)
3570 (*_bfd_error_handler
)
3571 (_("%s: short data segment overflowed (0x%lx >= 0x400000)"),
3572 bfd_get_filename (abfd
),
3573 (unsigned long) (max_short_vma
- min_short_vma
));
3576 else if ((gp_val
> min_short_vma
3577 && gp_val
- min_short_vma
> 0x200000)
3578 || (gp_val
< max_short_vma
3579 && max_short_vma
- gp_val
>= 0x200000))
3581 (*_bfd_error_handler
)
3582 (_("%s: __gp does not cover short data segment"),
3583 bfd_get_filename (abfd
));
3588 _bfd_set_gp_value (abfd
, gp_val
);
3592 gp
->root
.type
= bfd_link_hash_defined
;
3593 gp
->root
.u
.def
.value
= gp_val
;
3594 gp
->root
.u
.def
.section
= bfd_abs_section_ptr
;
3598 /* If we're producing a final executable, we need to sort the contents
3599 of the .IA_64.unwind section. Force this section to be relocated
3600 into memory rather than written immediately to the output file. */
3601 unwind_output_sec
= NULL
;
3602 if (!info
->relocateable
)
3604 asection
*s
= bfd_get_section_by_name (abfd
, ELF_STRING_ia64_unwind
);
3607 unwind_output_sec
= s
->output_section
;
3608 unwind_output_sec
->contents
3609 = bfd_malloc (unwind_output_sec
->_raw_size
);
3610 if (unwind_output_sec
->contents
== NULL
)
3615 /* Invoke the regular ELF backend linker to do all the work. */
3616 if (!bfd_elfNN_bfd_final_link (abfd
, info
))
3619 if (unwind_output_sec
)
3621 elfNN_ia64_unwind_entry_compare_bfd
= abfd
;
3622 qsort (unwind_output_sec
->contents
,
3623 (size_t) (unwind_output_sec
->_raw_size
/ 24),
3625 elfNN_ia64_unwind_entry_compare
);
3627 if (! bfd_set_section_contents (abfd
, unwind_output_sec
,
3628 unwind_output_sec
->contents
, (bfd_vma
) 0,
3629 unwind_output_sec
->_raw_size
))
3637 elfNN_ia64_relocate_section (output_bfd
, info
, input_bfd
, input_section
,
3638 contents
, relocs
, local_syms
, local_sections
)
3640 struct bfd_link_info
*info
;
3642 asection
*input_section
;
3644 Elf_Internal_Rela
*relocs
;
3645 Elf_Internal_Sym
*local_syms
;
3646 asection
**local_sections
;
3648 struct elfNN_ia64_link_hash_table
*ia64_info
;
3649 Elf_Internal_Shdr
*symtab_hdr
;
3650 Elf_Internal_Rela
*rel
;
3651 Elf_Internal_Rela
*relend
;
3653 boolean ret_val
= true; /* for non-fatal errors */
3656 symtab_hdr
= &elf_tdata (input_bfd
)->symtab_hdr
;
3657 ia64_info
= elfNN_ia64_hash_table (info
);
3659 /* Infect various flags from the input section to the output section. */
3660 if (info
->relocateable
)
3664 flags
= elf_section_data(input_section
)->this_hdr
.sh_flags
;
3665 flags
&= SHF_IA_64_NORECOV
;
3667 elf_section_data(input_section
->output_section
)
3668 ->this_hdr
.sh_flags
|= flags
;
3672 gp_val
= _bfd_get_gp_value (output_bfd
);
3673 srel
= get_reloc_section (input_bfd
, ia64_info
, input_section
, false);
3676 relend
= relocs
+ input_section
->reloc_count
;
3677 for (; rel
< relend
; ++rel
)
3679 struct elf_link_hash_entry
*h
;
3680 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
3681 bfd_reloc_status_type r
;
3682 reloc_howto_type
*howto
;
3683 unsigned long r_symndx
;
3684 Elf_Internal_Sym
*sym
;
3685 unsigned int r_type
;
3689 boolean dynamic_symbol_p
;
3690 boolean undef_weak_ref
;
3692 r_type
= ELFNN_R_TYPE (rel
->r_info
);
3693 if (r_type
> R_IA64_MAX_RELOC_CODE
)
3695 (*_bfd_error_handler
)
3696 (_("%s: unknown relocation type %d"),
3697 bfd_archive_filename (input_bfd
), (int)r_type
);
3698 bfd_set_error (bfd_error_bad_value
);
3703 howto
= lookup_howto (r_type
);
3704 r_symndx
= ELFNN_R_SYM (rel
->r_info
);
3708 undef_weak_ref
= false;
3710 if (r_symndx
< symtab_hdr
->sh_info
)
3712 /* Reloc against local symbol. */
3713 sym
= local_syms
+ r_symndx
;
3714 sym_sec
= local_sections
[r_symndx
];
3715 value
= _bfd_elf_rela_local_sym (output_bfd
, sym
, sym_sec
, rel
);
3716 if ((sym_sec
->flags
& SEC_MERGE
)
3717 && ELF_ST_TYPE (sym
->st_info
) == STT_SECTION
3718 && (elf_section_data (sym_sec
)->sec_info_type
3719 == ELF_INFO_TYPE_MERGE
))
3721 struct elfNN_ia64_local_hash_entry
*loc_h
;
3723 loc_h
= get_local_sym_hash (ia64_info
, input_bfd
, rel
, false);
3724 if (loc_h
&& ! loc_h
->sec_merge_done
)
3726 struct elfNN_ia64_dyn_sym_info
*dynent
;
3729 for (dynent
= loc_h
->info
; dynent
; dynent
= dynent
->next
)
3733 _bfd_merged_section_offset (output_bfd
, &msec
,
3734 elf_section_data (msec
)->
3739 dynent
->addend
-= sym
->st_value
;
3740 dynent
->addend
+= msec
->output_section
->vma
3741 + msec
->output_offset
3742 - sym_sec
->output_section
->vma
3743 - sym_sec
->output_offset
;
3745 loc_h
->sec_merge_done
= 1;
3753 /* Reloc against global symbol. */
3754 indx
= r_symndx
- symtab_hdr
->sh_info
;
3755 h
= elf_sym_hashes (input_bfd
)[indx
];
3756 while (h
->root
.type
== bfd_link_hash_indirect
3757 || h
->root
.type
== bfd_link_hash_warning
)
3758 h
= (struct elf_link_hash_entry
*) h
->root
.u
.i
.link
;
3761 if (h
->root
.type
== bfd_link_hash_defined
3762 || h
->root
.type
== bfd_link_hash_defweak
)
3764 sym_sec
= h
->root
.u
.def
.section
;
3766 /* Detect the cases that sym_sec->output_section is
3767 expected to be NULL -- all cases in which the symbol
3768 is defined in another shared module. This includes
3769 PLT relocs for which we've created a PLT entry and
3770 other relocs for which we're prepared to create
3771 dynamic relocations. */
3772 /* ??? Just accept it NULL and continue. */
3774 if (sym_sec
->output_section
!= NULL
)
3776 value
= (h
->root
.u
.def
.value
3777 + sym_sec
->output_section
->vma
3778 + sym_sec
->output_offset
);
3781 else if (h
->root
.type
== bfd_link_hash_undefweak
)
3782 undef_weak_ref
= true;
3783 else if (info
->shared
3784 && (!info
->symbolic
|| info
->allow_shlib_undefined
)
3785 && !info
->no_undefined
3786 && ELF_ST_VISIBILITY (h
->other
) == STV_DEFAULT
)
3790 if (! ((*info
->callbacks
->undefined_symbol
)
3791 (info
, h
->root
.root
.string
, input_bfd
,
3792 input_section
, rel
->r_offset
,
3793 (!info
->shared
|| info
->no_undefined
3794 || ELF_ST_VISIBILITY (h
->other
)))))
3801 hit_addr
= contents
+ rel
->r_offset
;
3802 value
+= rel
->r_addend
;
3803 dynamic_symbol_p
= elfNN_ia64_dynamic_symbol_p (h
, info
);
3814 case R_IA64_DIR32MSB
:
3815 case R_IA64_DIR32LSB
:
3816 case R_IA64_DIR64MSB
:
3817 case R_IA64_DIR64LSB
:
3818 /* Install a dynamic relocation for this reloc. */
3819 if ((dynamic_symbol_p
|| info
->shared
3820 || (elfNN_ia64_aix_vec (info
->hash
->creator
)
3821 /* Don't emit relocs for __GLOB_DATA_PTR on AIX. */
3822 && (!h
|| strcmp (h
->root
.root
.string
,
3823 "__GLOB_DATA_PTR") != 0)))
3825 && (input_section
->flags
& SEC_ALLOC
) != 0)
3827 unsigned int dyn_r_type
;
3831 BFD_ASSERT (srel
!= NULL
);
3833 /* If we don't need dynamic symbol lookup, find a
3834 matching RELATIVE relocation. */
3835 dyn_r_type
= r_type
;
3836 if (dynamic_symbol_p
)
3838 dynindx
= h
->dynindx
;
3839 addend
= rel
->r_addend
;
3846 case R_IA64_DIR32MSB
:
3847 dyn_r_type
= R_IA64_REL32MSB
;
3849 case R_IA64_DIR32LSB
:
3850 dyn_r_type
= R_IA64_REL32LSB
;
3852 case R_IA64_DIR64MSB
:
3853 dyn_r_type
= R_IA64_REL64MSB
;
3855 case R_IA64_DIR64LSB
:
3856 dyn_r_type
= R_IA64_REL64LSB
;
3860 /* We can't represent this without a dynamic symbol.
3861 Adjust the relocation to be against an output
3862 section symbol, which are always present in the
3863 dynamic symbol table. */
3864 /* ??? People shouldn't be doing non-pic code in
3865 shared libraries. Hork. */
3866 (*_bfd_error_handler
)
3867 (_("%s: linking non-pic code in a shared library"),
3868 bfd_archive_filename (input_bfd
));
3876 if (elfNN_ia64_aix_vec (info
->hash
->creator
))
3877 rel
->r_addend
= value
;
3878 elfNN_ia64_install_dyn_reloc (output_bfd
, info
, input_section
,
3879 srel
, rel
->r_offset
, dyn_r_type
,
3884 case R_IA64_LTV32MSB
:
3885 case R_IA64_LTV32LSB
:
3886 case R_IA64_LTV64MSB
:
3887 case R_IA64_LTV64LSB
:
3888 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
3891 case R_IA64_GPREL22
:
3892 case R_IA64_GPREL64I
:
3893 case R_IA64_GPREL32MSB
:
3894 case R_IA64_GPREL32LSB
:
3895 case R_IA64_GPREL64MSB
:
3896 case R_IA64_GPREL64LSB
:
3897 if (dynamic_symbol_p
)
3899 (*_bfd_error_handler
)
3900 (_("%s: @gprel relocation against dynamic symbol %s"),
3901 bfd_archive_filename (input_bfd
), h
->root
.root
.string
);
3906 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
3909 case R_IA64_LTOFF22
:
3910 case R_IA64_LTOFF22X
:
3911 case R_IA64_LTOFF64I
:
3912 dyn_i
= get_dyn_sym_info (ia64_info
, h
, input_bfd
, rel
, false);
3913 value
= set_got_entry (input_bfd
, info
, dyn_i
, (h
? h
->dynindx
: -1),
3914 rel
->r_addend
, value
, R_IA64_DIR64LSB
);
3916 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
3919 case R_IA64_PLTOFF22
:
3920 case R_IA64_PLTOFF64I
:
3921 case R_IA64_PLTOFF64MSB
:
3922 case R_IA64_PLTOFF64LSB
:
3923 dyn_i
= get_dyn_sym_info (ia64_info
, h
, input_bfd
, rel
, false);
3924 value
= set_pltoff_entry (output_bfd
, info
, dyn_i
, value
, false);
3926 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
3929 case R_IA64_FPTR64I
:
3930 case R_IA64_FPTR32MSB
:
3931 case R_IA64_FPTR32LSB
:
3932 case R_IA64_FPTR64MSB
:
3933 case R_IA64_FPTR64LSB
:
3934 dyn_i
= get_dyn_sym_info (ia64_info
, h
, input_bfd
, rel
, false);
3935 if (dyn_i
->want_fptr
)
3937 if (!undef_weak_ref
)
3938 value
= set_fptr_entry (output_bfd
, info
, dyn_i
, value
);
3944 /* Otherwise, we expect the dynamic linker to create
3949 if (h
->dynindx
!= -1)
3950 dynindx
= h
->dynindx
;
3952 dynindx
= (_bfd_elf_link_lookup_local_dynindx
3953 (info
, h
->root
.u
.def
.section
->owner
,
3954 global_sym_index (h
)));
3958 dynindx
= (_bfd_elf_link_lookup_local_dynindx
3959 (info
, input_bfd
, (long) r_symndx
));
3962 elfNN_ia64_install_dyn_reloc (output_bfd
, info
, input_section
,
3963 srel
, rel
->r_offset
, r_type
,
3964 dynindx
, rel
->r_addend
);
3968 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
3971 case R_IA64_LTOFF_FPTR22
:
3972 case R_IA64_LTOFF_FPTR64I
:
3973 case R_IA64_LTOFF_FPTR32MSB
:
3974 case R_IA64_LTOFF_FPTR32LSB
:
3975 case R_IA64_LTOFF_FPTR64MSB
:
3976 case R_IA64_LTOFF_FPTR64LSB
:
3980 dyn_i
= get_dyn_sym_info (ia64_info
, h
, input_bfd
, rel
, false);
3981 if (dyn_i
->want_fptr
)
3983 BFD_ASSERT (h
== NULL
|| h
->dynindx
== -1)
3984 if (!undef_weak_ref
)
3985 value
= set_fptr_entry (output_bfd
, info
, dyn_i
, value
);
3990 /* Otherwise, we expect the dynamic linker to create
3994 if (h
->dynindx
!= -1)
3995 dynindx
= h
->dynindx
;
3997 dynindx
= (_bfd_elf_link_lookup_local_dynindx
3998 (info
, h
->root
.u
.def
.section
->owner
,
3999 global_sym_index (h
)));
4002 dynindx
= (_bfd_elf_link_lookup_local_dynindx
4003 (info
, input_bfd
, (long) r_symndx
));
4007 value
= set_got_entry (output_bfd
, info
, dyn_i
, dynindx
,
4008 rel
->r_addend
, value
, R_IA64_FPTR64LSB
);
4010 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4014 case R_IA64_PCREL32MSB
:
4015 case R_IA64_PCREL32LSB
:
4016 case R_IA64_PCREL64MSB
:
4017 case R_IA64_PCREL64LSB
:
4018 /* Install a dynamic relocation for this reloc. */
4019 if ((dynamic_symbol_p
4020 || elfNN_ia64_aix_vec (info
->hash
->creator
))
4023 BFD_ASSERT (srel
!= NULL
);
4025 elfNN_ia64_install_dyn_reloc (output_bfd
, info
, input_section
,
4026 srel
, rel
->r_offset
, r_type
,
4027 h
->dynindx
, rel
->r_addend
);
4031 case R_IA64_PCREL21BI
:
4032 case R_IA64_PCREL21F
:
4033 case R_IA64_PCREL21M
:
4034 /* ??? These two are only used for speculation fixup code.
4035 They should never be dynamic. */
4036 if (dynamic_symbol_p
)
4038 (*_bfd_error_handler
)
4039 (_("%s: dynamic relocation against speculation fixup"),
4040 bfd_archive_filename (input_bfd
));
4046 (*_bfd_error_handler
)
4047 (_("%s: speculation fixup against undefined weak symbol"),
4048 bfd_archive_filename (input_bfd
));
4054 case R_IA64_PCREL21B
:
4055 case R_IA64_PCREL60B
:
4056 /* We should have created a PLT entry for any dynamic symbol. */
4059 dyn_i
= get_dyn_sym_info (ia64_info
, h
, NULL
, NULL
, false);
4061 if (dyn_i
&& dyn_i
->want_plt2
)
4063 /* Should have caught this earlier. */
4064 BFD_ASSERT (rel
->r_addend
== 0);
4066 value
= (ia64_info
->plt_sec
->output_section
->vma
4067 + ia64_info
->plt_sec
->output_offset
4068 + dyn_i
->plt2_offset
);
4072 /* Since there's no PLT entry, Validate that this is
4074 BFD_ASSERT (undef_weak_ref
|| sym_sec
->output_section
!= NULL
);
4076 /* If the symbol is undef_weak, we shouldn't be trying
4077 to call it. There's every chance that we'd wind up
4078 with an out-of-range fixup here. Don't bother setting
4079 any value at all. */
4085 case R_IA64_PCREL22
:
4086 case R_IA64_PCREL64I
:
4088 /* Make pc-relative. */
4089 value
-= (input_section
->output_section
->vma
4090 + input_section
->output_offset
4091 + rel
->r_offset
) & ~ (bfd_vma
) 0x3;
4092 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4095 case R_IA64_SEGREL32MSB
:
4096 case R_IA64_SEGREL32LSB
:
4097 case R_IA64_SEGREL64MSB
:
4098 case R_IA64_SEGREL64LSB
:
4101 /* If the input section was discarded from the output, then
4107 struct elf_segment_map
*m
;
4108 Elf_Internal_Phdr
*p
;
4110 /* Find the segment that contains the output_section. */
4111 for (m
= elf_tdata (output_bfd
)->segment_map
,
4112 p
= elf_tdata (output_bfd
)->phdr
;
4117 for (i
= m
->count
- 1; i
>= 0; i
--)
4118 if (m
->sections
[i
] == sym_sec
->output_section
)
4126 r
= bfd_reloc_notsupported
;
4130 /* The VMA of the segment is the vaddr of the associated
4132 if (value
> p
->p_vaddr
)
4133 value
-= p
->p_vaddr
;
4136 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
,
4142 case R_IA64_SECREL32MSB
:
4143 case R_IA64_SECREL32LSB
:
4144 case R_IA64_SECREL64MSB
:
4145 case R_IA64_SECREL64LSB
:
4146 /* Make output-section relative. */
4147 if (value
> input_section
->output_section
->vma
)
4148 value
-= input_section
->output_section
->vma
;
4151 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4154 case R_IA64_IPLTMSB
:
4155 case R_IA64_IPLTLSB
:
4156 /* Install a dynamic relocation for this reloc. */
4157 if ((dynamic_symbol_p
|| info
->shared
)
4158 && (input_section
->flags
& SEC_ALLOC
) != 0)
4160 BFD_ASSERT (srel
!= NULL
);
4162 /* If we don't need dynamic symbol lookup, install two
4163 RELATIVE relocations. */
4164 if (! dynamic_symbol_p
)
4166 unsigned int dyn_r_type
;
4168 if (r_type
== R_IA64_IPLTMSB
)
4169 dyn_r_type
= R_IA64_REL64MSB
;
4171 dyn_r_type
= R_IA64_REL64LSB
;
4173 elfNN_ia64_install_dyn_reloc (output_bfd
, info
,
4175 srel
, rel
->r_offset
,
4176 dyn_r_type
, 0, value
);
4177 elfNN_ia64_install_dyn_reloc (output_bfd
, info
,
4179 srel
, rel
->r_offset
+ 8,
4180 dyn_r_type
, 0, gp_val
);
4183 elfNN_ia64_install_dyn_reloc (output_bfd
, info
, input_section
,
4184 srel
, rel
->r_offset
, r_type
,
4185 h
->dynindx
, rel
->r_addend
);
4188 if (r_type
== R_IA64_IPLTMSB
)
4189 r_type
= R_IA64_DIR64MSB
;
4191 r_type
= R_IA64_DIR64LSB
;
4192 elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4193 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
+ 8, gp_val
,
4197 case R_IA64_TPREL14
:
4198 case R_IA64_TPREL22
:
4199 case R_IA64_TPREL64I
:
4200 value
-= elfNN_ia64_tprel_base (info
);
4201 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4204 case R_IA64_DTPREL14
:
4205 case R_IA64_DTPREL22
:
4206 case R_IA64_DTPREL64I
:
4207 value
-= elfNN_ia64_dtprel_base (info
);
4208 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
, r_type
);
4211 case R_IA64_LTOFF_TPREL22
:
4212 case R_IA64_LTOFF_DTPMOD22
:
4213 case R_IA64_LTOFF_DTPREL22
:
4220 case R_IA64_LTOFF_TPREL22
:
4221 if (!dynamic_symbol_p
&& !info
->shared
)
4222 value
-= elfNN_ia64_tprel_base (info
);
4223 got_r_type
= R_IA64_TPREL64LSB
;
4225 case R_IA64_LTOFF_DTPMOD22
:
4226 if (!dynamic_symbol_p
&& !info
->shared
)
4228 got_r_type
= R_IA64_DTPMOD64LSB
;
4230 case R_IA64_LTOFF_DTPREL22
:
4231 if (!dynamic_symbol_p
)
4232 value
-= elfNN_ia64_dtprel_base (info
);
4233 got_r_type
= R_IA64_DTPREL64LSB
;
4236 dyn_i
= get_dyn_sym_info (ia64_info
, h
, input_bfd
, rel
, false);
4237 value
= set_got_entry (input_bfd
, info
, dyn_i
,
4238 (h
? h
->dynindx
: -1), rel
->r_addend
,
4241 r
= elfNN_ia64_install_value (output_bfd
, hit_addr
, value
,
4247 r
= bfd_reloc_notsupported
;
4256 case bfd_reloc_undefined
:
4257 /* This can happen for global table relative relocs if
4258 __gp is undefined. This is a panic situation so we
4259 don't try to continue. */
4260 (*info
->callbacks
->undefined_symbol
)
4261 (info
, "__gp", input_bfd
, input_section
, rel
->r_offset
, 1);
4264 case bfd_reloc_notsupported
:
4269 name
= h
->root
.root
.string
;
4272 name
= bfd_elf_string_from_elf_section (input_bfd
,
4273 symtab_hdr
->sh_link
,
4278 name
= bfd_section_name (input_bfd
, input_section
);
4280 if (!(*info
->callbacks
->warning
) (info
, _("unsupported reloc"),
4282 input_section
, rel
->r_offset
))
4288 case bfd_reloc_dangerous
:
4289 case bfd_reloc_outofrange
:
4290 case bfd_reloc_overflow
:
4296 name
= h
->root
.root
.string
;
4299 name
= bfd_elf_string_from_elf_section (input_bfd
,
4300 symtab_hdr
->sh_link
,
4305 name
= bfd_section_name (input_bfd
, input_section
);
4307 if (!(*info
->callbacks
->reloc_overflow
) (info
, name
,
4324 elfNN_ia64_finish_dynamic_symbol (output_bfd
, info
, h
, sym
)
4326 struct bfd_link_info
*info
;
4327 struct elf_link_hash_entry
*h
;
4328 Elf_Internal_Sym
*sym
;
4330 struct elfNN_ia64_link_hash_table
*ia64_info
;
4331 struct elfNN_ia64_dyn_sym_info
*dyn_i
;
4333 ia64_info
= elfNN_ia64_hash_table (info
);
4334 dyn_i
= get_dyn_sym_info (ia64_info
, h
, NULL
, NULL
, false);
4336 /* Fill in the PLT data, if required. */
4337 if (dyn_i
&& dyn_i
->want_plt
)
4339 Elf_Internal_Rela outrel
;
4342 bfd_vma plt_addr
, pltoff_addr
, gp_val
, index
;
4343 ElfNN_External_Rela
*rel
;
4345 gp_val
= _bfd_get_gp_value (output_bfd
);
4347 /* Initialize the minimal PLT entry. */
4349 index
= (dyn_i
->plt_offset
- PLT_HEADER_SIZE
) / PLT_MIN_ENTRY_SIZE
;
4350 plt_sec
= ia64_info
->plt_sec
;
4351 loc
= plt_sec
->contents
+ dyn_i
->plt_offset
;
4353 memcpy (loc
, plt_min_entry
, PLT_MIN_ENTRY_SIZE
);
4354 elfNN_ia64_install_value (output_bfd
, loc
, index
, R_IA64_IMM22
);
4355 elfNN_ia64_install_value (output_bfd
, loc
+2, -dyn_i
->plt_offset
,
4358 plt_addr
= (plt_sec
->output_section
->vma
4359 + plt_sec
->output_offset
4360 + dyn_i
->plt_offset
);
4361 pltoff_addr
= set_pltoff_entry (output_bfd
, info
, dyn_i
, plt_addr
, true);
4363 /* Initialize the FULL PLT entry, if needed. */
4364 if (dyn_i
->want_plt2
)
4366 loc
= plt_sec
->contents
+ dyn_i
->plt2_offset
;
4368 memcpy (loc
, plt_full_entry
, PLT_FULL_ENTRY_SIZE
);
4369 elfNN_ia64_install_value (output_bfd
, loc
, pltoff_addr
- gp_val
,
4372 /* Mark the symbol as undefined, rather than as defined in the
4373 plt section. Leave the value alone. */
4374 /* ??? We didn't redefine it in adjust_dynamic_symbol in the
4375 first place. But perhaps elflink.h did some for us. */
4376 if ((h
->elf_link_hash_flags
& ELF_LINK_HASH_DEF_REGULAR
) == 0)
4377 sym
->st_shndx
= SHN_UNDEF
;
4380 /* Create the dynamic relocation. */
4381 outrel
.r_offset
= pltoff_addr
;
4382 if (bfd_little_endian (output_bfd
))
4383 outrel
.r_info
= ELFNN_R_INFO (h
->dynindx
, R_IA64_IPLTLSB
);
4385 outrel
.r_info
= ELFNN_R_INFO (h
->dynindx
, R_IA64_IPLTMSB
);
4386 outrel
.r_addend
= 0;
4388 /* This is fun. In the .IA_64.pltoff section, we've got entries
4389 that correspond both to real PLT entries, and those that
4390 happened to resolve to local symbols but need to be created
4391 to satisfy @pltoff relocations. The .rela.IA_64.pltoff
4392 relocations for the real PLT should come at the end of the
4393 section, so that they can be indexed by plt entry at runtime.
4395 We emitted all of the relocations for the non-PLT @pltoff
4396 entries during relocate_section. So we can consider the
4397 existing sec->reloc_count to be the base of the array of
4400 rel
= (ElfNN_External_Rela
*)ia64_info
->rel_pltoff_sec
->contents
;
4401 rel
+= ia64_info
->rel_pltoff_sec
->reloc_count
;
4403 bfd_elfNN_swap_reloca_out (output_bfd
, &outrel
, rel
+ index
);
4406 /* Mark some specially defined symbols as absolute. */
4407 if (strcmp (h
->root
.root
.string
, "_DYNAMIC") == 0
4408 || strcmp (h
->root
.root
.string
, "_GLOBAL_OFFSET_TABLE_") == 0
4409 || strcmp (h
->root
.root
.string
, "_PROCEDURE_LINKAGE_TABLE_") == 0)
4410 sym
->st_shndx
= SHN_ABS
;
4416 elfNN_ia64_finish_dynamic_sections (abfd
, info
)
4418 struct bfd_link_info
*info
;
4420 struct elfNN_ia64_link_hash_table
*ia64_info
;
4423 ia64_info
= elfNN_ia64_hash_table (info
);
4424 dynobj
= ia64_info
->root
.dynobj
;
4426 if (elf_hash_table (info
)->dynamic_sections_created
)
4428 ElfNN_External_Dyn
*dyncon
, *dynconend
;
4429 asection
*sdyn
, *sgotplt
;
4432 sdyn
= bfd_get_section_by_name (dynobj
, ".dynamic");
4433 sgotplt
= bfd_get_section_by_name (dynobj
, ".got.plt");
4434 BFD_ASSERT (sdyn
!= NULL
);
4435 dyncon
= (ElfNN_External_Dyn
*) sdyn
->contents
;
4436 dynconend
= (ElfNN_External_Dyn
*) (sdyn
->contents
+ sdyn
->_raw_size
);
4438 gp_val
= _bfd_get_gp_value (abfd
);
4440 for (; dyncon
< dynconend
; dyncon
++)
4442 Elf_Internal_Dyn dyn
;
4444 bfd_elfNN_swap_dyn_in (dynobj
, dyncon
, &dyn
);
4449 dyn
.d_un
.d_ptr
= gp_val
;
4453 dyn
.d_un
.d_val
= (ia64_info
->minplt_entries
4454 * sizeof (ElfNN_External_Rela
));
4458 /* See the comment above in finish_dynamic_symbol. */
4459 dyn
.d_un
.d_ptr
= (ia64_info
->rel_pltoff_sec
->output_section
->vma
4460 + ia64_info
->rel_pltoff_sec
->output_offset
4461 + (ia64_info
->rel_pltoff_sec
->reloc_count
4462 * sizeof (ElfNN_External_Rela
)));
4465 case DT_IA_64_PLT_RESERVE
:
4466 dyn
.d_un
.d_ptr
= (sgotplt
->output_section
->vma
4467 + sgotplt
->output_offset
);
4471 /* Do not have RELASZ include JMPREL. This makes things
4472 easier on ld.so. This is not what the rest of BFD set up. */
4473 dyn
.d_un
.d_val
-= (ia64_info
->minplt_entries
4474 * sizeof (ElfNN_External_Rela
));
4478 bfd_elfNN_swap_dyn_out (abfd
, &dyn
, dyncon
);
4481 /* Initialize the PLT0 entry */
4482 if (ia64_info
->plt_sec
)
4484 bfd_byte
*loc
= ia64_info
->plt_sec
->contents
;
4487 memcpy (loc
, plt_header
, PLT_HEADER_SIZE
);
4489 pltres
= (sgotplt
->output_section
->vma
4490 + sgotplt
->output_offset
4493 elfNN_ia64_install_value (abfd
, loc
+1, pltres
, R_IA64_GPREL22
);
4500 /* ELF file flag handling: */
4502 /* Function to keep IA-64 specific file flags. */
4504 elfNN_ia64_set_private_flags (abfd
, flags
)
4508 BFD_ASSERT (!elf_flags_init (abfd
)
4509 || elf_elfheader (abfd
)->e_flags
== flags
);
4511 elf_elfheader (abfd
)->e_flags
= flags
;
4512 elf_flags_init (abfd
) = true;
4516 /* Merge backend specific data from an object file to the output
4517 object file when linking. */
4519 elfNN_ia64_merge_private_bfd_data (ibfd
, obfd
)
4526 /* Don't even pretend to support mixed-format linking. */
4527 if (bfd_get_flavour (ibfd
) != bfd_target_elf_flavour
4528 || bfd_get_flavour (obfd
) != bfd_target_elf_flavour
)
4531 in_flags
= elf_elfheader (ibfd
)->e_flags
;
4532 out_flags
= elf_elfheader (obfd
)->e_flags
;
4534 if (! elf_flags_init (obfd
))
4536 elf_flags_init (obfd
) = true;
4537 elf_elfheader (obfd
)->e_flags
= in_flags
;
4539 if (bfd_get_arch (obfd
) == bfd_get_arch (ibfd
)
4540 && bfd_get_arch_info (obfd
)->the_default
)
4542 return bfd_set_arch_mach (obfd
, bfd_get_arch (ibfd
),
4543 bfd_get_mach (ibfd
));
4549 /* Check flag compatibility. */
4550 if (in_flags
== out_flags
)
4553 /* Output has EF_IA_64_REDUCEDFP set only if all inputs have it set. */
4554 if (!(in_flags
& EF_IA_64_REDUCEDFP
) && (out_flags
& EF_IA_64_REDUCEDFP
))
4555 elf_elfheader (obfd
)->e_flags
&= ~EF_IA_64_REDUCEDFP
;
4557 if ((in_flags
& EF_IA_64_TRAPNIL
) != (out_flags
& EF_IA_64_TRAPNIL
))
4559 (*_bfd_error_handler
)
4560 (_("%s: linking trap-on-NULL-dereference with non-trapping files"),
4561 bfd_archive_filename (ibfd
));
4563 bfd_set_error (bfd_error_bad_value
);
4566 if ((in_flags
& EF_IA_64_BE
) != (out_flags
& EF_IA_64_BE
))
4568 (*_bfd_error_handler
)
4569 (_("%s: linking big-endian files with little-endian files"),
4570 bfd_archive_filename (ibfd
));
4572 bfd_set_error (bfd_error_bad_value
);
4575 if ((in_flags
& EF_IA_64_ABI64
) != (out_flags
& EF_IA_64_ABI64
))
4577 (*_bfd_error_handler
)
4578 (_("%s: linking 64-bit files with 32-bit files"),
4579 bfd_archive_filename (ibfd
));
4581 bfd_set_error (bfd_error_bad_value
);
4584 if ((in_flags
& EF_IA_64_CONS_GP
) != (out_flags
& EF_IA_64_CONS_GP
))
4586 (*_bfd_error_handler
)
4587 (_("%s: linking constant-gp files with non-constant-gp files"),
4588 bfd_archive_filename (ibfd
));
4590 bfd_set_error (bfd_error_bad_value
);
4593 if ((in_flags
& EF_IA_64_NOFUNCDESC_CONS_GP
)
4594 != (out_flags
& EF_IA_64_NOFUNCDESC_CONS_GP
))
4596 (*_bfd_error_handler
)
4597 (_("%s: linking auto-pic files with non-auto-pic files"),
4598 bfd_archive_filename (ibfd
));
4600 bfd_set_error (bfd_error_bad_value
);
4608 elfNN_ia64_print_private_bfd_data (abfd
, ptr
)
4612 FILE *file
= (FILE *) ptr
;
4613 flagword flags
= elf_elfheader (abfd
)->e_flags
;
4615 BFD_ASSERT (abfd
!= NULL
&& ptr
!= NULL
);
4617 fprintf (file
, "private flags = %s%s%s%s%s%s%s%s\n",
4618 (flags
& EF_IA_64_TRAPNIL
) ? "TRAPNIL, " : "",
4619 (flags
& EF_IA_64_EXT
) ? "EXT, " : "",
4620 (flags
& EF_IA_64_BE
) ? "BE, " : "LE, ",
4621 (flags
& EF_IA_64_REDUCEDFP
) ? "REDUCEDFP, " : "",
4622 (flags
& EF_IA_64_CONS_GP
) ? "CONS_GP, " : "",
4623 (flags
& EF_IA_64_NOFUNCDESC_CONS_GP
) ? "NOFUNCDESC_CONS_GP, " : "",
4624 (flags
& EF_IA_64_ABSOLUTE
) ? "ABSOLUTE, " : "",
4625 (flags
& EF_IA_64_ABI64
) ? "ABI64" : "ABI32");
4627 _bfd_elf_print_private_bfd_data (abfd
, ptr
);
4631 static enum elf_reloc_type_class
4632 elfNN_ia64_reloc_type_class (rela
)
4633 const Elf_Internal_Rela
*rela
;
4635 switch ((int) ELFNN_R_TYPE (rela
->r_info
))
4637 case R_IA64_REL32MSB
:
4638 case R_IA64_REL32LSB
:
4639 case R_IA64_REL64MSB
:
4640 case R_IA64_REL64LSB
:
4641 return reloc_class_relative
;
4642 case R_IA64_IPLTMSB
:
4643 case R_IA64_IPLTLSB
:
4644 return reloc_class_plt
;
4646 return reloc_class_copy
;
4648 return reloc_class_normal
;
4653 elfNN_ia64_hpux_vec (const bfd_target
*vec
)
4655 extern const bfd_target bfd_elfNN_ia64_hpux_big_vec
;
4656 return (vec
== & bfd_elfNN_ia64_hpux_big_vec
);
4660 elfNN_hpux_post_process_headers (abfd
, info
)
4662 struct bfd_link_info
*info ATTRIBUTE_UNUSED
;
4664 Elf_Internal_Ehdr
*i_ehdrp
= elf_elfheader (abfd
);
4666 i_ehdrp
->e_ident
[EI_OSABI
] = ELFOSABI_HPUX
;
4667 i_ehdrp
->e_ident
[EI_ABIVERSION
] = 1;
4671 elfNN_hpux_backend_section_from_bfd_section (abfd
, sec
, retval
)
4672 bfd
*abfd ATTRIBUTE_UNUSED
;
4676 if (bfd_is_com_section (sec
))
4678 *retval
= SHN_IA_64_ANSI_COMMON
;
4684 #define TARGET_LITTLE_SYM bfd_elfNN_ia64_little_vec
4685 #define TARGET_LITTLE_NAME "elfNN-ia64-little"
4686 #define TARGET_BIG_SYM bfd_elfNN_ia64_big_vec
4687 #define TARGET_BIG_NAME "elfNN-ia64-big"
4688 #define ELF_ARCH bfd_arch_ia64
4689 #define ELF_MACHINE_CODE EM_IA_64
4690 #define ELF_MACHINE_ALT1 1999 /* EAS2.3 */
4691 #define ELF_MACHINE_ALT2 1998 /* EAS2.2 */
4692 #define ELF_MAXPAGESIZE 0x10000 /* 64KB */
4694 #define elf_backend_section_from_shdr \
4695 elfNN_ia64_section_from_shdr
4696 #define elf_backend_section_flags \
4697 elfNN_ia64_section_flags
4698 #define elf_backend_fake_sections \
4699 elfNN_ia64_fake_sections
4700 #define elf_backend_final_write_processing \
4701 elfNN_ia64_final_write_processing
4702 #define elf_backend_add_symbol_hook \
4703 elfNN_ia64_add_symbol_hook
4704 #define elf_backend_additional_program_headers \
4705 elfNN_ia64_additional_program_headers
4706 #define elf_backend_modify_segment_map \
4707 elfNN_ia64_modify_segment_map
4708 #define elf_info_to_howto \
4709 elfNN_ia64_info_to_howto
4711 #define bfd_elfNN_bfd_reloc_type_lookup \
4712 elfNN_ia64_reloc_type_lookup
4713 #define bfd_elfNN_bfd_is_local_label_name \
4714 elfNN_ia64_is_local_label_name
4715 #define bfd_elfNN_bfd_relax_section \
4716 elfNN_ia64_relax_section
4718 /* Stuff for the BFD linker: */
4719 #define bfd_elfNN_bfd_link_hash_table_create \
4720 elfNN_ia64_hash_table_create
4721 #define elf_backend_create_dynamic_sections \
4722 elfNN_ia64_create_dynamic_sections
4723 #define elf_backend_check_relocs \
4724 elfNN_ia64_check_relocs
4725 #define elf_backend_adjust_dynamic_symbol \
4726 elfNN_ia64_adjust_dynamic_symbol
4727 #define elf_backend_size_dynamic_sections \
4728 elfNN_ia64_size_dynamic_sections
4729 #define elf_backend_relocate_section \
4730 elfNN_ia64_relocate_section
4731 #define elf_backend_finish_dynamic_symbol \
4732 elfNN_ia64_finish_dynamic_symbol
4733 #define elf_backend_finish_dynamic_sections \
4734 elfNN_ia64_finish_dynamic_sections
4735 #define bfd_elfNN_bfd_final_link \
4736 elfNN_ia64_final_link
4738 #define bfd_elfNN_bfd_merge_private_bfd_data \
4739 elfNN_ia64_merge_private_bfd_data
4740 #define bfd_elfNN_bfd_set_private_flags \
4741 elfNN_ia64_set_private_flags
4742 #define bfd_elfNN_bfd_print_private_bfd_data \
4743 elfNN_ia64_print_private_bfd_data
4745 #define elf_backend_plt_readonly 1
4746 #define elf_backend_want_plt_sym 0
4747 #define elf_backend_plt_alignment 5
4748 #define elf_backend_got_header_size 0
4749 #define elf_backend_plt_header_size PLT_HEADER_SIZE
4750 #define elf_backend_want_got_plt 1
4751 #define elf_backend_may_use_rel_p 1
4752 #define elf_backend_may_use_rela_p 1
4753 #define elf_backend_default_use_rela_p 1
4754 #define elf_backend_want_dynbss 0
4755 #define elf_backend_copy_indirect_symbol elfNN_ia64_hash_copy_indirect
4756 #define elf_backend_hide_symbol elfNN_ia64_hash_hide_symbol
4757 #define elf_backend_reloc_type_class elfNN_ia64_reloc_type_class
4758 #define elf_backend_rela_normal 1
4760 #include "elfNN-target.h"
4762 /* AIX-specific vectors. */
4764 #undef TARGET_LITTLE_SYM
4765 #define TARGET_LITTLE_SYM bfd_elfNN_ia64_aix_little_vec
4766 #undef TARGET_LITTLE_NAME
4767 #define TARGET_LITTLE_NAME "elfNN-ia64-aix-little"
4768 #undef TARGET_BIG_SYM
4769 #define TARGET_BIG_SYM bfd_elfNN_ia64_aix_big_vec
4770 #undef TARGET_BIG_NAME
4771 #define TARGET_BIG_NAME "elfNN-ia64-aix-big"
4773 #undef elf_backend_add_symbol_hook
4774 #define elf_backend_add_symbol_hook elfNN_ia64_aix_add_symbol_hook
4776 #undef bfd_elfNN_bfd_link_add_symbols
4777 #define bfd_elfNN_bfd_link_add_symbols elfNN_ia64_aix_link_add_symbols
4779 #define elfNN_bed elfNN_ia64_aix_bed
4781 #include "elfNN-target.h"
4783 /* HPUX-specific vectors. */
4785 #undef TARGET_LITTLE_SYM
4786 #undef TARGET_LITTLE_NAME
4787 #undef TARGET_BIG_SYM
4788 #define TARGET_BIG_SYM bfd_elfNN_ia64_hpux_big_vec
4789 #undef TARGET_BIG_NAME
4790 #define TARGET_BIG_NAME "elfNN-ia64-hpux-big"
4792 /* We need to undo the AIX specific functions. */
4794 #undef elf_backend_add_symbol_hook
4795 #define elf_backend_add_symbol_hook elfNN_ia64_add_symbol_hook
4797 #undef bfd_elfNN_bfd_link_add_symbols
4798 #define bfd_elfNN_bfd_link_add_symbols _bfd_generic_link_add_symbols
4800 /* These are HP-UX specific functions. */
4802 #undef elf_backend_post_process_headers
4803 #define elf_backend_post_process_headers elfNN_hpux_post_process_headers
4805 #undef elf_backend_section_from_bfd_section
4806 #define elf_backend_section_from_bfd_section elfNN_hpux_backend_section_from_bfd_section
4808 #undef elf_backend_want_p_paddr_set_to_zero
4809 #define elf_backend_want_p_paddr_set_to_zero 1
4811 #undef ELF_MAXPAGESIZE
4812 #define ELF_MAXPAGESIZE 0x1000 /* 1K */
4815 #define elfNN_bed elfNN_ia64_hpux_bed
4817 #include "elfNN-target.h"
4819 #undef elf_backend_want_p_paddr_set_to_zero