elf64-ia64-vms.c revision 1.1.1.1.4.2 1 1.1.1.1.4.2 yamt /* IA-64 support for OpenVMS
2 1.1.1.1.4.2 yamt Copyright 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007,
3 1.1.1.1.4.2 yamt 2008, 2009, 2010, 2012 Free Software Foundation, Inc.
4 1.1.1.1.4.2 yamt
5 1.1.1.1.4.2 yamt This file is part of BFD, the Binary File Descriptor library.
6 1.1.1.1.4.2 yamt
7 1.1.1.1.4.2 yamt This program is free software; you can redistribute it and/or modify
8 1.1.1.1.4.2 yamt it under the terms of the GNU General Public License as published by
9 1.1.1.1.4.2 yamt the Free Software Foundation; either version 3 of the License, or
10 1.1.1.1.4.2 yamt (at your option) any later version.
11 1.1.1.1.4.2 yamt
12 1.1.1.1.4.2 yamt This program is distributed in the hope that it will be useful,
13 1.1.1.1.4.2 yamt but WITHOUT ANY WARRANTY; without even the implied warranty of
14 1.1.1.1.4.2 yamt MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 1.1.1.1.4.2 yamt GNU General Public License for more details.
16 1.1.1.1.4.2 yamt
17 1.1.1.1.4.2 yamt You should have received a copy of the GNU General Public License
18 1.1.1.1.4.2 yamt along with this program; if not, write to the Free Software
19 1.1.1.1.4.2 yamt Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 1.1.1.1.4.2 yamt MA 02110-1301, USA. */
21 1.1.1.1.4.2 yamt
22 1.1.1.1.4.2 yamt #include "sysdep.h"
23 1.1.1.1.4.2 yamt #include "bfd.h"
24 1.1.1.1.4.2 yamt #include "libbfd.h"
25 1.1.1.1.4.2 yamt #include "elf-bfd.h"
26 1.1.1.1.4.2 yamt #include "opcode/ia64.h"
27 1.1.1.1.4.2 yamt #include "elf/ia64.h"
28 1.1.1.1.4.2 yamt #include "objalloc.h"
29 1.1.1.1.4.2 yamt #include "hashtab.h"
30 1.1.1.1.4.2 yamt #include "elfxx-ia64.h"
31 1.1.1.1.4.2 yamt #include "vms.h"
32 1.1.1.1.4.2 yamt #include "bfdver.h"
33 1.1.1.1.4.2 yamt
34 1.1.1.1.4.2 yamt /* THE RULES for all the stuff the linker creates --
35 1.1.1.1.4.2 yamt
36 1.1.1.1.4.2 yamt GOT Entries created in response to LTOFF or LTOFF_FPTR
37 1.1.1.1.4.2 yamt relocations. Dynamic relocs created for dynamic
38 1.1.1.1.4.2 yamt symbols in an application; REL relocs for locals
39 1.1.1.1.4.2 yamt in a shared library.
40 1.1.1.1.4.2 yamt
41 1.1.1.1.4.2 yamt FPTR The canonical function descriptor. Created for local
42 1.1.1.1.4.2 yamt symbols in applications. Descriptors for dynamic symbols
43 1.1.1.1.4.2 yamt and local symbols in shared libraries are created by
44 1.1.1.1.4.2 yamt ld.so. Thus there are no dynamic relocs against these
45 1.1.1.1.4.2 yamt objects. The FPTR relocs for such _are_ passed through
46 1.1.1.1.4.2 yamt to the dynamic relocation tables.
47 1.1.1.1.4.2 yamt
48 1.1.1.1.4.2 yamt FULL_PLT Created for a PCREL21B relocation against a dynamic symbol.
49 1.1.1.1.4.2 yamt Requires the creation of a PLTOFF entry. This does not
50 1.1.1.1.4.2 yamt require any dynamic relocations.
51 1.1.1.1.4.2 yamt
52 1.1.1.1.4.2 yamt PLTOFF Created by PLTOFF relocations. For local symbols, this
53 1.1.1.1.4.2 yamt is an alternate function descriptor, and in shared libraries
54 1.1.1.1.4.2 yamt requires two REL relocations. Note that this cannot be
55 1.1.1.1.4.2 yamt transformed into an FPTR relocation, since it must be in
56 1.1.1.1.4.2 yamt range of the GP. For dynamic symbols, this is a function
57 1.1.1.1.4.2 yamt descriptor. */
58 1.1.1.1.4.2 yamt
59 1.1.1.1.4.2 yamt typedef struct bfd_hash_entry *(*new_hash_entry_func)
60 1.1.1.1.4.2 yamt (struct bfd_hash_entry *, struct bfd_hash_table *, const char *);
61 1.1.1.1.4.2 yamt
62 1.1.1.1.4.2 yamt /* In dynamically (linker-) created sections, we generally need to keep track
63 1.1.1.1.4.2 yamt of the place a symbol or expression got allocated to. This is done via hash
64 1.1.1.1.4.2 yamt tables that store entries of the following type. */
65 1.1.1.1.4.2 yamt
66 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info
67 1.1.1.1.4.2 yamt {
68 1.1.1.1.4.2 yamt /* The addend for which this entry is relevant. */
69 1.1.1.1.4.2 yamt bfd_vma addend;
70 1.1.1.1.4.2 yamt
71 1.1.1.1.4.2 yamt bfd_vma got_offset;
72 1.1.1.1.4.2 yamt bfd_vma fptr_offset;
73 1.1.1.1.4.2 yamt bfd_vma pltoff_offset;
74 1.1.1.1.4.2 yamt bfd_vma plt_offset;
75 1.1.1.1.4.2 yamt bfd_vma plt2_offset;
76 1.1.1.1.4.2 yamt
77 1.1.1.1.4.2 yamt /* The symbol table entry, if any, that this was derived from. */
78 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h;
79 1.1.1.1.4.2 yamt
80 1.1.1.1.4.2 yamt /* Used to count non-got, non-plt relocations for delayed sizing
81 1.1.1.1.4.2 yamt of relocation sections. */
82 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_reloc_entry
83 1.1.1.1.4.2 yamt {
84 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_reloc_entry *next;
85 1.1.1.1.4.2 yamt asection *srel;
86 1.1.1.1.4.2 yamt int type;
87 1.1.1.1.4.2 yamt int count;
88 1.1.1.1.4.2 yamt } *reloc_entries;
89 1.1.1.1.4.2 yamt
90 1.1.1.1.4.2 yamt /* TRUE when the section contents have been updated. */
91 1.1.1.1.4.2 yamt unsigned got_done : 1;
92 1.1.1.1.4.2 yamt unsigned fptr_done : 1;
93 1.1.1.1.4.2 yamt unsigned pltoff_done : 1;
94 1.1.1.1.4.2 yamt
95 1.1.1.1.4.2 yamt /* TRUE for the different kinds of linker data we want created. */
96 1.1.1.1.4.2 yamt unsigned want_got : 1;
97 1.1.1.1.4.2 yamt unsigned want_gotx : 1;
98 1.1.1.1.4.2 yamt unsigned want_fptr : 1;
99 1.1.1.1.4.2 yamt unsigned want_ltoff_fptr : 1;
100 1.1.1.1.4.2 yamt unsigned want_plt : 1; /* A MIN_PLT entry. */
101 1.1.1.1.4.2 yamt unsigned want_plt2 : 1; /* A FULL_PLT. */
102 1.1.1.1.4.2 yamt unsigned want_pltoff : 1;
103 1.1.1.1.4.2 yamt };
104 1.1.1.1.4.2 yamt
105 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry
106 1.1.1.1.4.2 yamt {
107 1.1.1.1.4.2 yamt int id;
108 1.1.1.1.4.2 yamt unsigned int r_sym;
109 1.1.1.1.4.2 yamt /* The number of elements in elf64_ia64_dyn_sym_info array. */
110 1.1.1.1.4.2 yamt unsigned int count;
111 1.1.1.1.4.2 yamt /* The number of sorted elements in elf64_ia64_dyn_sym_info array. */
112 1.1.1.1.4.2 yamt unsigned int sorted_count;
113 1.1.1.1.4.2 yamt /* The size of elf64_ia64_dyn_sym_info array. */
114 1.1.1.1.4.2 yamt unsigned int size;
115 1.1.1.1.4.2 yamt /* The array of elf64_ia64_dyn_sym_info. */
116 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *info;
117 1.1.1.1.4.2 yamt
118 1.1.1.1.4.2 yamt /* TRUE if this hash entry's addends was translated for
119 1.1.1.1.4.2 yamt SHF_MERGE optimization. */
120 1.1.1.1.4.2 yamt unsigned sec_merge_done : 1;
121 1.1.1.1.4.2 yamt };
122 1.1.1.1.4.2 yamt
123 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry
124 1.1.1.1.4.2 yamt {
125 1.1.1.1.4.2 yamt struct elf_link_hash_entry root;
126 1.1.1.1.4.2 yamt
127 1.1.1.1.4.2 yamt /* Set if this symbol is defined in a shared library.
128 1.1.1.1.4.2 yamt We can't use root.u.def.section->owner as the symbol is an absolute
129 1.1.1.1.4.2 yamt symbol. */
130 1.1.1.1.4.2 yamt bfd *shl;
131 1.1.1.1.4.2 yamt
132 1.1.1.1.4.2 yamt /* The number of elements in elf64_ia64_dyn_sym_info array. */
133 1.1.1.1.4.2 yamt unsigned int count;
134 1.1.1.1.4.2 yamt /* The number of sorted elements in elf64_ia64_dyn_sym_info array. */
135 1.1.1.1.4.2 yamt unsigned int sorted_count;
136 1.1.1.1.4.2 yamt /* The size of elf64_ia64_dyn_sym_info array. */
137 1.1.1.1.4.2 yamt unsigned int size;
138 1.1.1.1.4.2 yamt /* The array of elf64_ia64_dyn_sym_info. */
139 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *info;
140 1.1.1.1.4.2 yamt };
141 1.1.1.1.4.2 yamt
142 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table
143 1.1.1.1.4.2 yamt {
144 1.1.1.1.4.2 yamt /* The main hash table. */
145 1.1.1.1.4.2 yamt struct elf_link_hash_table root;
146 1.1.1.1.4.2 yamt
147 1.1.1.1.4.2 yamt asection *fptr_sec; /* Function descriptor table (or NULL). */
148 1.1.1.1.4.2 yamt asection *rel_fptr_sec; /* Dynamic relocation section for same. */
149 1.1.1.1.4.2 yamt asection *pltoff_sec; /* Private descriptors for plt (or NULL). */
150 1.1.1.1.4.2 yamt asection *fixups_sec; /* Fixups section. */
151 1.1.1.1.4.2 yamt asection *transfer_sec; /* Transfer vector section. */
152 1.1.1.1.4.2 yamt asection *note_sec; /* .note section. */
153 1.1.1.1.4.2 yamt
154 1.1.1.1.4.2 yamt /* There are maybe R_IA64_GPREL22 relocations, including those
155 1.1.1.1.4.2 yamt optimized from R_IA64_LTOFF22X, against non-SHF_IA_64_SHORT
156 1.1.1.1.4.2 yamt sections. We need to record those sections so that we can choose
157 1.1.1.1.4.2 yamt a proper GP to cover all R_IA64_GPREL22 relocations. */
158 1.1.1.1.4.2 yamt asection *max_short_sec; /* Maximum short output section. */
159 1.1.1.1.4.2 yamt bfd_vma max_short_offset; /* Maximum short offset. */
160 1.1.1.1.4.2 yamt asection *min_short_sec; /* Minimum short output section. */
161 1.1.1.1.4.2 yamt bfd_vma min_short_offset; /* Minimum short offset. */
162 1.1.1.1.4.2 yamt
163 1.1.1.1.4.2 yamt htab_t loc_hash_table;
164 1.1.1.1.4.2 yamt void *loc_hash_memory;
165 1.1.1.1.4.2 yamt };
166 1.1.1.1.4.2 yamt
167 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data
168 1.1.1.1.4.2 yamt {
169 1.1.1.1.4.2 yamt struct bfd_link_info *info;
170 1.1.1.1.4.2 yamt bfd_size_type ofs;
171 1.1.1.1.4.2 yamt };
172 1.1.1.1.4.2 yamt
173 1.1.1.1.4.2 yamt #define elf64_ia64_hash_table(p) \
174 1.1.1.1.4.2 yamt (elf_hash_table_id ((struct elf_link_hash_table *) ((p)->hash)) \
175 1.1.1.1.4.2 yamt == IA64_ELF_DATA ? ((struct elf64_ia64_link_hash_table *) ((p)->hash)) : NULL)
176 1.1.1.1.4.2 yamt
177 1.1.1.1.4.2 yamt struct elf64_ia64_vms_obj_tdata
178 1.1.1.1.4.2 yamt {
179 1.1.1.1.4.2 yamt struct elf_obj_tdata root;
180 1.1.1.1.4.2 yamt
181 1.1.1.1.4.2 yamt /* Ident for shared library. */
182 1.1.1.1.4.2 yamt bfd_uint64_t ident;
183 1.1.1.1.4.2 yamt
184 1.1.1.1.4.2 yamt /* Used only during link: offset in the .fixups section for this bfd. */
185 1.1.1.1.4.2 yamt bfd_vma fixups_off;
186 1.1.1.1.4.2 yamt
187 1.1.1.1.4.2 yamt /* Max number of shared libraries. */
188 1.1.1.1.4.2 yamt unsigned int needed_count;
189 1.1.1.1.4.2 yamt };
190 1.1.1.1.4.2 yamt
191 1.1.1.1.4.2 yamt #define elf_ia64_vms_tdata(abfd) \
192 1.1.1.1.4.2 yamt ((struct elf64_ia64_vms_obj_tdata *)((abfd)->tdata.any))
193 1.1.1.1.4.2 yamt #define elf_ia64_vms_ident(abfd) (elf_ia64_vms_tdata(abfd)->ident)
194 1.1.1.1.4.2 yamt
195 1.1.1.1.4.2 yamt struct elf64_vms_transfer
196 1.1.1.1.4.2 yamt {
197 1.1.1.1.4.2 yamt unsigned char size[4];
198 1.1.1.1.4.2 yamt unsigned char spare[4];
199 1.1.1.1.4.2 yamt unsigned char tfradr1[8];
200 1.1.1.1.4.2 yamt unsigned char tfradr2[8];
201 1.1.1.1.4.2 yamt unsigned char tfradr3[8];
202 1.1.1.1.4.2 yamt unsigned char tfradr4[8];
203 1.1.1.1.4.2 yamt unsigned char tfradr5[8];
204 1.1.1.1.4.2 yamt
205 1.1.1.1.4.2 yamt /* Local function descriptor for tfr3. */
206 1.1.1.1.4.2 yamt unsigned char tfr3_func[8];
207 1.1.1.1.4.2 yamt unsigned char tfr3_gp[8];
208 1.1.1.1.4.2 yamt };
209 1.1.1.1.4.2 yamt
210 1.1.1.1.4.2 yamt typedef struct
211 1.1.1.1.4.2 yamt {
212 1.1.1.1.4.2 yamt Elf64_External_Ehdr ehdr;
213 1.1.1.1.4.2 yamt unsigned char vms_needed_count[8];
214 1.1.1.1.4.2 yamt } Elf64_External_VMS_Ehdr;
215 1.1.1.1.4.2 yamt
216 1.1.1.1.4.2 yamt static struct elf64_ia64_dyn_sym_info * get_dyn_sym_info
217 1.1.1.1.4.2 yamt (struct elf64_ia64_link_hash_table *,
218 1.1.1.1.4.2 yamt struct elf_link_hash_entry *,
219 1.1.1.1.4.2 yamt bfd *, const Elf_Internal_Rela *, bfd_boolean);
220 1.1.1.1.4.2 yamt static bfd_boolean elf64_ia64_dynamic_symbol_p
221 1.1.1.1.4.2 yamt (struct elf_link_hash_entry *);
222 1.1.1.1.4.2 yamt static bfd_boolean elf64_ia64_choose_gp
223 1.1.1.1.4.2 yamt (bfd *, struct bfd_link_info *, bfd_boolean);
224 1.1.1.1.4.2 yamt static void elf64_ia64_dyn_sym_traverse
225 1.1.1.1.4.2 yamt (struct elf64_ia64_link_hash_table *,
226 1.1.1.1.4.2 yamt bfd_boolean (*) (struct elf64_ia64_dyn_sym_info *, void *),
227 1.1.1.1.4.2 yamt void *);
228 1.1.1.1.4.2 yamt static bfd_boolean allocate_global_data_got
229 1.1.1.1.4.2 yamt (struct elf64_ia64_dyn_sym_info *, void *);
230 1.1.1.1.4.2 yamt static bfd_boolean allocate_global_fptr_got
231 1.1.1.1.4.2 yamt (struct elf64_ia64_dyn_sym_info *, void *);
232 1.1.1.1.4.2 yamt static bfd_boolean allocate_local_got
233 1.1.1.1.4.2 yamt (struct elf64_ia64_dyn_sym_info *, void *);
234 1.1.1.1.4.2 yamt static bfd_boolean allocate_dynrel_entries
235 1.1.1.1.4.2 yamt (struct elf64_ia64_dyn_sym_info *, void *);
236 1.1.1.1.4.2 yamt static asection *get_pltoff
237 1.1.1.1.4.2 yamt (bfd *, struct elf64_ia64_link_hash_table *);
238 1.1.1.1.4.2 yamt static asection *get_got
239 1.1.1.1.4.2 yamt (bfd *, struct elf64_ia64_link_hash_table *);
240 1.1.1.1.4.2 yamt
241 1.1.1.1.4.2 yamt
242 1.1.1.1.4.2 yamt /* Given a ELF reloc, return the matching HOWTO structure. */
243 1.1.1.1.4.2 yamt
244 1.1.1.1.4.2 yamt static void
245 1.1.1.1.4.2 yamt elf64_ia64_info_to_howto (bfd *abfd ATTRIBUTE_UNUSED,
246 1.1.1.1.4.2 yamt arelent *bfd_reloc,
247 1.1.1.1.4.2 yamt Elf_Internal_Rela *elf_reloc)
248 1.1.1.1.4.2 yamt {
249 1.1.1.1.4.2 yamt bfd_reloc->howto
250 1.1.1.1.4.2 yamt = ia64_elf_lookup_howto ((unsigned int) ELF64_R_TYPE (elf_reloc->r_info));
251 1.1.1.1.4.2 yamt }
252 1.1.1.1.4.2 yamt
253 1.1.1.1.4.2 yamt
254 1.1.1.1.4.2 yamt #define PLT_FULL_ENTRY_SIZE (2 * 16)
255 1.1.1.1.4.2 yamt
256 1.1.1.1.4.2 yamt static const bfd_byte plt_full_entry[PLT_FULL_ENTRY_SIZE] =
257 1.1.1.1.4.2 yamt {
258 1.1.1.1.4.2 yamt 0x0b, 0x78, 0x00, 0x02, 0x00, 0x24, /* [MMI] addl r15=0,r1;; */
259 1.1.1.1.4.2 yamt 0x00, 0x41, 0x3c, 0x70, 0x29, 0xc0, /* ld8.acq r16=[r15],8*/
260 1.1.1.1.4.2 yamt 0x01, 0x08, 0x00, 0x84, /* mov r14=r1;; */
261 1.1.1.1.4.2 yamt 0x11, 0x08, 0x00, 0x1e, 0x18, 0x10, /* [MIB] ld8 r1=[r15] */
262 1.1.1.1.4.2 yamt 0x60, 0x80, 0x04, 0x80, 0x03, 0x00, /* mov b6=r16 */
263 1.1.1.1.4.2 yamt 0x60, 0x00, 0x80, 0x00 /* br.few b6;; */
264 1.1.1.1.4.2 yamt };
265 1.1.1.1.4.2 yamt
266 1.1.1.1.4.2 yamt static const bfd_byte oor_brl[16] =
267 1.1.1.1.4.2 yamt {
268 1.1.1.1.4.2 yamt 0x05, 0x00, 0x00, 0x00, 0x01, 0x00, /* [MLX] nop.m 0 */
269 1.1.1.1.4.2 yamt 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, /* brl.sptk.few tgt;;*/
270 1.1.1.1.4.2 yamt 0x00, 0x00, 0x00, 0xc0
271 1.1.1.1.4.2 yamt };
272 1.1.1.1.4.2 yamt
273 1.1.1.1.4.2 yamt
274 1.1.1.1.4.2 yamt /* These functions do relaxation for IA-64 ELF. */
275 1.1.1.1.4.2 yamt
276 1.1.1.1.4.2 yamt /* Rename some of the generic section flags to better document how they
277 1.1.1.1.4.2 yamt are used here. */
278 1.1.1.1.4.2 yamt #define skip_relax_pass_0 sec_flg0
279 1.1.1.1.4.2 yamt #define skip_relax_pass_1 sec_flg1
280 1.1.1.1.4.2 yamt
281 1.1.1.1.4.2 yamt static void
282 1.1.1.1.4.2 yamt elf64_ia64_update_short_info (asection *sec, bfd_vma offset,
283 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info)
284 1.1.1.1.4.2 yamt {
285 1.1.1.1.4.2 yamt /* Skip ABS and SHF_IA_64_SHORT sections. */
286 1.1.1.1.4.2 yamt if (sec == bfd_abs_section_ptr
287 1.1.1.1.4.2 yamt || (sec->flags & SEC_SMALL_DATA) != 0)
288 1.1.1.1.4.2 yamt return;
289 1.1.1.1.4.2 yamt
290 1.1.1.1.4.2 yamt if (!ia64_info->min_short_sec)
291 1.1.1.1.4.2 yamt {
292 1.1.1.1.4.2 yamt ia64_info->max_short_sec = sec;
293 1.1.1.1.4.2 yamt ia64_info->max_short_offset = offset;
294 1.1.1.1.4.2 yamt ia64_info->min_short_sec = sec;
295 1.1.1.1.4.2 yamt ia64_info->min_short_offset = offset;
296 1.1.1.1.4.2 yamt }
297 1.1.1.1.4.2 yamt else if (sec == ia64_info->max_short_sec
298 1.1.1.1.4.2 yamt && offset > ia64_info->max_short_offset)
299 1.1.1.1.4.2 yamt ia64_info->max_short_offset = offset;
300 1.1.1.1.4.2 yamt else if (sec == ia64_info->min_short_sec
301 1.1.1.1.4.2 yamt && offset < ia64_info->min_short_offset)
302 1.1.1.1.4.2 yamt ia64_info->min_short_offset = offset;
303 1.1.1.1.4.2 yamt else if (sec->output_section->vma
304 1.1.1.1.4.2 yamt > ia64_info->max_short_sec->vma)
305 1.1.1.1.4.2 yamt {
306 1.1.1.1.4.2 yamt ia64_info->max_short_sec = sec;
307 1.1.1.1.4.2 yamt ia64_info->max_short_offset = offset;
308 1.1.1.1.4.2 yamt }
309 1.1.1.1.4.2 yamt else if (sec->output_section->vma
310 1.1.1.1.4.2 yamt < ia64_info->min_short_sec->vma)
311 1.1.1.1.4.2 yamt {
312 1.1.1.1.4.2 yamt ia64_info->min_short_sec = sec;
313 1.1.1.1.4.2 yamt ia64_info->min_short_offset = offset;
314 1.1.1.1.4.2 yamt }
315 1.1.1.1.4.2 yamt }
316 1.1.1.1.4.2 yamt
317 1.1.1.1.4.2 yamt /* Use a two passes algorithm. In the first pass, branches are relaxed
318 1.1.1.1.4.2 yamt (which may increase the size of the section). In the second pass,
319 1.1.1.1.4.2 yamt the other relaxations are done.
320 1.1.1.1.4.2 yamt */
321 1.1.1.1.4.2 yamt
322 1.1.1.1.4.2 yamt static bfd_boolean
323 1.1.1.1.4.2 yamt elf64_ia64_relax_section (bfd *abfd, asection *sec,
324 1.1.1.1.4.2 yamt struct bfd_link_info *link_info,
325 1.1.1.1.4.2 yamt bfd_boolean *again)
326 1.1.1.1.4.2 yamt {
327 1.1.1.1.4.2 yamt struct one_fixup
328 1.1.1.1.4.2 yamt {
329 1.1.1.1.4.2 yamt struct one_fixup *next;
330 1.1.1.1.4.2 yamt asection *tsec;
331 1.1.1.1.4.2 yamt bfd_vma toff;
332 1.1.1.1.4.2 yamt bfd_vma trampoff;
333 1.1.1.1.4.2 yamt };
334 1.1.1.1.4.2 yamt
335 1.1.1.1.4.2 yamt Elf_Internal_Shdr *symtab_hdr;
336 1.1.1.1.4.2 yamt Elf_Internal_Rela *internal_relocs;
337 1.1.1.1.4.2 yamt Elf_Internal_Rela *irel, *irelend;
338 1.1.1.1.4.2 yamt bfd_byte *contents;
339 1.1.1.1.4.2 yamt Elf_Internal_Sym *isymbuf = NULL;
340 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
341 1.1.1.1.4.2 yamt struct one_fixup *fixups = NULL;
342 1.1.1.1.4.2 yamt bfd_boolean changed_contents = FALSE;
343 1.1.1.1.4.2 yamt bfd_boolean changed_relocs = FALSE;
344 1.1.1.1.4.2 yamt bfd_boolean skip_relax_pass_0 = TRUE;
345 1.1.1.1.4.2 yamt bfd_boolean skip_relax_pass_1 = TRUE;
346 1.1.1.1.4.2 yamt bfd_vma gp = 0;
347 1.1.1.1.4.2 yamt
348 1.1.1.1.4.2 yamt /* Assume we're not going to change any sizes, and we'll only need
349 1.1.1.1.4.2 yamt one pass. */
350 1.1.1.1.4.2 yamt *again = FALSE;
351 1.1.1.1.4.2 yamt
352 1.1.1.1.4.2 yamt if (link_info->relocatable)
353 1.1.1.1.4.2 yamt (*link_info->callbacks->einfo)
354 1.1.1.1.4.2 yamt (_("%P%F: --relax and -r may not be used together\n"));
355 1.1.1.1.4.2 yamt
356 1.1.1.1.4.2 yamt /* Don't even try to relax for non-ELF outputs. */
357 1.1.1.1.4.2 yamt if (!is_elf_hash_table (link_info->hash))
358 1.1.1.1.4.2 yamt return FALSE;
359 1.1.1.1.4.2 yamt
360 1.1.1.1.4.2 yamt /* Nothing to do if there are no relocations or there is no need for
361 1.1.1.1.4.2 yamt the current pass. */
362 1.1.1.1.4.2 yamt if ((sec->flags & SEC_RELOC) == 0
363 1.1.1.1.4.2 yamt || sec->reloc_count == 0
364 1.1.1.1.4.2 yamt || (link_info->relax_pass == 0 && sec->skip_relax_pass_0)
365 1.1.1.1.4.2 yamt || (link_info->relax_pass == 1 && sec->skip_relax_pass_1))
366 1.1.1.1.4.2 yamt return TRUE;
367 1.1.1.1.4.2 yamt
368 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (link_info);
369 1.1.1.1.4.2 yamt if (ia64_info == NULL)
370 1.1.1.1.4.2 yamt return FALSE;
371 1.1.1.1.4.2 yamt
372 1.1.1.1.4.2 yamt symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
373 1.1.1.1.4.2 yamt
374 1.1.1.1.4.2 yamt /* Load the relocations for this section. */
375 1.1.1.1.4.2 yamt internal_relocs = (_bfd_elf_link_read_relocs
376 1.1.1.1.4.2 yamt (abfd, sec, NULL, (Elf_Internal_Rela *) NULL,
377 1.1.1.1.4.2 yamt link_info->keep_memory));
378 1.1.1.1.4.2 yamt if (internal_relocs == NULL)
379 1.1.1.1.4.2 yamt return FALSE;
380 1.1.1.1.4.2 yamt
381 1.1.1.1.4.2 yamt irelend = internal_relocs + sec->reloc_count;
382 1.1.1.1.4.2 yamt
383 1.1.1.1.4.2 yamt /* Get the section contents. */
384 1.1.1.1.4.2 yamt if (elf_section_data (sec)->this_hdr.contents != NULL)
385 1.1.1.1.4.2 yamt contents = elf_section_data (sec)->this_hdr.contents;
386 1.1.1.1.4.2 yamt else
387 1.1.1.1.4.2 yamt {
388 1.1.1.1.4.2 yamt if (!bfd_malloc_and_get_section (abfd, sec, &contents))
389 1.1.1.1.4.2 yamt goto error_return;
390 1.1.1.1.4.2 yamt }
391 1.1.1.1.4.2 yamt
392 1.1.1.1.4.2 yamt for (irel = internal_relocs; irel < irelend; irel++)
393 1.1.1.1.4.2 yamt {
394 1.1.1.1.4.2 yamt unsigned long r_type = ELF64_R_TYPE (irel->r_info);
395 1.1.1.1.4.2 yamt bfd_vma symaddr, reladdr, trampoff, toff, roff;
396 1.1.1.1.4.2 yamt asection *tsec;
397 1.1.1.1.4.2 yamt struct one_fixup *f;
398 1.1.1.1.4.2 yamt bfd_size_type amt;
399 1.1.1.1.4.2 yamt bfd_boolean is_branch;
400 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
401 1.1.1.1.4.2 yamt
402 1.1.1.1.4.2 yamt switch (r_type)
403 1.1.1.1.4.2 yamt {
404 1.1.1.1.4.2 yamt case R_IA64_PCREL21B:
405 1.1.1.1.4.2 yamt case R_IA64_PCREL21BI:
406 1.1.1.1.4.2 yamt case R_IA64_PCREL21M:
407 1.1.1.1.4.2 yamt case R_IA64_PCREL21F:
408 1.1.1.1.4.2 yamt /* In pass 1, all br relaxations are done. We can skip it. */
409 1.1.1.1.4.2 yamt if (link_info->relax_pass == 1)
410 1.1.1.1.4.2 yamt continue;
411 1.1.1.1.4.2 yamt skip_relax_pass_0 = FALSE;
412 1.1.1.1.4.2 yamt is_branch = TRUE;
413 1.1.1.1.4.2 yamt break;
414 1.1.1.1.4.2 yamt
415 1.1.1.1.4.2 yamt case R_IA64_PCREL60B:
416 1.1.1.1.4.2 yamt /* We can't optimize brl to br in pass 0 since br relaxations
417 1.1.1.1.4.2 yamt will increase the code size. Defer it to pass 1. */
418 1.1.1.1.4.2 yamt if (link_info->relax_pass == 0)
419 1.1.1.1.4.2 yamt {
420 1.1.1.1.4.2 yamt skip_relax_pass_1 = FALSE;
421 1.1.1.1.4.2 yamt continue;
422 1.1.1.1.4.2 yamt }
423 1.1.1.1.4.2 yamt is_branch = TRUE;
424 1.1.1.1.4.2 yamt break;
425 1.1.1.1.4.2 yamt
426 1.1.1.1.4.2 yamt case R_IA64_GPREL22:
427 1.1.1.1.4.2 yamt /* Update max_short_sec/min_short_sec. */
428 1.1.1.1.4.2 yamt
429 1.1.1.1.4.2 yamt case R_IA64_LTOFF22X:
430 1.1.1.1.4.2 yamt case R_IA64_LDXMOV:
431 1.1.1.1.4.2 yamt /* We can't relax ldx/mov in pass 0 since br relaxations will
432 1.1.1.1.4.2 yamt increase the code size. Defer it to pass 1. */
433 1.1.1.1.4.2 yamt if (link_info->relax_pass == 0)
434 1.1.1.1.4.2 yamt {
435 1.1.1.1.4.2 yamt skip_relax_pass_1 = FALSE;
436 1.1.1.1.4.2 yamt continue;
437 1.1.1.1.4.2 yamt }
438 1.1.1.1.4.2 yamt is_branch = FALSE;
439 1.1.1.1.4.2 yamt break;
440 1.1.1.1.4.2 yamt
441 1.1.1.1.4.2 yamt default:
442 1.1.1.1.4.2 yamt continue;
443 1.1.1.1.4.2 yamt }
444 1.1.1.1.4.2 yamt
445 1.1.1.1.4.2 yamt /* Get the value of the symbol referred to by the reloc. */
446 1.1.1.1.4.2 yamt if (ELF64_R_SYM (irel->r_info) < symtab_hdr->sh_info)
447 1.1.1.1.4.2 yamt {
448 1.1.1.1.4.2 yamt /* A local symbol. */
449 1.1.1.1.4.2 yamt Elf_Internal_Sym *isym;
450 1.1.1.1.4.2 yamt
451 1.1.1.1.4.2 yamt /* Read this BFD's local symbols. */
452 1.1.1.1.4.2 yamt if (isymbuf == NULL)
453 1.1.1.1.4.2 yamt {
454 1.1.1.1.4.2 yamt isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
455 1.1.1.1.4.2 yamt if (isymbuf == NULL)
456 1.1.1.1.4.2 yamt isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
457 1.1.1.1.4.2 yamt symtab_hdr->sh_info, 0,
458 1.1.1.1.4.2 yamt NULL, NULL, NULL);
459 1.1.1.1.4.2 yamt if (isymbuf == 0)
460 1.1.1.1.4.2 yamt goto error_return;
461 1.1.1.1.4.2 yamt }
462 1.1.1.1.4.2 yamt
463 1.1.1.1.4.2 yamt isym = isymbuf + ELF64_R_SYM (irel->r_info);
464 1.1.1.1.4.2 yamt if (isym->st_shndx == SHN_UNDEF)
465 1.1.1.1.4.2 yamt continue; /* We can't do anything with undefined symbols. */
466 1.1.1.1.4.2 yamt else if (isym->st_shndx == SHN_ABS)
467 1.1.1.1.4.2 yamt tsec = bfd_abs_section_ptr;
468 1.1.1.1.4.2 yamt else if (isym->st_shndx == SHN_COMMON)
469 1.1.1.1.4.2 yamt tsec = bfd_com_section_ptr;
470 1.1.1.1.4.2 yamt else if (isym->st_shndx == SHN_IA_64_ANSI_COMMON)
471 1.1.1.1.4.2 yamt tsec = bfd_com_section_ptr;
472 1.1.1.1.4.2 yamt else
473 1.1.1.1.4.2 yamt tsec = bfd_section_from_elf_index (abfd, isym->st_shndx);
474 1.1.1.1.4.2 yamt
475 1.1.1.1.4.2 yamt toff = isym->st_value;
476 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, NULL, abfd, irel, FALSE);
477 1.1.1.1.4.2 yamt }
478 1.1.1.1.4.2 yamt else
479 1.1.1.1.4.2 yamt {
480 1.1.1.1.4.2 yamt unsigned long indx;
481 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h;
482 1.1.1.1.4.2 yamt
483 1.1.1.1.4.2 yamt indx = ELF64_R_SYM (irel->r_info) - symtab_hdr->sh_info;
484 1.1.1.1.4.2 yamt h = elf_sym_hashes (abfd)[indx];
485 1.1.1.1.4.2 yamt BFD_ASSERT (h != NULL);
486 1.1.1.1.4.2 yamt
487 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
488 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
489 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
490 1.1.1.1.4.2 yamt
491 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, abfd, irel, FALSE);
492 1.1.1.1.4.2 yamt
493 1.1.1.1.4.2 yamt /* For branches to dynamic symbols, we're interested instead
494 1.1.1.1.4.2 yamt in a branch to the PLT entry. */
495 1.1.1.1.4.2 yamt if (is_branch && dyn_i && dyn_i->want_plt2)
496 1.1.1.1.4.2 yamt {
497 1.1.1.1.4.2 yamt /* Internal branches shouldn't be sent to the PLT.
498 1.1.1.1.4.2 yamt Leave this for now and we'll give an error later. */
499 1.1.1.1.4.2 yamt if (r_type != R_IA64_PCREL21B)
500 1.1.1.1.4.2 yamt continue;
501 1.1.1.1.4.2 yamt
502 1.1.1.1.4.2 yamt tsec = ia64_info->root.splt;
503 1.1.1.1.4.2 yamt toff = dyn_i->plt2_offset;
504 1.1.1.1.4.2 yamt BFD_ASSERT (irel->r_addend == 0);
505 1.1.1.1.4.2 yamt }
506 1.1.1.1.4.2 yamt
507 1.1.1.1.4.2 yamt /* Can't do anything else with dynamic symbols. */
508 1.1.1.1.4.2 yamt else if (elf64_ia64_dynamic_symbol_p (h))
509 1.1.1.1.4.2 yamt continue;
510 1.1.1.1.4.2 yamt
511 1.1.1.1.4.2 yamt else
512 1.1.1.1.4.2 yamt {
513 1.1.1.1.4.2 yamt /* We can't do anything with undefined symbols. */
514 1.1.1.1.4.2 yamt if (h->root.type == bfd_link_hash_undefined
515 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_undefweak)
516 1.1.1.1.4.2 yamt continue;
517 1.1.1.1.4.2 yamt
518 1.1.1.1.4.2 yamt tsec = h->root.u.def.section;
519 1.1.1.1.4.2 yamt toff = h->root.u.def.value;
520 1.1.1.1.4.2 yamt }
521 1.1.1.1.4.2 yamt }
522 1.1.1.1.4.2 yamt
523 1.1.1.1.4.2 yamt toff += irel->r_addend;
524 1.1.1.1.4.2 yamt
525 1.1.1.1.4.2 yamt symaddr = tsec->output_section->vma + tsec->output_offset + toff;
526 1.1.1.1.4.2 yamt
527 1.1.1.1.4.2 yamt roff = irel->r_offset;
528 1.1.1.1.4.2 yamt
529 1.1.1.1.4.2 yamt if (is_branch)
530 1.1.1.1.4.2 yamt {
531 1.1.1.1.4.2 yamt bfd_signed_vma offset;
532 1.1.1.1.4.2 yamt
533 1.1.1.1.4.2 yamt reladdr = (sec->output_section->vma
534 1.1.1.1.4.2 yamt + sec->output_offset
535 1.1.1.1.4.2 yamt + roff) & (bfd_vma) -4;
536 1.1.1.1.4.2 yamt
537 1.1.1.1.4.2 yamt /* The .plt section is aligned at 32byte and the .text section
538 1.1.1.1.4.2 yamt is aligned at 64byte. The .text section is right after the
539 1.1.1.1.4.2 yamt .plt section. After the first relaxation pass, linker may
540 1.1.1.1.4.2 yamt increase the gap between the .plt and .text sections up
541 1.1.1.1.4.2 yamt to 32byte. We assume linker will always insert 32byte
542 1.1.1.1.4.2 yamt between the .plt and .text sections after the the first
543 1.1.1.1.4.2 yamt relaxation pass. */
544 1.1.1.1.4.2 yamt if (tsec == ia64_info->root.splt)
545 1.1.1.1.4.2 yamt offset = -0x1000000 + 32;
546 1.1.1.1.4.2 yamt else
547 1.1.1.1.4.2 yamt offset = -0x1000000;
548 1.1.1.1.4.2 yamt
549 1.1.1.1.4.2 yamt /* If the branch is in range, no need to do anything. */
550 1.1.1.1.4.2 yamt if ((bfd_signed_vma) (symaddr - reladdr) >= offset
551 1.1.1.1.4.2 yamt && (bfd_signed_vma) (symaddr - reladdr) <= 0x0FFFFF0)
552 1.1.1.1.4.2 yamt {
553 1.1.1.1.4.2 yamt /* If the 60-bit branch is in 21-bit range, optimize it. */
554 1.1.1.1.4.2 yamt if (r_type == R_IA64_PCREL60B)
555 1.1.1.1.4.2 yamt {
556 1.1.1.1.4.2 yamt ia64_elf_relax_brl (contents, roff);
557 1.1.1.1.4.2 yamt
558 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
559 1.1.1.1.4.2 yamt R_IA64_PCREL21B);
560 1.1.1.1.4.2 yamt
561 1.1.1.1.4.2 yamt /* If the original relocation offset points to slot
562 1.1.1.1.4.2 yamt 1, change it to slot 2. */
563 1.1.1.1.4.2 yamt if ((irel->r_offset & 3) == 1)
564 1.1.1.1.4.2 yamt irel->r_offset += 1;
565 1.1.1.1.4.2 yamt }
566 1.1.1.1.4.2 yamt
567 1.1.1.1.4.2 yamt continue;
568 1.1.1.1.4.2 yamt }
569 1.1.1.1.4.2 yamt else if (r_type == R_IA64_PCREL60B)
570 1.1.1.1.4.2 yamt continue;
571 1.1.1.1.4.2 yamt else if (ia64_elf_relax_br (contents, roff))
572 1.1.1.1.4.2 yamt {
573 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
574 1.1.1.1.4.2 yamt R_IA64_PCREL60B);
575 1.1.1.1.4.2 yamt
576 1.1.1.1.4.2 yamt /* Make the relocation offset point to slot 1. */
577 1.1.1.1.4.2 yamt irel->r_offset = (irel->r_offset & ~((bfd_vma) 0x3)) + 1;
578 1.1.1.1.4.2 yamt continue;
579 1.1.1.1.4.2 yamt }
580 1.1.1.1.4.2 yamt
581 1.1.1.1.4.2 yamt /* We can't put a trampoline in a .init/.fini section. Issue
582 1.1.1.1.4.2 yamt an error. */
583 1.1.1.1.4.2 yamt if (strcmp (sec->output_section->name, ".init") == 0
584 1.1.1.1.4.2 yamt || strcmp (sec->output_section->name, ".fini") == 0)
585 1.1.1.1.4.2 yamt {
586 1.1.1.1.4.2 yamt (*_bfd_error_handler)
587 1.1.1.1.4.2 yamt (_("%B: Can't relax br at 0x%lx in section `%A'. Please use brl or indirect branch."),
588 1.1.1.1.4.2 yamt sec->owner, sec, (unsigned long) roff);
589 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
590 1.1.1.1.4.2 yamt goto error_return;
591 1.1.1.1.4.2 yamt }
592 1.1.1.1.4.2 yamt
593 1.1.1.1.4.2 yamt /* If the branch and target are in the same section, you've
594 1.1.1.1.4.2 yamt got one honking big section and we can't help you unless
595 1.1.1.1.4.2 yamt you are branching backwards. You'll get an error message
596 1.1.1.1.4.2 yamt later. */
597 1.1.1.1.4.2 yamt if (tsec == sec && toff > roff)
598 1.1.1.1.4.2 yamt continue;
599 1.1.1.1.4.2 yamt
600 1.1.1.1.4.2 yamt /* Look for an existing fixup to this address. */
601 1.1.1.1.4.2 yamt for (f = fixups; f ; f = f->next)
602 1.1.1.1.4.2 yamt if (f->tsec == tsec && f->toff == toff)
603 1.1.1.1.4.2 yamt break;
604 1.1.1.1.4.2 yamt
605 1.1.1.1.4.2 yamt if (f == NULL)
606 1.1.1.1.4.2 yamt {
607 1.1.1.1.4.2 yamt /* Two alternatives: If it's a branch to a PLT entry, we can
608 1.1.1.1.4.2 yamt make a copy of the FULL_PLT entry. Otherwise, we'll have
609 1.1.1.1.4.2 yamt to use a `brl' insn to get where we're going. */
610 1.1.1.1.4.2 yamt
611 1.1.1.1.4.2 yamt size_t size;
612 1.1.1.1.4.2 yamt
613 1.1.1.1.4.2 yamt if (tsec == ia64_info->root.splt)
614 1.1.1.1.4.2 yamt size = sizeof (plt_full_entry);
615 1.1.1.1.4.2 yamt else
616 1.1.1.1.4.2 yamt size = sizeof (oor_brl);
617 1.1.1.1.4.2 yamt
618 1.1.1.1.4.2 yamt /* Resize the current section to make room for the new branch. */
619 1.1.1.1.4.2 yamt trampoff = (sec->size + 15) & (bfd_vma) -16;
620 1.1.1.1.4.2 yamt
621 1.1.1.1.4.2 yamt /* If trampoline is out of range, there is nothing we
622 1.1.1.1.4.2 yamt can do. */
623 1.1.1.1.4.2 yamt offset = trampoff - (roff & (bfd_vma) -4);
624 1.1.1.1.4.2 yamt if (offset < -0x1000000 || offset > 0x0FFFFF0)
625 1.1.1.1.4.2 yamt continue;
626 1.1.1.1.4.2 yamt
627 1.1.1.1.4.2 yamt amt = trampoff + size;
628 1.1.1.1.4.2 yamt contents = (bfd_byte *) bfd_realloc (contents, amt);
629 1.1.1.1.4.2 yamt if (contents == NULL)
630 1.1.1.1.4.2 yamt goto error_return;
631 1.1.1.1.4.2 yamt sec->size = amt;
632 1.1.1.1.4.2 yamt
633 1.1.1.1.4.2 yamt if (tsec == ia64_info->root.splt)
634 1.1.1.1.4.2 yamt {
635 1.1.1.1.4.2 yamt memcpy (contents + trampoff, plt_full_entry, size);
636 1.1.1.1.4.2 yamt
637 1.1.1.1.4.2 yamt /* Hijack the old relocation for use as the PLTOFF reloc. */
638 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
639 1.1.1.1.4.2 yamt R_IA64_PLTOFF22);
640 1.1.1.1.4.2 yamt irel->r_offset = trampoff;
641 1.1.1.1.4.2 yamt }
642 1.1.1.1.4.2 yamt else
643 1.1.1.1.4.2 yamt {
644 1.1.1.1.4.2 yamt memcpy (contents + trampoff, oor_brl, size);
645 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
646 1.1.1.1.4.2 yamt R_IA64_PCREL60B);
647 1.1.1.1.4.2 yamt irel->r_offset = trampoff + 2;
648 1.1.1.1.4.2 yamt }
649 1.1.1.1.4.2 yamt
650 1.1.1.1.4.2 yamt /* Record the fixup so we don't do it again this section. */
651 1.1.1.1.4.2 yamt f = (struct one_fixup *)
652 1.1.1.1.4.2 yamt bfd_malloc ((bfd_size_type) sizeof (*f));
653 1.1.1.1.4.2 yamt f->next = fixups;
654 1.1.1.1.4.2 yamt f->tsec = tsec;
655 1.1.1.1.4.2 yamt f->toff = toff;
656 1.1.1.1.4.2 yamt f->trampoff = trampoff;
657 1.1.1.1.4.2 yamt fixups = f;
658 1.1.1.1.4.2 yamt }
659 1.1.1.1.4.2 yamt else
660 1.1.1.1.4.2 yamt {
661 1.1.1.1.4.2 yamt /* If trampoline is out of range, there is nothing we
662 1.1.1.1.4.2 yamt can do. */
663 1.1.1.1.4.2 yamt offset = f->trampoff - (roff & (bfd_vma) -4);
664 1.1.1.1.4.2 yamt if (offset < -0x1000000 || offset > 0x0FFFFF0)
665 1.1.1.1.4.2 yamt continue;
666 1.1.1.1.4.2 yamt
667 1.1.1.1.4.2 yamt /* Nop out the reloc, since we're finalizing things here. */
668 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (0, R_IA64_NONE);
669 1.1.1.1.4.2 yamt }
670 1.1.1.1.4.2 yamt
671 1.1.1.1.4.2 yamt /* Fix up the existing branch to hit the trampoline. */
672 1.1.1.1.4.2 yamt if (ia64_elf_install_value (contents + roff, offset, r_type)
673 1.1.1.1.4.2 yamt != bfd_reloc_ok)
674 1.1.1.1.4.2 yamt goto error_return;
675 1.1.1.1.4.2 yamt
676 1.1.1.1.4.2 yamt changed_contents = TRUE;
677 1.1.1.1.4.2 yamt changed_relocs = TRUE;
678 1.1.1.1.4.2 yamt }
679 1.1.1.1.4.2 yamt else
680 1.1.1.1.4.2 yamt {
681 1.1.1.1.4.2 yamt /* Fetch the gp. */
682 1.1.1.1.4.2 yamt if (gp == 0)
683 1.1.1.1.4.2 yamt {
684 1.1.1.1.4.2 yamt bfd *obfd = sec->output_section->owner;
685 1.1.1.1.4.2 yamt gp = _bfd_get_gp_value (obfd);
686 1.1.1.1.4.2 yamt if (gp == 0)
687 1.1.1.1.4.2 yamt {
688 1.1.1.1.4.2 yamt if (!elf64_ia64_choose_gp (obfd, link_info, FALSE))
689 1.1.1.1.4.2 yamt goto error_return;
690 1.1.1.1.4.2 yamt gp = _bfd_get_gp_value (obfd);
691 1.1.1.1.4.2 yamt }
692 1.1.1.1.4.2 yamt }
693 1.1.1.1.4.2 yamt
694 1.1.1.1.4.2 yamt /* If the data is out of range, do nothing. */
695 1.1.1.1.4.2 yamt if ((bfd_signed_vma) (symaddr - gp) >= 0x200000
696 1.1.1.1.4.2 yamt ||(bfd_signed_vma) (symaddr - gp) < -0x200000)
697 1.1.1.1.4.2 yamt continue;
698 1.1.1.1.4.2 yamt
699 1.1.1.1.4.2 yamt if (r_type == R_IA64_GPREL22)
700 1.1.1.1.4.2 yamt elf64_ia64_update_short_info (tsec->output_section,
701 1.1.1.1.4.2 yamt tsec->output_offset + toff,
702 1.1.1.1.4.2 yamt ia64_info);
703 1.1.1.1.4.2 yamt else if (r_type == R_IA64_LTOFF22X)
704 1.1.1.1.4.2 yamt {
705 1.1.1.1.4.2 yamt /* Can't deal yet correctly with ABS symbols. */
706 1.1.1.1.4.2 yamt if (bfd_is_abs_section (tsec))
707 1.1.1.1.4.2 yamt continue;
708 1.1.1.1.4.2 yamt
709 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (ELF64_R_SYM (irel->r_info),
710 1.1.1.1.4.2 yamt R_IA64_GPREL22);
711 1.1.1.1.4.2 yamt changed_relocs = TRUE;
712 1.1.1.1.4.2 yamt
713 1.1.1.1.4.2 yamt elf64_ia64_update_short_info (tsec->output_section,
714 1.1.1.1.4.2 yamt tsec->output_offset + toff,
715 1.1.1.1.4.2 yamt ia64_info);
716 1.1.1.1.4.2 yamt }
717 1.1.1.1.4.2 yamt else
718 1.1.1.1.4.2 yamt {
719 1.1.1.1.4.2 yamt ia64_elf_relax_ldxmov (contents, roff);
720 1.1.1.1.4.2 yamt irel->r_info = ELF64_R_INFO (0, R_IA64_NONE);
721 1.1.1.1.4.2 yamt changed_contents = TRUE;
722 1.1.1.1.4.2 yamt changed_relocs = TRUE;
723 1.1.1.1.4.2 yamt }
724 1.1.1.1.4.2 yamt }
725 1.1.1.1.4.2 yamt }
726 1.1.1.1.4.2 yamt
727 1.1.1.1.4.2 yamt /* ??? If we created fixups, this may push the code segment large
728 1.1.1.1.4.2 yamt enough that the data segment moves, which will change the GP.
729 1.1.1.1.4.2 yamt Reset the GP so that we re-calculate next round. We need to
730 1.1.1.1.4.2 yamt do this at the _beginning_ of the next round; now will not do. */
731 1.1.1.1.4.2 yamt
732 1.1.1.1.4.2 yamt /* Clean up and go home. */
733 1.1.1.1.4.2 yamt while (fixups)
734 1.1.1.1.4.2 yamt {
735 1.1.1.1.4.2 yamt struct one_fixup *f = fixups;
736 1.1.1.1.4.2 yamt fixups = fixups->next;
737 1.1.1.1.4.2 yamt free (f);
738 1.1.1.1.4.2 yamt }
739 1.1.1.1.4.2 yamt
740 1.1.1.1.4.2 yamt if (isymbuf != NULL
741 1.1.1.1.4.2 yamt && symtab_hdr->contents != (unsigned char *) isymbuf)
742 1.1.1.1.4.2 yamt {
743 1.1.1.1.4.2 yamt if (! link_info->keep_memory)
744 1.1.1.1.4.2 yamt free (isymbuf);
745 1.1.1.1.4.2 yamt else
746 1.1.1.1.4.2 yamt {
747 1.1.1.1.4.2 yamt /* Cache the symbols for elf_link_input_bfd. */
748 1.1.1.1.4.2 yamt symtab_hdr->contents = (unsigned char *) isymbuf;
749 1.1.1.1.4.2 yamt }
750 1.1.1.1.4.2 yamt }
751 1.1.1.1.4.2 yamt
752 1.1.1.1.4.2 yamt if (contents != NULL
753 1.1.1.1.4.2 yamt && elf_section_data (sec)->this_hdr.contents != contents)
754 1.1.1.1.4.2 yamt {
755 1.1.1.1.4.2 yamt if (!changed_contents && !link_info->keep_memory)
756 1.1.1.1.4.2 yamt free (contents);
757 1.1.1.1.4.2 yamt else
758 1.1.1.1.4.2 yamt {
759 1.1.1.1.4.2 yamt /* Cache the section contents for elf_link_input_bfd. */
760 1.1.1.1.4.2 yamt elf_section_data (sec)->this_hdr.contents = contents;
761 1.1.1.1.4.2 yamt }
762 1.1.1.1.4.2 yamt }
763 1.1.1.1.4.2 yamt
764 1.1.1.1.4.2 yamt if (elf_section_data (sec)->relocs != internal_relocs)
765 1.1.1.1.4.2 yamt {
766 1.1.1.1.4.2 yamt if (!changed_relocs)
767 1.1.1.1.4.2 yamt free (internal_relocs);
768 1.1.1.1.4.2 yamt else
769 1.1.1.1.4.2 yamt elf_section_data (sec)->relocs = internal_relocs;
770 1.1.1.1.4.2 yamt }
771 1.1.1.1.4.2 yamt
772 1.1.1.1.4.2 yamt if (link_info->relax_pass == 0)
773 1.1.1.1.4.2 yamt {
774 1.1.1.1.4.2 yamt /* Pass 0 is only needed to relax br. */
775 1.1.1.1.4.2 yamt sec->skip_relax_pass_0 = skip_relax_pass_0;
776 1.1.1.1.4.2 yamt sec->skip_relax_pass_1 = skip_relax_pass_1;
777 1.1.1.1.4.2 yamt }
778 1.1.1.1.4.2 yamt
779 1.1.1.1.4.2 yamt *again = changed_contents || changed_relocs;
780 1.1.1.1.4.2 yamt return TRUE;
781 1.1.1.1.4.2 yamt
782 1.1.1.1.4.2 yamt error_return:
783 1.1.1.1.4.2 yamt if (isymbuf != NULL && (unsigned char *) isymbuf != symtab_hdr->contents)
784 1.1.1.1.4.2 yamt free (isymbuf);
785 1.1.1.1.4.2 yamt if (contents != NULL
786 1.1.1.1.4.2 yamt && elf_section_data (sec)->this_hdr.contents != contents)
787 1.1.1.1.4.2 yamt free (contents);
788 1.1.1.1.4.2 yamt if (internal_relocs != NULL
789 1.1.1.1.4.2 yamt && elf_section_data (sec)->relocs != internal_relocs)
790 1.1.1.1.4.2 yamt free (internal_relocs);
791 1.1.1.1.4.2 yamt return FALSE;
792 1.1.1.1.4.2 yamt }
793 1.1.1.1.4.2 yamt #undef skip_relax_pass_0
794 1.1.1.1.4.2 yamt #undef skip_relax_pass_1
795 1.1.1.1.4.2 yamt
796 1.1.1.1.4.2 yamt /* Return TRUE if NAME is an unwind table section name. */
797 1.1.1.1.4.2 yamt
798 1.1.1.1.4.2 yamt static inline bfd_boolean
799 1.1.1.1.4.2 yamt is_unwind_section_name (bfd *abfd ATTRIBUTE_UNUSED, const char *name)
800 1.1.1.1.4.2 yamt {
801 1.1.1.1.4.2 yamt return ((CONST_STRNEQ (name, ELF_STRING_ia64_unwind)
802 1.1.1.1.4.2 yamt && ! CONST_STRNEQ (name, ELF_STRING_ia64_unwind_info))
803 1.1.1.1.4.2 yamt || CONST_STRNEQ (name, ELF_STRING_ia64_unwind_once));
804 1.1.1.1.4.2 yamt }
805 1.1.1.1.4.2 yamt
806 1.1.1.1.4.2 yamt
807 1.1.1.1.4.2 yamt /* Convert IA-64 specific section flags to bfd internal section flags. */
808 1.1.1.1.4.2 yamt
809 1.1.1.1.4.2 yamt /* ??? There is no bfd internal flag equivalent to the SHF_IA_64_NORECOV
810 1.1.1.1.4.2 yamt flag. */
811 1.1.1.1.4.2 yamt
812 1.1.1.1.4.2 yamt static bfd_boolean
813 1.1.1.1.4.2 yamt elf64_ia64_section_flags (flagword *flags,
814 1.1.1.1.4.2 yamt const Elf_Internal_Shdr *hdr)
815 1.1.1.1.4.2 yamt {
816 1.1.1.1.4.2 yamt if (hdr->sh_flags & SHF_IA_64_SHORT)
817 1.1.1.1.4.2 yamt *flags |= SEC_SMALL_DATA;
818 1.1.1.1.4.2 yamt
819 1.1.1.1.4.2 yamt return TRUE;
820 1.1.1.1.4.2 yamt }
821 1.1.1.1.4.2 yamt
822 1.1.1.1.4.2 yamt /* Set the correct type for an IA-64 ELF section. We do this by the
823 1.1.1.1.4.2 yamt section name, which is a hack, but ought to work. */
824 1.1.1.1.4.2 yamt
825 1.1.1.1.4.2 yamt static bfd_boolean
826 1.1.1.1.4.2 yamt elf64_ia64_fake_sections (bfd *abfd, Elf_Internal_Shdr *hdr,
827 1.1.1.1.4.2 yamt asection *sec)
828 1.1.1.1.4.2 yamt {
829 1.1.1.1.4.2 yamt const char *name;
830 1.1.1.1.4.2 yamt
831 1.1.1.1.4.2 yamt name = bfd_get_section_name (abfd, sec);
832 1.1.1.1.4.2 yamt
833 1.1.1.1.4.2 yamt if (is_unwind_section_name (abfd, name))
834 1.1.1.1.4.2 yamt {
835 1.1.1.1.4.2 yamt /* We don't have the sections numbered at this point, so sh_info
836 1.1.1.1.4.2 yamt is set later, in elf64_ia64_final_write_processing. */
837 1.1.1.1.4.2 yamt hdr->sh_type = SHT_IA_64_UNWIND;
838 1.1.1.1.4.2 yamt hdr->sh_flags |= SHF_LINK_ORDER;
839 1.1.1.1.4.2 yamt }
840 1.1.1.1.4.2 yamt else if (strcmp (name, ELF_STRING_ia64_archext) == 0)
841 1.1.1.1.4.2 yamt hdr->sh_type = SHT_IA_64_EXT;
842 1.1.1.1.4.2 yamt
843 1.1.1.1.4.2 yamt if (sec->flags & SEC_SMALL_DATA)
844 1.1.1.1.4.2 yamt hdr->sh_flags |= SHF_IA_64_SHORT;
845 1.1.1.1.4.2 yamt
846 1.1.1.1.4.2 yamt return TRUE;
847 1.1.1.1.4.2 yamt }
848 1.1.1.1.4.2 yamt
849 1.1.1.1.4.2 yamt /* Hook called by the linker routine which adds symbols from an object
850 1.1.1.1.4.2 yamt file. We use it to put .comm items in .sbss, and not .bss. */
851 1.1.1.1.4.2 yamt
852 1.1.1.1.4.2 yamt static bfd_boolean
853 1.1.1.1.4.2 yamt elf64_ia64_add_symbol_hook (bfd *abfd,
854 1.1.1.1.4.2 yamt struct bfd_link_info *info,
855 1.1.1.1.4.2 yamt Elf_Internal_Sym *sym,
856 1.1.1.1.4.2 yamt const char **namep ATTRIBUTE_UNUSED,
857 1.1.1.1.4.2 yamt flagword *flagsp ATTRIBUTE_UNUSED,
858 1.1.1.1.4.2 yamt asection **secp,
859 1.1.1.1.4.2 yamt bfd_vma *valp)
860 1.1.1.1.4.2 yamt {
861 1.1.1.1.4.2 yamt if (sym->st_shndx == SHN_COMMON
862 1.1.1.1.4.2 yamt && !info->relocatable
863 1.1.1.1.4.2 yamt && sym->st_size <= elf_gp_size (abfd))
864 1.1.1.1.4.2 yamt {
865 1.1.1.1.4.2 yamt /* Common symbols less than or equal to -G nn bytes are
866 1.1.1.1.4.2 yamt automatically put into .sbss. */
867 1.1.1.1.4.2 yamt
868 1.1.1.1.4.2 yamt asection *scomm = bfd_get_section_by_name (abfd, ".scommon");
869 1.1.1.1.4.2 yamt
870 1.1.1.1.4.2 yamt if (scomm == NULL)
871 1.1.1.1.4.2 yamt {
872 1.1.1.1.4.2 yamt scomm = bfd_make_section_with_flags (abfd, ".scommon",
873 1.1.1.1.4.2 yamt (SEC_ALLOC
874 1.1.1.1.4.2 yamt | SEC_IS_COMMON
875 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
876 1.1.1.1.4.2 yamt if (scomm == NULL)
877 1.1.1.1.4.2 yamt return FALSE;
878 1.1.1.1.4.2 yamt }
879 1.1.1.1.4.2 yamt
880 1.1.1.1.4.2 yamt *secp = scomm;
881 1.1.1.1.4.2 yamt *valp = sym->st_size;
882 1.1.1.1.4.2 yamt }
883 1.1.1.1.4.2 yamt
884 1.1.1.1.4.2 yamt return TRUE;
885 1.1.1.1.4.2 yamt }
886 1.1.1.1.4.2 yamt
887 1.1.1.1.4.2 yamt /* According to the Tahoe assembler spec, all labels starting with a
888 1.1.1.1.4.2 yamt '.' are local. */
889 1.1.1.1.4.2 yamt
890 1.1.1.1.4.2 yamt static bfd_boolean
891 1.1.1.1.4.2 yamt elf64_ia64_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED,
892 1.1.1.1.4.2 yamt const char *name)
893 1.1.1.1.4.2 yamt {
894 1.1.1.1.4.2 yamt return name[0] == '.';
895 1.1.1.1.4.2 yamt }
896 1.1.1.1.4.2 yamt
897 1.1.1.1.4.2 yamt /* Should we do dynamic things to this symbol? */
898 1.1.1.1.4.2 yamt
899 1.1.1.1.4.2 yamt static bfd_boolean
900 1.1.1.1.4.2 yamt elf64_ia64_dynamic_symbol_p (struct elf_link_hash_entry *h)
901 1.1.1.1.4.2 yamt {
902 1.1.1.1.4.2 yamt return h != NULL && h->def_dynamic;
903 1.1.1.1.4.2 yamt }
904 1.1.1.1.4.2 yamt
905 1.1.1.1.4.2 yamt static struct bfd_hash_entry*
906 1.1.1.1.4.2 yamt elf64_ia64_new_elf_hash_entry (struct bfd_hash_entry *entry,
907 1.1.1.1.4.2 yamt struct bfd_hash_table *table,
908 1.1.1.1.4.2 yamt const char *string)
909 1.1.1.1.4.2 yamt {
910 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *ret;
911 1.1.1.1.4.2 yamt ret = (struct elf64_ia64_link_hash_entry *) entry;
912 1.1.1.1.4.2 yamt
913 1.1.1.1.4.2 yamt /* Allocate the structure if it has not already been allocated by a
914 1.1.1.1.4.2 yamt subclass. */
915 1.1.1.1.4.2 yamt if (!ret)
916 1.1.1.1.4.2 yamt ret = bfd_hash_allocate (table, sizeof (*ret));
917 1.1.1.1.4.2 yamt
918 1.1.1.1.4.2 yamt if (!ret)
919 1.1.1.1.4.2 yamt return 0;
920 1.1.1.1.4.2 yamt
921 1.1.1.1.4.2 yamt /* Call the allocation method of the superclass. */
922 1.1.1.1.4.2 yamt ret = ((struct elf64_ia64_link_hash_entry *)
923 1.1.1.1.4.2 yamt _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
924 1.1.1.1.4.2 yamt table, string));
925 1.1.1.1.4.2 yamt
926 1.1.1.1.4.2 yamt ret->info = NULL;
927 1.1.1.1.4.2 yamt ret->count = 0;
928 1.1.1.1.4.2 yamt ret->sorted_count = 0;
929 1.1.1.1.4.2 yamt ret->size = 0;
930 1.1.1.1.4.2 yamt return (struct bfd_hash_entry *) ret;
931 1.1.1.1.4.2 yamt }
932 1.1.1.1.4.2 yamt
933 1.1.1.1.4.2 yamt static void
934 1.1.1.1.4.2 yamt elf64_ia64_hash_hide_symbol (struct bfd_link_info *info,
935 1.1.1.1.4.2 yamt struct elf_link_hash_entry *xh,
936 1.1.1.1.4.2 yamt bfd_boolean force_local)
937 1.1.1.1.4.2 yamt {
938 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *h;
939 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
940 1.1.1.1.4.2 yamt unsigned int count;
941 1.1.1.1.4.2 yamt
942 1.1.1.1.4.2 yamt h = (struct elf64_ia64_link_hash_entry *)xh;
943 1.1.1.1.4.2 yamt
944 1.1.1.1.4.2 yamt _bfd_elf_link_hash_hide_symbol (info, &h->root, force_local);
945 1.1.1.1.4.2 yamt
946 1.1.1.1.4.2 yamt for (count = h->count, dyn_i = h->info;
947 1.1.1.1.4.2 yamt count != 0;
948 1.1.1.1.4.2 yamt count--, dyn_i++)
949 1.1.1.1.4.2 yamt {
950 1.1.1.1.4.2 yamt dyn_i->want_plt2 = 0;
951 1.1.1.1.4.2 yamt dyn_i->want_plt = 0;
952 1.1.1.1.4.2 yamt }
953 1.1.1.1.4.2 yamt }
954 1.1.1.1.4.2 yamt
955 1.1.1.1.4.2 yamt /* Compute a hash of a local hash entry. */
956 1.1.1.1.4.2 yamt
957 1.1.1.1.4.2 yamt static hashval_t
958 1.1.1.1.4.2 yamt elf64_ia64_local_htab_hash (const void *ptr)
959 1.1.1.1.4.2 yamt {
960 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *entry
961 1.1.1.1.4.2 yamt = (struct elf64_ia64_local_hash_entry *) ptr;
962 1.1.1.1.4.2 yamt
963 1.1.1.1.4.2 yamt return ELF_LOCAL_SYMBOL_HASH (entry->id, entry->r_sym);
964 1.1.1.1.4.2 yamt }
965 1.1.1.1.4.2 yamt
966 1.1.1.1.4.2 yamt /* Compare local hash entries. */
967 1.1.1.1.4.2 yamt
968 1.1.1.1.4.2 yamt static int
969 1.1.1.1.4.2 yamt elf64_ia64_local_htab_eq (const void *ptr1, const void *ptr2)
970 1.1.1.1.4.2 yamt {
971 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *entry1
972 1.1.1.1.4.2 yamt = (struct elf64_ia64_local_hash_entry *) ptr1;
973 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *entry2
974 1.1.1.1.4.2 yamt = (struct elf64_ia64_local_hash_entry *) ptr2;
975 1.1.1.1.4.2 yamt
976 1.1.1.1.4.2 yamt return entry1->id == entry2->id && entry1->r_sym == entry2->r_sym;
977 1.1.1.1.4.2 yamt }
978 1.1.1.1.4.2 yamt
979 1.1.1.1.4.2 yamt /* Create the derived linker hash table. The IA-64 ELF port uses this
980 1.1.1.1.4.2 yamt derived hash table to keep information specific to the IA-64 ElF
981 1.1.1.1.4.2 yamt linker (without using static variables). */
982 1.1.1.1.4.2 yamt
983 1.1.1.1.4.2 yamt static struct bfd_link_hash_table *
984 1.1.1.1.4.2 yamt elf64_ia64_hash_table_create (bfd *abfd)
985 1.1.1.1.4.2 yamt {
986 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ret;
987 1.1.1.1.4.2 yamt
988 1.1.1.1.4.2 yamt ret = bfd_zmalloc ((bfd_size_type) sizeof (*ret));
989 1.1.1.1.4.2 yamt if (!ret)
990 1.1.1.1.4.2 yamt return NULL;
991 1.1.1.1.4.2 yamt
992 1.1.1.1.4.2 yamt if (!_bfd_elf_link_hash_table_init (&ret->root, abfd,
993 1.1.1.1.4.2 yamt elf64_ia64_new_elf_hash_entry,
994 1.1.1.1.4.2 yamt sizeof (struct elf64_ia64_link_hash_entry),
995 1.1.1.1.4.2 yamt IA64_ELF_DATA))
996 1.1.1.1.4.2 yamt {
997 1.1.1.1.4.2 yamt free (ret);
998 1.1.1.1.4.2 yamt return NULL;
999 1.1.1.1.4.2 yamt }
1000 1.1.1.1.4.2 yamt
1001 1.1.1.1.4.2 yamt ret->loc_hash_table = htab_try_create (1024, elf64_ia64_local_htab_hash,
1002 1.1.1.1.4.2 yamt elf64_ia64_local_htab_eq, NULL);
1003 1.1.1.1.4.2 yamt ret->loc_hash_memory = objalloc_create ();
1004 1.1.1.1.4.2 yamt if (!ret->loc_hash_table || !ret->loc_hash_memory)
1005 1.1.1.1.4.2 yamt {
1006 1.1.1.1.4.2 yamt free (ret);
1007 1.1.1.1.4.2 yamt return NULL;
1008 1.1.1.1.4.2 yamt }
1009 1.1.1.1.4.2 yamt
1010 1.1.1.1.4.2 yamt return &ret->root.root;
1011 1.1.1.1.4.2 yamt }
1012 1.1.1.1.4.2 yamt
1013 1.1.1.1.4.2 yamt /* Free the global elf64_ia64_dyn_sym_info array. */
1014 1.1.1.1.4.2 yamt
1015 1.1.1.1.4.2 yamt static bfd_boolean
1016 1.1.1.1.4.2 yamt elf64_ia64_global_dyn_info_free (void **xentry,
1017 1.1.1.1.4.2 yamt void * unused ATTRIBUTE_UNUSED)
1018 1.1.1.1.4.2 yamt {
1019 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *entry
1020 1.1.1.1.4.2 yamt = (struct elf64_ia64_link_hash_entry *) xentry;
1021 1.1.1.1.4.2 yamt
1022 1.1.1.1.4.2 yamt if (entry->root.root.type == bfd_link_hash_warning)
1023 1.1.1.1.4.2 yamt entry = (struct elf64_ia64_link_hash_entry *) entry->root.root.u.i.link;
1024 1.1.1.1.4.2 yamt
1025 1.1.1.1.4.2 yamt if (entry->info)
1026 1.1.1.1.4.2 yamt {
1027 1.1.1.1.4.2 yamt free (entry->info);
1028 1.1.1.1.4.2 yamt entry->info = NULL;
1029 1.1.1.1.4.2 yamt entry->count = 0;
1030 1.1.1.1.4.2 yamt entry->sorted_count = 0;
1031 1.1.1.1.4.2 yamt entry->size = 0;
1032 1.1.1.1.4.2 yamt }
1033 1.1.1.1.4.2 yamt
1034 1.1.1.1.4.2 yamt return TRUE;
1035 1.1.1.1.4.2 yamt }
1036 1.1.1.1.4.2 yamt
1037 1.1.1.1.4.2 yamt /* Free the local elf64_ia64_dyn_sym_info array. */
1038 1.1.1.1.4.2 yamt
1039 1.1.1.1.4.2 yamt static bfd_boolean
1040 1.1.1.1.4.2 yamt elf64_ia64_local_dyn_info_free (void **slot,
1041 1.1.1.1.4.2 yamt void * unused ATTRIBUTE_UNUSED)
1042 1.1.1.1.4.2 yamt {
1043 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *entry
1044 1.1.1.1.4.2 yamt = (struct elf64_ia64_local_hash_entry *) *slot;
1045 1.1.1.1.4.2 yamt
1046 1.1.1.1.4.2 yamt if (entry->info)
1047 1.1.1.1.4.2 yamt {
1048 1.1.1.1.4.2 yamt free (entry->info);
1049 1.1.1.1.4.2 yamt entry->info = NULL;
1050 1.1.1.1.4.2 yamt entry->count = 0;
1051 1.1.1.1.4.2 yamt entry->sorted_count = 0;
1052 1.1.1.1.4.2 yamt entry->size = 0;
1053 1.1.1.1.4.2 yamt }
1054 1.1.1.1.4.2 yamt
1055 1.1.1.1.4.2 yamt return TRUE;
1056 1.1.1.1.4.2 yamt }
1057 1.1.1.1.4.2 yamt
1058 1.1.1.1.4.2 yamt /* Destroy IA-64 linker hash table. */
1059 1.1.1.1.4.2 yamt
1060 1.1.1.1.4.2 yamt static void
1061 1.1.1.1.4.2 yamt elf64_ia64_hash_table_free (struct bfd_link_hash_table *hash)
1062 1.1.1.1.4.2 yamt {
1063 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info
1064 1.1.1.1.4.2 yamt = (struct elf64_ia64_link_hash_table *) hash;
1065 1.1.1.1.4.2 yamt if (ia64_info->loc_hash_table)
1066 1.1.1.1.4.2 yamt {
1067 1.1.1.1.4.2 yamt htab_traverse (ia64_info->loc_hash_table,
1068 1.1.1.1.4.2 yamt elf64_ia64_local_dyn_info_free, NULL);
1069 1.1.1.1.4.2 yamt htab_delete (ia64_info->loc_hash_table);
1070 1.1.1.1.4.2 yamt }
1071 1.1.1.1.4.2 yamt if (ia64_info->loc_hash_memory)
1072 1.1.1.1.4.2 yamt objalloc_free ((struct objalloc *) ia64_info->loc_hash_memory);
1073 1.1.1.1.4.2 yamt elf_link_hash_traverse (&ia64_info->root,
1074 1.1.1.1.4.2 yamt elf64_ia64_global_dyn_info_free, NULL);
1075 1.1.1.1.4.2 yamt _bfd_generic_link_hash_table_free (hash);
1076 1.1.1.1.4.2 yamt }
1077 1.1.1.1.4.2 yamt
1078 1.1.1.1.4.2 yamt /* Traverse both local and global hash tables. */
1079 1.1.1.1.4.2 yamt
1080 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_traverse_data
1081 1.1.1.1.4.2 yamt {
1082 1.1.1.1.4.2 yamt bfd_boolean (*func) (struct elf64_ia64_dyn_sym_info *, void *);
1083 1.1.1.1.4.2 yamt void * data;
1084 1.1.1.1.4.2 yamt };
1085 1.1.1.1.4.2 yamt
1086 1.1.1.1.4.2 yamt static bfd_boolean
1087 1.1.1.1.4.2 yamt elf64_ia64_global_dyn_sym_thunk (struct bfd_hash_entry *xentry,
1088 1.1.1.1.4.2 yamt void * xdata)
1089 1.1.1.1.4.2 yamt {
1090 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *entry
1091 1.1.1.1.4.2 yamt = (struct elf64_ia64_link_hash_entry *) xentry;
1092 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_traverse_data *data
1093 1.1.1.1.4.2 yamt = (struct elf64_ia64_dyn_sym_traverse_data *) xdata;
1094 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
1095 1.1.1.1.4.2 yamt unsigned int count;
1096 1.1.1.1.4.2 yamt
1097 1.1.1.1.4.2 yamt if (entry->root.root.type == bfd_link_hash_warning)
1098 1.1.1.1.4.2 yamt entry = (struct elf64_ia64_link_hash_entry *) entry->root.root.u.i.link;
1099 1.1.1.1.4.2 yamt
1100 1.1.1.1.4.2 yamt for (count = entry->count, dyn_i = entry->info;
1101 1.1.1.1.4.2 yamt count != 0;
1102 1.1.1.1.4.2 yamt count--, dyn_i++)
1103 1.1.1.1.4.2 yamt if (! (*data->func) (dyn_i, data->data))
1104 1.1.1.1.4.2 yamt return FALSE;
1105 1.1.1.1.4.2 yamt return TRUE;
1106 1.1.1.1.4.2 yamt }
1107 1.1.1.1.4.2 yamt
1108 1.1.1.1.4.2 yamt static bfd_boolean
1109 1.1.1.1.4.2 yamt elf64_ia64_local_dyn_sym_thunk (void **slot, void * xdata)
1110 1.1.1.1.4.2 yamt {
1111 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *entry
1112 1.1.1.1.4.2 yamt = (struct elf64_ia64_local_hash_entry *) *slot;
1113 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_traverse_data *data
1114 1.1.1.1.4.2 yamt = (struct elf64_ia64_dyn_sym_traverse_data *) xdata;
1115 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
1116 1.1.1.1.4.2 yamt unsigned int count;
1117 1.1.1.1.4.2 yamt
1118 1.1.1.1.4.2 yamt for (count = entry->count, dyn_i = entry->info;
1119 1.1.1.1.4.2 yamt count != 0;
1120 1.1.1.1.4.2 yamt count--, dyn_i++)
1121 1.1.1.1.4.2 yamt if (! (*data->func) (dyn_i, data->data))
1122 1.1.1.1.4.2 yamt return FALSE;
1123 1.1.1.1.4.2 yamt return TRUE;
1124 1.1.1.1.4.2 yamt }
1125 1.1.1.1.4.2 yamt
1126 1.1.1.1.4.2 yamt static void
1127 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (struct elf64_ia64_link_hash_table *ia64_info,
1128 1.1.1.1.4.2 yamt bfd_boolean (*func) (struct elf64_ia64_dyn_sym_info *, void *),
1129 1.1.1.1.4.2 yamt void * data)
1130 1.1.1.1.4.2 yamt {
1131 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_traverse_data xdata;
1132 1.1.1.1.4.2 yamt
1133 1.1.1.1.4.2 yamt xdata.func = func;
1134 1.1.1.1.4.2 yamt xdata.data = data;
1135 1.1.1.1.4.2 yamt
1136 1.1.1.1.4.2 yamt elf_link_hash_traverse (&ia64_info->root,
1137 1.1.1.1.4.2 yamt elf64_ia64_global_dyn_sym_thunk, &xdata);
1138 1.1.1.1.4.2 yamt htab_traverse (ia64_info->loc_hash_table,
1139 1.1.1.1.4.2 yamt elf64_ia64_local_dyn_sym_thunk, &xdata);
1140 1.1.1.1.4.2 yamt }
1141 1.1.1.1.4.2 yamt
1142 1.1.1.1.4.2 yamt #define NOTE_NAME "IPF/VMS"
1143 1.1.1.1.4.2 yamt
1144 1.1.1.1.4.2 yamt static bfd_boolean
1145 1.1.1.1.4.2 yamt create_ia64_vms_notes (bfd *abfd, struct bfd_link_info *info,
1146 1.1.1.1.4.2 yamt unsigned int time_hi, unsigned int time_lo)
1147 1.1.1.1.4.2 yamt {
1148 1.1.1.1.4.2 yamt #define NBR_NOTES 7
1149 1.1.1.1.4.2 yamt Elf_Internal_Note notes[NBR_NOTES];
1150 1.1.1.1.4.2 yamt char *module_name;
1151 1.1.1.1.4.2 yamt int module_name_len;
1152 1.1.1.1.4.2 yamt unsigned char cur_time[8];
1153 1.1.1.1.4.2 yamt Elf64_External_VMS_ORIG_DYN_Note *orig_dyn;
1154 1.1.1.1.4.2 yamt unsigned int orig_dyn_size;
1155 1.1.1.1.4.2 yamt unsigned int note_size;
1156 1.1.1.1.4.2 yamt int i;
1157 1.1.1.1.4.2 yamt unsigned char *noteptr;
1158 1.1.1.1.4.2 yamt unsigned char *note_contents;
1159 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
1160 1.1.1.1.4.2 yamt
1161 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
1162 1.1.1.1.4.2 yamt
1163 1.1.1.1.4.2 yamt module_name = vms_get_module_name (bfd_get_filename (abfd), TRUE);
1164 1.1.1.1.4.2 yamt module_name_len = strlen (module_name) + 1;
1165 1.1.1.1.4.2 yamt
1166 1.1.1.1.4.2 yamt bfd_putl32 (time_lo, cur_time + 0);
1167 1.1.1.1.4.2 yamt bfd_putl32 (time_hi, cur_time + 4);
1168 1.1.1.1.4.2 yamt
1169 1.1.1.1.4.2 yamt /* Note 0: IMGNAM. */
1170 1.1.1.1.4.2 yamt notes[0].type = NT_VMS_IMGNAM;
1171 1.1.1.1.4.2 yamt notes[0].descdata = module_name;
1172 1.1.1.1.4.2 yamt notes[0].descsz = module_name_len;
1173 1.1.1.1.4.2 yamt
1174 1.1.1.1.4.2 yamt /* Note 1: GSTNAM. */
1175 1.1.1.1.4.2 yamt notes[1].type = NT_VMS_GSTNAM;
1176 1.1.1.1.4.2 yamt notes[1].descdata = module_name;
1177 1.1.1.1.4.2 yamt notes[1].descsz = module_name_len;
1178 1.1.1.1.4.2 yamt
1179 1.1.1.1.4.2 yamt /* Note 2: IMGID. */
1180 1.1.1.1.4.2 yamt #define IMG_ID "V1.0"
1181 1.1.1.1.4.2 yamt notes[2].type = NT_VMS_IMGID;
1182 1.1.1.1.4.2 yamt notes[2].descdata = IMG_ID;
1183 1.1.1.1.4.2 yamt notes[2].descsz = sizeof (IMG_ID);
1184 1.1.1.1.4.2 yamt
1185 1.1.1.1.4.2 yamt /* Note 3: Linktime. */
1186 1.1.1.1.4.2 yamt notes[3].type = NT_VMS_LINKTIME;
1187 1.1.1.1.4.2 yamt notes[3].descdata = (char *)cur_time;
1188 1.1.1.1.4.2 yamt notes[3].descsz = sizeof (cur_time);
1189 1.1.1.1.4.2 yamt
1190 1.1.1.1.4.2 yamt /* Note 4: Linker id. */
1191 1.1.1.1.4.2 yamt notes[4].type = NT_VMS_LINKID;
1192 1.1.1.1.4.2 yamt notes[4].descdata = "GNU ld " BFD_VERSION_STRING;
1193 1.1.1.1.4.2 yamt notes[4].descsz = strlen (notes[4].descdata) + 1;
1194 1.1.1.1.4.2 yamt
1195 1.1.1.1.4.2 yamt /* Note 5: Original dyn. */
1196 1.1.1.1.4.2 yamt orig_dyn_size = (sizeof (*orig_dyn) + sizeof (IMG_ID) - 1 + 7) & ~7;
1197 1.1.1.1.4.2 yamt orig_dyn = bfd_zalloc (abfd, orig_dyn_size);
1198 1.1.1.1.4.2 yamt if (orig_dyn == NULL)
1199 1.1.1.1.4.2 yamt return FALSE;
1200 1.1.1.1.4.2 yamt bfd_putl32 (1, orig_dyn->major_id);
1201 1.1.1.1.4.2 yamt bfd_putl32 (3, orig_dyn->minor_id);
1202 1.1.1.1.4.2 yamt memcpy (orig_dyn->manipulation_date, cur_time, sizeof (cur_time));
1203 1.1.1.1.4.2 yamt bfd_putl64 (VMS_LF_IMGSTA | VMS_LF_MAIN, orig_dyn->link_flags);
1204 1.1.1.1.4.2 yamt bfd_putl32 (EF_IA_64_ABI64, orig_dyn->elf_flags);
1205 1.1.1.1.4.2 yamt memcpy (orig_dyn->imgid, IMG_ID, sizeof (IMG_ID));
1206 1.1.1.1.4.2 yamt notes[5].type = NT_VMS_ORIG_DYN;
1207 1.1.1.1.4.2 yamt notes[5].descdata = (char *)orig_dyn;
1208 1.1.1.1.4.2 yamt notes[5].descsz = orig_dyn_size;
1209 1.1.1.1.4.2 yamt
1210 1.1.1.1.4.2 yamt /* Note 3: Patchtime. */
1211 1.1.1.1.4.2 yamt notes[6].type = NT_VMS_PATCHTIME;
1212 1.1.1.1.4.2 yamt notes[6].descdata = (char *)cur_time;
1213 1.1.1.1.4.2 yamt notes[6].descsz = sizeof (cur_time);
1214 1.1.1.1.4.2 yamt
1215 1.1.1.1.4.2 yamt /* Compute notes size. */
1216 1.1.1.1.4.2 yamt note_size = 0;
1217 1.1.1.1.4.2 yamt for (i = 0; i < NBR_NOTES; i++)
1218 1.1.1.1.4.2 yamt note_size += sizeof (Elf64_External_VMS_Note) - 1
1219 1.1.1.1.4.2 yamt + ((sizeof (NOTE_NAME) - 1 + 7) & ~7)
1220 1.1.1.1.4.2 yamt + ((notes[i].descsz + 7) & ~7);
1221 1.1.1.1.4.2 yamt
1222 1.1.1.1.4.2 yamt /* Malloc a temporary buffer large enough for most notes */
1223 1.1.1.1.4.2 yamt note_contents = (unsigned char *) bfd_zalloc (abfd, note_size);
1224 1.1.1.1.4.2 yamt if (note_contents == NULL)
1225 1.1.1.1.4.2 yamt return FALSE;
1226 1.1.1.1.4.2 yamt noteptr = note_contents;
1227 1.1.1.1.4.2 yamt
1228 1.1.1.1.4.2 yamt /* Fill notes. */
1229 1.1.1.1.4.2 yamt for (i = 0; i < NBR_NOTES; i++)
1230 1.1.1.1.4.2 yamt {
1231 1.1.1.1.4.2 yamt Elf64_External_VMS_Note *enote = (Elf64_External_VMS_Note *) noteptr;
1232 1.1.1.1.4.2 yamt
1233 1.1.1.1.4.2 yamt bfd_putl64 (sizeof (NOTE_NAME) - 1, enote->namesz);
1234 1.1.1.1.4.2 yamt bfd_putl64 (notes[i].descsz, enote->descsz);
1235 1.1.1.1.4.2 yamt bfd_putl64 (notes[i].type, enote->type);
1236 1.1.1.1.4.2 yamt
1237 1.1.1.1.4.2 yamt noteptr = (unsigned char *)enote->name;
1238 1.1.1.1.4.2 yamt memcpy (noteptr, NOTE_NAME, sizeof (NOTE_NAME) - 1);
1239 1.1.1.1.4.2 yamt noteptr += (sizeof (NOTE_NAME) - 1 + 7) & ~7;
1240 1.1.1.1.4.2 yamt memcpy (noteptr, notes[i].descdata, notes[i].descsz);
1241 1.1.1.1.4.2 yamt noteptr += (notes[i].descsz + 7) & ~7;
1242 1.1.1.1.4.2 yamt }
1243 1.1.1.1.4.2 yamt
1244 1.1.1.1.4.2 yamt ia64_info->note_sec->contents = note_contents;
1245 1.1.1.1.4.2 yamt ia64_info->note_sec->size = note_size;
1246 1.1.1.1.4.2 yamt
1247 1.1.1.1.4.2 yamt free (module_name);
1248 1.1.1.1.4.2 yamt
1249 1.1.1.1.4.2 yamt return TRUE;
1250 1.1.1.1.4.2 yamt }
1251 1.1.1.1.4.2 yamt
1252 1.1.1.1.4.2 yamt static bfd_boolean
1253 1.1.1.1.4.2 yamt elf64_ia64_create_dynamic_sections (bfd *abfd,
1254 1.1.1.1.4.2 yamt struct bfd_link_info *info)
1255 1.1.1.1.4.2 yamt {
1256 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
1257 1.1.1.1.4.2 yamt asection *s;
1258 1.1.1.1.4.2 yamt flagword flags;
1259 1.1.1.1.4.2 yamt const struct elf_backend_data *bed;
1260 1.1.1.1.4.2 yamt
1261 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
1262 1.1.1.1.4.2 yamt if (ia64_info == NULL)
1263 1.1.1.1.4.2 yamt return FALSE;
1264 1.1.1.1.4.2 yamt
1265 1.1.1.1.4.2 yamt if (elf_hash_table (info)->dynamic_sections_created)
1266 1.1.1.1.4.2 yamt return TRUE;
1267 1.1.1.1.4.2 yamt
1268 1.1.1.1.4.2 yamt abfd = elf_hash_table (info)->dynobj;
1269 1.1.1.1.4.2 yamt bed = get_elf_backend_data (abfd);
1270 1.1.1.1.4.2 yamt
1271 1.1.1.1.4.2 yamt flags = bed->dynamic_sec_flags;
1272 1.1.1.1.4.2 yamt
1273 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".dynamic",
1274 1.1.1.1.4.2 yamt flags | SEC_READONLY);
1275 1.1.1.1.4.2 yamt if (s == NULL
1276 1.1.1.1.4.2 yamt || ! bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
1277 1.1.1.1.4.2 yamt return FALSE;
1278 1.1.1.1.4.2 yamt
1279 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".plt", flags | SEC_READONLY);
1280 1.1.1.1.4.2 yamt if (s == NULL
1281 1.1.1.1.4.2 yamt || ! bfd_set_section_alignment (abfd, s, bed->plt_alignment))
1282 1.1.1.1.4.2 yamt return FALSE;
1283 1.1.1.1.4.2 yamt ia64_info->root.splt = s;
1284 1.1.1.1.4.2 yamt
1285 1.1.1.1.4.2 yamt if (!get_got (abfd, ia64_info))
1286 1.1.1.1.4.2 yamt return FALSE;
1287 1.1.1.1.4.2 yamt
1288 1.1.1.1.4.2 yamt if (!get_pltoff (abfd, ia64_info))
1289 1.1.1.1.4.2 yamt return FALSE;
1290 1.1.1.1.4.2 yamt
1291 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".vmsdynstr",
1292 1.1.1.1.4.2 yamt (SEC_ALLOC
1293 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1294 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1295 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
1296 1.1.1.1.4.2 yamt if (s == NULL
1297 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (abfd, s, 0))
1298 1.1.1.1.4.2 yamt return FALSE;
1299 1.1.1.1.4.2 yamt
1300 1.1.1.1.4.2 yamt /* Create a fixup section. */
1301 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".fixups",
1302 1.1.1.1.4.2 yamt (SEC_ALLOC
1303 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1304 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1305 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
1306 1.1.1.1.4.2 yamt if (s == NULL
1307 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (abfd, s, 3))
1308 1.1.1.1.4.2 yamt return FALSE;
1309 1.1.1.1.4.2 yamt ia64_info->fixups_sec = s;
1310 1.1.1.1.4.2 yamt
1311 1.1.1.1.4.2 yamt /* Create the transfer fixup section. */
1312 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".transfer",
1313 1.1.1.1.4.2 yamt (SEC_ALLOC
1314 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1315 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1316 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
1317 1.1.1.1.4.2 yamt if (s == NULL
1318 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (abfd, s, 3))
1319 1.1.1.1.4.2 yamt return FALSE;
1320 1.1.1.1.4.2 yamt s->size = sizeof (struct elf64_vms_transfer);
1321 1.1.1.1.4.2 yamt ia64_info->transfer_sec = s;
1322 1.1.1.1.4.2 yamt
1323 1.1.1.1.4.2 yamt /* Create note section. */
1324 1.1.1.1.4.2 yamt s = bfd_make_section_anyway_with_flags (abfd, ".vms.note",
1325 1.1.1.1.4.2 yamt (SEC_LINKER_CREATED
1326 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1327 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1328 1.1.1.1.4.2 yamt | SEC_READONLY));
1329 1.1.1.1.4.2 yamt if (s == NULL
1330 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (abfd, s, 3))
1331 1.1.1.1.4.2 yamt return FALSE;
1332 1.1.1.1.4.2 yamt ia64_info->note_sec = s;
1333 1.1.1.1.4.2 yamt
1334 1.1.1.1.4.2 yamt elf_hash_table (info)->dynamic_sections_created = TRUE;
1335 1.1.1.1.4.2 yamt return TRUE;
1336 1.1.1.1.4.2 yamt }
1337 1.1.1.1.4.2 yamt
1338 1.1.1.1.4.2 yamt /* Find and/or create a hash entry for local symbol. */
1339 1.1.1.1.4.2 yamt static struct elf64_ia64_local_hash_entry *
1340 1.1.1.1.4.2 yamt get_local_sym_hash (struct elf64_ia64_link_hash_table *ia64_info,
1341 1.1.1.1.4.2 yamt bfd *abfd, const Elf_Internal_Rela *rel,
1342 1.1.1.1.4.2 yamt bfd_boolean create)
1343 1.1.1.1.4.2 yamt {
1344 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry e, *ret;
1345 1.1.1.1.4.2 yamt asection *sec = abfd->sections;
1346 1.1.1.1.4.2 yamt hashval_t h = ELF_LOCAL_SYMBOL_HASH (sec->id,
1347 1.1.1.1.4.2 yamt ELF64_R_SYM (rel->r_info));
1348 1.1.1.1.4.2 yamt void **slot;
1349 1.1.1.1.4.2 yamt
1350 1.1.1.1.4.2 yamt e.id = sec->id;
1351 1.1.1.1.4.2 yamt e.r_sym = ELF64_R_SYM (rel->r_info);
1352 1.1.1.1.4.2 yamt slot = htab_find_slot_with_hash (ia64_info->loc_hash_table, &e, h,
1353 1.1.1.1.4.2 yamt create ? INSERT : NO_INSERT);
1354 1.1.1.1.4.2 yamt
1355 1.1.1.1.4.2 yamt if (!slot)
1356 1.1.1.1.4.2 yamt return NULL;
1357 1.1.1.1.4.2 yamt
1358 1.1.1.1.4.2 yamt if (*slot)
1359 1.1.1.1.4.2 yamt return (struct elf64_ia64_local_hash_entry *) *slot;
1360 1.1.1.1.4.2 yamt
1361 1.1.1.1.4.2 yamt ret = (struct elf64_ia64_local_hash_entry *)
1362 1.1.1.1.4.2 yamt objalloc_alloc ((struct objalloc *) ia64_info->loc_hash_memory,
1363 1.1.1.1.4.2 yamt sizeof (struct elf64_ia64_local_hash_entry));
1364 1.1.1.1.4.2 yamt if (ret)
1365 1.1.1.1.4.2 yamt {
1366 1.1.1.1.4.2 yamt memset (ret, 0, sizeof (*ret));
1367 1.1.1.1.4.2 yamt ret->id = sec->id;
1368 1.1.1.1.4.2 yamt ret->r_sym = ELF64_R_SYM (rel->r_info);
1369 1.1.1.1.4.2 yamt *slot = ret;
1370 1.1.1.1.4.2 yamt }
1371 1.1.1.1.4.2 yamt return ret;
1372 1.1.1.1.4.2 yamt }
1373 1.1.1.1.4.2 yamt
1374 1.1.1.1.4.2 yamt /* Used to sort elf64_ia64_dyn_sym_info array. */
1375 1.1.1.1.4.2 yamt
1376 1.1.1.1.4.2 yamt static int
1377 1.1.1.1.4.2 yamt addend_compare (const void *xp, const void *yp)
1378 1.1.1.1.4.2 yamt {
1379 1.1.1.1.4.2 yamt const struct elf64_ia64_dyn_sym_info *x
1380 1.1.1.1.4.2 yamt = (const struct elf64_ia64_dyn_sym_info *) xp;
1381 1.1.1.1.4.2 yamt const struct elf64_ia64_dyn_sym_info *y
1382 1.1.1.1.4.2 yamt = (const struct elf64_ia64_dyn_sym_info *) yp;
1383 1.1.1.1.4.2 yamt
1384 1.1.1.1.4.2 yamt return x->addend < y->addend ? -1 : x->addend > y->addend ? 1 : 0;
1385 1.1.1.1.4.2 yamt }
1386 1.1.1.1.4.2 yamt
1387 1.1.1.1.4.2 yamt /* Sort elf64_ia64_dyn_sym_info array and remove duplicates. */
1388 1.1.1.1.4.2 yamt
1389 1.1.1.1.4.2 yamt static unsigned int
1390 1.1.1.1.4.2 yamt sort_dyn_sym_info (struct elf64_ia64_dyn_sym_info *info,
1391 1.1.1.1.4.2 yamt unsigned int count)
1392 1.1.1.1.4.2 yamt {
1393 1.1.1.1.4.2 yamt bfd_vma curr, prev, got_offset;
1394 1.1.1.1.4.2 yamt unsigned int i, kept, dupes, diff, dest, src, len;
1395 1.1.1.1.4.2 yamt
1396 1.1.1.1.4.2 yamt qsort (info, count, sizeof (*info), addend_compare);
1397 1.1.1.1.4.2 yamt
1398 1.1.1.1.4.2 yamt /* Find the first duplicate. */
1399 1.1.1.1.4.2 yamt prev = info [0].addend;
1400 1.1.1.1.4.2 yamt got_offset = info [0].got_offset;
1401 1.1.1.1.4.2 yamt for (i = 1; i < count; i++)
1402 1.1.1.1.4.2 yamt {
1403 1.1.1.1.4.2 yamt curr = info [i].addend;
1404 1.1.1.1.4.2 yamt if (curr == prev)
1405 1.1.1.1.4.2 yamt {
1406 1.1.1.1.4.2 yamt /* For duplicates, make sure that GOT_OFFSET is valid. */
1407 1.1.1.1.4.2 yamt if (got_offset == (bfd_vma) -1)
1408 1.1.1.1.4.2 yamt got_offset = info [i].got_offset;
1409 1.1.1.1.4.2 yamt break;
1410 1.1.1.1.4.2 yamt }
1411 1.1.1.1.4.2 yamt got_offset = info [i].got_offset;
1412 1.1.1.1.4.2 yamt prev = curr;
1413 1.1.1.1.4.2 yamt }
1414 1.1.1.1.4.2 yamt
1415 1.1.1.1.4.2 yamt /* We may move a block of elements to here. */
1416 1.1.1.1.4.2 yamt dest = i++;
1417 1.1.1.1.4.2 yamt
1418 1.1.1.1.4.2 yamt /* Remove duplicates. */
1419 1.1.1.1.4.2 yamt if (i < count)
1420 1.1.1.1.4.2 yamt {
1421 1.1.1.1.4.2 yamt while (i < count)
1422 1.1.1.1.4.2 yamt {
1423 1.1.1.1.4.2 yamt /* For duplicates, make sure that the kept one has a valid
1424 1.1.1.1.4.2 yamt got_offset. */
1425 1.1.1.1.4.2 yamt kept = dest - 1;
1426 1.1.1.1.4.2 yamt if (got_offset != (bfd_vma) -1)
1427 1.1.1.1.4.2 yamt info [kept].got_offset = got_offset;
1428 1.1.1.1.4.2 yamt
1429 1.1.1.1.4.2 yamt curr = info [i].addend;
1430 1.1.1.1.4.2 yamt got_offset = info [i].got_offset;
1431 1.1.1.1.4.2 yamt
1432 1.1.1.1.4.2 yamt /* Move a block of elements whose first one is different from
1433 1.1.1.1.4.2 yamt the previous. */
1434 1.1.1.1.4.2 yamt if (curr == prev)
1435 1.1.1.1.4.2 yamt {
1436 1.1.1.1.4.2 yamt for (src = i + 1; src < count; src++)
1437 1.1.1.1.4.2 yamt {
1438 1.1.1.1.4.2 yamt if (info [src].addend != curr)
1439 1.1.1.1.4.2 yamt break;
1440 1.1.1.1.4.2 yamt /* For duplicates, make sure that GOT_OFFSET is
1441 1.1.1.1.4.2 yamt valid. */
1442 1.1.1.1.4.2 yamt if (got_offset == (bfd_vma) -1)
1443 1.1.1.1.4.2 yamt got_offset = info [src].got_offset;
1444 1.1.1.1.4.2 yamt }
1445 1.1.1.1.4.2 yamt
1446 1.1.1.1.4.2 yamt /* Make sure that the kept one has a valid got_offset. */
1447 1.1.1.1.4.2 yamt if (got_offset != (bfd_vma) -1)
1448 1.1.1.1.4.2 yamt info [kept].got_offset = got_offset;
1449 1.1.1.1.4.2 yamt }
1450 1.1.1.1.4.2 yamt else
1451 1.1.1.1.4.2 yamt src = i;
1452 1.1.1.1.4.2 yamt
1453 1.1.1.1.4.2 yamt if (src >= count)
1454 1.1.1.1.4.2 yamt break;
1455 1.1.1.1.4.2 yamt
1456 1.1.1.1.4.2 yamt /* Find the next duplicate. SRC will be kept. */
1457 1.1.1.1.4.2 yamt prev = info [src].addend;
1458 1.1.1.1.4.2 yamt got_offset = info [src].got_offset;
1459 1.1.1.1.4.2 yamt for (dupes = src + 1; dupes < count; dupes ++)
1460 1.1.1.1.4.2 yamt {
1461 1.1.1.1.4.2 yamt curr = info [dupes].addend;
1462 1.1.1.1.4.2 yamt if (curr == prev)
1463 1.1.1.1.4.2 yamt {
1464 1.1.1.1.4.2 yamt /* Make sure that got_offset is valid. */
1465 1.1.1.1.4.2 yamt if (got_offset == (bfd_vma) -1)
1466 1.1.1.1.4.2 yamt got_offset = info [dupes].got_offset;
1467 1.1.1.1.4.2 yamt
1468 1.1.1.1.4.2 yamt /* For duplicates, make sure that the kept one has
1469 1.1.1.1.4.2 yamt a valid got_offset. */
1470 1.1.1.1.4.2 yamt if (got_offset != (bfd_vma) -1)
1471 1.1.1.1.4.2 yamt info [dupes - 1].got_offset = got_offset;
1472 1.1.1.1.4.2 yamt break;
1473 1.1.1.1.4.2 yamt }
1474 1.1.1.1.4.2 yamt got_offset = info [dupes].got_offset;
1475 1.1.1.1.4.2 yamt prev = curr;
1476 1.1.1.1.4.2 yamt }
1477 1.1.1.1.4.2 yamt
1478 1.1.1.1.4.2 yamt /* How much to move. */
1479 1.1.1.1.4.2 yamt len = dupes - src;
1480 1.1.1.1.4.2 yamt i = dupes + 1;
1481 1.1.1.1.4.2 yamt
1482 1.1.1.1.4.2 yamt if (len == 1 && dupes < count)
1483 1.1.1.1.4.2 yamt {
1484 1.1.1.1.4.2 yamt /* If we only move 1 element, we combine it with the next
1485 1.1.1.1.4.2 yamt one. There must be at least a duplicate. Find the
1486 1.1.1.1.4.2 yamt next different one. */
1487 1.1.1.1.4.2 yamt for (diff = dupes + 1, src++; diff < count; diff++, src++)
1488 1.1.1.1.4.2 yamt {
1489 1.1.1.1.4.2 yamt if (info [diff].addend != curr)
1490 1.1.1.1.4.2 yamt break;
1491 1.1.1.1.4.2 yamt /* Make sure that got_offset is valid. */
1492 1.1.1.1.4.2 yamt if (got_offset == (bfd_vma) -1)
1493 1.1.1.1.4.2 yamt got_offset = info [diff].got_offset;
1494 1.1.1.1.4.2 yamt }
1495 1.1.1.1.4.2 yamt
1496 1.1.1.1.4.2 yamt /* Makre sure that the last duplicated one has an valid
1497 1.1.1.1.4.2 yamt offset. */
1498 1.1.1.1.4.2 yamt BFD_ASSERT (curr == prev);
1499 1.1.1.1.4.2 yamt if (got_offset != (bfd_vma) -1)
1500 1.1.1.1.4.2 yamt info [diff - 1].got_offset = got_offset;
1501 1.1.1.1.4.2 yamt
1502 1.1.1.1.4.2 yamt if (diff < count)
1503 1.1.1.1.4.2 yamt {
1504 1.1.1.1.4.2 yamt /* Find the next duplicate. Track the current valid
1505 1.1.1.1.4.2 yamt offset. */
1506 1.1.1.1.4.2 yamt prev = info [diff].addend;
1507 1.1.1.1.4.2 yamt got_offset = info [diff].got_offset;
1508 1.1.1.1.4.2 yamt for (dupes = diff + 1; dupes < count; dupes ++)
1509 1.1.1.1.4.2 yamt {
1510 1.1.1.1.4.2 yamt curr = info [dupes].addend;
1511 1.1.1.1.4.2 yamt if (curr == prev)
1512 1.1.1.1.4.2 yamt {
1513 1.1.1.1.4.2 yamt /* For duplicates, make sure that GOT_OFFSET
1514 1.1.1.1.4.2 yamt is valid. */
1515 1.1.1.1.4.2 yamt if (got_offset == (bfd_vma) -1)
1516 1.1.1.1.4.2 yamt got_offset = info [dupes].got_offset;
1517 1.1.1.1.4.2 yamt break;
1518 1.1.1.1.4.2 yamt }
1519 1.1.1.1.4.2 yamt got_offset = info [dupes].got_offset;
1520 1.1.1.1.4.2 yamt prev = curr;
1521 1.1.1.1.4.2 yamt diff++;
1522 1.1.1.1.4.2 yamt }
1523 1.1.1.1.4.2 yamt
1524 1.1.1.1.4.2 yamt len = diff - src + 1;
1525 1.1.1.1.4.2 yamt i = diff + 1;
1526 1.1.1.1.4.2 yamt }
1527 1.1.1.1.4.2 yamt }
1528 1.1.1.1.4.2 yamt
1529 1.1.1.1.4.2 yamt memmove (&info [dest], &info [src], len * sizeof (*info));
1530 1.1.1.1.4.2 yamt
1531 1.1.1.1.4.2 yamt dest += len;
1532 1.1.1.1.4.2 yamt }
1533 1.1.1.1.4.2 yamt
1534 1.1.1.1.4.2 yamt count = dest;
1535 1.1.1.1.4.2 yamt }
1536 1.1.1.1.4.2 yamt else
1537 1.1.1.1.4.2 yamt {
1538 1.1.1.1.4.2 yamt /* When we get here, either there is no duplicate at all or
1539 1.1.1.1.4.2 yamt the only duplicate is the last element. */
1540 1.1.1.1.4.2 yamt if (dest < count)
1541 1.1.1.1.4.2 yamt {
1542 1.1.1.1.4.2 yamt /* If the last element is a duplicate, make sure that the
1543 1.1.1.1.4.2 yamt kept one has a valid got_offset. We also update count. */
1544 1.1.1.1.4.2 yamt if (got_offset != (bfd_vma) -1)
1545 1.1.1.1.4.2 yamt info [dest - 1].got_offset = got_offset;
1546 1.1.1.1.4.2 yamt count = dest;
1547 1.1.1.1.4.2 yamt }
1548 1.1.1.1.4.2 yamt }
1549 1.1.1.1.4.2 yamt
1550 1.1.1.1.4.2 yamt return count;
1551 1.1.1.1.4.2 yamt }
1552 1.1.1.1.4.2 yamt
1553 1.1.1.1.4.2 yamt /* Find and/or create a descriptor for dynamic symbol info. This will
1554 1.1.1.1.4.2 yamt vary based on global or local symbol, and the addend to the reloc.
1555 1.1.1.1.4.2 yamt
1556 1.1.1.1.4.2 yamt We don't sort when inserting. Also, we sort and eliminate
1557 1.1.1.1.4.2 yamt duplicates if there is an unsorted section. Typically, this will
1558 1.1.1.1.4.2 yamt only happen once, because we do all insertions before lookups. We
1559 1.1.1.1.4.2 yamt then use bsearch to do a lookup. This also allows lookups to be
1560 1.1.1.1.4.2 yamt fast. So we have fast insertion (O(log N) due to duplicate check),
1561 1.1.1.1.4.2 yamt fast lookup (O(log N)) and one sort (O(N log N) expected time).
1562 1.1.1.1.4.2 yamt Previously, all lookups were O(N) because of the use of the linked
1563 1.1.1.1.4.2 yamt list and also all insertions were O(N) because of the check for
1564 1.1.1.1.4.2 yamt duplicates. There are some complications here because the array
1565 1.1.1.1.4.2 yamt size grows occasionally, which may add an O(N) factor, but this
1566 1.1.1.1.4.2 yamt should be rare. Also, we free the excess array allocation, which
1567 1.1.1.1.4.2 yamt requires a copy which is O(N), but this only happens once. */
1568 1.1.1.1.4.2 yamt
1569 1.1.1.1.4.2 yamt static struct elf64_ia64_dyn_sym_info *
1570 1.1.1.1.4.2 yamt get_dyn_sym_info (struct elf64_ia64_link_hash_table *ia64_info,
1571 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h, bfd *abfd,
1572 1.1.1.1.4.2 yamt const Elf_Internal_Rela *rel, bfd_boolean create)
1573 1.1.1.1.4.2 yamt {
1574 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info **info_p, *info, *dyn_i, key;
1575 1.1.1.1.4.2 yamt unsigned int *count_p, *sorted_count_p, *size_p;
1576 1.1.1.1.4.2 yamt unsigned int count, sorted_count, size;
1577 1.1.1.1.4.2 yamt bfd_vma addend = rel ? rel->r_addend : 0;
1578 1.1.1.1.4.2 yamt bfd_size_type amt;
1579 1.1.1.1.4.2 yamt
1580 1.1.1.1.4.2 yamt if (h)
1581 1.1.1.1.4.2 yamt {
1582 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *global_h;
1583 1.1.1.1.4.2 yamt
1584 1.1.1.1.4.2 yamt global_h = (struct elf64_ia64_link_hash_entry *) h;
1585 1.1.1.1.4.2 yamt info_p = &global_h->info;
1586 1.1.1.1.4.2 yamt count_p = &global_h->count;
1587 1.1.1.1.4.2 yamt sorted_count_p = &global_h->sorted_count;
1588 1.1.1.1.4.2 yamt size_p = &global_h->size;
1589 1.1.1.1.4.2 yamt }
1590 1.1.1.1.4.2 yamt else
1591 1.1.1.1.4.2 yamt {
1592 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *loc_h;
1593 1.1.1.1.4.2 yamt
1594 1.1.1.1.4.2 yamt loc_h = get_local_sym_hash (ia64_info, abfd, rel, create);
1595 1.1.1.1.4.2 yamt if (!loc_h)
1596 1.1.1.1.4.2 yamt {
1597 1.1.1.1.4.2 yamt BFD_ASSERT (!create);
1598 1.1.1.1.4.2 yamt return NULL;
1599 1.1.1.1.4.2 yamt }
1600 1.1.1.1.4.2 yamt
1601 1.1.1.1.4.2 yamt info_p = &loc_h->info;
1602 1.1.1.1.4.2 yamt count_p = &loc_h->count;
1603 1.1.1.1.4.2 yamt sorted_count_p = &loc_h->sorted_count;
1604 1.1.1.1.4.2 yamt size_p = &loc_h->size;
1605 1.1.1.1.4.2 yamt }
1606 1.1.1.1.4.2 yamt
1607 1.1.1.1.4.2 yamt count = *count_p;
1608 1.1.1.1.4.2 yamt sorted_count = *sorted_count_p;
1609 1.1.1.1.4.2 yamt size = *size_p;
1610 1.1.1.1.4.2 yamt info = *info_p;
1611 1.1.1.1.4.2 yamt if (create)
1612 1.1.1.1.4.2 yamt {
1613 1.1.1.1.4.2 yamt /* When we create the array, we don't check for duplicates,
1614 1.1.1.1.4.2 yamt except in the previously sorted section if one exists, and
1615 1.1.1.1.4.2 yamt against the last inserted entry. This allows insertions to
1616 1.1.1.1.4.2 yamt be fast. */
1617 1.1.1.1.4.2 yamt if (info)
1618 1.1.1.1.4.2 yamt {
1619 1.1.1.1.4.2 yamt if (sorted_count)
1620 1.1.1.1.4.2 yamt {
1621 1.1.1.1.4.2 yamt /* Try bsearch first on the sorted section. */
1622 1.1.1.1.4.2 yamt key.addend = addend;
1623 1.1.1.1.4.2 yamt dyn_i = bsearch (&key, info, sorted_count,
1624 1.1.1.1.4.2 yamt sizeof (*info), addend_compare);
1625 1.1.1.1.4.2 yamt
1626 1.1.1.1.4.2 yamt if (dyn_i)
1627 1.1.1.1.4.2 yamt {
1628 1.1.1.1.4.2 yamt return dyn_i;
1629 1.1.1.1.4.2 yamt }
1630 1.1.1.1.4.2 yamt }
1631 1.1.1.1.4.2 yamt
1632 1.1.1.1.4.2 yamt /* Do a quick check for the last inserted entry. */
1633 1.1.1.1.4.2 yamt dyn_i = info + count - 1;
1634 1.1.1.1.4.2 yamt if (dyn_i->addend == addend)
1635 1.1.1.1.4.2 yamt {
1636 1.1.1.1.4.2 yamt return dyn_i;
1637 1.1.1.1.4.2 yamt }
1638 1.1.1.1.4.2 yamt }
1639 1.1.1.1.4.2 yamt
1640 1.1.1.1.4.2 yamt if (size == 0)
1641 1.1.1.1.4.2 yamt {
1642 1.1.1.1.4.2 yamt /* It is the very first element. We create the array of size
1643 1.1.1.1.4.2 yamt 1. */
1644 1.1.1.1.4.2 yamt size = 1;
1645 1.1.1.1.4.2 yamt amt = size * sizeof (*info);
1646 1.1.1.1.4.2 yamt info = bfd_malloc (amt);
1647 1.1.1.1.4.2 yamt }
1648 1.1.1.1.4.2 yamt else if (size <= count)
1649 1.1.1.1.4.2 yamt {
1650 1.1.1.1.4.2 yamt /* We double the array size every time when we reach the
1651 1.1.1.1.4.2 yamt size limit. */
1652 1.1.1.1.4.2 yamt size += size;
1653 1.1.1.1.4.2 yamt amt = size * sizeof (*info);
1654 1.1.1.1.4.2 yamt info = bfd_realloc (info, amt);
1655 1.1.1.1.4.2 yamt }
1656 1.1.1.1.4.2 yamt else
1657 1.1.1.1.4.2 yamt goto has_space;
1658 1.1.1.1.4.2 yamt
1659 1.1.1.1.4.2 yamt if (info == NULL)
1660 1.1.1.1.4.2 yamt return NULL;
1661 1.1.1.1.4.2 yamt *size_p = size;
1662 1.1.1.1.4.2 yamt *info_p = info;
1663 1.1.1.1.4.2 yamt
1664 1.1.1.1.4.2 yamt has_space:
1665 1.1.1.1.4.2 yamt /* Append the new one to the array. */
1666 1.1.1.1.4.2 yamt dyn_i = info + count;
1667 1.1.1.1.4.2 yamt memset (dyn_i, 0, sizeof (*dyn_i));
1668 1.1.1.1.4.2 yamt dyn_i->got_offset = (bfd_vma) -1;
1669 1.1.1.1.4.2 yamt dyn_i->addend = addend;
1670 1.1.1.1.4.2 yamt
1671 1.1.1.1.4.2 yamt /* We increment count only since the new ones are unsorted and
1672 1.1.1.1.4.2 yamt may have duplicate. */
1673 1.1.1.1.4.2 yamt (*count_p)++;
1674 1.1.1.1.4.2 yamt }
1675 1.1.1.1.4.2 yamt else
1676 1.1.1.1.4.2 yamt {
1677 1.1.1.1.4.2 yamt /* It is a lookup without insertion. Sort array if part of the
1678 1.1.1.1.4.2 yamt array isn't sorted. */
1679 1.1.1.1.4.2 yamt if (count != sorted_count)
1680 1.1.1.1.4.2 yamt {
1681 1.1.1.1.4.2 yamt count = sort_dyn_sym_info (info, count);
1682 1.1.1.1.4.2 yamt *count_p = count;
1683 1.1.1.1.4.2 yamt *sorted_count_p = count;
1684 1.1.1.1.4.2 yamt }
1685 1.1.1.1.4.2 yamt
1686 1.1.1.1.4.2 yamt /* Free unused memory. */
1687 1.1.1.1.4.2 yamt if (size != count)
1688 1.1.1.1.4.2 yamt {
1689 1.1.1.1.4.2 yamt amt = count * sizeof (*info);
1690 1.1.1.1.4.2 yamt info = bfd_malloc (amt);
1691 1.1.1.1.4.2 yamt if (info != NULL)
1692 1.1.1.1.4.2 yamt {
1693 1.1.1.1.4.2 yamt memcpy (info, *info_p, amt);
1694 1.1.1.1.4.2 yamt free (*info_p);
1695 1.1.1.1.4.2 yamt *size_p = count;
1696 1.1.1.1.4.2 yamt *info_p = info;
1697 1.1.1.1.4.2 yamt }
1698 1.1.1.1.4.2 yamt }
1699 1.1.1.1.4.2 yamt
1700 1.1.1.1.4.2 yamt key.addend = addend;
1701 1.1.1.1.4.2 yamt dyn_i = bsearch (&key, info, count,
1702 1.1.1.1.4.2 yamt sizeof (*info), addend_compare);
1703 1.1.1.1.4.2 yamt }
1704 1.1.1.1.4.2 yamt
1705 1.1.1.1.4.2 yamt return dyn_i;
1706 1.1.1.1.4.2 yamt }
1707 1.1.1.1.4.2 yamt
1708 1.1.1.1.4.2 yamt static asection *
1709 1.1.1.1.4.2 yamt get_got (bfd *abfd, struct elf64_ia64_link_hash_table *ia64_info)
1710 1.1.1.1.4.2 yamt {
1711 1.1.1.1.4.2 yamt asection *got;
1712 1.1.1.1.4.2 yamt bfd *dynobj;
1713 1.1.1.1.4.2 yamt
1714 1.1.1.1.4.2 yamt got = ia64_info->root.sgot;
1715 1.1.1.1.4.2 yamt if (!got)
1716 1.1.1.1.4.2 yamt {
1717 1.1.1.1.4.2 yamt flagword flags;
1718 1.1.1.1.4.2 yamt
1719 1.1.1.1.4.2 yamt dynobj = ia64_info->root.dynobj;
1720 1.1.1.1.4.2 yamt if (!dynobj)
1721 1.1.1.1.4.2 yamt ia64_info->root.dynobj = dynobj = abfd;
1722 1.1.1.1.4.2 yamt
1723 1.1.1.1.4.2 yamt /* The .got section is always aligned at 8 bytes. */
1724 1.1.1.1.4.2 yamt flags = get_elf_backend_data (dynobj)->dynamic_sec_flags;
1725 1.1.1.1.4.2 yamt got = bfd_make_section_anyway_with_flags (dynobj, ".got",
1726 1.1.1.1.4.2 yamt flags | SEC_SMALL_DATA);
1727 1.1.1.1.4.2 yamt if (got == NULL
1728 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (dynobj, got, 3))
1729 1.1.1.1.4.2 yamt return NULL;
1730 1.1.1.1.4.2 yamt ia64_info->root.sgot = got;
1731 1.1.1.1.4.2 yamt }
1732 1.1.1.1.4.2 yamt
1733 1.1.1.1.4.2 yamt return got;
1734 1.1.1.1.4.2 yamt }
1735 1.1.1.1.4.2 yamt
1736 1.1.1.1.4.2 yamt /* Create function descriptor section (.opd). This section is called .opd
1737 1.1.1.1.4.2 yamt because it contains "official procedure descriptors". The "official"
1738 1.1.1.1.4.2 yamt refers to the fact that these descriptors are used when taking the address
1739 1.1.1.1.4.2 yamt of a procedure, thus ensuring a unique address for each procedure. */
1740 1.1.1.1.4.2 yamt
1741 1.1.1.1.4.2 yamt static asection *
1742 1.1.1.1.4.2 yamt get_fptr (bfd *abfd, struct bfd_link_info *info,
1743 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info)
1744 1.1.1.1.4.2 yamt {
1745 1.1.1.1.4.2 yamt asection *fptr;
1746 1.1.1.1.4.2 yamt bfd *dynobj;
1747 1.1.1.1.4.2 yamt
1748 1.1.1.1.4.2 yamt fptr = ia64_info->fptr_sec;
1749 1.1.1.1.4.2 yamt if (!fptr)
1750 1.1.1.1.4.2 yamt {
1751 1.1.1.1.4.2 yamt dynobj = ia64_info->root.dynobj;
1752 1.1.1.1.4.2 yamt if (!dynobj)
1753 1.1.1.1.4.2 yamt ia64_info->root.dynobj = dynobj = abfd;
1754 1.1.1.1.4.2 yamt
1755 1.1.1.1.4.2 yamt fptr = bfd_make_section_anyway_with_flags (dynobj, ".opd",
1756 1.1.1.1.4.2 yamt (SEC_ALLOC
1757 1.1.1.1.4.2 yamt | SEC_LOAD
1758 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1759 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1760 1.1.1.1.4.2 yamt | (info->pie ? 0
1761 1.1.1.1.4.2 yamt : SEC_READONLY)
1762 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
1763 1.1.1.1.4.2 yamt if (!fptr
1764 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (dynobj, fptr, 4))
1765 1.1.1.1.4.2 yamt {
1766 1.1.1.1.4.2 yamt BFD_ASSERT (0);
1767 1.1.1.1.4.2 yamt return NULL;
1768 1.1.1.1.4.2 yamt }
1769 1.1.1.1.4.2 yamt
1770 1.1.1.1.4.2 yamt ia64_info->fptr_sec = fptr;
1771 1.1.1.1.4.2 yamt
1772 1.1.1.1.4.2 yamt if (info->pie)
1773 1.1.1.1.4.2 yamt {
1774 1.1.1.1.4.2 yamt asection *fptr_rel;
1775 1.1.1.1.4.2 yamt fptr_rel = bfd_make_section_anyway_with_flags (dynobj, ".rela.opd",
1776 1.1.1.1.4.2 yamt (SEC_ALLOC | SEC_LOAD
1777 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1778 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1779 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED
1780 1.1.1.1.4.2 yamt | SEC_READONLY));
1781 1.1.1.1.4.2 yamt if (fptr_rel == NULL
1782 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (dynobj, fptr_rel, 3))
1783 1.1.1.1.4.2 yamt {
1784 1.1.1.1.4.2 yamt BFD_ASSERT (0);
1785 1.1.1.1.4.2 yamt return NULL;
1786 1.1.1.1.4.2 yamt }
1787 1.1.1.1.4.2 yamt
1788 1.1.1.1.4.2 yamt ia64_info->rel_fptr_sec = fptr_rel;
1789 1.1.1.1.4.2 yamt }
1790 1.1.1.1.4.2 yamt }
1791 1.1.1.1.4.2 yamt
1792 1.1.1.1.4.2 yamt return fptr;
1793 1.1.1.1.4.2 yamt }
1794 1.1.1.1.4.2 yamt
1795 1.1.1.1.4.2 yamt static asection *
1796 1.1.1.1.4.2 yamt get_pltoff (bfd *abfd, struct elf64_ia64_link_hash_table *ia64_info)
1797 1.1.1.1.4.2 yamt {
1798 1.1.1.1.4.2 yamt asection *pltoff;
1799 1.1.1.1.4.2 yamt bfd *dynobj;
1800 1.1.1.1.4.2 yamt
1801 1.1.1.1.4.2 yamt pltoff = ia64_info->pltoff_sec;
1802 1.1.1.1.4.2 yamt if (!pltoff)
1803 1.1.1.1.4.2 yamt {
1804 1.1.1.1.4.2 yamt dynobj = ia64_info->root.dynobj;
1805 1.1.1.1.4.2 yamt if (!dynobj)
1806 1.1.1.1.4.2 yamt ia64_info->root.dynobj = dynobj = abfd;
1807 1.1.1.1.4.2 yamt
1808 1.1.1.1.4.2 yamt pltoff = bfd_make_section_anyway_with_flags (dynobj,
1809 1.1.1.1.4.2 yamt ELF_STRING_ia64_pltoff,
1810 1.1.1.1.4.2 yamt (SEC_ALLOC
1811 1.1.1.1.4.2 yamt | SEC_LOAD
1812 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1813 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1814 1.1.1.1.4.2 yamt | SEC_SMALL_DATA
1815 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED));
1816 1.1.1.1.4.2 yamt if (!pltoff
1817 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (dynobj, pltoff, 4))
1818 1.1.1.1.4.2 yamt {
1819 1.1.1.1.4.2 yamt BFD_ASSERT (0);
1820 1.1.1.1.4.2 yamt return NULL;
1821 1.1.1.1.4.2 yamt }
1822 1.1.1.1.4.2 yamt
1823 1.1.1.1.4.2 yamt ia64_info->pltoff_sec = pltoff;
1824 1.1.1.1.4.2 yamt }
1825 1.1.1.1.4.2 yamt
1826 1.1.1.1.4.2 yamt return pltoff;
1827 1.1.1.1.4.2 yamt }
1828 1.1.1.1.4.2 yamt
1829 1.1.1.1.4.2 yamt static asection *
1830 1.1.1.1.4.2 yamt get_reloc_section (bfd *abfd,
1831 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info,
1832 1.1.1.1.4.2 yamt asection *sec, bfd_boolean create)
1833 1.1.1.1.4.2 yamt {
1834 1.1.1.1.4.2 yamt const char *srel_name;
1835 1.1.1.1.4.2 yamt asection *srel;
1836 1.1.1.1.4.2 yamt bfd *dynobj;
1837 1.1.1.1.4.2 yamt
1838 1.1.1.1.4.2 yamt srel_name = (bfd_elf_string_from_elf_section
1839 1.1.1.1.4.2 yamt (abfd, elf_elfheader(abfd)->e_shstrndx,
1840 1.1.1.1.4.2 yamt _bfd_elf_single_rel_hdr (sec)->sh_name));
1841 1.1.1.1.4.2 yamt if (srel_name == NULL)
1842 1.1.1.1.4.2 yamt return NULL;
1843 1.1.1.1.4.2 yamt
1844 1.1.1.1.4.2 yamt BFD_ASSERT ((CONST_STRNEQ (srel_name, ".rela")
1845 1.1.1.1.4.2 yamt && strcmp (bfd_get_section_name (abfd, sec),
1846 1.1.1.1.4.2 yamt srel_name+5) == 0)
1847 1.1.1.1.4.2 yamt || (CONST_STRNEQ (srel_name, ".rel")
1848 1.1.1.1.4.2 yamt && strcmp (bfd_get_section_name (abfd, sec),
1849 1.1.1.1.4.2 yamt srel_name+4) == 0));
1850 1.1.1.1.4.2 yamt
1851 1.1.1.1.4.2 yamt dynobj = ia64_info->root.dynobj;
1852 1.1.1.1.4.2 yamt if (!dynobj)
1853 1.1.1.1.4.2 yamt ia64_info->root.dynobj = dynobj = abfd;
1854 1.1.1.1.4.2 yamt
1855 1.1.1.1.4.2 yamt srel = bfd_get_linker_section (dynobj, srel_name);
1856 1.1.1.1.4.2 yamt if (srel == NULL && create)
1857 1.1.1.1.4.2 yamt {
1858 1.1.1.1.4.2 yamt srel = bfd_make_section_anyway_with_flags (dynobj, srel_name,
1859 1.1.1.1.4.2 yamt (SEC_ALLOC | SEC_LOAD
1860 1.1.1.1.4.2 yamt | SEC_HAS_CONTENTS
1861 1.1.1.1.4.2 yamt | SEC_IN_MEMORY
1862 1.1.1.1.4.2 yamt | SEC_LINKER_CREATED
1863 1.1.1.1.4.2 yamt | SEC_READONLY));
1864 1.1.1.1.4.2 yamt if (srel == NULL
1865 1.1.1.1.4.2 yamt || !bfd_set_section_alignment (dynobj, srel, 3))
1866 1.1.1.1.4.2 yamt return NULL;
1867 1.1.1.1.4.2 yamt }
1868 1.1.1.1.4.2 yamt
1869 1.1.1.1.4.2 yamt return srel;
1870 1.1.1.1.4.2 yamt }
1871 1.1.1.1.4.2 yamt
1872 1.1.1.1.4.2 yamt static bfd_boolean
1873 1.1.1.1.4.2 yamt count_dyn_reloc (bfd *abfd, struct elf64_ia64_dyn_sym_info *dyn_i,
1874 1.1.1.1.4.2 yamt asection *srel, int type)
1875 1.1.1.1.4.2 yamt {
1876 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_reloc_entry *rent;
1877 1.1.1.1.4.2 yamt
1878 1.1.1.1.4.2 yamt for (rent = dyn_i->reloc_entries; rent; rent = rent->next)
1879 1.1.1.1.4.2 yamt if (rent->srel == srel && rent->type == type)
1880 1.1.1.1.4.2 yamt break;
1881 1.1.1.1.4.2 yamt
1882 1.1.1.1.4.2 yamt if (!rent)
1883 1.1.1.1.4.2 yamt {
1884 1.1.1.1.4.2 yamt rent = ((struct elf64_ia64_dyn_reloc_entry *)
1885 1.1.1.1.4.2 yamt bfd_alloc (abfd, (bfd_size_type) sizeof (*rent)));
1886 1.1.1.1.4.2 yamt if (!rent)
1887 1.1.1.1.4.2 yamt return FALSE;
1888 1.1.1.1.4.2 yamt
1889 1.1.1.1.4.2 yamt rent->next = dyn_i->reloc_entries;
1890 1.1.1.1.4.2 yamt rent->srel = srel;
1891 1.1.1.1.4.2 yamt rent->type = type;
1892 1.1.1.1.4.2 yamt rent->count = 0;
1893 1.1.1.1.4.2 yamt dyn_i->reloc_entries = rent;
1894 1.1.1.1.4.2 yamt }
1895 1.1.1.1.4.2 yamt rent->count++;
1896 1.1.1.1.4.2 yamt
1897 1.1.1.1.4.2 yamt return TRUE;
1898 1.1.1.1.4.2 yamt }
1899 1.1.1.1.4.2 yamt
1900 1.1.1.1.4.2 yamt static bfd_boolean
1901 1.1.1.1.4.2 yamt elf64_ia64_check_relocs (bfd *abfd, struct bfd_link_info *info,
1902 1.1.1.1.4.2 yamt asection *sec,
1903 1.1.1.1.4.2 yamt const Elf_Internal_Rela *relocs)
1904 1.1.1.1.4.2 yamt {
1905 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
1906 1.1.1.1.4.2 yamt const Elf_Internal_Rela *relend;
1907 1.1.1.1.4.2 yamt Elf_Internal_Shdr *symtab_hdr;
1908 1.1.1.1.4.2 yamt const Elf_Internal_Rela *rel;
1909 1.1.1.1.4.2 yamt asection *got, *fptr, *srel, *pltoff;
1910 1.1.1.1.4.2 yamt enum {
1911 1.1.1.1.4.2 yamt NEED_GOT = 1,
1912 1.1.1.1.4.2 yamt NEED_GOTX = 2,
1913 1.1.1.1.4.2 yamt NEED_FPTR = 4,
1914 1.1.1.1.4.2 yamt NEED_PLTOFF = 8,
1915 1.1.1.1.4.2 yamt NEED_MIN_PLT = 16,
1916 1.1.1.1.4.2 yamt NEED_FULL_PLT = 32,
1917 1.1.1.1.4.2 yamt NEED_DYNREL = 64,
1918 1.1.1.1.4.2 yamt NEED_LTOFF_FPTR = 128
1919 1.1.1.1.4.2 yamt };
1920 1.1.1.1.4.2 yamt int need_entry;
1921 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h;
1922 1.1.1.1.4.2 yamt unsigned long r_symndx;
1923 1.1.1.1.4.2 yamt bfd_boolean maybe_dynamic;
1924 1.1.1.1.4.2 yamt
1925 1.1.1.1.4.2 yamt if (info->relocatable)
1926 1.1.1.1.4.2 yamt return TRUE;
1927 1.1.1.1.4.2 yamt
1928 1.1.1.1.4.2 yamt symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
1929 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
1930 1.1.1.1.4.2 yamt if (ia64_info == NULL)
1931 1.1.1.1.4.2 yamt return FALSE;
1932 1.1.1.1.4.2 yamt
1933 1.1.1.1.4.2 yamt got = fptr = srel = pltoff = NULL;
1934 1.1.1.1.4.2 yamt
1935 1.1.1.1.4.2 yamt relend = relocs + sec->reloc_count;
1936 1.1.1.1.4.2 yamt
1937 1.1.1.1.4.2 yamt /* We scan relocations first to create dynamic relocation arrays. We
1938 1.1.1.1.4.2 yamt modified get_dyn_sym_info to allow fast insertion and support fast
1939 1.1.1.1.4.2 yamt lookup in the next loop. */
1940 1.1.1.1.4.2 yamt for (rel = relocs; rel < relend; ++rel)
1941 1.1.1.1.4.2 yamt {
1942 1.1.1.1.4.2 yamt r_symndx = ELF64_R_SYM (rel->r_info);
1943 1.1.1.1.4.2 yamt if (r_symndx >= symtab_hdr->sh_info)
1944 1.1.1.1.4.2 yamt {
1945 1.1.1.1.4.2 yamt long indx = r_symndx - symtab_hdr->sh_info;
1946 1.1.1.1.4.2 yamt h = elf_sym_hashes (abfd)[indx];
1947 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
1948 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
1949 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
1950 1.1.1.1.4.2 yamt }
1951 1.1.1.1.4.2 yamt else
1952 1.1.1.1.4.2 yamt h = NULL;
1953 1.1.1.1.4.2 yamt
1954 1.1.1.1.4.2 yamt /* We can only get preliminary data on whether a symbol is
1955 1.1.1.1.4.2 yamt locally or externally defined, as not all of the input files
1956 1.1.1.1.4.2 yamt have yet been processed. Do something with what we know, as
1957 1.1.1.1.4.2 yamt this may help reduce memory usage and processing time later. */
1958 1.1.1.1.4.2 yamt maybe_dynamic = (h && ((!info->executable
1959 1.1.1.1.4.2 yamt && (!SYMBOLIC_BIND (info, h)
1960 1.1.1.1.4.2 yamt || info->unresolved_syms_in_shared_libs == RM_IGNORE))
1961 1.1.1.1.4.2 yamt || !h->def_regular
1962 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_defweak));
1963 1.1.1.1.4.2 yamt
1964 1.1.1.1.4.2 yamt need_entry = 0;
1965 1.1.1.1.4.2 yamt switch (ELF64_R_TYPE (rel->r_info))
1966 1.1.1.1.4.2 yamt {
1967 1.1.1.1.4.2 yamt case R_IA64_TPREL64MSB:
1968 1.1.1.1.4.2 yamt case R_IA64_TPREL64LSB:
1969 1.1.1.1.4.2 yamt case R_IA64_LTOFF_TPREL22:
1970 1.1.1.1.4.2 yamt case R_IA64_DTPREL32MSB:
1971 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
1972 1.1.1.1.4.2 yamt case R_IA64_DTPREL64MSB:
1973 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
1974 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPREL22:
1975 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64MSB:
1976 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64LSB:
1977 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPMOD22:
1978 1.1.1.1.4.2 yamt abort ();
1979 1.1.1.1.4.2 yamt break;
1980 1.1.1.1.4.2 yamt
1981 1.1.1.1.4.2 yamt case R_IA64_IPLTMSB:
1982 1.1.1.1.4.2 yamt case R_IA64_IPLTLSB:
1983 1.1.1.1.4.2 yamt break;
1984 1.1.1.1.4.2 yamt
1985 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR22:
1986 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64I:
1987 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32MSB:
1988 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32LSB:
1989 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64MSB:
1990 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64LSB:
1991 1.1.1.1.4.2 yamt need_entry = NEED_FPTR | NEED_GOT | NEED_LTOFF_FPTR;
1992 1.1.1.1.4.2 yamt break;
1993 1.1.1.1.4.2 yamt
1994 1.1.1.1.4.2 yamt case R_IA64_FPTR64I:
1995 1.1.1.1.4.2 yamt case R_IA64_FPTR32MSB:
1996 1.1.1.1.4.2 yamt case R_IA64_FPTR32LSB:
1997 1.1.1.1.4.2 yamt case R_IA64_FPTR64MSB:
1998 1.1.1.1.4.2 yamt case R_IA64_FPTR64LSB:
1999 1.1.1.1.4.2 yamt if (info->shared || h)
2000 1.1.1.1.4.2 yamt need_entry = NEED_FPTR | NEED_DYNREL;
2001 1.1.1.1.4.2 yamt else
2002 1.1.1.1.4.2 yamt need_entry = NEED_FPTR;
2003 1.1.1.1.4.2 yamt break;
2004 1.1.1.1.4.2 yamt
2005 1.1.1.1.4.2 yamt case R_IA64_LTOFF22:
2006 1.1.1.1.4.2 yamt case R_IA64_LTOFF64I:
2007 1.1.1.1.4.2 yamt need_entry = NEED_GOT;
2008 1.1.1.1.4.2 yamt break;
2009 1.1.1.1.4.2 yamt
2010 1.1.1.1.4.2 yamt case R_IA64_LTOFF22X:
2011 1.1.1.1.4.2 yamt need_entry = NEED_GOTX;
2012 1.1.1.1.4.2 yamt break;
2013 1.1.1.1.4.2 yamt
2014 1.1.1.1.4.2 yamt case R_IA64_PLTOFF22:
2015 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64I:
2016 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64MSB:
2017 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64LSB:
2018 1.1.1.1.4.2 yamt need_entry = NEED_PLTOFF;
2019 1.1.1.1.4.2 yamt if (h)
2020 1.1.1.1.4.2 yamt {
2021 1.1.1.1.4.2 yamt if (maybe_dynamic)
2022 1.1.1.1.4.2 yamt need_entry |= NEED_MIN_PLT;
2023 1.1.1.1.4.2 yamt }
2024 1.1.1.1.4.2 yamt else
2025 1.1.1.1.4.2 yamt {
2026 1.1.1.1.4.2 yamt (*info->callbacks->warning)
2027 1.1.1.1.4.2 yamt (info, _("@pltoff reloc against local symbol"), 0,
2028 1.1.1.1.4.2 yamt abfd, 0, (bfd_vma) 0);
2029 1.1.1.1.4.2 yamt }
2030 1.1.1.1.4.2 yamt break;
2031 1.1.1.1.4.2 yamt
2032 1.1.1.1.4.2 yamt case R_IA64_PCREL21B:
2033 1.1.1.1.4.2 yamt case R_IA64_PCREL60B:
2034 1.1.1.1.4.2 yamt /* Depending on where this symbol is defined, we may or may not
2035 1.1.1.1.4.2 yamt need a full plt entry. Only skip if we know we'll not need
2036 1.1.1.1.4.2 yamt the entry -- static or symbolic, and the symbol definition
2037 1.1.1.1.4.2 yamt has already been seen. */
2038 1.1.1.1.4.2 yamt if (maybe_dynamic && rel->r_addend == 0)
2039 1.1.1.1.4.2 yamt need_entry = NEED_FULL_PLT;
2040 1.1.1.1.4.2 yamt break;
2041 1.1.1.1.4.2 yamt
2042 1.1.1.1.4.2 yamt case R_IA64_IMM14:
2043 1.1.1.1.4.2 yamt case R_IA64_IMM22:
2044 1.1.1.1.4.2 yamt case R_IA64_IMM64:
2045 1.1.1.1.4.2 yamt case R_IA64_DIR32MSB:
2046 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
2047 1.1.1.1.4.2 yamt case R_IA64_DIR64MSB:
2048 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
2049 1.1.1.1.4.2 yamt /* Shared objects will always need at least a REL relocation. */
2050 1.1.1.1.4.2 yamt if (info->shared || maybe_dynamic)
2051 1.1.1.1.4.2 yamt need_entry = NEED_DYNREL;
2052 1.1.1.1.4.2 yamt break;
2053 1.1.1.1.4.2 yamt
2054 1.1.1.1.4.2 yamt case R_IA64_PCREL22:
2055 1.1.1.1.4.2 yamt case R_IA64_PCREL64I:
2056 1.1.1.1.4.2 yamt case R_IA64_PCREL32MSB:
2057 1.1.1.1.4.2 yamt case R_IA64_PCREL32LSB:
2058 1.1.1.1.4.2 yamt case R_IA64_PCREL64MSB:
2059 1.1.1.1.4.2 yamt case R_IA64_PCREL64LSB:
2060 1.1.1.1.4.2 yamt if (maybe_dynamic)
2061 1.1.1.1.4.2 yamt need_entry = NEED_DYNREL;
2062 1.1.1.1.4.2 yamt break;
2063 1.1.1.1.4.2 yamt }
2064 1.1.1.1.4.2 yamt
2065 1.1.1.1.4.2 yamt if (!need_entry)
2066 1.1.1.1.4.2 yamt continue;
2067 1.1.1.1.4.2 yamt
2068 1.1.1.1.4.2 yamt if ((need_entry & NEED_FPTR) != 0
2069 1.1.1.1.4.2 yamt && rel->r_addend)
2070 1.1.1.1.4.2 yamt {
2071 1.1.1.1.4.2 yamt (*info->callbacks->warning)
2072 1.1.1.1.4.2 yamt (info, _("non-zero addend in @fptr reloc"), 0,
2073 1.1.1.1.4.2 yamt abfd, 0, (bfd_vma) 0);
2074 1.1.1.1.4.2 yamt }
2075 1.1.1.1.4.2 yamt
2076 1.1.1.1.4.2 yamt if (get_dyn_sym_info (ia64_info, h, abfd, rel, TRUE) == NULL)
2077 1.1.1.1.4.2 yamt return FALSE;
2078 1.1.1.1.4.2 yamt }
2079 1.1.1.1.4.2 yamt
2080 1.1.1.1.4.2 yamt /* Now, we only do lookup without insertion, which is very fast
2081 1.1.1.1.4.2 yamt with the modified get_dyn_sym_info. */
2082 1.1.1.1.4.2 yamt for (rel = relocs; rel < relend; ++rel)
2083 1.1.1.1.4.2 yamt {
2084 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
2085 1.1.1.1.4.2 yamt int dynrel_type = R_IA64_NONE;
2086 1.1.1.1.4.2 yamt
2087 1.1.1.1.4.2 yamt r_symndx = ELF64_R_SYM (rel->r_info);
2088 1.1.1.1.4.2 yamt if (r_symndx >= symtab_hdr->sh_info)
2089 1.1.1.1.4.2 yamt {
2090 1.1.1.1.4.2 yamt /* We're dealing with a global symbol -- find its hash entry
2091 1.1.1.1.4.2 yamt and mark it as being referenced. */
2092 1.1.1.1.4.2 yamt long indx = r_symndx - symtab_hdr->sh_info;
2093 1.1.1.1.4.2 yamt h = elf_sym_hashes (abfd)[indx];
2094 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
2095 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
2096 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
2097 1.1.1.1.4.2 yamt
2098 1.1.1.1.4.2 yamt h->ref_regular = 1;
2099 1.1.1.1.4.2 yamt }
2100 1.1.1.1.4.2 yamt else
2101 1.1.1.1.4.2 yamt h = NULL;
2102 1.1.1.1.4.2 yamt
2103 1.1.1.1.4.2 yamt /* We can only get preliminary data on whether a symbol is
2104 1.1.1.1.4.2 yamt locally or externally defined, as not all of the input files
2105 1.1.1.1.4.2 yamt have yet been processed. Do something with what we know, as
2106 1.1.1.1.4.2 yamt this may help reduce memory usage and processing time later. */
2107 1.1.1.1.4.2 yamt maybe_dynamic = (h && ((!info->executable
2108 1.1.1.1.4.2 yamt && (!SYMBOLIC_BIND (info, h)
2109 1.1.1.1.4.2 yamt || info->unresolved_syms_in_shared_libs == RM_IGNORE))
2110 1.1.1.1.4.2 yamt || !h->def_regular
2111 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_defweak));
2112 1.1.1.1.4.2 yamt
2113 1.1.1.1.4.2 yamt need_entry = 0;
2114 1.1.1.1.4.2 yamt switch (ELF64_R_TYPE (rel->r_info))
2115 1.1.1.1.4.2 yamt {
2116 1.1.1.1.4.2 yamt case R_IA64_TPREL64MSB:
2117 1.1.1.1.4.2 yamt case R_IA64_TPREL64LSB:
2118 1.1.1.1.4.2 yamt case R_IA64_LTOFF_TPREL22:
2119 1.1.1.1.4.2 yamt case R_IA64_DTPREL32MSB:
2120 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
2121 1.1.1.1.4.2 yamt case R_IA64_DTPREL64MSB:
2122 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
2123 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPREL22:
2124 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64MSB:
2125 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64LSB:
2126 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPMOD22:
2127 1.1.1.1.4.2 yamt abort ();
2128 1.1.1.1.4.2 yamt break;
2129 1.1.1.1.4.2 yamt
2130 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR22:
2131 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64I:
2132 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32MSB:
2133 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32LSB:
2134 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64MSB:
2135 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64LSB:
2136 1.1.1.1.4.2 yamt need_entry = NEED_FPTR | NEED_GOT | NEED_LTOFF_FPTR;
2137 1.1.1.1.4.2 yamt break;
2138 1.1.1.1.4.2 yamt
2139 1.1.1.1.4.2 yamt case R_IA64_FPTR64I:
2140 1.1.1.1.4.2 yamt case R_IA64_FPTR32MSB:
2141 1.1.1.1.4.2 yamt case R_IA64_FPTR32LSB:
2142 1.1.1.1.4.2 yamt case R_IA64_FPTR64MSB:
2143 1.1.1.1.4.2 yamt case R_IA64_FPTR64LSB:
2144 1.1.1.1.4.2 yamt if (info->shared || h)
2145 1.1.1.1.4.2 yamt need_entry = NEED_FPTR | NEED_DYNREL;
2146 1.1.1.1.4.2 yamt else
2147 1.1.1.1.4.2 yamt need_entry = NEED_FPTR;
2148 1.1.1.1.4.2 yamt dynrel_type = R_IA64_FPTR64LSB;
2149 1.1.1.1.4.2 yamt break;
2150 1.1.1.1.4.2 yamt
2151 1.1.1.1.4.2 yamt case R_IA64_LTOFF22:
2152 1.1.1.1.4.2 yamt case R_IA64_LTOFF64I:
2153 1.1.1.1.4.2 yamt need_entry = NEED_GOT;
2154 1.1.1.1.4.2 yamt break;
2155 1.1.1.1.4.2 yamt
2156 1.1.1.1.4.2 yamt case R_IA64_LTOFF22X:
2157 1.1.1.1.4.2 yamt need_entry = NEED_GOTX;
2158 1.1.1.1.4.2 yamt break;
2159 1.1.1.1.4.2 yamt
2160 1.1.1.1.4.2 yamt case R_IA64_PLTOFF22:
2161 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64I:
2162 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64MSB:
2163 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64LSB:
2164 1.1.1.1.4.2 yamt need_entry = NEED_PLTOFF;
2165 1.1.1.1.4.2 yamt if (h)
2166 1.1.1.1.4.2 yamt {
2167 1.1.1.1.4.2 yamt if (maybe_dynamic)
2168 1.1.1.1.4.2 yamt need_entry |= NEED_MIN_PLT;
2169 1.1.1.1.4.2 yamt }
2170 1.1.1.1.4.2 yamt break;
2171 1.1.1.1.4.2 yamt
2172 1.1.1.1.4.2 yamt case R_IA64_PCREL21B:
2173 1.1.1.1.4.2 yamt case R_IA64_PCREL60B:
2174 1.1.1.1.4.2 yamt /* Depending on where this symbol is defined, we may or may not
2175 1.1.1.1.4.2 yamt need a full plt entry. Only skip if we know we'll not need
2176 1.1.1.1.4.2 yamt the entry -- static or symbolic, and the symbol definition
2177 1.1.1.1.4.2 yamt has already been seen. */
2178 1.1.1.1.4.2 yamt if (maybe_dynamic && rel->r_addend == 0)
2179 1.1.1.1.4.2 yamt need_entry = NEED_FULL_PLT;
2180 1.1.1.1.4.2 yamt break;
2181 1.1.1.1.4.2 yamt
2182 1.1.1.1.4.2 yamt case R_IA64_IMM14:
2183 1.1.1.1.4.2 yamt case R_IA64_IMM22:
2184 1.1.1.1.4.2 yamt case R_IA64_IMM64:
2185 1.1.1.1.4.2 yamt case R_IA64_DIR32MSB:
2186 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
2187 1.1.1.1.4.2 yamt case R_IA64_DIR64MSB:
2188 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
2189 1.1.1.1.4.2 yamt /* Shared objects will always need at least a REL relocation. */
2190 1.1.1.1.4.2 yamt if (info->shared || maybe_dynamic)
2191 1.1.1.1.4.2 yamt need_entry = NEED_DYNREL;
2192 1.1.1.1.4.2 yamt dynrel_type = R_IA64_DIR64LSB;
2193 1.1.1.1.4.2 yamt break;
2194 1.1.1.1.4.2 yamt
2195 1.1.1.1.4.2 yamt case R_IA64_IPLTMSB:
2196 1.1.1.1.4.2 yamt case R_IA64_IPLTLSB:
2197 1.1.1.1.4.2 yamt break;
2198 1.1.1.1.4.2 yamt
2199 1.1.1.1.4.2 yamt case R_IA64_PCREL22:
2200 1.1.1.1.4.2 yamt case R_IA64_PCREL64I:
2201 1.1.1.1.4.2 yamt case R_IA64_PCREL32MSB:
2202 1.1.1.1.4.2 yamt case R_IA64_PCREL32LSB:
2203 1.1.1.1.4.2 yamt case R_IA64_PCREL64MSB:
2204 1.1.1.1.4.2 yamt case R_IA64_PCREL64LSB:
2205 1.1.1.1.4.2 yamt if (maybe_dynamic)
2206 1.1.1.1.4.2 yamt need_entry = NEED_DYNREL;
2207 1.1.1.1.4.2 yamt dynrel_type = R_IA64_PCREL64LSB;
2208 1.1.1.1.4.2 yamt break;
2209 1.1.1.1.4.2 yamt }
2210 1.1.1.1.4.2 yamt
2211 1.1.1.1.4.2 yamt if (!need_entry)
2212 1.1.1.1.4.2 yamt continue;
2213 1.1.1.1.4.2 yamt
2214 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, abfd, rel, FALSE);
2215 1.1.1.1.4.2 yamt
2216 1.1.1.1.4.2 yamt /* Record whether or not this is a local symbol. */
2217 1.1.1.1.4.2 yamt dyn_i->h = h;
2218 1.1.1.1.4.2 yamt
2219 1.1.1.1.4.2 yamt /* Create what's needed. */
2220 1.1.1.1.4.2 yamt if (need_entry & (NEED_GOT | NEED_GOTX))
2221 1.1.1.1.4.2 yamt {
2222 1.1.1.1.4.2 yamt if (!got)
2223 1.1.1.1.4.2 yamt {
2224 1.1.1.1.4.2 yamt got = get_got (abfd, ia64_info);
2225 1.1.1.1.4.2 yamt if (!got)
2226 1.1.1.1.4.2 yamt return FALSE;
2227 1.1.1.1.4.2 yamt }
2228 1.1.1.1.4.2 yamt if (need_entry & NEED_GOT)
2229 1.1.1.1.4.2 yamt dyn_i->want_got = 1;
2230 1.1.1.1.4.2 yamt if (need_entry & NEED_GOTX)
2231 1.1.1.1.4.2 yamt dyn_i->want_gotx = 1;
2232 1.1.1.1.4.2 yamt }
2233 1.1.1.1.4.2 yamt if (need_entry & NEED_FPTR)
2234 1.1.1.1.4.2 yamt {
2235 1.1.1.1.4.2 yamt /* Create the .opd section. */
2236 1.1.1.1.4.2 yamt if (!fptr)
2237 1.1.1.1.4.2 yamt {
2238 1.1.1.1.4.2 yamt fptr = get_fptr (abfd, info, ia64_info);
2239 1.1.1.1.4.2 yamt if (!fptr)
2240 1.1.1.1.4.2 yamt return FALSE;
2241 1.1.1.1.4.2 yamt }
2242 1.1.1.1.4.2 yamt dyn_i->want_fptr = 1;
2243 1.1.1.1.4.2 yamt }
2244 1.1.1.1.4.2 yamt if (need_entry & NEED_LTOFF_FPTR)
2245 1.1.1.1.4.2 yamt dyn_i->want_ltoff_fptr = 1;
2246 1.1.1.1.4.2 yamt if (need_entry & (NEED_MIN_PLT | NEED_FULL_PLT))
2247 1.1.1.1.4.2 yamt {
2248 1.1.1.1.4.2 yamt if (!ia64_info->root.dynobj)
2249 1.1.1.1.4.2 yamt ia64_info->root.dynobj = abfd;
2250 1.1.1.1.4.2 yamt h->needs_plt = 1;
2251 1.1.1.1.4.2 yamt dyn_i->want_plt = 1;
2252 1.1.1.1.4.2 yamt }
2253 1.1.1.1.4.2 yamt if (need_entry & NEED_FULL_PLT)
2254 1.1.1.1.4.2 yamt dyn_i->want_plt2 = 1;
2255 1.1.1.1.4.2 yamt if (need_entry & NEED_PLTOFF)
2256 1.1.1.1.4.2 yamt {
2257 1.1.1.1.4.2 yamt /* This is needed here, in case @pltoff is used in a non-shared
2258 1.1.1.1.4.2 yamt link. */
2259 1.1.1.1.4.2 yamt if (!pltoff)
2260 1.1.1.1.4.2 yamt {
2261 1.1.1.1.4.2 yamt pltoff = get_pltoff (abfd, ia64_info);
2262 1.1.1.1.4.2 yamt if (!pltoff)
2263 1.1.1.1.4.2 yamt return FALSE;
2264 1.1.1.1.4.2 yamt }
2265 1.1.1.1.4.2 yamt
2266 1.1.1.1.4.2 yamt dyn_i->want_pltoff = 1;
2267 1.1.1.1.4.2 yamt }
2268 1.1.1.1.4.2 yamt if ((need_entry & NEED_DYNREL) && (sec->flags & SEC_ALLOC))
2269 1.1.1.1.4.2 yamt {
2270 1.1.1.1.4.2 yamt if (!srel)
2271 1.1.1.1.4.2 yamt {
2272 1.1.1.1.4.2 yamt srel = get_reloc_section (abfd, ia64_info, sec, TRUE);
2273 1.1.1.1.4.2 yamt if (!srel)
2274 1.1.1.1.4.2 yamt return FALSE;
2275 1.1.1.1.4.2 yamt }
2276 1.1.1.1.4.2 yamt if (!count_dyn_reloc (abfd, dyn_i, srel, dynrel_type))
2277 1.1.1.1.4.2 yamt return FALSE;
2278 1.1.1.1.4.2 yamt }
2279 1.1.1.1.4.2 yamt }
2280 1.1.1.1.4.2 yamt
2281 1.1.1.1.4.2 yamt return TRUE;
2282 1.1.1.1.4.2 yamt }
2283 1.1.1.1.4.2 yamt
2284 1.1.1.1.4.2 yamt /* For cleanliness, and potentially faster dynamic loading, allocate
2285 1.1.1.1.4.2 yamt external GOT entries first. */
2286 1.1.1.1.4.2 yamt
2287 1.1.1.1.4.2 yamt static bfd_boolean
2288 1.1.1.1.4.2 yamt allocate_global_data_got (struct elf64_ia64_dyn_sym_info *dyn_i,
2289 1.1.1.1.4.2 yamt void * data)
2290 1.1.1.1.4.2 yamt {
2291 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2292 1.1.1.1.4.2 yamt
2293 1.1.1.1.4.2 yamt if ((dyn_i->want_got || dyn_i->want_gotx)
2294 1.1.1.1.4.2 yamt && ! dyn_i->want_fptr
2295 1.1.1.1.4.2 yamt && elf64_ia64_dynamic_symbol_p (dyn_i->h))
2296 1.1.1.1.4.2 yamt {
2297 1.1.1.1.4.2 yamt /* GOT entry with FPTR is done by allocate_global_fptr_got. */
2298 1.1.1.1.4.2 yamt dyn_i->got_offset = x->ofs;
2299 1.1.1.1.4.2 yamt x->ofs += 8;
2300 1.1.1.1.4.2 yamt }
2301 1.1.1.1.4.2 yamt return TRUE;
2302 1.1.1.1.4.2 yamt }
2303 1.1.1.1.4.2 yamt
2304 1.1.1.1.4.2 yamt /* Next, allocate all the GOT entries used by LTOFF_FPTR relocs. */
2305 1.1.1.1.4.2 yamt
2306 1.1.1.1.4.2 yamt static bfd_boolean
2307 1.1.1.1.4.2 yamt allocate_global_fptr_got (struct elf64_ia64_dyn_sym_info *dyn_i,
2308 1.1.1.1.4.2 yamt void * data)
2309 1.1.1.1.4.2 yamt {
2310 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2311 1.1.1.1.4.2 yamt
2312 1.1.1.1.4.2 yamt if (dyn_i->want_got
2313 1.1.1.1.4.2 yamt && dyn_i->want_fptr
2314 1.1.1.1.4.2 yamt && elf64_ia64_dynamic_symbol_p (dyn_i->h))
2315 1.1.1.1.4.2 yamt {
2316 1.1.1.1.4.2 yamt dyn_i->got_offset = x->ofs;
2317 1.1.1.1.4.2 yamt x->ofs += 8;
2318 1.1.1.1.4.2 yamt }
2319 1.1.1.1.4.2 yamt return TRUE;
2320 1.1.1.1.4.2 yamt }
2321 1.1.1.1.4.2 yamt
2322 1.1.1.1.4.2 yamt /* Lastly, allocate all the GOT entries for local data. */
2323 1.1.1.1.4.2 yamt
2324 1.1.1.1.4.2 yamt static bfd_boolean
2325 1.1.1.1.4.2 yamt allocate_local_got (struct elf64_ia64_dyn_sym_info *dyn_i,
2326 1.1.1.1.4.2 yamt void * data)
2327 1.1.1.1.4.2 yamt {
2328 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *) data;
2329 1.1.1.1.4.2 yamt
2330 1.1.1.1.4.2 yamt if ((dyn_i->want_got || dyn_i->want_gotx)
2331 1.1.1.1.4.2 yamt && !elf64_ia64_dynamic_symbol_p (dyn_i->h))
2332 1.1.1.1.4.2 yamt {
2333 1.1.1.1.4.2 yamt dyn_i->got_offset = x->ofs;
2334 1.1.1.1.4.2 yamt x->ofs += 8;
2335 1.1.1.1.4.2 yamt }
2336 1.1.1.1.4.2 yamt return TRUE;
2337 1.1.1.1.4.2 yamt }
2338 1.1.1.1.4.2 yamt
2339 1.1.1.1.4.2 yamt /* Allocate function descriptors. We can do these for every function
2340 1.1.1.1.4.2 yamt in a main executable that is not exported. */
2341 1.1.1.1.4.2 yamt
2342 1.1.1.1.4.2 yamt static bfd_boolean
2343 1.1.1.1.4.2 yamt allocate_fptr (struct elf64_ia64_dyn_sym_info *dyn_i, void * data)
2344 1.1.1.1.4.2 yamt {
2345 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *) data;
2346 1.1.1.1.4.2 yamt
2347 1.1.1.1.4.2 yamt if (dyn_i->want_fptr)
2348 1.1.1.1.4.2 yamt {
2349 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h = dyn_i->h;
2350 1.1.1.1.4.2 yamt
2351 1.1.1.1.4.2 yamt if (h)
2352 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
2353 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
2354 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
2355 1.1.1.1.4.2 yamt
2356 1.1.1.1.4.2 yamt if (h == NULL || !h->def_dynamic)
2357 1.1.1.1.4.2 yamt {
2358 1.1.1.1.4.2 yamt /* A non dynamic symbol. */
2359 1.1.1.1.4.2 yamt dyn_i->fptr_offset = x->ofs;
2360 1.1.1.1.4.2 yamt x->ofs += 16;
2361 1.1.1.1.4.2 yamt }
2362 1.1.1.1.4.2 yamt else
2363 1.1.1.1.4.2 yamt dyn_i->want_fptr = 0;
2364 1.1.1.1.4.2 yamt }
2365 1.1.1.1.4.2 yamt return TRUE;
2366 1.1.1.1.4.2 yamt }
2367 1.1.1.1.4.2 yamt
2368 1.1.1.1.4.2 yamt /* Allocate all the minimal PLT entries. */
2369 1.1.1.1.4.2 yamt
2370 1.1.1.1.4.2 yamt static bfd_boolean
2371 1.1.1.1.4.2 yamt allocate_plt_entries (struct elf64_ia64_dyn_sym_info *dyn_i,
2372 1.1.1.1.4.2 yamt void * data ATTRIBUTE_UNUSED)
2373 1.1.1.1.4.2 yamt {
2374 1.1.1.1.4.2 yamt if (dyn_i->want_plt)
2375 1.1.1.1.4.2 yamt {
2376 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h = dyn_i->h;
2377 1.1.1.1.4.2 yamt
2378 1.1.1.1.4.2 yamt if (h)
2379 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
2380 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
2381 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
2382 1.1.1.1.4.2 yamt
2383 1.1.1.1.4.2 yamt /* ??? Versioned symbols seem to lose NEEDS_PLT. */
2384 1.1.1.1.4.2 yamt if (elf64_ia64_dynamic_symbol_p (h))
2385 1.1.1.1.4.2 yamt {
2386 1.1.1.1.4.2 yamt dyn_i->want_pltoff = 1;
2387 1.1.1.1.4.2 yamt }
2388 1.1.1.1.4.2 yamt else
2389 1.1.1.1.4.2 yamt {
2390 1.1.1.1.4.2 yamt dyn_i->want_plt = 0;
2391 1.1.1.1.4.2 yamt dyn_i->want_plt2 = 0;
2392 1.1.1.1.4.2 yamt }
2393 1.1.1.1.4.2 yamt }
2394 1.1.1.1.4.2 yamt return TRUE;
2395 1.1.1.1.4.2 yamt }
2396 1.1.1.1.4.2 yamt
2397 1.1.1.1.4.2 yamt /* Allocate all the full PLT entries. */
2398 1.1.1.1.4.2 yamt
2399 1.1.1.1.4.2 yamt static bfd_boolean
2400 1.1.1.1.4.2 yamt allocate_plt2_entries (struct elf64_ia64_dyn_sym_info *dyn_i,
2401 1.1.1.1.4.2 yamt void * data)
2402 1.1.1.1.4.2 yamt {
2403 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2404 1.1.1.1.4.2 yamt
2405 1.1.1.1.4.2 yamt if (dyn_i->want_plt2)
2406 1.1.1.1.4.2 yamt {
2407 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h = dyn_i->h;
2408 1.1.1.1.4.2 yamt bfd_size_type ofs = x->ofs;
2409 1.1.1.1.4.2 yamt
2410 1.1.1.1.4.2 yamt dyn_i->plt2_offset = ofs;
2411 1.1.1.1.4.2 yamt x->ofs = ofs + PLT_FULL_ENTRY_SIZE;
2412 1.1.1.1.4.2 yamt
2413 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
2414 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
2415 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
2416 1.1.1.1.4.2 yamt dyn_i->h->plt.offset = ofs;
2417 1.1.1.1.4.2 yamt }
2418 1.1.1.1.4.2 yamt return TRUE;
2419 1.1.1.1.4.2 yamt }
2420 1.1.1.1.4.2 yamt
2421 1.1.1.1.4.2 yamt /* Allocate all the PLTOFF entries requested by relocations and
2422 1.1.1.1.4.2 yamt plt entries. We can't share space with allocated FPTR entries,
2423 1.1.1.1.4.2 yamt because the latter are not necessarily addressable by the GP.
2424 1.1.1.1.4.2 yamt ??? Relaxation might be able to determine that they are. */
2425 1.1.1.1.4.2 yamt
2426 1.1.1.1.4.2 yamt static bfd_boolean
2427 1.1.1.1.4.2 yamt allocate_pltoff_entries (struct elf64_ia64_dyn_sym_info *dyn_i,
2428 1.1.1.1.4.2 yamt void * data)
2429 1.1.1.1.4.2 yamt {
2430 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2431 1.1.1.1.4.2 yamt
2432 1.1.1.1.4.2 yamt if (dyn_i->want_pltoff)
2433 1.1.1.1.4.2 yamt {
2434 1.1.1.1.4.2 yamt dyn_i->pltoff_offset = x->ofs;
2435 1.1.1.1.4.2 yamt x->ofs += 16;
2436 1.1.1.1.4.2 yamt }
2437 1.1.1.1.4.2 yamt return TRUE;
2438 1.1.1.1.4.2 yamt }
2439 1.1.1.1.4.2 yamt
2440 1.1.1.1.4.2 yamt /* Allocate dynamic relocations for those symbols that turned out
2441 1.1.1.1.4.2 yamt to be dynamic. */
2442 1.1.1.1.4.2 yamt
2443 1.1.1.1.4.2 yamt static bfd_boolean
2444 1.1.1.1.4.2 yamt allocate_dynrel_entries (struct elf64_ia64_dyn_sym_info *dyn_i,
2445 1.1.1.1.4.2 yamt void * data)
2446 1.1.1.1.4.2 yamt {
2447 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data *x = (struct elf64_ia64_allocate_data *)data;
2448 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
2449 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_reloc_entry *rent;
2450 1.1.1.1.4.2 yamt bfd_boolean dynamic_symbol, shared, resolved_zero;
2451 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *h_ia64;
2452 1.1.1.1.4.2 yamt
2453 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (x->info);
2454 1.1.1.1.4.2 yamt if (ia64_info == NULL)
2455 1.1.1.1.4.2 yamt return FALSE;
2456 1.1.1.1.4.2 yamt
2457 1.1.1.1.4.2 yamt /* Note that this can't be used in relation to FPTR relocs below. */
2458 1.1.1.1.4.2 yamt dynamic_symbol = elf64_ia64_dynamic_symbol_p (dyn_i->h);
2459 1.1.1.1.4.2 yamt
2460 1.1.1.1.4.2 yamt shared = x->info->shared;
2461 1.1.1.1.4.2 yamt resolved_zero = (dyn_i->h
2462 1.1.1.1.4.2 yamt && ELF_ST_VISIBILITY (dyn_i->h->other)
2463 1.1.1.1.4.2 yamt && dyn_i->h->root.type == bfd_link_hash_undefweak);
2464 1.1.1.1.4.2 yamt
2465 1.1.1.1.4.2 yamt /* Take care of the GOT and PLT relocations. */
2466 1.1.1.1.4.2 yamt
2467 1.1.1.1.4.2 yamt if ((!resolved_zero
2468 1.1.1.1.4.2 yamt && (dynamic_symbol || shared)
2469 1.1.1.1.4.2 yamt && (dyn_i->want_got || dyn_i->want_gotx))
2470 1.1.1.1.4.2 yamt || (dyn_i->want_ltoff_fptr
2471 1.1.1.1.4.2 yamt && dyn_i->h
2472 1.1.1.1.4.2 yamt && dyn_i->h->def_dynamic))
2473 1.1.1.1.4.2 yamt {
2474 1.1.1.1.4.2 yamt /* VMS: FIX64. */
2475 1.1.1.1.4.2 yamt if (dyn_i->h != NULL && dyn_i->h->def_dynamic)
2476 1.1.1.1.4.2 yamt {
2477 1.1.1.1.4.2 yamt h_ia64 = (struct elf64_ia64_link_hash_entry *) dyn_i->h;
2478 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (h_ia64->shl)->fixups_off +=
2479 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2480 1.1.1.1.4.2 yamt ia64_info->fixups_sec->size +=
2481 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2482 1.1.1.1.4.2 yamt }
2483 1.1.1.1.4.2 yamt }
2484 1.1.1.1.4.2 yamt
2485 1.1.1.1.4.2 yamt if (ia64_info->rel_fptr_sec && dyn_i->want_fptr)
2486 1.1.1.1.4.2 yamt {
2487 1.1.1.1.4.2 yamt /* VMS: only image reloc. */
2488 1.1.1.1.4.2 yamt if (dyn_i->h == NULL || dyn_i->h->root.type != bfd_link_hash_undefweak)
2489 1.1.1.1.4.2 yamt ia64_info->rel_fptr_sec->size += sizeof (Elf64_External_Rela);
2490 1.1.1.1.4.2 yamt }
2491 1.1.1.1.4.2 yamt
2492 1.1.1.1.4.2 yamt if (!resolved_zero && dyn_i->want_pltoff)
2493 1.1.1.1.4.2 yamt {
2494 1.1.1.1.4.2 yamt /* VMS: FIXFD. */
2495 1.1.1.1.4.2 yamt if (dyn_i->h != NULL && dyn_i->h->def_dynamic)
2496 1.1.1.1.4.2 yamt {
2497 1.1.1.1.4.2 yamt h_ia64 = (struct elf64_ia64_link_hash_entry *) dyn_i->h;
2498 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (h_ia64->shl)->fixups_off +=
2499 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2500 1.1.1.1.4.2 yamt ia64_info->fixups_sec->size +=
2501 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2502 1.1.1.1.4.2 yamt }
2503 1.1.1.1.4.2 yamt }
2504 1.1.1.1.4.2 yamt
2505 1.1.1.1.4.2 yamt /* Take care of the normal data relocations. */
2506 1.1.1.1.4.2 yamt
2507 1.1.1.1.4.2 yamt for (rent = dyn_i->reloc_entries; rent; rent = rent->next)
2508 1.1.1.1.4.2 yamt {
2509 1.1.1.1.4.2 yamt int count = rent->count;
2510 1.1.1.1.4.2 yamt
2511 1.1.1.1.4.2 yamt switch (rent->type)
2512 1.1.1.1.4.2 yamt {
2513 1.1.1.1.4.2 yamt case R_IA64_FPTR32LSB:
2514 1.1.1.1.4.2 yamt case R_IA64_FPTR64LSB:
2515 1.1.1.1.4.2 yamt /* Allocate one iff !want_fptr and not PIE, which by this point
2516 1.1.1.1.4.2 yamt will be true only if we're actually allocating one statically
2517 1.1.1.1.4.2 yamt in the main executable. Position independent executables
2518 1.1.1.1.4.2 yamt need a relative reloc. */
2519 1.1.1.1.4.2 yamt if (dyn_i->want_fptr && !x->info->pie)
2520 1.1.1.1.4.2 yamt continue;
2521 1.1.1.1.4.2 yamt break;
2522 1.1.1.1.4.2 yamt case R_IA64_PCREL32LSB:
2523 1.1.1.1.4.2 yamt case R_IA64_PCREL64LSB:
2524 1.1.1.1.4.2 yamt if (!dynamic_symbol)
2525 1.1.1.1.4.2 yamt continue;
2526 1.1.1.1.4.2 yamt break;
2527 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
2528 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
2529 1.1.1.1.4.2 yamt if (!dynamic_symbol && !shared)
2530 1.1.1.1.4.2 yamt continue;
2531 1.1.1.1.4.2 yamt break;
2532 1.1.1.1.4.2 yamt case R_IA64_IPLTLSB:
2533 1.1.1.1.4.2 yamt if (!dynamic_symbol && !shared)
2534 1.1.1.1.4.2 yamt continue;
2535 1.1.1.1.4.2 yamt /* Use two REL relocations for IPLT relocations
2536 1.1.1.1.4.2 yamt against local symbols. */
2537 1.1.1.1.4.2 yamt if (!dynamic_symbol)
2538 1.1.1.1.4.2 yamt count *= 2;
2539 1.1.1.1.4.2 yamt break;
2540 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
2541 1.1.1.1.4.2 yamt case R_IA64_TPREL64LSB:
2542 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
2543 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64LSB:
2544 1.1.1.1.4.2 yamt break;
2545 1.1.1.1.4.2 yamt default:
2546 1.1.1.1.4.2 yamt abort ();
2547 1.1.1.1.4.2 yamt }
2548 1.1.1.1.4.2 yamt
2549 1.1.1.1.4.2 yamt /* Add a fixup. */
2550 1.1.1.1.4.2 yamt if (!dynamic_symbol)
2551 1.1.1.1.4.2 yamt abort ();
2552 1.1.1.1.4.2 yamt
2553 1.1.1.1.4.2 yamt h_ia64 = (struct elf64_ia64_link_hash_entry *) dyn_i->h;
2554 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (h_ia64->shl)->fixups_off +=
2555 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2556 1.1.1.1.4.2 yamt ia64_info->fixups_sec->size +=
2557 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2558 1.1.1.1.4.2 yamt }
2559 1.1.1.1.4.2 yamt
2560 1.1.1.1.4.2 yamt return TRUE;
2561 1.1.1.1.4.2 yamt }
2562 1.1.1.1.4.2 yamt
2563 1.1.1.1.4.2 yamt static bfd_boolean
2564 1.1.1.1.4.2 yamt elf64_ia64_adjust_dynamic_symbol (struct bfd_link_info *info ATTRIBUTE_UNUSED,
2565 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h)
2566 1.1.1.1.4.2 yamt {
2567 1.1.1.1.4.2 yamt /* ??? Undefined symbols with PLT entries should be re-defined
2568 1.1.1.1.4.2 yamt to be the PLT entry. */
2569 1.1.1.1.4.2 yamt
2570 1.1.1.1.4.2 yamt /* If this is a weak symbol, and there is a real definition, the
2571 1.1.1.1.4.2 yamt processor independent code will have arranged for us to see the
2572 1.1.1.1.4.2 yamt real definition first, and we can just use the same value. */
2573 1.1.1.1.4.2 yamt if (h->u.weakdef != NULL)
2574 1.1.1.1.4.2 yamt {
2575 1.1.1.1.4.2 yamt BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
2576 1.1.1.1.4.2 yamt || h->u.weakdef->root.type == bfd_link_hash_defweak);
2577 1.1.1.1.4.2 yamt h->root.u.def.section = h->u.weakdef->root.u.def.section;
2578 1.1.1.1.4.2 yamt h->root.u.def.value = h->u.weakdef->root.u.def.value;
2579 1.1.1.1.4.2 yamt return TRUE;
2580 1.1.1.1.4.2 yamt }
2581 1.1.1.1.4.2 yamt
2582 1.1.1.1.4.2 yamt /* If this is a reference to a symbol defined by a dynamic object which
2583 1.1.1.1.4.2 yamt is not a function, we might allocate the symbol in our .dynbss section
2584 1.1.1.1.4.2 yamt and allocate a COPY dynamic relocation.
2585 1.1.1.1.4.2 yamt
2586 1.1.1.1.4.2 yamt But IA-64 code is canonically PIC, so as a rule we can avoid this sort
2587 1.1.1.1.4.2 yamt of hackery. */
2588 1.1.1.1.4.2 yamt
2589 1.1.1.1.4.2 yamt return TRUE;
2590 1.1.1.1.4.2 yamt }
2591 1.1.1.1.4.2 yamt
2592 1.1.1.1.4.2 yamt static bfd_boolean
2593 1.1.1.1.4.2 yamt elf64_ia64_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
2594 1.1.1.1.4.2 yamt struct bfd_link_info *info)
2595 1.1.1.1.4.2 yamt {
2596 1.1.1.1.4.2 yamt struct elf64_ia64_allocate_data data;
2597 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
2598 1.1.1.1.4.2 yamt asection *sec;
2599 1.1.1.1.4.2 yamt bfd *dynobj;
2600 1.1.1.1.4.2 yamt struct elf_link_hash_table *hash_table;
2601 1.1.1.1.4.2 yamt
2602 1.1.1.1.4.2 yamt hash_table = elf_hash_table (info);
2603 1.1.1.1.4.2 yamt dynobj = hash_table->dynobj;
2604 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
2605 1.1.1.1.4.2 yamt if (ia64_info == NULL)
2606 1.1.1.1.4.2 yamt return FALSE;
2607 1.1.1.1.4.2 yamt BFD_ASSERT(dynobj != NULL);
2608 1.1.1.1.4.2 yamt data.info = info;
2609 1.1.1.1.4.2 yamt
2610 1.1.1.1.4.2 yamt /* Allocate the GOT entries. */
2611 1.1.1.1.4.2 yamt
2612 1.1.1.1.4.2 yamt if (ia64_info->root.sgot)
2613 1.1.1.1.4.2 yamt {
2614 1.1.1.1.4.2 yamt data.ofs = 0;
2615 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_global_data_got, &data);
2616 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_global_fptr_got, &data);
2617 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_local_got, &data);
2618 1.1.1.1.4.2 yamt ia64_info->root.sgot->size = data.ofs;
2619 1.1.1.1.4.2 yamt }
2620 1.1.1.1.4.2 yamt
2621 1.1.1.1.4.2 yamt /* Allocate the FPTR entries. */
2622 1.1.1.1.4.2 yamt
2623 1.1.1.1.4.2 yamt if (ia64_info->fptr_sec)
2624 1.1.1.1.4.2 yamt {
2625 1.1.1.1.4.2 yamt data.ofs = 0;
2626 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_fptr, &data);
2627 1.1.1.1.4.2 yamt ia64_info->fptr_sec->size = data.ofs;
2628 1.1.1.1.4.2 yamt }
2629 1.1.1.1.4.2 yamt
2630 1.1.1.1.4.2 yamt /* Now that we've seen all of the input files, we can decide which
2631 1.1.1.1.4.2 yamt symbols need plt entries. Allocate the minimal PLT entries first.
2632 1.1.1.1.4.2 yamt We do this even though dynamic_sections_created may be FALSE, because
2633 1.1.1.1.4.2 yamt this has the side-effect of clearing want_plt and want_plt2. */
2634 1.1.1.1.4.2 yamt
2635 1.1.1.1.4.2 yamt data.ofs = 0;
2636 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_plt_entries, &data);
2637 1.1.1.1.4.2 yamt
2638 1.1.1.1.4.2 yamt /* Align the pointer for the plt2 entries. */
2639 1.1.1.1.4.2 yamt data.ofs = (data.ofs + 31) & (bfd_vma) -32;
2640 1.1.1.1.4.2 yamt
2641 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_plt2_entries, &data);
2642 1.1.1.1.4.2 yamt if (data.ofs != 0 || ia64_info->root.dynamic_sections_created)
2643 1.1.1.1.4.2 yamt {
2644 1.1.1.1.4.2 yamt /* FIXME: we always reserve the memory for dynamic linker even if
2645 1.1.1.1.4.2 yamt there are no PLT entries since dynamic linker may assume the
2646 1.1.1.1.4.2 yamt reserved memory always exists. */
2647 1.1.1.1.4.2 yamt
2648 1.1.1.1.4.2 yamt BFD_ASSERT (ia64_info->root.dynamic_sections_created);
2649 1.1.1.1.4.2 yamt
2650 1.1.1.1.4.2 yamt ia64_info->root.splt->size = data.ofs;
2651 1.1.1.1.4.2 yamt }
2652 1.1.1.1.4.2 yamt
2653 1.1.1.1.4.2 yamt /* Allocate the PLTOFF entries. */
2654 1.1.1.1.4.2 yamt
2655 1.1.1.1.4.2 yamt if (ia64_info->pltoff_sec)
2656 1.1.1.1.4.2 yamt {
2657 1.1.1.1.4.2 yamt data.ofs = 0;
2658 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_pltoff_entries, &data);
2659 1.1.1.1.4.2 yamt ia64_info->pltoff_sec->size = data.ofs;
2660 1.1.1.1.4.2 yamt }
2661 1.1.1.1.4.2 yamt
2662 1.1.1.1.4.2 yamt if (ia64_info->root.dynamic_sections_created)
2663 1.1.1.1.4.2 yamt {
2664 1.1.1.1.4.2 yamt /* Allocate space for the dynamic relocations that turned out to be
2665 1.1.1.1.4.2 yamt required. */
2666 1.1.1.1.4.2 yamt elf64_ia64_dyn_sym_traverse (ia64_info, allocate_dynrel_entries, &data);
2667 1.1.1.1.4.2 yamt }
2668 1.1.1.1.4.2 yamt
2669 1.1.1.1.4.2 yamt /* We have now determined the sizes of the various dynamic sections.
2670 1.1.1.1.4.2 yamt Allocate memory for them. */
2671 1.1.1.1.4.2 yamt for (sec = dynobj->sections; sec != NULL; sec = sec->next)
2672 1.1.1.1.4.2 yamt {
2673 1.1.1.1.4.2 yamt bfd_boolean strip;
2674 1.1.1.1.4.2 yamt
2675 1.1.1.1.4.2 yamt if (!(sec->flags & SEC_LINKER_CREATED))
2676 1.1.1.1.4.2 yamt continue;
2677 1.1.1.1.4.2 yamt
2678 1.1.1.1.4.2 yamt /* If we don't need this section, strip it from the output file.
2679 1.1.1.1.4.2 yamt There were several sections primarily related to dynamic
2680 1.1.1.1.4.2 yamt linking that must be create before the linker maps input
2681 1.1.1.1.4.2 yamt sections to output sections. The linker does that before
2682 1.1.1.1.4.2 yamt bfd_elf_size_dynamic_sections is called, and it is that
2683 1.1.1.1.4.2 yamt function which decides whether anything needs to go into
2684 1.1.1.1.4.2 yamt these sections. */
2685 1.1.1.1.4.2 yamt
2686 1.1.1.1.4.2 yamt strip = (sec->size == 0);
2687 1.1.1.1.4.2 yamt
2688 1.1.1.1.4.2 yamt if (sec == ia64_info->root.sgot)
2689 1.1.1.1.4.2 yamt strip = FALSE;
2690 1.1.1.1.4.2 yamt else if (sec == ia64_info->root.srelgot)
2691 1.1.1.1.4.2 yamt {
2692 1.1.1.1.4.2 yamt if (strip)
2693 1.1.1.1.4.2 yamt ia64_info->root.srelgot = NULL;
2694 1.1.1.1.4.2 yamt else
2695 1.1.1.1.4.2 yamt /* We use the reloc_count field as a counter if we need to
2696 1.1.1.1.4.2 yamt copy relocs into the output file. */
2697 1.1.1.1.4.2 yamt sec->reloc_count = 0;
2698 1.1.1.1.4.2 yamt }
2699 1.1.1.1.4.2 yamt else if (sec == ia64_info->fptr_sec)
2700 1.1.1.1.4.2 yamt {
2701 1.1.1.1.4.2 yamt if (strip)
2702 1.1.1.1.4.2 yamt ia64_info->fptr_sec = NULL;
2703 1.1.1.1.4.2 yamt }
2704 1.1.1.1.4.2 yamt else if (sec == ia64_info->rel_fptr_sec)
2705 1.1.1.1.4.2 yamt {
2706 1.1.1.1.4.2 yamt if (strip)
2707 1.1.1.1.4.2 yamt ia64_info->rel_fptr_sec = NULL;
2708 1.1.1.1.4.2 yamt else
2709 1.1.1.1.4.2 yamt /* We use the reloc_count field as a counter if we need to
2710 1.1.1.1.4.2 yamt copy relocs into the output file. */
2711 1.1.1.1.4.2 yamt sec->reloc_count = 0;
2712 1.1.1.1.4.2 yamt }
2713 1.1.1.1.4.2 yamt else if (sec == ia64_info->root.splt)
2714 1.1.1.1.4.2 yamt {
2715 1.1.1.1.4.2 yamt if (strip)
2716 1.1.1.1.4.2 yamt ia64_info->root.splt = NULL;
2717 1.1.1.1.4.2 yamt }
2718 1.1.1.1.4.2 yamt else if (sec == ia64_info->pltoff_sec)
2719 1.1.1.1.4.2 yamt {
2720 1.1.1.1.4.2 yamt if (strip)
2721 1.1.1.1.4.2 yamt ia64_info->pltoff_sec = NULL;
2722 1.1.1.1.4.2 yamt }
2723 1.1.1.1.4.2 yamt else if (sec == ia64_info->fixups_sec)
2724 1.1.1.1.4.2 yamt {
2725 1.1.1.1.4.2 yamt if (strip)
2726 1.1.1.1.4.2 yamt ia64_info->fixups_sec = NULL;
2727 1.1.1.1.4.2 yamt }
2728 1.1.1.1.4.2 yamt else if (sec == ia64_info->transfer_sec)
2729 1.1.1.1.4.2 yamt {
2730 1.1.1.1.4.2 yamt ;
2731 1.1.1.1.4.2 yamt }
2732 1.1.1.1.4.2 yamt else
2733 1.1.1.1.4.2 yamt {
2734 1.1.1.1.4.2 yamt const char *name;
2735 1.1.1.1.4.2 yamt
2736 1.1.1.1.4.2 yamt /* It's OK to base decisions on the section name, because none
2737 1.1.1.1.4.2 yamt of the dynobj section names depend upon the input files. */
2738 1.1.1.1.4.2 yamt name = bfd_get_section_name (dynobj, sec);
2739 1.1.1.1.4.2 yamt
2740 1.1.1.1.4.2 yamt if (strcmp (name, ".got.plt") == 0)
2741 1.1.1.1.4.2 yamt strip = FALSE;
2742 1.1.1.1.4.2 yamt else if (CONST_STRNEQ (name, ".rel"))
2743 1.1.1.1.4.2 yamt {
2744 1.1.1.1.4.2 yamt if (!strip)
2745 1.1.1.1.4.2 yamt {
2746 1.1.1.1.4.2 yamt /* We use the reloc_count field as a counter if we need to
2747 1.1.1.1.4.2 yamt copy relocs into the output file. */
2748 1.1.1.1.4.2 yamt sec->reloc_count = 0;
2749 1.1.1.1.4.2 yamt }
2750 1.1.1.1.4.2 yamt }
2751 1.1.1.1.4.2 yamt else
2752 1.1.1.1.4.2 yamt continue;
2753 1.1.1.1.4.2 yamt }
2754 1.1.1.1.4.2 yamt
2755 1.1.1.1.4.2 yamt if (strip)
2756 1.1.1.1.4.2 yamt sec->flags |= SEC_EXCLUDE;
2757 1.1.1.1.4.2 yamt else
2758 1.1.1.1.4.2 yamt {
2759 1.1.1.1.4.2 yamt /* Allocate memory for the section contents. */
2760 1.1.1.1.4.2 yamt sec->contents = (bfd_byte *) bfd_zalloc (dynobj, sec->size);
2761 1.1.1.1.4.2 yamt if (sec->contents == NULL && sec->size != 0)
2762 1.1.1.1.4.2 yamt return FALSE;
2763 1.1.1.1.4.2 yamt }
2764 1.1.1.1.4.2 yamt }
2765 1.1.1.1.4.2 yamt
2766 1.1.1.1.4.2 yamt if (elf_hash_table (info)->dynamic_sections_created)
2767 1.1.1.1.4.2 yamt {
2768 1.1.1.1.4.2 yamt bfd *abfd;
2769 1.1.1.1.4.2 yamt asection *dynsec;
2770 1.1.1.1.4.2 yamt asection *dynstrsec;
2771 1.1.1.1.4.2 yamt Elf_Internal_Dyn dyn;
2772 1.1.1.1.4.2 yamt const struct elf_backend_data *bed;
2773 1.1.1.1.4.2 yamt unsigned int shl_num = 0;
2774 1.1.1.1.4.2 yamt bfd_vma fixups_off = 0;
2775 1.1.1.1.4.2 yamt bfd_vma strdyn_off;
2776 1.1.1.1.4.2 yamt unsigned int time_hi, time_lo;
2777 1.1.1.1.4.2 yamt
2778 1.1.1.1.4.2 yamt /* The .dynamic section must exist and be empty. */
2779 1.1.1.1.4.2 yamt dynsec = bfd_get_linker_section (hash_table->dynobj, ".dynamic");
2780 1.1.1.1.4.2 yamt BFD_ASSERT (dynsec != NULL);
2781 1.1.1.1.4.2 yamt BFD_ASSERT (dynsec->size == 0);
2782 1.1.1.1.4.2 yamt
2783 1.1.1.1.4.2 yamt dynstrsec = bfd_get_linker_section (hash_table->dynobj, ".vmsdynstr");
2784 1.1.1.1.4.2 yamt BFD_ASSERT (dynstrsec != NULL);
2785 1.1.1.1.4.2 yamt BFD_ASSERT (dynstrsec->size == 0);
2786 1.1.1.1.4.2 yamt dynstrsec->size = 1; /* Initial blank. */
2787 1.1.1.1.4.2 yamt
2788 1.1.1.1.4.2 yamt /* Ident + link time. */
2789 1.1.1.1.4.2 yamt vms_get_time (&time_hi, &time_lo);
2790 1.1.1.1.4.2 yamt
2791 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_IDENT, 0))
2792 1.1.1.1.4.2 yamt return FALSE;
2793 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_LINKTIME,
2794 1.1.1.1.4.2 yamt (((bfd_uint64_t)time_hi) << 32)
2795 1.1.1.1.4.2 yamt + time_lo))
2796 1.1.1.1.4.2 yamt return FALSE;
2797 1.1.1.1.4.2 yamt
2798 1.1.1.1.4.2 yamt /* Strtab. */
2799 1.1.1.1.4.2 yamt strdyn_off = dynsec->size;
2800 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_STRTAB_OFFSET, 0))
2801 1.1.1.1.4.2 yamt return FALSE;
2802 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_STRSZ, 0))
2803 1.1.1.1.4.2 yamt return FALSE;
2804 1.1.1.1.4.2 yamt
2805 1.1.1.1.4.2 yamt /* PLTGOT */
2806 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_PLTGOT_SEG, 0))
2807 1.1.1.1.4.2 yamt return FALSE;
2808 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_PLTGOT_OFFSET, 0))
2809 1.1.1.1.4.2 yamt return FALSE;
2810 1.1.1.1.4.2 yamt
2811 1.1.1.1.4.2 yamt /* Misc. */
2812 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_FPMODE, 0x9800000))
2813 1.1.1.1.4.2 yamt return FALSE;
2814 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_LNKFLAGS,
2815 1.1.1.1.4.2 yamt VMS_LF_IMGSTA | VMS_LF_MAIN))
2816 1.1.1.1.4.2 yamt return FALSE;
2817 1.1.1.1.4.2 yamt
2818 1.1.1.1.4.2 yamt /* Add entries for shared libraries. */
2819 1.1.1.1.4.2 yamt for (abfd = info->input_bfds; abfd; abfd = abfd->link_next)
2820 1.1.1.1.4.2 yamt {
2821 1.1.1.1.4.2 yamt char *soname;
2822 1.1.1.1.4.2 yamt size_t soname_len;
2823 1.1.1.1.4.2 yamt bfd_size_type strindex;
2824 1.1.1.1.4.2 yamt bfd_byte *newcontents;
2825 1.1.1.1.4.2 yamt bfd_vma fixups_shl_off;
2826 1.1.1.1.4.2 yamt
2827 1.1.1.1.4.2 yamt if (!(abfd->flags & DYNAMIC))
2828 1.1.1.1.4.2 yamt continue;
2829 1.1.1.1.4.2 yamt BFD_ASSERT (abfd->xvec == output_bfd->xvec);
2830 1.1.1.1.4.2 yamt
2831 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_NEEDED_IDENT,
2832 1.1.1.1.4.2 yamt elf_ia64_vms_ident (abfd)))
2833 1.1.1.1.4.2 yamt return FALSE;
2834 1.1.1.1.4.2 yamt
2835 1.1.1.1.4.2 yamt soname = vms_get_module_name (abfd->filename, TRUE);
2836 1.1.1.1.4.2 yamt if (soname == NULL)
2837 1.1.1.1.4.2 yamt return FALSE;
2838 1.1.1.1.4.2 yamt strindex = dynstrsec->size;
2839 1.1.1.1.4.2 yamt soname_len = strlen (soname) + 1;
2840 1.1.1.1.4.2 yamt newcontents = (bfd_byte *) bfd_realloc (dynstrsec->contents,
2841 1.1.1.1.4.2 yamt strindex + soname_len);
2842 1.1.1.1.4.2 yamt if (newcontents == NULL)
2843 1.1.1.1.4.2 yamt return FALSE;
2844 1.1.1.1.4.2 yamt memcpy (newcontents + strindex, soname, soname_len);
2845 1.1.1.1.4.2 yamt dynstrsec->size += soname_len;
2846 1.1.1.1.4.2 yamt dynstrsec->contents = newcontents;
2847 1.1.1.1.4.2 yamt
2848 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_NEEDED, strindex))
2849 1.1.1.1.4.2 yamt return FALSE;
2850 1.1.1.1.4.2 yamt
2851 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_FIXUP_NEEDED,
2852 1.1.1.1.4.2 yamt shl_num))
2853 1.1.1.1.4.2 yamt return FALSE;
2854 1.1.1.1.4.2 yamt shl_num++;
2855 1.1.1.1.4.2 yamt
2856 1.1.1.1.4.2 yamt /* The fixups_off was in fact containing the size of the fixup
2857 1.1.1.1.4.2 yamt section. Remap into the offset. */
2858 1.1.1.1.4.2 yamt fixups_shl_off = elf_ia64_vms_tdata (abfd)->fixups_off;
2859 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (abfd)->fixups_off = fixups_off;
2860 1.1.1.1.4.2 yamt
2861 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry
2862 1.1.1.1.4.2 yamt (info, DT_IA_64_VMS_FIXUP_RELA_CNT,
2863 1.1.1.1.4.2 yamt fixups_shl_off / sizeof (Elf64_External_VMS_IMAGE_FIXUP)))
2864 1.1.1.1.4.2 yamt return FALSE;
2865 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_FIXUP_RELA_OFF,
2866 1.1.1.1.4.2 yamt fixups_off))
2867 1.1.1.1.4.2 yamt return FALSE;
2868 1.1.1.1.4.2 yamt fixups_off += fixups_shl_off;
2869 1.1.1.1.4.2 yamt }
2870 1.1.1.1.4.2 yamt
2871 1.1.1.1.4.2 yamt /* Unwind. */
2872 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_UNWINDSZ, 0))
2873 1.1.1.1.4.2 yamt return FALSE;
2874 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_UNWIND_CODSEG, 0))
2875 1.1.1.1.4.2 yamt return FALSE;
2876 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_UNWIND_INFOSEG, 0))
2877 1.1.1.1.4.2 yamt return FALSE;
2878 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_UNWIND_OFFSET, 0))
2879 1.1.1.1.4.2 yamt return FALSE;
2880 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_IA_64_VMS_UNWIND_SEG, 0))
2881 1.1.1.1.4.2 yamt return FALSE;
2882 1.1.1.1.4.2 yamt
2883 1.1.1.1.4.2 yamt if (!_bfd_elf_add_dynamic_entry (info, DT_NULL, 0xdead))
2884 1.1.1.1.4.2 yamt return FALSE;
2885 1.1.1.1.4.2 yamt
2886 1.1.1.1.4.2 yamt /* Fix the strtab entries. */
2887 1.1.1.1.4.2 yamt bed = get_elf_backend_data (hash_table->dynobj);
2888 1.1.1.1.4.2 yamt
2889 1.1.1.1.4.2 yamt if (dynstrsec->size > 1)
2890 1.1.1.1.4.2 yamt dynstrsec->contents[0] = 0;
2891 1.1.1.1.4.2 yamt else
2892 1.1.1.1.4.2 yamt dynstrsec->size = 0;
2893 1.1.1.1.4.2 yamt
2894 1.1.1.1.4.2 yamt /* Note: one 'spare' (ie DT_NULL) entry is added by
2895 1.1.1.1.4.2 yamt bfd_elf_size_dynsym_hash_dynstr. */
2896 1.1.1.1.4.2 yamt dyn.d_tag = DT_IA_64_VMS_STRTAB_OFFSET;
2897 1.1.1.1.4.2 yamt dyn.d_un.d_val = dynsec->size /* + sizeof (Elf64_External_Dyn) */;
2898 1.1.1.1.4.2 yamt bed->s->swap_dyn_out (hash_table->dynobj, &dyn,
2899 1.1.1.1.4.2 yamt dynsec->contents + strdyn_off);
2900 1.1.1.1.4.2 yamt
2901 1.1.1.1.4.2 yamt dyn.d_tag = DT_STRSZ;
2902 1.1.1.1.4.2 yamt dyn.d_un.d_val = dynstrsec->size;
2903 1.1.1.1.4.2 yamt bed->s->swap_dyn_out (hash_table->dynobj, &dyn,
2904 1.1.1.1.4.2 yamt dynsec->contents + strdyn_off + bed->s->sizeof_dyn);
2905 1.1.1.1.4.2 yamt
2906 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (output_bfd)->needed_count = shl_num;
2907 1.1.1.1.4.2 yamt
2908 1.1.1.1.4.2 yamt /* Note section. */
2909 1.1.1.1.4.2 yamt if (!create_ia64_vms_notes (output_bfd, info, time_hi, time_lo))
2910 1.1.1.1.4.2 yamt return FALSE;
2911 1.1.1.1.4.2 yamt }
2912 1.1.1.1.4.2 yamt
2913 1.1.1.1.4.2 yamt /* ??? Perhaps force __gp local. */
2914 1.1.1.1.4.2 yamt
2915 1.1.1.1.4.2 yamt return TRUE;
2916 1.1.1.1.4.2 yamt }
2917 1.1.1.1.4.2 yamt
2918 1.1.1.1.4.2 yamt static void
2919 1.1.1.1.4.2 yamt elf64_ia64_install_fixup (bfd *output_bfd,
2920 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info,
2921 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h,
2922 1.1.1.1.4.2 yamt unsigned int type, asection *sec, bfd_vma offset,
2923 1.1.1.1.4.2 yamt bfd_vma addend)
2924 1.1.1.1.4.2 yamt {
2925 1.1.1.1.4.2 yamt asection *relsec;
2926 1.1.1.1.4.2 yamt Elf64_External_VMS_IMAGE_FIXUP *fixup;
2927 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_entry *h_ia64;
2928 1.1.1.1.4.2 yamt bfd_vma fixoff;
2929 1.1.1.1.4.2 yamt Elf_Internal_Phdr *phdr;
2930 1.1.1.1.4.2 yamt
2931 1.1.1.1.4.2 yamt if (h == NULL || !h->def_dynamic)
2932 1.1.1.1.4.2 yamt abort ();
2933 1.1.1.1.4.2 yamt
2934 1.1.1.1.4.2 yamt h_ia64 = (struct elf64_ia64_link_hash_entry *) h;
2935 1.1.1.1.4.2 yamt fixoff = elf_ia64_vms_tdata (h_ia64->shl)->fixups_off;
2936 1.1.1.1.4.2 yamt elf_ia64_vms_tdata (h_ia64->shl)->fixups_off +=
2937 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_IMAGE_FIXUP);
2938 1.1.1.1.4.2 yamt relsec = ia64_info->fixups_sec;
2939 1.1.1.1.4.2 yamt
2940 1.1.1.1.4.2 yamt fixup = (Elf64_External_VMS_IMAGE_FIXUP *)(relsec->contents + fixoff);
2941 1.1.1.1.4.2 yamt offset += sec->output_section->vma + sec->output_offset;
2942 1.1.1.1.4.2 yamt
2943 1.1.1.1.4.2 yamt /* FIXME: this is slow. We should cache the last one used, or create a
2944 1.1.1.1.4.2 yamt map. */
2945 1.1.1.1.4.2 yamt phdr = _bfd_elf_find_segment_containing_section
2946 1.1.1.1.4.2 yamt (output_bfd, sec->output_section);
2947 1.1.1.1.4.2 yamt BFD_ASSERT (phdr != NULL);
2948 1.1.1.1.4.2 yamt
2949 1.1.1.1.4.2 yamt bfd_putl64 (offset - phdr->p_vaddr, fixup->fixup_offset);
2950 1.1.1.1.4.2 yamt bfd_putl32 (type, fixup->type);
2951 1.1.1.1.4.2 yamt bfd_putl32 (phdr - elf_tdata (output_bfd)->phdr, fixup->fixup_seg);
2952 1.1.1.1.4.2 yamt bfd_putl64 (addend, fixup->addend);
2953 1.1.1.1.4.2 yamt bfd_putl32 (h->root.u.def.value, fixup->symvec_index);
2954 1.1.1.1.4.2 yamt bfd_putl32 (2, fixup->data_type);
2955 1.1.1.1.4.2 yamt }
2956 1.1.1.1.4.2 yamt
2957 1.1.1.1.4.2 yamt /* Store an entry for target address TARGET_ADDR in the linkage table
2958 1.1.1.1.4.2 yamt and return the gp-relative address of the linkage table entry. */
2959 1.1.1.1.4.2 yamt
2960 1.1.1.1.4.2 yamt static bfd_vma
2961 1.1.1.1.4.2 yamt set_got_entry (bfd *abfd, struct bfd_link_info *info,
2962 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i,
2963 1.1.1.1.4.2 yamt bfd_vma addend, bfd_vma value, unsigned int dyn_r_type)
2964 1.1.1.1.4.2 yamt {
2965 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
2966 1.1.1.1.4.2 yamt asection *got_sec;
2967 1.1.1.1.4.2 yamt bfd_boolean done;
2968 1.1.1.1.4.2 yamt bfd_vma got_offset;
2969 1.1.1.1.4.2 yamt
2970 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
2971 1.1.1.1.4.2 yamt if (ia64_info == NULL)
2972 1.1.1.1.4.2 yamt return 0;
2973 1.1.1.1.4.2 yamt
2974 1.1.1.1.4.2 yamt got_sec = ia64_info->root.sgot;
2975 1.1.1.1.4.2 yamt
2976 1.1.1.1.4.2 yamt switch (dyn_r_type)
2977 1.1.1.1.4.2 yamt {
2978 1.1.1.1.4.2 yamt case R_IA64_TPREL64LSB:
2979 1.1.1.1.4.2 yamt case R_IA64_DTPMOD64LSB:
2980 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
2981 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
2982 1.1.1.1.4.2 yamt abort ();
2983 1.1.1.1.4.2 yamt break;
2984 1.1.1.1.4.2 yamt default:
2985 1.1.1.1.4.2 yamt done = dyn_i->got_done;
2986 1.1.1.1.4.2 yamt dyn_i->got_done = TRUE;
2987 1.1.1.1.4.2 yamt got_offset = dyn_i->got_offset;
2988 1.1.1.1.4.2 yamt break;
2989 1.1.1.1.4.2 yamt }
2990 1.1.1.1.4.2 yamt
2991 1.1.1.1.4.2 yamt BFD_ASSERT ((got_offset & 7) == 0);
2992 1.1.1.1.4.2 yamt
2993 1.1.1.1.4.2 yamt if (! done)
2994 1.1.1.1.4.2 yamt {
2995 1.1.1.1.4.2 yamt /* Store the target address in the linkage table entry. */
2996 1.1.1.1.4.2 yamt bfd_put_64 (abfd, value, got_sec->contents + got_offset);
2997 1.1.1.1.4.2 yamt
2998 1.1.1.1.4.2 yamt /* Install a dynamic relocation if needed. */
2999 1.1.1.1.4.2 yamt if (((info->shared
3000 1.1.1.1.4.2 yamt && (!dyn_i->h
3001 1.1.1.1.4.2 yamt || ELF_ST_VISIBILITY (dyn_i->h->other) == STV_DEFAULT
3002 1.1.1.1.4.2 yamt || dyn_i->h->root.type != bfd_link_hash_undefweak))
3003 1.1.1.1.4.2 yamt || elf64_ia64_dynamic_symbol_p (dyn_i->h))
3004 1.1.1.1.4.2 yamt && (!dyn_i->want_ltoff_fptr
3005 1.1.1.1.4.2 yamt || !info->pie
3006 1.1.1.1.4.2 yamt || !dyn_i->h
3007 1.1.1.1.4.2 yamt || dyn_i->h->root.type != bfd_link_hash_undefweak))
3008 1.1.1.1.4.2 yamt {
3009 1.1.1.1.4.2 yamt if (!dyn_i->h || !dyn_i->h->def_dynamic)
3010 1.1.1.1.4.2 yamt {
3011 1.1.1.1.4.2 yamt dyn_r_type = R_IA64_REL64LSB;
3012 1.1.1.1.4.2 yamt addend = value;
3013 1.1.1.1.4.2 yamt }
3014 1.1.1.1.4.2 yamt
3015 1.1.1.1.4.2 yamt /* VMS: install a FIX32 or FIX64. */
3016 1.1.1.1.4.2 yamt switch (dyn_r_type)
3017 1.1.1.1.4.2 yamt {
3018 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
3019 1.1.1.1.4.2 yamt case R_IA64_FPTR32LSB:
3020 1.1.1.1.4.2 yamt dyn_r_type = R_IA64_VMS_FIX32;
3021 1.1.1.1.4.2 yamt break;
3022 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
3023 1.1.1.1.4.2 yamt case R_IA64_FPTR64LSB:
3024 1.1.1.1.4.2 yamt dyn_r_type = R_IA64_VMS_FIX64;
3025 1.1.1.1.4.2 yamt break;
3026 1.1.1.1.4.2 yamt default:
3027 1.1.1.1.4.2 yamt BFD_ASSERT (FALSE);
3028 1.1.1.1.4.2 yamt break;
3029 1.1.1.1.4.2 yamt }
3030 1.1.1.1.4.2 yamt elf64_ia64_install_fixup
3031 1.1.1.1.4.2 yamt (info->output_bfd, ia64_info, dyn_i->h,
3032 1.1.1.1.4.2 yamt dyn_r_type, got_sec, got_offset, addend);
3033 1.1.1.1.4.2 yamt }
3034 1.1.1.1.4.2 yamt }
3035 1.1.1.1.4.2 yamt
3036 1.1.1.1.4.2 yamt /* Return the address of the linkage table entry. */
3037 1.1.1.1.4.2 yamt value = (got_sec->output_section->vma
3038 1.1.1.1.4.2 yamt + got_sec->output_offset
3039 1.1.1.1.4.2 yamt + got_offset);
3040 1.1.1.1.4.2 yamt
3041 1.1.1.1.4.2 yamt return value;
3042 1.1.1.1.4.2 yamt }
3043 1.1.1.1.4.2 yamt
3044 1.1.1.1.4.2 yamt /* Fill in a function descriptor consisting of the function's code
3045 1.1.1.1.4.2 yamt address and its global pointer. Return the descriptor's address. */
3046 1.1.1.1.4.2 yamt
3047 1.1.1.1.4.2 yamt static bfd_vma
3048 1.1.1.1.4.2 yamt set_fptr_entry (bfd *abfd, struct bfd_link_info *info,
3049 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i,
3050 1.1.1.1.4.2 yamt bfd_vma value)
3051 1.1.1.1.4.2 yamt {
3052 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3053 1.1.1.1.4.2 yamt asection *fptr_sec;
3054 1.1.1.1.4.2 yamt
3055 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3056 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3057 1.1.1.1.4.2 yamt return 0;
3058 1.1.1.1.4.2 yamt
3059 1.1.1.1.4.2 yamt fptr_sec = ia64_info->fptr_sec;
3060 1.1.1.1.4.2 yamt
3061 1.1.1.1.4.2 yamt if (!dyn_i->fptr_done)
3062 1.1.1.1.4.2 yamt {
3063 1.1.1.1.4.2 yamt dyn_i->fptr_done = 1;
3064 1.1.1.1.4.2 yamt
3065 1.1.1.1.4.2 yamt /* Fill in the function descriptor. */
3066 1.1.1.1.4.2 yamt bfd_put_64 (abfd, value, fptr_sec->contents + dyn_i->fptr_offset);
3067 1.1.1.1.4.2 yamt bfd_put_64 (abfd, _bfd_get_gp_value (abfd),
3068 1.1.1.1.4.2 yamt fptr_sec->contents + dyn_i->fptr_offset + 8);
3069 1.1.1.1.4.2 yamt }
3070 1.1.1.1.4.2 yamt
3071 1.1.1.1.4.2 yamt /* Return the descriptor's address. */
3072 1.1.1.1.4.2 yamt value = (fptr_sec->output_section->vma
3073 1.1.1.1.4.2 yamt + fptr_sec->output_offset
3074 1.1.1.1.4.2 yamt + dyn_i->fptr_offset);
3075 1.1.1.1.4.2 yamt
3076 1.1.1.1.4.2 yamt return value;
3077 1.1.1.1.4.2 yamt }
3078 1.1.1.1.4.2 yamt
3079 1.1.1.1.4.2 yamt /* Fill in a PLTOFF entry consisting of the function's code address
3080 1.1.1.1.4.2 yamt and its global pointer. Return the descriptor's address. */
3081 1.1.1.1.4.2 yamt
3082 1.1.1.1.4.2 yamt static bfd_vma
3083 1.1.1.1.4.2 yamt set_pltoff_entry (bfd *abfd, struct bfd_link_info *info,
3084 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i,
3085 1.1.1.1.4.2 yamt bfd_vma value, bfd_boolean is_plt)
3086 1.1.1.1.4.2 yamt {
3087 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3088 1.1.1.1.4.2 yamt asection *pltoff_sec;
3089 1.1.1.1.4.2 yamt
3090 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3091 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3092 1.1.1.1.4.2 yamt return 0;
3093 1.1.1.1.4.2 yamt
3094 1.1.1.1.4.2 yamt pltoff_sec = ia64_info->pltoff_sec;
3095 1.1.1.1.4.2 yamt
3096 1.1.1.1.4.2 yamt /* Don't do anything if this symbol uses a real PLT entry. In
3097 1.1.1.1.4.2 yamt that case, we'll fill this in during finish_dynamic_symbol. */
3098 1.1.1.1.4.2 yamt if ((! dyn_i->want_plt || is_plt)
3099 1.1.1.1.4.2 yamt && !dyn_i->pltoff_done)
3100 1.1.1.1.4.2 yamt {
3101 1.1.1.1.4.2 yamt bfd_vma gp = _bfd_get_gp_value (abfd);
3102 1.1.1.1.4.2 yamt
3103 1.1.1.1.4.2 yamt /* Fill in the function descriptor. */
3104 1.1.1.1.4.2 yamt bfd_put_64 (abfd, value, pltoff_sec->contents + dyn_i->pltoff_offset);
3105 1.1.1.1.4.2 yamt bfd_put_64 (abfd, gp, pltoff_sec->contents + dyn_i->pltoff_offset + 8);
3106 1.1.1.1.4.2 yamt
3107 1.1.1.1.4.2 yamt /* Install dynamic relocations if needed. */
3108 1.1.1.1.4.2 yamt if (!is_plt
3109 1.1.1.1.4.2 yamt && info->shared
3110 1.1.1.1.4.2 yamt && (!dyn_i->h
3111 1.1.1.1.4.2 yamt || ELF_ST_VISIBILITY (dyn_i->h->other) == STV_DEFAULT
3112 1.1.1.1.4.2 yamt || dyn_i->h->root.type != bfd_link_hash_undefweak))
3113 1.1.1.1.4.2 yamt {
3114 1.1.1.1.4.2 yamt /* VMS: */
3115 1.1.1.1.4.2 yamt abort ();
3116 1.1.1.1.4.2 yamt }
3117 1.1.1.1.4.2 yamt
3118 1.1.1.1.4.2 yamt dyn_i->pltoff_done = 1;
3119 1.1.1.1.4.2 yamt }
3120 1.1.1.1.4.2 yamt
3121 1.1.1.1.4.2 yamt /* Return the descriptor's address. */
3122 1.1.1.1.4.2 yamt value = (pltoff_sec->output_section->vma
3123 1.1.1.1.4.2 yamt + pltoff_sec->output_offset
3124 1.1.1.1.4.2 yamt + dyn_i->pltoff_offset);
3125 1.1.1.1.4.2 yamt
3126 1.1.1.1.4.2 yamt return value;
3127 1.1.1.1.4.2 yamt }
3128 1.1.1.1.4.2 yamt
3129 1.1.1.1.4.2 yamt /* Called through qsort to sort the .IA_64.unwind section during a
3130 1.1.1.1.4.2 yamt non-relocatable link. Set elf64_ia64_unwind_entry_compare_bfd
3131 1.1.1.1.4.2 yamt to the output bfd so we can do proper endianness frobbing. */
3132 1.1.1.1.4.2 yamt
3133 1.1.1.1.4.2 yamt static bfd *elf64_ia64_unwind_entry_compare_bfd;
3134 1.1.1.1.4.2 yamt
3135 1.1.1.1.4.2 yamt static int
3136 1.1.1.1.4.2 yamt elf64_ia64_unwind_entry_compare (const void * a, const void * b)
3137 1.1.1.1.4.2 yamt {
3138 1.1.1.1.4.2 yamt bfd_vma av, bv;
3139 1.1.1.1.4.2 yamt
3140 1.1.1.1.4.2 yamt av = bfd_get_64 (elf64_ia64_unwind_entry_compare_bfd, a);
3141 1.1.1.1.4.2 yamt bv = bfd_get_64 (elf64_ia64_unwind_entry_compare_bfd, b);
3142 1.1.1.1.4.2 yamt
3143 1.1.1.1.4.2 yamt return (av < bv ? -1 : av > bv ? 1 : 0);
3144 1.1.1.1.4.2 yamt }
3145 1.1.1.1.4.2 yamt
3146 1.1.1.1.4.2 yamt /* Make sure we've got ourselves a nice fat __gp value. */
3147 1.1.1.1.4.2 yamt static bfd_boolean
3148 1.1.1.1.4.2 yamt elf64_ia64_choose_gp (bfd *abfd, struct bfd_link_info *info, bfd_boolean final)
3149 1.1.1.1.4.2 yamt {
3150 1.1.1.1.4.2 yamt bfd_vma min_vma = (bfd_vma) -1, max_vma = 0;
3151 1.1.1.1.4.2 yamt bfd_vma min_short_vma = min_vma, max_short_vma = 0;
3152 1.1.1.1.4.2 yamt struct elf_link_hash_entry *gp;
3153 1.1.1.1.4.2 yamt bfd_vma gp_val;
3154 1.1.1.1.4.2 yamt asection *os;
3155 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3156 1.1.1.1.4.2 yamt
3157 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3158 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3159 1.1.1.1.4.2 yamt return FALSE;
3160 1.1.1.1.4.2 yamt
3161 1.1.1.1.4.2 yamt /* Find the min and max vma of all sections marked short. Also collect
3162 1.1.1.1.4.2 yamt min and max vma of any type, for use in selecting a nice gp. */
3163 1.1.1.1.4.2 yamt for (os = abfd->sections; os ; os = os->next)
3164 1.1.1.1.4.2 yamt {
3165 1.1.1.1.4.2 yamt bfd_vma lo, hi;
3166 1.1.1.1.4.2 yamt
3167 1.1.1.1.4.2 yamt if ((os->flags & SEC_ALLOC) == 0)
3168 1.1.1.1.4.2 yamt continue;
3169 1.1.1.1.4.2 yamt
3170 1.1.1.1.4.2 yamt lo = os->vma;
3171 1.1.1.1.4.2 yamt /* When this function is called from elfNN_ia64_final_link
3172 1.1.1.1.4.2 yamt the correct value to use is os->size. When called from
3173 1.1.1.1.4.2 yamt elfNN_ia64_relax_section we are in the middle of section
3174 1.1.1.1.4.2 yamt sizing; some sections will already have os->size set, others
3175 1.1.1.1.4.2 yamt will have os->size zero and os->rawsize the previous size. */
3176 1.1.1.1.4.2 yamt hi = os->vma + (!final && os->rawsize ? os->rawsize : os->size);
3177 1.1.1.1.4.2 yamt if (hi < lo)
3178 1.1.1.1.4.2 yamt hi = (bfd_vma) -1;
3179 1.1.1.1.4.2 yamt
3180 1.1.1.1.4.2 yamt if (min_vma > lo)
3181 1.1.1.1.4.2 yamt min_vma = lo;
3182 1.1.1.1.4.2 yamt if (max_vma < hi)
3183 1.1.1.1.4.2 yamt max_vma = hi;
3184 1.1.1.1.4.2 yamt if (os->flags & SEC_SMALL_DATA)
3185 1.1.1.1.4.2 yamt {
3186 1.1.1.1.4.2 yamt if (min_short_vma > lo)
3187 1.1.1.1.4.2 yamt min_short_vma = lo;
3188 1.1.1.1.4.2 yamt if (max_short_vma < hi)
3189 1.1.1.1.4.2 yamt max_short_vma = hi;
3190 1.1.1.1.4.2 yamt }
3191 1.1.1.1.4.2 yamt }
3192 1.1.1.1.4.2 yamt
3193 1.1.1.1.4.2 yamt if (ia64_info->min_short_sec)
3194 1.1.1.1.4.2 yamt {
3195 1.1.1.1.4.2 yamt if (min_short_vma
3196 1.1.1.1.4.2 yamt > (ia64_info->min_short_sec->vma
3197 1.1.1.1.4.2 yamt + ia64_info->min_short_offset))
3198 1.1.1.1.4.2 yamt min_short_vma = (ia64_info->min_short_sec->vma
3199 1.1.1.1.4.2 yamt + ia64_info->min_short_offset);
3200 1.1.1.1.4.2 yamt if (max_short_vma
3201 1.1.1.1.4.2 yamt < (ia64_info->max_short_sec->vma
3202 1.1.1.1.4.2 yamt + ia64_info->max_short_offset))
3203 1.1.1.1.4.2 yamt max_short_vma = (ia64_info->max_short_sec->vma
3204 1.1.1.1.4.2 yamt + ia64_info->max_short_offset);
3205 1.1.1.1.4.2 yamt }
3206 1.1.1.1.4.2 yamt
3207 1.1.1.1.4.2 yamt /* See if the user wants to force a value. */
3208 1.1.1.1.4.2 yamt gp = elf_link_hash_lookup (elf_hash_table (info), "__gp", FALSE,
3209 1.1.1.1.4.2 yamt FALSE, FALSE);
3210 1.1.1.1.4.2 yamt
3211 1.1.1.1.4.2 yamt if (gp
3212 1.1.1.1.4.2 yamt && (gp->root.type == bfd_link_hash_defined
3213 1.1.1.1.4.2 yamt || gp->root.type == bfd_link_hash_defweak))
3214 1.1.1.1.4.2 yamt {
3215 1.1.1.1.4.2 yamt asection *gp_sec = gp->root.u.def.section;
3216 1.1.1.1.4.2 yamt gp_val = (gp->root.u.def.value
3217 1.1.1.1.4.2 yamt + gp_sec->output_section->vma
3218 1.1.1.1.4.2 yamt + gp_sec->output_offset);
3219 1.1.1.1.4.2 yamt }
3220 1.1.1.1.4.2 yamt else
3221 1.1.1.1.4.2 yamt {
3222 1.1.1.1.4.2 yamt /* Pick a sensible value. */
3223 1.1.1.1.4.2 yamt
3224 1.1.1.1.4.2 yamt if (ia64_info->min_short_sec)
3225 1.1.1.1.4.2 yamt {
3226 1.1.1.1.4.2 yamt bfd_vma short_range = max_short_vma - min_short_vma;
3227 1.1.1.1.4.2 yamt
3228 1.1.1.1.4.2 yamt /* If min_short_sec is set, pick one in the middle bewteen
3229 1.1.1.1.4.2 yamt min_short_vma and max_short_vma. */
3230 1.1.1.1.4.2 yamt if (short_range >= 0x400000)
3231 1.1.1.1.4.2 yamt goto overflow;
3232 1.1.1.1.4.2 yamt gp_val = min_short_vma + short_range / 2;
3233 1.1.1.1.4.2 yamt }
3234 1.1.1.1.4.2 yamt else
3235 1.1.1.1.4.2 yamt {
3236 1.1.1.1.4.2 yamt asection *got_sec = ia64_info->root.sgot;
3237 1.1.1.1.4.2 yamt
3238 1.1.1.1.4.2 yamt /* Start with just the address of the .got. */
3239 1.1.1.1.4.2 yamt if (got_sec)
3240 1.1.1.1.4.2 yamt gp_val = got_sec->output_section->vma;
3241 1.1.1.1.4.2 yamt else if (max_short_vma != 0)
3242 1.1.1.1.4.2 yamt gp_val = min_short_vma;
3243 1.1.1.1.4.2 yamt else if (max_vma - min_vma < 0x200000)
3244 1.1.1.1.4.2 yamt gp_val = min_vma;
3245 1.1.1.1.4.2 yamt else
3246 1.1.1.1.4.2 yamt gp_val = max_vma - 0x200000 + 8;
3247 1.1.1.1.4.2 yamt }
3248 1.1.1.1.4.2 yamt
3249 1.1.1.1.4.2 yamt /* If it is possible to address the entire image, but we
3250 1.1.1.1.4.2 yamt don't with the choice above, adjust. */
3251 1.1.1.1.4.2 yamt if (max_vma - min_vma < 0x400000
3252 1.1.1.1.4.2 yamt && (max_vma - gp_val >= 0x200000
3253 1.1.1.1.4.2 yamt || gp_val - min_vma > 0x200000))
3254 1.1.1.1.4.2 yamt gp_val = min_vma + 0x200000;
3255 1.1.1.1.4.2 yamt else if (max_short_vma != 0)
3256 1.1.1.1.4.2 yamt {
3257 1.1.1.1.4.2 yamt /* If we don't cover all the short data, adjust. */
3258 1.1.1.1.4.2 yamt if (max_short_vma - gp_val >= 0x200000)
3259 1.1.1.1.4.2 yamt gp_val = min_short_vma + 0x200000;
3260 1.1.1.1.4.2 yamt
3261 1.1.1.1.4.2 yamt /* If we're addressing stuff past the end, adjust back. */
3262 1.1.1.1.4.2 yamt if (gp_val > max_vma)
3263 1.1.1.1.4.2 yamt gp_val = max_vma - 0x200000 + 8;
3264 1.1.1.1.4.2 yamt }
3265 1.1.1.1.4.2 yamt }
3266 1.1.1.1.4.2 yamt
3267 1.1.1.1.4.2 yamt /* Validate whether all SHF_IA_64_SHORT sections are within
3268 1.1.1.1.4.2 yamt range of the chosen GP. */
3269 1.1.1.1.4.2 yamt
3270 1.1.1.1.4.2 yamt if (max_short_vma != 0)
3271 1.1.1.1.4.2 yamt {
3272 1.1.1.1.4.2 yamt if (max_short_vma - min_short_vma >= 0x400000)
3273 1.1.1.1.4.2 yamt {
3274 1.1.1.1.4.2 yamt overflow:
3275 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3276 1.1.1.1.4.2 yamt (_("%s: short data segment overflowed (0x%lx >= 0x400000)"),
3277 1.1.1.1.4.2 yamt bfd_get_filename (abfd),
3278 1.1.1.1.4.2 yamt (unsigned long) (max_short_vma - min_short_vma));
3279 1.1.1.1.4.2 yamt return FALSE;
3280 1.1.1.1.4.2 yamt }
3281 1.1.1.1.4.2 yamt else if ((gp_val > min_short_vma
3282 1.1.1.1.4.2 yamt && gp_val - min_short_vma > 0x200000)
3283 1.1.1.1.4.2 yamt || (gp_val < max_short_vma
3284 1.1.1.1.4.2 yamt && max_short_vma - gp_val >= 0x200000))
3285 1.1.1.1.4.2 yamt {
3286 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3287 1.1.1.1.4.2 yamt (_("%s: __gp does not cover short data segment"),
3288 1.1.1.1.4.2 yamt bfd_get_filename (abfd));
3289 1.1.1.1.4.2 yamt return FALSE;
3290 1.1.1.1.4.2 yamt }
3291 1.1.1.1.4.2 yamt }
3292 1.1.1.1.4.2 yamt
3293 1.1.1.1.4.2 yamt _bfd_set_gp_value (abfd, gp_val);
3294 1.1.1.1.4.2 yamt
3295 1.1.1.1.4.2 yamt return TRUE;
3296 1.1.1.1.4.2 yamt }
3297 1.1.1.1.4.2 yamt
3298 1.1.1.1.4.2 yamt static bfd_boolean
3299 1.1.1.1.4.2 yamt elf64_ia64_final_link (bfd *abfd, struct bfd_link_info *info)
3300 1.1.1.1.4.2 yamt {
3301 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3302 1.1.1.1.4.2 yamt asection *unwind_output_sec;
3303 1.1.1.1.4.2 yamt
3304 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3305 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3306 1.1.1.1.4.2 yamt return FALSE;
3307 1.1.1.1.4.2 yamt
3308 1.1.1.1.4.2 yamt /* Make sure we've got ourselves a nice fat __gp value. */
3309 1.1.1.1.4.2 yamt if (!info->relocatable)
3310 1.1.1.1.4.2 yamt {
3311 1.1.1.1.4.2 yamt bfd_vma gp_val;
3312 1.1.1.1.4.2 yamt struct elf_link_hash_entry *gp;
3313 1.1.1.1.4.2 yamt
3314 1.1.1.1.4.2 yamt /* We assume after gp is set, section size will only decrease. We
3315 1.1.1.1.4.2 yamt need to adjust gp for it. */
3316 1.1.1.1.4.2 yamt _bfd_set_gp_value (abfd, 0);
3317 1.1.1.1.4.2 yamt if (! elf64_ia64_choose_gp (abfd, info, TRUE))
3318 1.1.1.1.4.2 yamt return FALSE;
3319 1.1.1.1.4.2 yamt gp_val = _bfd_get_gp_value (abfd);
3320 1.1.1.1.4.2 yamt
3321 1.1.1.1.4.2 yamt gp = elf_link_hash_lookup (elf_hash_table (info), "__gp", FALSE,
3322 1.1.1.1.4.2 yamt FALSE, FALSE);
3323 1.1.1.1.4.2 yamt if (gp)
3324 1.1.1.1.4.2 yamt {
3325 1.1.1.1.4.2 yamt gp->root.type = bfd_link_hash_defined;
3326 1.1.1.1.4.2 yamt gp->root.u.def.value = gp_val;
3327 1.1.1.1.4.2 yamt gp->root.u.def.section = bfd_abs_section_ptr;
3328 1.1.1.1.4.2 yamt }
3329 1.1.1.1.4.2 yamt }
3330 1.1.1.1.4.2 yamt
3331 1.1.1.1.4.2 yamt /* If we're producing a final executable, we need to sort the contents
3332 1.1.1.1.4.2 yamt of the .IA_64.unwind section. Force this section to be relocated
3333 1.1.1.1.4.2 yamt into memory rather than written immediately to the output file. */
3334 1.1.1.1.4.2 yamt unwind_output_sec = NULL;
3335 1.1.1.1.4.2 yamt if (!info->relocatable)
3336 1.1.1.1.4.2 yamt {
3337 1.1.1.1.4.2 yamt asection *s = bfd_get_section_by_name (abfd, ELF_STRING_ia64_unwind);
3338 1.1.1.1.4.2 yamt if (s)
3339 1.1.1.1.4.2 yamt {
3340 1.1.1.1.4.2 yamt unwind_output_sec = s->output_section;
3341 1.1.1.1.4.2 yamt unwind_output_sec->contents
3342 1.1.1.1.4.2 yamt = bfd_malloc (unwind_output_sec->size);
3343 1.1.1.1.4.2 yamt if (unwind_output_sec->contents == NULL)
3344 1.1.1.1.4.2 yamt return FALSE;
3345 1.1.1.1.4.2 yamt }
3346 1.1.1.1.4.2 yamt }
3347 1.1.1.1.4.2 yamt
3348 1.1.1.1.4.2 yamt /* Invoke the regular ELF backend linker to do all the work. */
3349 1.1.1.1.4.2 yamt if (!bfd_elf_final_link (abfd, info))
3350 1.1.1.1.4.2 yamt return FALSE;
3351 1.1.1.1.4.2 yamt
3352 1.1.1.1.4.2 yamt if (unwind_output_sec)
3353 1.1.1.1.4.2 yamt {
3354 1.1.1.1.4.2 yamt elf64_ia64_unwind_entry_compare_bfd = abfd;
3355 1.1.1.1.4.2 yamt qsort (unwind_output_sec->contents,
3356 1.1.1.1.4.2 yamt (size_t) (unwind_output_sec->size / 24),
3357 1.1.1.1.4.2 yamt 24,
3358 1.1.1.1.4.2 yamt elf64_ia64_unwind_entry_compare);
3359 1.1.1.1.4.2 yamt
3360 1.1.1.1.4.2 yamt if (! bfd_set_section_contents (abfd, unwind_output_sec,
3361 1.1.1.1.4.2 yamt unwind_output_sec->contents, (bfd_vma) 0,
3362 1.1.1.1.4.2 yamt unwind_output_sec->size))
3363 1.1.1.1.4.2 yamt return FALSE;
3364 1.1.1.1.4.2 yamt }
3365 1.1.1.1.4.2 yamt
3366 1.1.1.1.4.2 yamt return TRUE;
3367 1.1.1.1.4.2 yamt }
3368 1.1.1.1.4.2 yamt
3369 1.1.1.1.4.2 yamt static bfd_boolean
3370 1.1.1.1.4.2 yamt elf64_ia64_relocate_section (bfd *output_bfd,
3371 1.1.1.1.4.2 yamt struct bfd_link_info *info,
3372 1.1.1.1.4.2 yamt bfd *input_bfd,
3373 1.1.1.1.4.2 yamt asection *input_section,
3374 1.1.1.1.4.2 yamt bfd_byte *contents,
3375 1.1.1.1.4.2 yamt Elf_Internal_Rela *relocs,
3376 1.1.1.1.4.2 yamt Elf_Internal_Sym *local_syms,
3377 1.1.1.1.4.2 yamt asection **local_sections)
3378 1.1.1.1.4.2 yamt {
3379 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3380 1.1.1.1.4.2 yamt Elf_Internal_Shdr *symtab_hdr;
3381 1.1.1.1.4.2 yamt Elf_Internal_Rela *rel;
3382 1.1.1.1.4.2 yamt Elf_Internal_Rela *relend;
3383 1.1.1.1.4.2 yamt bfd_boolean ret_val = TRUE; /* for non-fatal errors */
3384 1.1.1.1.4.2 yamt bfd_vma gp_val;
3385 1.1.1.1.4.2 yamt
3386 1.1.1.1.4.2 yamt symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
3387 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3388 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3389 1.1.1.1.4.2 yamt return FALSE;
3390 1.1.1.1.4.2 yamt
3391 1.1.1.1.4.2 yamt /* Infect various flags from the input section to the output section. */
3392 1.1.1.1.4.2 yamt if (info->relocatable)
3393 1.1.1.1.4.2 yamt {
3394 1.1.1.1.4.2 yamt bfd_vma flags;
3395 1.1.1.1.4.2 yamt
3396 1.1.1.1.4.2 yamt flags = elf_section_data(input_section)->this_hdr.sh_flags;
3397 1.1.1.1.4.2 yamt flags &= SHF_IA_64_NORECOV;
3398 1.1.1.1.4.2 yamt
3399 1.1.1.1.4.2 yamt elf_section_data(input_section->output_section)
3400 1.1.1.1.4.2 yamt ->this_hdr.sh_flags |= flags;
3401 1.1.1.1.4.2 yamt }
3402 1.1.1.1.4.2 yamt
3403 1.1.1.1.4.2 yamt gp_val = _bfd_get_gp_value (output_bfd);
3404 1.1.1.1.4.2 yamt
3405 1.1.1.1.4.2 yamt rel = relocs;
3406 1.1.1.1.4.2 yamt relend = relocs + input_section->reloc_count;
3407 1.1.1.1.4.2 yamt for (; rel < relend; ++rel)
3408 1.1.1.1.4.2 yamt {
3409 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h;
3410 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
3411 1.1.1.1.4.2 yamt bfd_reloc_status_type r;
3412 1.1.1.1.4.2 yamt reloc_howto_type *howto;
3413 1.1.1.1.4.2 yamt unsigned long r_symndx;
3414 1.1.1.1.4.2 yamt Elf_Internal_Sym *sym;
3415 1.1.1.1.4.2 yamt unsigned int r_type;
3416 1.1.1.1.4.2 yamt bfd_vma value;
3417 1.1.1.1.4.2 yamt asection *sym_sec;
3418 1.1.1.1.4.2 yamt bfd_byte *hit_addr;
3419 1.1.1.1.4.2 yamt bfd_boolean dynamic_symbol_p;
3420 1.1.1.1.4.2 yamt bfd_boolean undef_weak_ref;
3421 1.1.1.1.4.2 yamt
3422 1.1.1.1.4.2 yamt r_type = ELF64_R_TYPE (rel->r_info);
3423 1.1.1.1.4.2 yamt if (r_type > R_IA64_MAX_RELOC_CODE)
3424 1.1.1.1.4.2 yamt {
3425 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3426 1.1.1.1.4.2 yamt (_("%B: unknown relocation type %d"),
3427 1.1.1.1.4.2 yamt input_bfd, (int) r_type);
3428 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
3429 1.1.1.1.4.2 yamt ret_val = FALSE;
3430 1.1.1.1.4.2 yamt continue;
3431 1.1.1.1.4.2 yamt }
3432 1.1.1.1.4.2 yamt
3433 1.1.1.1.4.2 yamt howto = ia64_elf_lookup_howto (r_type);
3434 1.1.1.1.4.2 yamt r_symndx = ELF64_R_SYM (rel->r_info);
3435 1.1.1.1.4.2 yamt h = NULL;
3436 1.1.1.1.4.2 yamt sym = NULL;
3437 1.1.1.1.4.2 yamt sym_sec = NULL;
3438 1.1.1.1.4.2 yamt undef_weak_ref = FALSE;
3439 1.1.1.1.4.2 yamt
3440 1.1.1.1.4.2 yamt if (r_symndx < symtab_hdr->sh_info)
3441 1.1.1.1.4.2 yamt {
3442 1.1.1.1.4.2 yamt /* Reloc against local symbol. */
3443 1.1.1.1.4.2 yamt asection *msec;
3444 1.1.1.1.4.2 yamt sym = local_syms + r_symndx;
3445 1.1.1.1.4.2 yamt sym_sec = local_sections[r_symndx];
3446 1.1.1.1.4.2 yamt msec = sym_sec;
3447 1.1.1.1.4.2 yamt value = _bfd_elf_rela_local_sym (output_bfd, sym, &msec, rel);
3448 1.1.1.1.4.2 yamt if (!info->relocatable
3449 1.1.1.1.4.2 yamt && (sym_sec->flags & SEC_MERGE) != 0
3450 1.1.1.1.4.2 yamt && ELF_ST_TYPE (sym->st_info) == STT_SECTION
3451 1.1.1.1.4.2 yamt && sym_sec->sec_info_type == SEC_INFO_TYPE_MERGE)
3452 1.1.1.1.4.2 yamt {
3453 1.1.1.1.4.2 yamt struct elf64_ia64_local_hash_entry *loc_h;
3454 1.1.1.1.4.2 yamt
3455 1.1.1.1.4.2 yamt loc_h = get_local_sym_hash (ia64_info, input_bfd, rel, FALSE);
3456 1.1.1.1.4.2 yamt if (loc_h && ! loc_h->sec_merge_done)
3457 1.1.1.1.4.2 yamt {
3458 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dynent;
3459 1.1.1.1.4.2 yamt unsigned int count;
3460 1.1.1.1.4.2 yamt
3461 1.1.1.1.4.2 yamt for (count = loc_h->count, dynent = loc_h->info;
3462 1.1.1.1.4.2 yamt count != 0;
3463 1.1.1.1.4.2 yamt count--, dynent++)
3464 1.1.1.1.4.2 yamt {
3465 1.1.1.1.4.2 yamt msec = sym_sec;
3466 1.1.1.1.4.2 yamt dynent->addend =
3467 1.1.1.1.4.2 yamt _bfd_merged_section_offset (output_bfd, &msec,
3468 1.1.1.1.4.2 yamt elf_section_data (msec)->
3469 1.1.1.1.4.2 yamt sec_info,
3470 1.1.1.1.4.2 yamt sym->st_value
3471 1.1.1.1.4.2 yamt + dynent->addend);
3472 1.1.1.1.4.2 yamt dynent->addend -= sym->st_value;
3473 1.1.1.1.4.2 yamt dynent->addend += msec->output_section->vma
3474 1.1.1.1.4.2 yamt + msec->output_offset
3475 1.1.1.1.4.2 yamt - sym_sec->output_section->vma
3476 1.1.1.1.4.2 yamt - sym_sec->output_offset;
3477 1.1.1.1.4.2 yamt }
3478 1.1.1.1.4.2 yamt
3479 1.1.1.1.4.2 yamt /* We may have introduced duplicated entries. We need
3480 1.1.1.1.4.2 yamt to remove them properly. */
3481 1.1.1.1.4.2 yamt count = sort_dyn_sym_info (loc_h->info, loc_h->count);
3482 1.1.1.1.4.2 yamt if (count != loc_h->count)
3483 1.1.1.1.4.2 yamt {
3484 1.1.1.1.4.2 yamt loc_h->count = count;
3485 1.1.1.1.4.2 yamt loc_h->sorted_count = count;
3486 1.1.1.1.4.2 yamt }
3487 1.1.1.1.4.2 yamt
3488 1.1.1.1.4.2 yamt loc_h->sec_merge_done = 1;
3489 1.1.1.1.4.2 yamt }
3490 1.1.1.1.4.2 yamt }
3491 1.1.1.1.4.2 yamt }
3492 1.1.1.1.4.2 yamt else
3493 1.1.1.1.4.2 yamt {
3494 1.1.1.1.4.2 yamt bfd_boolean unresolved_reloc;
3495 1.1.1.1.4.2 yamt bfd_boolean warned;
3496 1.1.1.1.4.2 yamt struct elf_link_hash_entry **sym_hashes = elf_sym_hashes (input_bfd);
3497 1.1.1.1.4.2 yamt
3498 1.1.1.1.4.2 yamt RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
3499 1.1.1.1.4.2 yamt r_symndx, symtab_hdr, sym_hashes,
3500 1.1.1.1.4.2 yamt h, sym_sec, value,
3501 1.1.1.1.4.2 yamt unresolved_reloc, warned);
3502 1.1.1.1.4.2 yamt
3503 1.1.1.1.4.2 yamt if (h->root.type == bfd_link_hash_undefweak)
3504 1.1.1.1.4.2 yamt undef_weak_ref = TRUE;
3505 1.1.1.1.4.2 yamt else if (warned)
3506 1.1.1.1.4.2 yamt continue;
3507 1.1.1.1.4.2 yamt }
3508 1.1.1.1.4.2 yamt
3509 1.1.1.1.4.2 yamt /* For relocs against symbols from removed linkonce sections,
3510 1.1.1.1.4.2 yamt or sections discarded by a linker script, we just want the
3511 1.1.1.1.4.2 yamt section contents zeroed. Avoid any special processing. */
3512 1.1.1.1.4.2 yamt if (sym_sec != NULL && discarded_section (sym_sec))
3513 1.1.1.1.4.2 yamt RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
3514 1.1.1.1.4.2 yamt rel, 1, relend, howto, 0, contents);
3515 1.1.1.1.4.2 yamt
3516 1.1.1.1.4.2 yamt if (info->relocatable)
3517 1.1.1.1.4.2 yamt continue;
3518 1.1.1.1.4.2 yamt
3519 1.1.1.1.4.2 yamt hit_addr = contents + rel->r_offset;
3520 1.1.1.1.4.2 yamt value += rel->r_addend;
3521 1.1.1.1.4.2 yamt dynamic_symbol_p = elf64_ia64_dynamic_symbol_p (h);
3522 1.1.1.1.4.2 yamt
3523 1.1.1.1.4.2 yamt switch (r_type)
3524 1.1.1.1.4.2 yamt {
3525 1.1.1.1.4.2 yamt case R_IA64_NONE:
3526 1.1.1.1.4.2 yamt case R_IA64_LDXMOV:
3527 1.1.1.1.4.2 yamt continue;
3528 1.1.1.1.4.2 yamt
3529 1.1.1.1.4.2 yamt case R_IA64_IMM14:
3530 1.1.1.1.4.2 yamt case R_IA64_IMM22:
3531 1.1.1.1.4.2 yamt case R_IA64_IMM64:
3532 1.1.1.1.4.2 yamt case R_IA64_DIR32MSB:
3533 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
3534 1.1.1.1.4.2 yamt case R_IA64_DIR64MSB:
3535 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
3536 1.1.1.1.4.2 yamt /* Install a dynamic relocation for this reloc. */
3537 1.1.1.1.4.2 yamt if ((dynamic_symbol_p || info->shared)
3538 1.1.1.1.4.2 yamt && r_symndx != 0
3539 1.1.1.1.4.2 yamt && (input_section->flags & SEC_ALLOC) != 0)
3540 1.1.1.1.4.2 yamt {
3541 1.1.1.1.4.2 yamt unsigned int dyn_r_type;
3542 1.1.1.1.4.2 yamt bfd_vma addend;
3543 1.1.1.1.4.2 yamt
3544 1.1.1.1.4.2 yamt switch (r_type)
3545 1.1.1.1.4.2 yamt {
3546 1.1.1.1.4.2 yamt case R_IA64_IMM14:
3547 1.1.1.1.4.2 yamt case R_IA64_IMM22:
3548 1.1.1.1.4.2 yamt case R_IA64_IMM64:
3549 1.1.1.1.4.2 yamt /* ??? People shouldn't be doing non-pic code in
3550 1.1.1.1.4.2 yamt shared libraries nor dynamic executables. */
3551 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3552 1.1.1.1.4.2 yamt (_("%B: non-pic code with imm relocation against dynamic symbol `%s'"),
3553 1.1.1.1.4.2 yamt input_bfd,
3554 1.1.1.1.4.2 yamt h ? h->root.root.string
3555 1.1.1.1.4.2 yamt : bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
3556 1.1.1.1.4.2 yamt sym_sec));
3557 1.1.1.1.4.2 yamt ret_val = FALSE;
3558 1.1.1.1.4.2 yamt continue;
3559 1.1.1.1.4.2 yamt
3560 1.1.1.1.4.2 yamt default:
3561 1.1.1.1.4.2 yamt break;
3562 1.1.1.1.4.2 yamt }
3563 1.1.1.1.4.2 yamt
3564 1.1.1.1.4.2 yamt /* If we don't need dynamic symbol lookup, find a
3565 1.1.1.1.4.2 yamt matching RELATIVE relocation. */
3566 1.1.1.1.4.2 yamt dyn_r_type = r_type;
3567 1.1.1.1.4.2 yamt if (dynamic_symbol_p)
3568 1.1.1.1.4.2 yamt {
3569 1.1.1.1.4.2 yamt addend = rel->r_addend;
3570 1.1.1.1.4.2 yamt value = 0;
3571 1.1.1.1.4.2 yamt }
3572 1.1.1.1.4.2 yamt else
3573 1.1.1.1.4.2 yamt {
3574 1.1.1.1.4.2 yamt addend = value;
3575 1.1.1.1.4.2 yamt }
3576 1.1.1.1.4.2 yamt
3577 1.1.1.1.4.2 yamt /* VMS: install a FIX64. */
3578 1.1.1.1.4.2 yamt switch (dyn_r_type)
3579 1.1.1.1.4.2 yamt {
3580 1.1.1.1.4.2 yamt case R_IA64_DIR32LSB:
3581 1.1.1.1.4.2 yamt dyn_r_type = R_IA64_VMS_FIX32;
3582 1.1.1.1.4.2 yamt break;
3583 1.1.1.1.4.2 yamt case R_IA64_DIR64LSB:
3584 1.1.1.1.4.2 yamt dyn_r_type = R_IA64_VMS_FIX64;
3585 1.1.1.1.4.2 yamt break;
3586 1.1.1.1.4.2 yamt default:
3587 1.1.1.1.4.2 yamt BFD_ASSERT (FALSE);
3588 1.1.1.1.4.2 yamt break;
3589 1.1.1.1.4.2 yamt }
3590 1.1.1.1.4.2 yamt elf64_ia64_install_fixup
3591 1.1.1.1.4.2 yamt (output_bfd, ia64_info, h,
3592 1.1.1.1.4.2 yamt dyn_r_type, input_section, rel->r_offset, addend);
3593 1.1.1.1.4.2 yamt r = bfd_reloc_ok;
3594 1.1.1.1.4.2 yamt break;
3595 1.1.1.1.4.2 yamt }
3596 1.1.1.1.4.2 yamt /* Fall through. */
3597 1.1.1.1.4.2 yamt
3598 1.1.1.1.4.2 yamt case R_IA64_LTV32MSB:
3599 1.1.1.1.4.2 yamt case R_IA64_LTV32LSB:
3600 1.1.1.1.4.2 yamt case R_IA64_LTV64MSB:
3601 1.1.1.1.4.2 yamt case R_IA64_LTV64LSB:
3602 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3603 1.1.1.1.4.2 yamt break;
3604 1.1.1.1.4.2 yamt
3605 1.1.1.1.4.2 yamt case R_IA64_GPREL22:
3606 1.1.1.1.4.2 yamt case R_IA64_GPREL64I:
3607 1.1.1.1.4.2 yamt case R_IA64_GPREL32MSB:
3608 1.1.1.1.4.2 yamt case R_IA64_GPREL32LSB:
3609 1.1.1.1.4.2 yamt case R_IA64_GPREL64MSB:
3610 1.1.1.1.4.2 yamt case R_IA64_GPREL64LSB:
3611 1.1.1.1.4.2 yamt if (dynamic_symbol_p)
3612 1.1.1.1.4.2 yamt {
3613 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3614 1.1.1.1.4.2 yamt (_("%B: @gprel relocation against dynamic symbol %s"),
3615 1.1.1.1.4.2 yamt input_bfd,
3616 1.1.1.1.4.2 yamt h ? h->root.root.string
3617 1.1.1.1.4.2 yamt : bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
3618 1.1.1.1.4.2 yamt sym_sec));
3619 1.1.1.1.4.2 yamt ret_val = FALSE;
3620 1.1.1.1.4.2 yamt continue;
3621 1.1.1.1.4.2 yamt }
3622 1.1.1.1.4.2 yamt value -= gp_val;
3623 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3624 1.1.1.1.4.2 yamt break;
3625 1.1.1.1.4.2 yamt
3626 1.1.1.1.4.2 yamt case R_IA64_LTOFF22:
3627 1.1.1.1.4.2 yamt case R_IA64_LTOFF22X:
3628 1.1.1.1.4.2 yamt case R_IA64_LTOFF64I:
3629 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, FALSE);
3630 1.1.1.1.4.2 yamt value = set_got_entry (input_bfd, info, dyn_i,
3631 1.1.1.1.4.2 yamt rel->r_addend, value, R_IA64_DIR64LSB);
3632 1.1.1.1.4.2 yamt value -= gp_val;
3633 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3634 1.1.1.1.4.2 yamt break;
3635 1.1.1.1.4.2 yamt
3636 1.1.1.1.4.2 yamt case R_IA64_PLTOFF22:
3637 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64I:
3638 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64MSB:
3639 1.1.1.1.4.2 yamt case R_IA64_PLTOFF64LSB:
3640 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, FALSE);
3641 1.1.1.1.4.2 yamt value = set_pltoff_entry (output_bfd, info, dyn_i, value, FALSE);
3642 1.1.1.1.4.2 yamt value -= gp_val;
3643 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3644 1.1.1.1.4.2 yamt break;
3645 1.1.1.1.4.2 yamt
3646 1.1.1.1.4.2 yamt case R_IA64_FPTR64I:
3647 1.1.1.1.4.2 yamt case R_IA64_FPTR32MSB:
3648 1.1.1.1.4.2 yamt case R_IA64_FPTR32LSB:
3649 1.1.1.1.4.2 yamt case R_IA64_FPTR64MSB:
3650 1.1.1.1.4.2 yamt case R_IA64_FPTR64LSB:
3651 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, FALSE);
3652 1.1.1.1.4.2 yamt if (dyn_i->want_fptr)
3653 1.1.1.1.4.2 yamt {
3654 1.1.1.1.4.2 yamt if (!undef_weak_ref)
3655 1.1.1.1.4.2 yamt value = set_fptr_entry (output_bfd, info, dyn_i, value);
3656 1.1.1.1.4.2 yamt }
3657 1.1.1.1.4.2 yamt if (!dyn_i->want_fptr || info->pie)
3658 1.1.1.1.4.2 yamt {
3659 1.1.1.1.4.2 yamt /* Otherwise, we expect the dynamic linker to create
3660 1.1.1.1.4.2 yamt the entry. */
3661 1.1.1.1.4.2 yamt
3662 1.1.1.1.4.2 yamt if (dyn_i->want_fptr)
3663 1.1.1.1.4.2 yamt {
3664 1.1.1.1.4.2 yamt if (r_type == R_IA64_FPTR64I)
3665 1.1.1.1.4.2 yamt {
3666 1.1.1.1.4.2 yamt /* We can't represent this without a dynamic symbol.
3667 1.1.1.1.4.2 yamt Adjust the relocation to be against an output
3668 1.1.1.1.4.2 yamt section symbol, which are always present in the
3669 1.1.1.1.4.2 yamt dynamic symbol table. */
3670 1.1.1.1.4.2 yamt /* ??? People shouldn't be doing non-pic code in
3671 1.1.1.1.4.2 yamt shared libraries. Hork. */
3672 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3673 1.1.1.1.4.2 yamt (_("%B: linking non-pic code in a position independent executable"),
3674 1.1.1.1.4.2 yamt input_bfd);
3675 1.1.1.1.4.2 yamt ret_val = FALSE;
3676 1.1.1.1.4.2 yamt continue;
3677 1.1.1.1.4.2 yamt }
3678 1.1.1.1.4.2 yamt }
3679 1.1.1.1.4.2 yamt else
3680 1.1.1.1.4.2 yamt {
3681 1.1.1.1.4.2 yamt value = 0;
3682 1.1.1.1.4.2 yamt }
3683 1.1.1.1.4.2 yamt
3684 1.1.1.1.4.2 yamt /* VMS: FIXFD. */
3685 1.1.1.1.4.2 yamt elf64_ia64_install_fixup
3686 1.1.1.1.4.2 yamt (output_bfd, ia64_info, h, R_IA64_VMS_FIXFD,
3687 1.1.1.1.4.2 yamt input_section, rel->r_offset, 0);
3688 1.1.1.1.4.2 yamt r = bfd_reloc_ok;
3689 1.1.1.1.4.2 yamt break;
3690 1.1.1.1.4.2 yamt }
3691 1.1.1.1.4.2 yamt
3692 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3693 1.1.1.1.4.2 yamt break;
3694 1.1.1.1.4.2 yamt
3695 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR22:
3696 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64I:
3697 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32MSB:
3698 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR32LSB:
3699 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64MSB:
3700 1.1.1.1.4.2 yamt case R_IA64_LTOFF_FPTR64LSB:
3701 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, input_bfd, rel, FALSE);
3702 1.1.1.1.4.2 yamt if (dyn_i->want_fptr)
3703 1.1.1.1.4.2 yamt {
3704 1.1.1.1.4.2 yamt BFD_ASSERT (h == NULL || !h->def_dynamic);
3705 1.1.1.1.4.2 yamt if (!undef_weak_ref)
3706 1.1.1.1.4.2 yamt value = set_fptr_entry (output_bfd, info, dyn_i, value);
3707 1.1.1.1.4.2 yamt }
3708 1.1.1.1.4.2 yamt else
3709 1.1.1.1.4.2 yamt value = 0;
3710 1.1.1.1.4.2 yamt
3711 1.1.1.1.4.2 yamt value = set_got_entry (output_bfd, info, dyn_i,
3712 1.1.1.1.4.2 yamt rel->r_addend, value, R_IA64_FPTR64LSB);
3713 1.1.1.1.4.2 yamt value -= gp_val;
3714 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3715 1.1.1.1.4.2 yamt break;
3716 1.1.1.1.4.2 yamt
3717 1.1.1.1.4.2 yamt case R_IA64_PCREL32MSB:
3718 1.1.1.1.4.2 yamt case R_IA64_PCREL32LSB:
3719 1.1.1.1.4.2 yamt case R_IA64_PCREL64MSB:
3720 1.1.1.1.4.2 yamt case R_IA64_PCREL64LSB:
3721 1.1.1.1.4.2 yamt /* Install a dynamic relocation for this reloc. */
3722 1.1.1.1.4.2 yamt if (dynamic_symbol_p && r_symndx != 0)
3723 1.1.1.1.4.2 yamt {
3724 1.1.1.1.4.2 yamt /* VMS: doesn't exist ??? */
3725 1.1.1.1.4.2 yamt abort ();
3726 1.1.1.1.4.2 yamt }
3727 1.1.1.1.4.2 yamt goto finish_pcrel;
3728 1.1.1.1.4.2 yamt
3729 1.1.1.1.4.2 yamt case R_IA64_PCREL21B:
3730 1.1.1.1.4.2 yamt case R_IA64_PCREL60B:
3731 1.1.1.1.4.2 yamt /* We should have created a PLT entry for any dynamic symbol. */
3732 1.1.1.1.4.2 yamt dyn_i = NULL;
3733 1.1.1.1.4.2 yamt if (h)
3734 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, FALSE);
3735 1.1.1.1.4.2 yamt
3736 1.1.1.1.4.2 yamt if (dyn_i && dyn_i->want_plt2)
3737 1.1.1.1.4.2 yamt {
3738 1.1.1.1.4.2 yamt /* Should have caught this earlier. */
3739 1.1.1.1.4.2 yamt BFD_ASSERT (rel->r_addend == 0);
3740 1.1.1.1.4.2 yamt
3741 1.1.1.1.4.2 yamt value = (ia64_info->root.splt->output_section->vma
3742 1.1.1.1.4.2 yamt + ia64_info->root.splt->output_offset
3743 1.1.1.1.4.2 yamt + dyn_i->plt2_offset);
3744 1.1.1.1.4.2 yamt }
3745 1.1.1.1.4.2 yamt else
3746 1.1.1.1.4.2 yamt {
3747 1.1.1.1.4.2 yamt /* Since there's no PLT entry, Validate that this is
3748 1.1.1.1.4.2 yamt locally defined. */
3749 1.1.1.1.4.2 yamt BFD_ASSERT (undef_weak_ref || sym_sec->output_section != NULL);
3750 1.1.1.1.4.2 yamt
3751 1.1.1.1.4.2 yamt /* If the symbol is undef_weak, we shouldn't be trying
3752 1.1.1.1.4.2 yamt to call it. There's every chance that we'd wind up
3753 1.1.1.1.4.2 yamt with an out-of-range fixup here. Don't bother setting
3754 1.1.1.1.4.2 yamt any value at all. */
3755 1.1.1.1.4.2 yamt if (undef_weak_ref)
3756 1.1.1.1.4.2 yamt continue;
3757 1.1.1.1.4.2 yamt }
3758 1.1.1.1.4.2 yamt goto finish_pcrel;
3759 1.1.1.1.4.2 yamt
3760 1.1.1.1.4.2 yamt case R_IA64_PCREL21BI:
3761 1.1.1.1.4.2 yamt case R_IA64_PCREL21F:
3762 1.1.1.1.4.2 yamt case R_IA64_PCREL21M:
3763 1.1.1.1.4.2 yamt case R_IA64_PCREL22:
3764 1.1.1.1.4.2 yamt case R_IA64_PCREL64I:
3765 1.1.1.1.4.2 yamt /* The PCREL21BI reloc is specifically not intended for use with
3766 1.1.1.1.4.2 yamt dynamic relocs. PCREL21F and PCREL21M are used for speculation
3767 1.1.1.1.4.2 yamt fixup code, and thus probably ought not be dynamic. The
3768 1.1.1.1.4.2 yamt PCREL22 and PCREL64I relocs aren't emitted as dynamic relocs. */
3769 1.1.1.1.4.2 yamt if (dynamic_symbol_p)
3770 1.1.1.1.4.2 yamt {
3771 1.1.1.1.4.2 yamt const char *msg;
3772 1.1.1.1.4.2 yamt
3773 1.1.1.1.4.2 yamt if (r_type == R_IA64_PCREL21BI)
3774 1.1.1.1.4.2 yamt msg = _("%B: @internal branch to dynamic symbol %s");
3775 1.1.1.1.4.2 yamt else if (r_type == R_IA64_PCREL21F || r_type == R_IA64_PCREL21M)
3776 1.1.1.1.4.2 yamt msg = _("%B: speculation fixup to dynamic symbol %s");
3777 1.1.1.1.4.2 yamt else
3778 1.1.1.1.4.2 yamt msg = _("%B: @pcrel relocation against dynamic symbol %s");
3779 1.1.1.1.4.2 yamt (*_bfd_error_handler) (msg, input_bfd,
3780 1.1.1.1.4.2 yamt h ? h->root.root.string
3781 1.1.1.1.4.2 yamt : bfd_elf_sym_name (input_bfd,
3782 1.1.1.1.4.2 yamt symtab_hdr,
3783 1.1.1.1.4.2 yamt sym,
3784 1.1.1.1.4.2 yamt sym_sec));
3785 1.1.1.1.4.2 yamt ret_val = FALSE;
3786 1.1.1.1.4.2 yamt continue;
3787 1.1.1.1.4.2 yamt }
3788 1.1.1.1.4.2 yamt goto finish_pcrel;
3789 1.1.1.1.4.2 yamt
3790 1.1.1.1.4.2 yamt finish_pcrel:
3791 1.1.1.1.4.2 yamt /* Make pc-relative. */
3792 1.1.1.1.4.2 yamt value -= (input_section->output_section->vma
3793 1.1.1.1.4.2 yamt + input_section->output_offset
3794 1.1.1.1.4.2 yamt + rel->r_offset) & ~ (bfd_vma) 0x3;
3795 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3796 1.1.1.1.4.2 yamt break;
3797 1.1.1.1.4.2 yamt
3798 1.1.1.1.4.2 yamt case R_IA64_SEGREL32MSB:
3799 1.1.1.1.4.2 yamt case R_IA64_SEGREL32LSB:
3800 1.1.1.1.4.2 yamt case R_IA64_SEGREL64MSB:
3801 1.1.1.1.4.2 yamt case R_IA64_SEGREL64LSB:
3802 1.1.1.1.4.2 yamt {
3803 1.1.1.1.4.2 yamt /* Find the segment that contains the output_section. */
3804 1.1.1.1.4.2 yamt Elf_Internal_Phdr *p = _bfd_elf_find_segment_containing_section
3805 1.1.1.1.4.2 yamt (output_bfd, sym_sec->output_section);
3806 1.1.1.1.4.2 yamt
3807 1.1.1.1.4.2 yamt if (p == NULL)
3808 1.1.1.1.4.2 yamt {
3809 1.1.1.1.4.2 yamt r = bfd_reloc_notsupported;
3810 1.1.1.1.4.2 yamt }
3811 1.1.1.1.4.2 yamt else
3812 1.1.1.1.4.2 yamt {
3813 1.1.1.1.4.2 yamt /* The VMA of the segment is the vaddr of the associated
3814 1.1.1.1.4.2 yamt program header. */
3815 1.1.1.1.4.2 yamt if (value > p->p_vaddr)
3816 1.1.1.1.4.2 yamt value -= p->p_vaddr;
3817 1.1.1.1.4.2 yamt else
3818 1.1.1.1.4.2 yamt value = 0;
3819 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3820 1.1.1.1.4.2 yamt }
3821 1.1.1.1.4.2 yamt break;
3822 1.1.1.1.4.2 yamt }
3823 1.1.1.1.4.2 yamt
3824 1.1.1.1.4.2 yamt case R_IA64_SECREL32MSB:
3825 1.1.1.1.4.2 yamt case R_IA64_SECREL32LSB:
3826 1.1.1.1.4.2 yamt case R_IA64_SECREL64MSB:
3827 1.1.1.1.4.2 yamt case R_IA64_SECREL64LSB:
3828 1.1.1.1.4.2 yamt /* Make output-section relative to section where the symbol
3829 1.1.1.1.4.2 yamt is defined. PR 475 */
3830 1.1.1.1.4.2 yamt if (sym_sec)
3831 1.1.1.1.4.2 yamt value -= sym_sec->output_section->vma;
3832 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr, value, r_type);
3833 1.1.1.1.4.2 yamt break;
3834 1.1.1.1.4.2 yamt
3835 1.1.1.1.4.2 yamt case R_IA64_IPLTMSB:
3836 1.1.1.1.4.2 yamt case R_IA64_IPLTLSB:
3837 1.1.1.1.4.2 yamt /* Install a dynamic relocation for this reloc. */
3838 1.1.1.1.4.2 yamt if ((dynamic_symbol_p || info->shared)
3839 1.1.1.1.4.2 yamt && (input_section->flags & SEC_ALLOC) != 0)
3840 1.1.1.1.4.2 yamt {
3841 1.1.1.1.4.2 yamt /* VMS: FIXFD ?? */
3842 1.1.1.1.4.2 yamt abort ();
3843 1.1.1.1.4.2 yamt }
3844 1.1.1.1.4.2 yamt
3845 1.1.1.1.4.2 yamt if (r_type == R_IA64_IPLTMSB)
3846 1.1.1.1.4.2 yamt r_type = R_IA64_DIR64MSB;
3847 1.1.1.1.4.2 yamt else
3848 1.1.1.1.4.2 yamt r_type = R_IA64_DIR64LSB;
3849 1.1.1.1.4.2 yamt ia64_elf_install_value (hit_addr, value, r_type);
3850 1.1.1.1.4.2 yamt r = ia64_elf_install_value (hit_addr + 8, gp_val, r_type);
3851 1.1.1.1.4.2 yamt break;
3852 1.1.1.1.4.2 yamt
3853 1.1.1.1.4.2 yamt case R_IA64_TPREL14:
3854 1.1.1.1.4.2 yamt case R_IA64_TPREL22:
3855 1.1.1.1.4.2 yamt case R_IA64_TPREL64I:
3856 1.1.1.1.4.2 yamt r = bfd_reloc_notsupported;
3857 1.1.1.1.4.2 yamt break;
3858 1.1.1.1.4.2 yamt
3859 1.1.1.1.4.2 yamt case R_IA64_DTPREL14:
3860 1.1.1.1.4.2 yamt case R_IA64_DTPREL22:
3861 1.1.1.1.4.2 yamt case R_IA64_DTPREL64I:
3862 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
3863 1.1.1.1.4.2 yamt case R_IA64_DTPREL32MSB:
3864 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
3865 1.1.1.1.4.2 yamt case R_IA64_DTPREL64MSB:
3866 1.1.1.1.4.2 yamt r = bfd_reloc_notsupported;
3867 1.1.1.1.4.2 yamt break;
3868 1.1.1.1.4.2 yamt
3869 1.1.1.1.4.2 yamt case R_IA64_LTOFF_TPREL22:
3870 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPMOD22:
3871 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPREL22:
3872 1.1.1.1.4.2 yamt r = bfd_reloc_notsupported;
3873 1.1.1.1.4.2 yamt break;
3874 1.1.1.1.4.2 yamt
3875 1.1.1.1.4.2 yamt default:
3876 1.1.1.1.4.2 yamt r = bfd_reloc_notsupported;
3877 1.1.1.1.4.2 yamt break;
3878 1.1.1.1.4.2 yamt }
3879 1.1.1.1.4.2 yamt
3880 1.1.1.1.4.2 yamt switch (r)
3881 1.1.1.1.4.2 yamt {
3882 1.1.1.1.4.2 yamt case bfd_reloc_ok:
3883 1.1.1.1.4.2 yamt break;
3884 1.1.1.1.4.2 yamt
3885 1.1.1.1.4.2 yamt case bfd_reloc_undefined:
3886 1.1.1.1.4.2 yamt /* This can happen for global table relative relocs if
3887 1.1.1.1.4.2 yamt __gp is undefined. This is a panic situation so we
3888 1.1.1.1.4.2 yamt don't try to continue. */
3889 1.1.1.1.4.2 yamt (*info->callbacks->undefined_symbol)
3890 1.1.1.1.4.2 yamt (info, "__gp", input_bfd, input_section, rel->r_offset, 1);
3891 1.1.1.1.4.2 yamt return FALSE;
3892 1.1.1.1.4.2 yamt
3893 1.1.1.1.4.2 yamt case bfd_reloc_notsupported:
3894 1.1.1.1.4.2 yamt {
3895 1.1.1.1.4.2 yamt const char *name;
3896 1.1.1.1.4.2 yamt
3897 1.1.1.1.4.2 yamt if (h)
3898 1.1.1.1.4.2 yamt name = h->root.root.string;
3899 1.1.1.1.4.2 yamt else
3900 1.1.1.1.4.2 yamt name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
3901 1.1.1.1.4.2 yamt sym_sec);
3902 1.1.1.1.4.2 yamt if (!(*info->callbacks->warning) (info, _("unsupported reloc"),
3903 1.1.1.1.4.2 yamt name, input_bfd,
3904 1.1.1.1.4.2 yamt input_section, rel->r_offset))
3905 1.1.1.1.4.2 yamt return FALSE;
3906 1.1.1.1.4.2 yamt ret_val = FALSE;
3907 1.1.1.1.4.2 yamt }
3908 1.1.1.1.4.2 yamt break;
3909 1.1.1.1.4.2 yamt
3910 1.1.1.1.4.2 yamt case bfd_reloc_dangerous:
3911 1.1.1.1.4.2 yamt case bfd_reloc_outofrange:
3912 1.1.1.1.4.2 yamt case bfd_reloc_overflow:
3913 1.1.1.1.4.2 yamt default:
3914 1.1.1.1.4.2 yamt {
3915 1.1.1.1.4.2 yamt const char *name;
3916 1.1.1.1.4.2 yamt
3917 1.1.1.1.4.2 yamt if (h)
3918 1.1.1.1.4.2 yamt name = h->root.root.string;
3919 1.1.1.1.4.2 yamt else
3920 1.1.1.1.4.2 yamt name = bfd_elf_sym_name (input_bfd, symtab_hdr, sym,
3921 1.1.1.1.4.2 yamt sym_sec);
3922 1.1.1.1.4.2 yamt
3923 1.1.1.1.4.2 yamt switch (r_type)
3924 1.1.1.1.4.2 yamt {
3925 1.1.1.1.4.2 yamt case R_IA64_TPREL14:
3926 1.1.1.1.4.2 yamt case R_IA64_TPREL22:
3927 1.1.1.1.4.2 yamt case R_IA64_TPREL64I:
3928 1.1.1.1.4.2 yamt case R_IA64_DTPREL14:
3929 1.1.1.1.4.2 yamt case R_IA64_DTPREL22:
3930 1.1.1.1.4.2 yamt case R_IA64_DTPREL64I:
3931 1.1.1.1.4.2 yamt case R_IA64_DTPREL32LSB:
3932 1.1.1.1.4.2 yamt case R_IA64_DTPREL32MSB:
3933 1.1.1.1.4.2 yamt case R_IA64_DTPREL64LSB:
3934 1.1.1.1.4.2 yamt case R_IA64_DTPREL64MSB:
3935 1.1.1.1.4.2 yamt case R_IA64_LTOFF_TPREL22:
3936 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPMOD22:
3937 1.1.1.1.4.2 yamt case R_IA64_LTOFF_DTPREL22:
3938 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3939 1.1.1.1.4.2 yamt (_("%B: missing TLS section for relocation %s against `%s' at 0x%lx in section `%A'."),
3940 1.1.1.1.4.2 yamt input_bfd, input_section, howto->name, name,
3941 1.1.1.1.4.2 yamt rel->r_offset);
3942 1.1.1.1.4.2 yamt break;
3943 1.1.1.1.4.2 yamt
3944 1.1.1.1.4.2 yamt case R_IA64_PCREL21B:
3945 1.1.1.1.4.2 yamt case R_IA64_PCREL21BI:
3946 1.1.1.1.4.2 yamt case R_IA64_PCREL21M:
3947 1.1.1.1.4.2 yamt case R_IA64_PCREL21F:
3948 1.1.1.1.4.2 yamt if (is_elf_hash_table (info->hash))
3949 1.1.1.1.4.2 yamt {
3950 1.1.1.1.4.2 yamt /* Relaxtion is always performed for ELF output.
3951 1.1.1.1.4.2 yamt Overflow failures for those relocations mean
3952 1.1.1.1.4.2 yamt that the section is too big to relax. */
3953 1.1.1.1.4.2 yamt (*_bfd_error_handler)
3954 1.1.1.1.4.2 yamt (_("%B: Can't relax br (%s) to `%s' at 0x%lx in section `%A' with size 0x%lx (> 0x1000000)."),
3955 1.1.1.1.4.2 yamt input_bfd, input_section, howto->name, name,
3956 1.1.1.1.4.2 yamt rel->r_offset, input_section->size);
3957 1.1.1.1.4.2 yamt break;
3958 1.1.1.1.4.2 yamt }
3959 1.1.1.1.4.2 yamt default:
3960 1.1.1.1.4.2 yamt if (!(*info->callbacks->reloc_overflow) (info,
3961 1.1.1.1.4.2 yamt &h->root,
3962 1.1.1.1.4.2 yamt name,
3963 1.1.1.1.4.2 yamt howto->name,
3964 1.1.1.1.4.2 yamt (bfd_vma) 0,
3965 1.1.1.1.4.2 yamt input_bfd,
3966 1.1.1.1.4.2 yamt input_section,
3967 1.1.1.1.4.2 yamt rel->r_offset))
3968 1.1.1.1.4.2 yamt return FALSE;
3969 1.1.1.1.4.2 yamt break;
3970 1.1.1.1.4.2 yamt }
3971 1.1.1.1.4.2 yamt
3972 1.1.1.1.4.2 yamt ret_val = FALSE;
3973 1.1.1.1.4.2 yamt }
3974 1.1.1.1.4.2 yamt break;
3975 1.1.1.1.4.2 yamt }
3976 1.1.1.1.4.2 yamt }
3977 1.1.1.1.4.2 yamt
3978 1.1.1.1.4.2 yamt return ret_val;
3979 1.1.1.1.4.2 yamt }
3980 1.1.1.1.4.2 yamt
3981 1.1.1.1.4.2 yamt static bfd_boolean
3982 1.1.1.1.4.2 yamt elf64_ia64_finish_dynamic_symbol (bfd *output_bfd,
3983 1.1.1.1.4.2 yamt struct bfd_link_info *info,
3984 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h,
3985 1.1.1.1.4.2 yamt Elf_Internal_Sym *sym)
3986 1.1.1.1.4.2 yamt {
3987 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
3988 1.1.1.1.4.2 yamt struct elf64_ia64_dyn_sym_info *dyn_i;
3989 1.1.1.1.4.2 yamt
3990 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
3991 1.1.1.1.4.2 yamt if (ia64_info == NULL)
3992 1.1.1.1.4.2 yamt return FALSE;
3993 1.1.1.1.4.2 yamt
3994 1.1.1.1.4.2 yamt dyn_i = get_dyn_sym_info (ia64_info, h, NULL, NULL, FALSE);
3995 1.1.1.1.4.2 yamt
3996 1.1.1.1.4.2 yamt /* Fill in the PLT data, if required. */
3997 1.1.1.1.4.2 yamt if (dyn_i && dyn_i->want_plt)
3998 1.1.1.1.4.2 yamt {
3999 1.1.1.1.4.2 yamt bfd_byte *loc;
4000 1.1.1.1.4.2 yamt asection *plt_sec;
4001 1.1.1.1.4.2 yamt bfd_vma plt_addr, pltoff_addr, gp_val;
4002 1.1.1.1.4.2 yamt
4003 1.1.1.1.4.2 yamt gp_val = _bfd_get_gp_value (output_bfd);
4004 1.1.1.1.4.2 yamt
4005 1.1.1.1.4.2 yamt plt_sec = ia64_info->root.splt;
4006 1.1.1.1.4.2 yamt plt_addr = 0; /* Not used as overriden by FIXUPs. */
4007 1.1.1.1.4.2 yamt pltoff_addr = set_pltoff_entry (output_bfd, info, dyn_i, plt_addr, TRUE);
4008 1.1.1.1.4.2 yamt
4009 1.1.1.1.4.2 yamt /* Initialize the FULL PLT entry, if needed. */
4010 1.1.1.1.4.2 yamt if (dyn_i->want_plt2)
4011 1.1.1.1.4.2 yamt {
4012 1.1.1.1.4.2 yamt loc = plt_sec->contents + dyn_i->plt2_offset;
4013 1.1.1.1.4.2 yamt
4014 1.1.1.1.4.2 yamt memcpy (loc, plt_full_entry, PLT_FULL_ENTRY_SIZE);
4015 1.1.1.1.4.2 yamt ia64_elf_install_value (loc, pltoff_addr - gp_val, R_IA64_IMM22);
4016 1.1.1.1.4.2 yamt
4017 1.1.1.1.4.2 yamt /* Mark the symbol as undefined, rather than as defined in the
4018 1.1.1.1.4.2 yamt plt section. Leave the value alone. */
4019 1.1.1.1.4.2 yamt /* ??? We didn't redefine it in adjust_dynamic_symbol in the
4020 1.1.1.1.4.2 yamt first place. But perhaps elflink.c did some for us. */
4021 1.1.1.1.4.2 yamt if (!h->def_regular)
4022 1.1.1.1.4.2 yamt sym->st_shndx = SHN_UNDEF;
4023 1.1.1.1.4.2 yamt }
4024 1.1.1.1.4.2 yamt
4025 1.1.1.1.4.2 yamt /* VMS: FIXFD. */
4026 1.1.1.1.4.2 yamt elf64_ia64_install_fixup
4027 1.1.1.1.4.2 yamt (output_bfd, ia64_info, h, R_IA64_VMS_FIXFD, ia64_info->pltoff_sec,
4028 1.1.1.1.4.2 yamt pltoff_addr - (ia64_info->pltoff_sec->output_section->vma
4029 1.1.1.1.4.2 yamt + ia64_info->pltoff_sec->output_offset), 0);
4030 1.1.1.1.4.2 yamt }
4031 1.1.1.1.4.2 yamt
4032 1.1.1.1.4.2 yamt /* Mark some specially defined symbols as absolute. */
4033 1.1.1.1.4.2 yamt if (strcmp (h->root.root.string, "_DYNAMIC") == 0
4034 1.1.1.1.4.2 yamt || h == ia64_info->root.hgot
4035 1.1.1.1.4.2 yamt || h == ia64_info->root.hplt)
4036 1.1.1.1.4.2 yamt sym->st_shndx = SHN_ABS;
4037 1.1.1.1.4.2 yamt
4038 1.1.1.1.4.2 yamt return TRUE;
4039 1.1.1.1.4.2 yamt }
4040 1.1.1.1.4.2 yamt
4041 1.1.1.1.4.2 yamt static bfd_boolean
4042 1.1.1.1.4.2 yamt elf64_ia64_finish_dynamic_sections (bfd *abfd,
4043 1.1.1.1.4.2 yamt struct bfd_link_info *info)
4044 1.1.1.1.4.2 yamt {
4045 1.1.1.1.4.2 yamt struct elf64_ia64_link_hash_table *ia64_info;
4046 1.1.1.1.4.2 yamt bfd *dynobj;
4047 1.1.1.1.4.2 yamt
4048 1.1.1.1.4.2 yamt ia64_info = elf64_ia64_hash_table (info);
4049 1.1.1.1.4.2 yamt if (ia64_info == NULL)
4050 1.1.1.1.4.2 yamt return FALSE;
4051 1.1.1.1.4.2 yamt
4052 1.1.1.1.4.2 yamt dynobj = ia64_info->root.dynobj;
4053 1.1.1.1.4.2 yamt
4054 1.1.1.1.4.2 yamt if (elf_hash_table (info)->dynamic_sections_created)
4055 1.1.1.1.4.2 yamt {
4056 1.1.1.1.4.2 yamt Elf64_External_Dyn *dyncon, *dynconend;
4057 1.1.1.1.4.2 yamt asection *sdyn;
4058 1.1.1.1.4.2 yamt asection *unwind_sec;
4059 1.1.1.1.4.2 yamt bfd_vma gp_val;
4060 1.1.1.1.4.2 yamt unsigned int gp_seg;
4061 1.1.1.1.4.2 yamt bfd_vma gp_off;
4062 1.1.1.1.4.2 yamt Elf_Internal_Phdr *phdr;
4063 1.1.1.1.4.2 yamt Elf_Internal_Phdr *base_phdr;
4064 1.1.1.1.4.2 yamt unsigned int unwind_seg = 0;
4065 1.1.1.1.4.2 yamt unsigned int code_seg = 0;
4066 1.1.1.1.4.2 yamt
4067 1.1.1.1.4.2 yamt sdyn = bfd_get_linker_section (dynobj, ".dynamic");
4068 1.1.1.1.4.2 yamt BFD_ASSERT (sdyn != NULL);
4069 1.1.1.1.4.2 yamt dyncon = (Elf64_External_Dyn *) sdyn->contents;
4070 1.1.1.1.4.2 yamt dynconend = (Elf64_External_Dyn *) (sdyn->contents + sdyn->size);
4071 1.1.1.1.4.2 yamt
4072 1.1.1.1.4.2 yamt gp_val = _bfd_get_gp_value (abfd);
4073 1.1.1.1.4.2 yamt phdr = _bfd_elf_find_segment_containing_section
4074 1.1.1.1.4.2 yamt (info->output_bfd, ia64_info->pltoff_sec->output_section);
4075 1.1.1.1.4.2 yamt BFD_ASSERT (phdr != NULL);
4076 1.1.1.1.4.2 yamt base_phdr = elf_tdata (info->output_bfd)->phdr;
4077 1.1.1.1.4.2 yamt gp_seg = phdr - base_phdr;
4078 1.1.1.1.4.2 yamt gp_off = gp_val - phdr->p_vaddr;
4079 1.1.1.1.4.2 yamt
4080 1.1.1.1.4.2 yamt unwind_sec = bfd_get_section_by_name (abfd, ELF_STRING_ia64_unwind);
4081 1.1.1.1.4.2 yamt if (unwind_sec != NULL)
4082 1.1.1.1.4.2 yamt {
4083 1.1.1.1.4.2 yamt asection *code_sec;
4084 1.1.1.1.4.2 yamt
4085 1.1.1.1.4.2 yamt phdr = _bfd_elf_find_segment_containing_section (abfd, unwind_sec);
4086 1.1.1.1.4.2 yamt BFD_ASSERT (phdr != NULL);
4087 1.1.1.1.4.2 yamt unwind_seg = phdr - base_phdr;
4088 1.1.1.1.4.2 yamt
4089 1.1.1.1.4.2 yamt code_sec = bfd_get_section_by_name (abfd, "$CODE$");
4090 1.1.1.1.4.2 yamt phdr = _bfd_elf_find_segment_containing_section (abfd, code_sec);
4091 1.1.1.1.4.2 yamt BFD_ASSERT (phdr != NULL);
4092 1.1.1.1.4.2 yamt code_seg = phdr - base_phdr;
4093 1.1.1.1.4.2 yamt }
4094 1.1.1.1.4.2 yamt
4095 1.1.1.1.4.2 yamt for (; dyncon < dynconend; dyncon++)
4096 1.1.1.1.4.2 yamt {
4097 1.1.1.1.4.2 yamt Elf_Internal_Dyn dyn;
4098 1.1.1.1.4.2 yamt
4099 1.1.1.1.4.2 yamt bfd_elf64_swap_dyn_in (dynobj, dyncon, &dyn);
4100 1.1.1.1.4.2 yamt
4101 1.1.1.1.4.2 yamt switch (dyn.d_tag)
4102 1.1.1.1.4.2 yamt {
4103 1.1.1.1.4.2 yamt case DT_IA_64_VMS_FIXUP_RELA_OFF:
4104 1.1.1.1.4.2 yamt dyn.d_un.d_val +=
4105 1.1.1.1.4.2 yamt (ia64_info->fixups_sec->output_section->vma
4106 1.1.1.1.4.2 yamt + ia64_info->fixups_sec->output_offset)
4107 1.1.1.1.4.2 yamt - (sdyn->output_section->vma + sdyn->output_offset);
4108 1.1.1.1.4.2 yamt break;
4109 1.1.1.1.4.2 yamt
4110 1.1.1.1.4.2 yamt case DT_IA_64_VMS_PLTGOT_OFFSET:
4111 1.1.1.1.4.2 yamt dyn.d_un.d_val = gp_off;
4112 1.1.1.1.4.2 yamt break;
4113 1.1.1.1.4.2 yamt
4114 1.1.1.1.4.2 yamt case DT_IA_64_VMS_PLTGOT_SEG:
4115 1.1.1.1.4.2 yamt dyn.d_un.d_val = gp_seg;
4116 1.1.1.1.4.2 yamt break;
4117 1.1.1.1.4.2 yamt
4118 1.1.1.1.4.2 yamt case DT_IA_64_VMS_UNWINDSZ:
4119 1.1.1.1.4.2 yamt if (unwind_sec == NULL)
4120 1.1.1.1.4.2 yamt {
4121 1.1.1.1.4.2 yamt dyn.d_tag = DT_NULL;
4122 1.1.1.1.4.2 yamt dyn.d_un.d_val = 0xdead;
4123 1.1.1.1.4.2 yamt }
4124 1.1.1.1.4.2 yamt else
4125 1.1.1.1.4.2 yamt dyn.d_un.d_val = unwind_sec->size;
4126 1.1.1.1.4.2 yamt break;
4127 1.1.1.1.4.2 yamt
4128 1.1.1.1.4.2 yamt case DT_IA_64_VMS_UNWIND_CODSEG:
4129 1.1.1.1.4.2 yamt dyn.d_un.d_val = code_seg;
4130 1.1.1.1.4.2 yamt break;
4131 1.1.1.1.4.2 yamt
4132 1.1.1.1.4.2 yamt case DT_IA_64_VMS_UNWIND_INFOSEG:
4133 1.1.1.1.4.2 yamt case DT_IA_64_VMS_UNWIND_SEG:
4134 1.1.1.1.4.2 yamt dyn.d_un.d_val = unwind_seg;
4135 1.1.1.1.4.2 yamt break;
4136 1.1.1.1.4.2 yamt
4137 1.1.1.1.4.2 yamt case DT_IA_64_VMS_UNWIND_OFFSET:
4138 1.1.1.1.4.2 yamt break;
4139 1.1.1.1.4.2 yamt
4140 1.1.1.1.4.2 yamt default:
4141 1.1.1.1.4.2 yamt /* No need to rewrite the entry. */
4142 1.1.1.1.4.2 yamt continue;
4143 1.1.1.1.4.2 yamt }
4144 1.1.1.1.4.2 yamt
4145 1.1.1.1.4.2 yamt bfd_elf64_swap_dyn_out (abfd, &dyn, dyncon);
4146 1.1.1.1.4.2 yamt }
4147 1.1.1.1.4.2 yamt }
4148 1.1.1.1.4.2 yamt
4149 1.1.1.1.4.2 yamt /* Handle transfer addresses. */
4150 1.1.1.1.4.2 yamt {
4151 1.1.1.1.4.2 yamt asection *tfr_sec = ia64_info->transfer_sec;
4152 1.1.1.1.4.2 yamt struct elf64_vms_transfer *tfr;
4153 1.1.1.1.4.2 yamt struct elf_link_hash_entry *tfr3;
4154 1.1.1.1.4.2 yamt
4155 1.1.1.1.4.2 yamt tfr = (struct elf64_vms_transfer *)tfr_sec->contents;
4156 1.1.1.1.4.2 yamt bfd_putl32 (6 * 8, tfr->size);
4157 1.1.1.1.4.2 yamt bfd_putl64 (tfr_sec->output_section->vma
4158 1.1.1.1.4.2 yamt + tfr_sec->output_offset
4159 1.1.1.1.4.2 yamt + 6 * 8, tfr->tfradr3);
4160 1.1.1.1.4.2 yamt
4161 1.1.1.1.4.2 yamt tfr3 = elf_link_hash_lookup (elf_hash_table (info), "ELF$TFRADR", FALSE,
4162 1.1.1.1.4.2 yamt FALSE, FALSE);
4163 1.1.1.1.4.2 yamt
4164 1.1.1.1.4.2 yamt if (tfr3
4165 1.1.1.1.4.2 yamt && (tfr3->root.type == bfd_link_hash_defined
4166 1.1.1.1.4.2 yamt || tfr3->root.type == bfd_link_hash_defweak))
4167 1.1.1.1.4.2 yamt {
4168 1.1.1.1.4.2 yamt asection *tfr3_sec = tfr3->root.u.def.section;
4169 1.1.1.1.4.2 yamt bfd_vma tfr3_val;
4170 1.1.1.1.4.2 yamt
4171 1.1.1.1.4.2 yamt tfr3_val = (tfr3->root.u.def.value
4172 1.1.1.1.4.2 yamt + tfr3_sec->output_section->vma
4173 1.1.1.1.4.2 yamt + tfr3_sec->output_offset);
4174 1.1.1.1.4.2 yamt
4175 1.1.1.1.4.2 yamt bfd_putl64 (tfr3_val, tfr->tfr3_func);
4176 1.1.1.1.4.2 yamt bfd_putl64 (_bfd_get_gp_value (info->output_bfd), tfr->tfr3_gp);
4177 1.1.1.1.4.2 yamt }
4178 1.1.1.1.4.2 yamt
4179 1.1.1.1.4.2 yamt /* FIXME: set linker flags,
4180 1.1.1.1.4.2 yamt handle lib$initialize. */
4181 1.1.1.1.4.2 yamt }
4182 1.1.1.1.4.2 yamt
4183 1.1.1.1.4.2 yamt return TRUE;
4184 1.1.1.1.4.2 yamt }
4185 1.1.1.1.4.2 yamt
4186 1.1.1.1.4.2 yamt /* ELF file flag handling: */
4187 1.1.1.1.4.2 yamt
4188 1.1.1.1.4.2 yamt /* Function to keep IA-64 specific file flags. */
4189 1.1.1.1.4.2 yamt static bfd_boolean
4190 1.1.1.1.4.2 yamt elf64_ia64_set_private_flags (bfd *abfd, flagword flags)
4191 1.1.1.1.4.2 yamt {
4192 1.1.1.1.4.2 yamt BFD_ASSERT (!elf_flags_init (abfd)
4193 1.1.1.1.4.2 yamt || elf_elfheader (abfd)->e_flags == flags);
4194 1.1.1.1.4.2 yamt
4195 1.1.1.1.4.2 yamt elf_elfheader (abfd)->e_flags = flags;
4196 1.1.1.1.4.2 yamt elf_flags_init (abfd) = TRUE;
4197 1.1.1.1.4.2 yamt return TRUE;
4198 1.1.1.1.4.2 yamt }
4199 1.1.1.1.4.2 yamt
4200 1.1.1.1.4.2 yamt /* Merge backend specific data from an object file to the output
4201 1.1.1.1.4.2 yamt object file when linking. */
4202 1.1.1.1.4.2 yamt static bfd_boolean
4203 1.1.1.1.4.2 yamt elf64_ia64_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
4204 1.1.1.1.4.2 yamt {
4205 1.1.1.1.4.2 yamt flagword out_flags;
4206 1.1.1.1.4.2 yamt flagword in_flags;
4207 1.1.1.1.4.2 yamt bfd_boolean ok = TRUE;
4208 1.1.1.1.4.2 yamt
4209 1.1.1.1.4.2 yamt /* Don't even pretend to support mixed-format linking. */
4210 1.1.1.1.4.2 yamt if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
4211 1.1.1.1.4.2 yamt || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
4212 1.1.1.1.4.2 yamt return FALSE;
4213 1.1.1.1.4.2 yamt
4214 1.1.1.1.4.2 yamt in_flags = elf_elfheader (ibfd)->e_flags;
4215 1.1.1.1.4.2 yamt out_flags = elf_elfheader (obfd)->e_flags;
4216 1.1.1.1.4.2 yamt
4217 1.1.1.1.4.2 yamt if (! elf_flags_init (obfd))
4218 1.1.1.1.4.2 yamt {
4219 1.1.1.1.4.2 yamt elf_flags_init (obfd) = TRUE;
4220 1.1.1.1.4.2 yamt elf_elfheader (obfd)->e_flags = in_flags;
4221 1.1.1.1.4.2 yamt
4222 1.1.1.1.4.2 yamt if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
4223 1.1.1.1.4.2 yamt && bfd_get_arch_info (obfd)->the_default)
4224 1.1.1.1.4.2 yamt {
4225 1.1.1.1.4.2 yamt return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd),
4226 1.1.1.1.4.2 yamt bfd_get_mach (ibfd));
4227 1.1.1.1.4.2 yamt }
4228 1.1.1.1.4.2 yamt
4229 1.1.1.1.4.2 yamt return TRUE;
4230 1.1.1.1.4.2 yamt }
4231 1.1.1.1.4.2 yamt
4232 1.1.1.1.4.2 yamt /* Check flag compatibility. */
4233 1.1.1.1.4.2 yamt if (in_flags == out_flags)
4234 1.1.1.1.4.2 yamt return TRUE;
4235 1.1.1.1.4.2 yamt
4236 1.1.1.1.4.2 yamt /* Output has EF_IA_64_REDUCEDFP set only if all inputs have it set. */
4237 1.1.1.1.4.2 yamt if (!(in_flags & EF_IA_64_REDUCEDFP) && (out_flags & EF_IA_64_REDUCEDFP))
4238 1.1.1.1.4.2 yamt elf_elfheader (obfd)->e_flags &= ~EF_IA_64_REDUCEDFP;
4239 1.1.1.1.4.2 yamt
4240 1.1.1.1.4.2 yamt if ((in_flags & EF_IA_64_TRAPNIL) != (out_flags & EF_IA_64_TRAPNIL))
4241 1.1.1.1.4.2 yamt {
4242 1.1.1.1.4.2 yamt (*_bfd_error_handler)
4243 1.1.1.1.4.2 yamt (_("%B: linking trap-on-NULL-dereference with non-trapping files"),
4244 1.1.1.1.4.2 yamt ibfd);
4245 1.1.1.1.4.2 yamt
4246 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4247 1.1.1.1.4.2 yamt ok = FALSE;
4248 1.1.1.1.4.2 yamt }
4249 1.1.1.1.4.2 yamt if ((in_flags & EF_IA_64_BE) != (out_flags & EF_IA_64_BE))
4250 1.1.1.1.4.2 yamt {
4251 1.1.1.1.4.2 yamt (*_bfd_error_handler)
4252 1.1.1.1.4.2 yamt (_("%B: linking big-endian files with little-endian files"),
4253 1.1.1.1.4.2 yamt ibfd);
4254 1.1.1.1.4.2 yamt
4255 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4256 1.1.1.1.4.2 yamt ok = FALSE;
4257 1.1.1.1.4.2 yamt }
4258 1.1.1.1.4.2 yamt if ((in_flags & EF_IA_64_ABI64) != (out_flags & EF_IA_64_ABI64))
4259 1.1.1.1.4.2 yamt {
4260 1.1.1.1.4.2 yamt (*_bfd_error_handler)
4261 1.1.1.1.4.2 yamt (_("%B: linking 64-bit files with 32-bit files"),
4262 1.1.1.1.4.2 yamt ibfd);
4263 1.1.1.1.4.2 yamt
4264 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4265 1.1.1.1.4.2 yamt ok = FALSE;
4266 1.1.1.1.4.2 yamt }
4267 1.1.1.1.4.2 yamt if ((in_flags & EF_IA_64_CONS_GP) != (out_flags & EF_IA_64_CONS_GP))
4268 1.1.1.1.4.2 yamt {
4269 1.1.1.1.4.2 yamt (*_bfd_error_handler)
4270 1.1.1.1.4.2 yamt (_("%B: linking constant-gp files with non-constant-gp files"),
4271 1.1.1.1.4.2 yamt ibfd);
4272 1.1.1.1.4.2 yamt
4273 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4274 1.1.1.1.4.2 yamt ok = FALSE;
4275 1.1.1.1.4.2 yamt }
4276 1.1.1.1.4.2 yamt if ((in_flags & EF_IA_64_NOFUNCDESC_CONS_GP)
4277 1.1.1.1.4.2 yamt != (out_flags & EF_IA_64_NOFUNCDESC_CONS_GP))
4278 1.1.1.1.4.2 yamt {
4279 1.1.1.1.4.2 yamt (*_bfd_error_handler)
4280 1.1.1.1.4.2 yamt (_("%B: linking auto-pic files with non-auto-pic files"),
4281 1.1.1.1.4.2 yamt ibfd);
4282 1.1.1.1.4.2 yamt
4283 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4284 1.1.1.1.4.2 yamt ok = FALSE;
4285 1.1.1.1.4.2 yamt }
4286 1.1.1.1.4.2 yamt
4287 1.1.1.1.4.2 yamt return ok;
4288 1.1.1.1.4.2 yamt }
4289 1.1.1.1.4.2 yamt
4290 1.1.1.1.4.2 yamt static bfd_boolean
4291 1.1.1.1.4.2 yamt elf64_ia64_print_private_bfd_data (bfd *abfd, void * ptr)
4292 1.1.1.1.4.2 yamt {
4293 1.1.1.1.4.2 yamt FILE *file = (FILE *) ptr;
4294 1.1.1.1.4.2 yamt flagword flags = elf_elfheader (abfd)->e_flags;
4295 1.1.1.1.4.2 yamt
4296 1.1.1.1.4.2 yamt BFD_ASSERT (abfd != NULL && ptr != NULL);
4297 1.1.1.1.4.2 yamt
4298 1.1.1.1.4.2 yamt fprintf (file, "private flags = %s%s%s%s%s%s%s%s\n",
4299 1.1.1.1.4.2 yamt (flags & EF_IA_64_TRAPNIL) ? "TRAPNIL, " : "",
4300 1.1.1.1.4.2 yamt (flags & EF_IA_64_EXT) ? "EXT, " : "",
4301 1.1.1.1.4.2 yamt (flags & EF_IA_64_BE) ? "BE, " : "LE, ",
4302 1.1.1.1.4.2 yamt (flags & EF_IA_64_REDUCEDFP) ? "REDUCEDFP, " : "",
4303 1.1.1.1.4.2 yamt (flags & EF_IA_64_CONS_GP) ? "CONS_GP, " : "",
4304 1.1.1.1.4.2 yamt (flags & EF_IA_64_NOFUNCDESC_CONS_GP) ? "NOFUNCDESC_CONS_GP, " : "",
4305 1.1.1.1.4.2 yamt (flags & EF_IA_64_ABSOLUTE) ? "ABSOLUTE, " : "",
4306 1.1.1.1.4.2 yamt (flags & EF_IA_64_ABI64) ? "ABI64" : "ABI32");
4307 1.1.1.1.4.2 yamt
4308 1.1.1.1.4.2 yamt _bfd_elf_print_private_bfd_data (abfd, ptr);
4309 1.1.1.1.4.2 yamt return TRUE;
4310 1.1.1.1.4.2 yamt }
4311 1.1.1.1.4.2 yamt
4312 1.1.1.1.4.2 yamt static enum elf_reloc_type_class
4313 1.1.1.1.4.2 yamt elf64_ia64_reloc_type_class (const Elf_Internal_Rela *rela)
4314 1.1.1.1.4.2 yamt {
4315 1.1.1.1.4.2 yamt switch ((int) ELF64_R_TYPE (rela->r_info))
4316 1.1.1.1.4.2 yamt {
4317 1.1.1.1.4.2 yamt case R_IA64_REL32MSB:
4318 1.1.1.1.4.2 yamt case R_IA64_REL32LSB:
4319 1.1.1.1.4.2 yamt case R_IA64_REL64MSB:
4320 1.1.1.1.4.2 yamt case R_IA64_REL64LSB:
4321 1.1.1.1.4.2 yamt return reloc_class_relative;
4322 1.1.1.1.4.2 yamt case R_IA64_IPLTMSB:
4323 1.1.1.1.4.2 yamt case R_IA64_IPLTLSB:
4324 1.1.1.1.4.2 yamt return reloc_class_plt;
4325 1.1.1.1.4.2 yamt case R_IA64_COPY:
4326 1.1.1.1.4.2 yamt return reloc_class_copy;
4327 1.1.1.1.4.2 yamt default:
4328 1.1.1.1.4.2 yamt return reloc_class_normal;
4329 1.1.1.1.4.2 yamt }
4330 1.1.1.1.4.2 yamt }
4331 1.1.1.1.4.2 yamt
4332 1.1.1.1.4.2 yamt static const struct bfd_elf_special_section elf64_ia64_special_sections[] =
4333 1.1.1.1.4.2 yamt {
4334 1.1.1.1.4.2 yamt { STRING_COMMA_LEN (".sbss"), -1, SHT_NOBITS, SHF_ALLOC + SHF_WRITE + SHF_IA_64_SHORT },
4335 1.1.1.1.4.2 yamt { STRING_COMMA_LEN (".sdata"), -1, SHT_PROGBITS, SHF_ALLOC + SHF_WRITE + SHF_IA_64_SHORT },
4336 1.1.1.1.4.2 yamt { NULL, 0, 0, 0, 0 }
4337 1.1.1.1.4.2 yamt };
4338 1.1.1.1.4.2 yamt
4339 1.1.1.1.4.2 yamt static bfd_boolean
4340 1.1.1.1.4.2 yamt elf64_ia64_object_p (bfd *abfd)
4341 1.1.1.1.4.2 yamt {
4342 1.1.1.1.4.2 yamt asection *sec;
4343 1.1.1.1.4.2 yamt asection *group, *unwi, *unw;
4344 1.1.1.1.4.2 yamt flagword flags;
4345 1.1.1.1.4.2 yamt const char *name;
4346 1.1.1.1.4.2 yamt char *unwi_name, *unw_name;
4347 1.1.1.1.4.2 yamt bfd_size_type amt;
4348 1.1.1.1.4.2 yamt
4349 1.1.1.1.4.2 yamt if (abfd->flags & DYNAMIC)
4350 1.1.1.1.4.2 yamt return TRUE;
4351 1.1.1.1.4.2 yamt
4352 1.1.1.1.4.2 yamt /* Flags for fake group section. */
4353 1.1.1.1.4.2 yamt flags = (SEC_LINKER_CREATED | SEC_GROUP | SEC_LINK_ONCE
4354 1.1.1.1.4.2 yamt | SEC_EXCLUDE);
4355 1.1.1.1.4.2 yamt
4356 1.1.1.1.4.2 yamt /* We add a fake section group for each .gnu.linkonce.t.* section,
4357 1.1.1.1.4.2 yamt which isn't in a section group, and its unwind sections. */
4358 1.1.1.1.4.2 yamt for (sec = abfd->sections; sec != NULL; sec = sec->next)
4359 1.1.1.1.4.2 yamt {
4360 1.1.1.1.4.2 yamt if (elf_sec_group (sec) == NULL
4361 1.1.1.1.4.2 yamt && ((sec->flags & (SEC_LINK_ONCE | SEC_CODE | SEC_GROUP))
4362 1.1.1.1.4.2 yamt == (SEC_LINK_ONCE | SEC_CODE))
4363 1.1.1.1.4.2 yamt && CONST_STRNEQ (sec->name, ".gnu.linkonce.t."))
4364 1.1.1.1.4.2 yamt {
4365 1.1.1.1.4.2 yamt name = sec->name + 16;
4366 1.1.1.1.4.2 yamt
4367 1.1.1.1.4.2 yamt amt = strlen (name) + sizeof (".gnu.linkonce.ia64unwi.");
4368 1.1.1.1.4.2 yamt unwi_name = bfd_alloc (abfd, amt);
4369 1.1.1.1.4.2 yamt if (!unwi_name)
4370 1.1.1.1.4.2 yamt return FALSE;
4371 1.1.1.1.4.2 yamt
4372 1.1.1.1.4.2 yamt strcpy (stpcpy (unwi_name, ".gnu.linkonce.ia64unwi."), name);
4373 1.1.1.1.4.2 yamt unwi = bfd_get_section_by_name (abfd, unwi_name);
4374 1.1.1.1.4.2 yamt
4375 1.1.1.1.4.2 yamt amt = strlen (name) + sizeof (".gnu.linkonce.ia64unw.");
4376 1.1.1.1.4.2 yamt unw_name = bfd_alloc (abfd, amt);
4377 1.1.1.1.4.2 yamt if (!unw_name)
4378 1.1.1.1.4.2 yamt return FALSE;
4379 1.1.1.1.4.2 yamt
4380 1.1.1.1.4.2 yamt strcpy (stpcpy (unw_name, ".gnu.linkonce.ia64unw."), name);
4381 1.1.1.1.4.2 yamt unw = bfd_get_section_by_name (abfd, unw_name);
4382 1.1.1.1.4.2 yamt
4383 1.1.1.1.4.2 yamt /* We need to create a fake group section for it and its
4384 1.1.1.1.4.2 yamt unwind sections. */
4385 1.1.1.1.4.2 yamt group = bfd_make_section_anyway_with_flags (abfd, name,
4386 1.1.1.1.4.2 yamt flags);
4387 1.1.1.1.4.2 yamt if (group == NULL)
4388 1.1.1.1.4.2 yamt return FALSE;
4389 1.1.1.1.4.2 yamt
4390 1.1.1.1.4.2 yamt /* Move the fake group section to the beginning. */
4391 1.1.1.1.4.2 yamt bfd_section_list_remove (abfd, group);
4392 1.1.1.1.4.2 yamt bfd_section_list_prepend (abfd, group);
4393 1.1.1.1.4.2 yamt
4394 1.1.1.1.4.2 yamt elf_next_in_group (group) = sec;
4395 1.1.1.1.4.2 yamt
4396 1.1.1.1.4.2 yamt elf_group_name (sec) = name;
4397 1.1.1.1.4.2 yamt elf_next_in_group (sec) = sec;
4398 1.1.1.1.4.2 yamt elf_sec_group (sec) = group;
4399 1.1.1.1.4.2 yamt
4400 1.1.1.1.4.2 yamt if (unwi)
4401 1.1.1.1.4.2 yamt {
4402 1.1.1.1.4.2 yamt elf_group_name (unwi) = name;
4403 1.1.1.1.4.2 yamt elf_next_in_group (unwi) = sec;
4404 1.1.1.1.4.2 yamt elf_next_in_group (sec) = unwi;
4405 1.1.1.1.4.2 yamt elf_sec_group (unwi) = group;
4406 1.1.1.1.4.2 yamt }
4407 1.1.1.1.4.2 yamt
4408 1.1.1.1.4.2 yamt if (unw)
4409 1.1.1.1.4.2 yamt {
4410 1.1.1.1.4.2 yamt elf_group_name (unw) = name;
4411 1.1.1.1.4.2 yamt if (unwi)
4412 1.1.1.1.4.2 yamt {
4413 1.1.1.1.4.2 yamt elf_next_in_group (unw) = elf_next_in_group (unwi);
4414 1.1.1.1.4.2 yamt elf_next_in_group (unwi) = unw;
4415 1.1.1.1.4.2 yamt }
4416 1.1.1.1.4.2 yamt else
4417 1.1.1.1.4.2 yamt {
4418 1.1.1.1.4.2 yamt elf_next_in_group (unw) = sec;
4419 1.1.1.1.4.2 yamt elf_next_in_group (sec) = unw;
4420 1.1.1.1.4.2 yamt }
4421 1.1.1.1.4.2 yamt elf_sec_group (unw) = group;
4422 1.1.1.1.4.2 yamt }
4423 1.1.1.1.4.2 yamt
4424 1.1.1.1.4.2 yamt /* Fake SHT_GROUP section header. */
4425 1.1.1.1.4.2 yamt elf_section_data (group)->this_hdr.bfd_section = group;
4426 1.1.1.1.4.2 yamt elf_section_data (group)->this_hdr.sh_type = SHT_GROUP;
4427 1.1.1.1.4.2 yamt }
4428 1.1.1.1.4.2 yamt }
4429 1.1.1.1.4.2 yamt return TRUE;
4430 1.1.1.1.4.2 yamt }
4431 1.1.1.1.4.2 yamt
4432 1.1.1.1.4.2 yamt /* Handle an IA-64 specific section when reading an object file. This
4433 1.1.1.1.4.2 yamt is called when bfd_section_from_shdr finds a section with an unknown
4434 1.1.1.1.4.2 yamt type. */
4435 1.1.1.1.4.2 yamt
4436 1.1.1.1.4.2 yamt static bfd_boolean
4437 1.1.1.1.4.2 yamt elf64_vms_section_from_shdr (bfd *abfd,
4438 1.1.1.1.4.2 yamt Elf_Internal_Shdr *hdr,
4439 1.1.1.1.4.2 yamt const char *name,
4440 1.1.1.1.4.2 yamt int shindex)
4441 1.1.1.1.4.2 yamt {
4442 1.1.1.1.4.2 yamt flagword secflags = 0;
4443 1.1.1.1.4.2 yamt
4444 1.1.1.1.4.2 yamt switch (hdr->sh_type)
4445 1.1.1.1.4.2 yamt {
4446 1.1.1.1.4.2 yamt case SHT_IA_64_VMS_TRACE:
4447 1.1.1.1.4.2 yamt case SHT_IA_64_VMS_DEBUG:
4448 1.1.1.1.4.2 yamt case SHT_IA_64_VMS_DEBUG_STR:
4449 1.1.1.1.4.2 yamt secflags = SEC_DEBUGGING;
4450 1.1.1.1.4.2 yamt break;
4451 1.1.1.1.4.2 yamt
4452 1.1.1.1.4.2 yamt case SHT_IA_64_UNWIND:
4453 1.1.1.1.4.2 yamt case SHT_IA_64_HP_OPT_ANOT:
4454 1.1.1.1.4.2 yamt break;
4455 1.1.1.1.4.2 yamt
4456 1.1.1.1.4.2 yamt case SHT_IA_64_EXT:
4457 1.1.1.1.4.2 yamt if (strcmp (name, ELF_STRING_ia64_archext) != 0)
4458 1.1.1.1.4.2 yamt return FALSE;
4459 1.1.1.1.4.2 yamt break;
4460 1.1.1.1.4.2 yamt
4461 1.1.1.1.4.2 yamt default:
4462 1.1.1.1.4.2 yamt return FALSE;
4463 1.1.1.1.4.2 yamt }
4464 1.1.1.1.4.2 yamt
4465 1.1.1.1.4.2 yamt if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex))
4466 1.1.1.1.4.2 yamt return FALSE;
4467 1.1.1.1.4.2 yamt
4468 1.1.1.1.4.2 yamt if (secflags != 0)
4469 1.1.1.1.4.2 yamt {
4470 1.1.1.1.4.2 yamt asection *newsect = hdr->bfd_section;
4471 1.1.1.1.4.2 yamt
4472 1.1.1.1.4.2 yamt if (! bfd_set_section_flags
4473 1.1.1.1.4.2 yamt (abfd, newsect, bfd_get_section_flags (abfd, newsect) | secflags))
4474 1.1.1.1.4.2 yamt return FALSE;
4475 1.1.1.1.4.2 yamt }
4476 1.1.1.1.4.2 yamt
4477 1.1.1.1.4.2 yamt return TRUE;
4478 1.1.1.1.4.2 yamt }
4479 1.1.1.1.4.2 yamt
4480 1.1.1.1.4.2 yamt static bfd_boolean
4481 1.1.1.1.4.2 yamt elf64_vms_object_p (bfd *abfd)
4482 1.1.1.1.4.2 yamt {
4483 1.1.1.1.4.2 yamt Elf_Internal_Ehdr *i_ehdrp = elf_elfheader (abfd);
4484 1.1.1.1.4.2 yamt Elf_Internal_Phdr *i_phdr = elf_tdata (abfd)->phdr;
4485 1.1.1.1.4.2 yamt unsigned int i;
4486 1.1.1.1.4.2 yamt unsigned int num_text = 0;
4487 1.1.1.1.4.2 yamt unsigned int num_data = 0;
4488 1.1.1.1.4.2 yamt unsigned int num_rodata = 0;
4489 1.1.1.1.4.2 yamt char name[16];
4490 1.1.1.1.4.2 yamt
4491 1.1.1.1.4.2 yamt if (!elf64_ia64_object_p (abfd))
4492 1.1.1.1.4.2 yamt return FALSE;
4493 1.1.1.1.4.2 yamt
4494 1.1.1.1.4.2 yamt /* Many VMS compilers do not generate sections for the corresponding
4495 1.1.1.1.4.2 yamt segment. This is boring as binutils tools won't be able to disassemble
4496 1.1.1.1.4.2 yamt the code. So we simply create all the missing sections. */
4497 1.1.1.1.4.2 yamt for (i = 0; i < i_ehdrp->e_phnum; i++, i_phdr++)
4498 1.1.1.1.4.2 yamt {
4499 1.1.1.1.4.2 yamt /* Is there a section for this segment? */
4500 1.1.1.1.4.2 yamt bfd_vma base_vma = i_phdr->p_vaddr;
4501 1.1.1.1.4.2 yamt bfd_vma limit_vma = base_vma + i_phdr->p_filesz;
4502 1.1.1.1.4.2 yamt
4503 1.1.1.1.4.2 yamt if (i_phdr->p_type != PT_LOAD)
4504 1.1.1.1.4.2 yamt continue;
4505 1.1.1.1.4.2 yamt
4506 1.1.1.1.4.2 yamt /* We need to cover from base_vms to limit_vma. */
4507 1.1.1.1.4.2 yamt again:
4508 1.1.1.1.4.2 yamt while (base_vma < limit_vma)
4509 1.1.1.1.4.2 yamt {
4510 1.1.1.1.4.2 yamt bfd_vma next_vma = limit_vma;
4511 1.1.1.1.4.2 yamt asection *nsec;
4512 1.1.1.1.4.2 yamt asection *sec;
4513 1.1.1.1.4.2 yamt flagword flags;
4514 1.1.1.1.4.2 yamt char *nname = NULL;
4515 1.1.1.1.4.2 yamt
4516 1.1.1.1.4.2 yamt /* Find a section covering [base_vma;limit_vma) */
4517 1.1.1.1.4.2 yamt for (sec = abfd->sections; sec != NULL; sec = sec->next)
4518 1.1.1.1.4.2 yamt {
4519 1.1.1.1.4.2 yamt /* Skip uninteresting sections (either not in memory or
4520 1.1.1.1.4.2 yamt below base_vma. */
4521 1.1.1.1.4.2 yamt if ((sec->flags & (SEC_ALLOC | SEC_LOAD)) == 0
4522 1.1.1.1.4.2 yamt || sec->vma + sec->size <= base_vma)
4523 1.1.1.1.4.2 yamt continue;
4524 1.1.1.1.4.2 yamt if (sec->vma <= base_vma)
4525 1.1.1.1.4.2 yamt {
4526 1.1.1.1.4.2 yamt /* This section covers (maybe partially) the beginning
4527 1.1.1.1.4.2 yamt of the range. */
4528 1.1.1.1.4.2 yamt base_vma = sec->vma + sec->size;
4529 1.1.1.1.4.2 yamt goto again;
4530 1.1.1.1.4.2 yamt }
4531 1.1.1.1.4.2 yamt if (sec->vma < next_vma)
4532 1.1.1.1.4.2 yamt {
4533 1.1.1.1.4.2 yamt /* This section partially covers the end of the range.
4534 1.1.1.1.4.2 yamt Used to compute the size of the hole. */
4535 1.1.1.1.4.2 yamt next_vma = sec->vma;
4536 1.1.1.1.4.2 yamt }
4537 1.1.1.1.4.2 yamt }
4538 1.1.1.1.4.2 yamt
4539 1.1.1.1.4.2 yamt /* No section covering [base_vma; next_vma). Create a fake one. */
4540 1.1.1.1.4.2 yamt flags = SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS;
4541 1.1.1.1.4.2 yamt if (i_phdr->p_flags & PF_X)
4542 1.1.1.1.4.2 yamt {
4543 1.1.1.1.4.2 yamt flags |= SEC_CODE;
4544 1.1.1.1.4.2 yamt if (num_text++ == 0)
4545 1.1.1.1.4.2 yamt nname = ".text";
4546 1.1.1.1.4.2 yamt else
4547 1.1.1.1.4.2 yamt sprintf (name, ".text$%u", num_text);
4548 1.1.1.1.4.2 yamt }
4549 1.1.1.1.4.2 yamt else if ((i_phdr->p_flags & (PF_R | PF_W)) == PF_R)
4550 1.1.1.1.4.2 yamt {
4551 1.1.1.1.4.2 yamt flags |= SEC_READONLY;
4552 1.1.1.1.4.2 yamt sprintf (name, ".rodata$%u", num_rodata++);
4553 1.1.1.1.4.2 yamt }
4554 1.1.1.1.4.2 yamt else
4555 1.1.1.1.4.2 yamt {
4556 1.1.1.1.4.2 yamt flags |= SEC_DATA;
4557 1.1.1.1.4.2 yamt sprintf (name, ".data$%u", num_data++);
4558 1.1.1.1.4.2 yamt }
4559 1.1.1.1.4.2 yamt
4560 1.1.1.1.4.2 yamt /* Allocate name. */
4561 1.1.1.1.4.2 yamt if (nname == NULL)
4562 1.1.1.1.4.2 yamt {
4563 1.1.1.1.4.2 yamt size_t name_len = strlen (name) + 1;
4564 1.1.1.1.4.2 yamt nname = bfd_alloc (abfd, name_len);
4565 1.1.1.1.4.2 yamt if (nname == NULL)
4566 1.1.1.1.4.2 yamt return FALSE;
4567 1.1.1.1.4.2 yamt memcpy (nname, name, name_len);
4568 1.1.1.1.4.2 yamt }
4569 1.1.1.1.4.2 yamt
4570 1.1.1.1.4.2 yamt /* Create and fill new section. */
4571 1.1.1.1.4.2 yamt nsec = bfd_make_section_anyway_with_flags (abfd, nname, flags);
4572 1.1.1.1.4.2 yamt if (nsec == NULL)
4573 1.1.1.1.4.2 yamt return FALSE;
4574 1.1.1.1.4.2 yamt nsec->vma = base_vma;
4575 1.1.1.1.4.2 yamt nsec->size = next_vma - base_vma;
4576 1.1.1.1.4.2 yamt nsec->filepos = i_phdr->p_offset + (base_vma - i_phdr->p_vaddr);
4577 1.1.1.1.4.2 yamt
4578 1.1.1.1.4.2 yamt base_vma = next_vma;
4579 1.1.1.1.4.2 yamt }
4580 1.1.1.1.4.2 yamt }
4581 1.1.1.1.4.2 yamt return TRUE;
4582 1.1.1.1.4.2 yamt }
4583 1.1.1.1.4.2 yamt
4584 1.1.1.1.4.2 yamt static void
4585 1.1.1.1.4.2 yamt elf64_vms_post_process_headers (bfd *abfd,
4586 1.1.1.1.4.2 yamt struct bfd_link_info *info ATTRIBUTE_UNUSED)
4587 1.1.1.1.4.2 yamt {
4588 1.1.1.1.4.2 yamt Elf_Internal_Ehdr *i_ehdrp = elf_elfheader (abfd);
4589 1.1.1.1.4.2 yamt
4590 1.1.1.1.4.2 yamt i_ehdrp->e_ident[EI_OSABI] = ELFOSABI_OPENVMS;
4591 1.1.1.1.4.2 yamt i_ehdrp->e_ident[EI_ABIVERSION] = 2;
4592 1.1.1.1.4.2 yamt }
4593 1.1.1.1.4.2 yamt
4594 1.1.1.1.4.2 yamt static bfd_boolean
4595 1.1.1.1.4.2 yamt elf64_vms_section_processing (bfd *abfd ATTRIBUTE_UNUSED,
4596 1.1.1.1.4.2 yamt Elf_Internal_Shdr *hdr)
4597 1.1.1.1.4.2 yamt {
4598 1.1.1.1.4.2 yamt if (hdr->bfd_section != NULL)
4599 1.1.1.1.4.2 yamt {
4600 1.1.1.1.4.2 yamt const char *name = bfd_get_section_name (abfd, hdr->bfd_section);
4601 1.1.1.1.4.2 yamt
4602 1.1.1.1.4.2 yamt if (strcmp (name, ".text") == 0)
4603 1.1.1.1.4.2 yamt hdr->sh_flags |= SHF_IA_64_VMS_SHARED;
4604 1.1.1.1.4.2 yamt else if ((strcmp (name, ".debug") == 0)
4605 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_abbrev") == 0)
4606 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_aranges") == 0)
4607 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_frame") == 0)
4608 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_info") == 0)
4609 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_loc") == 0)
4610 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_macinfo") == 0)
4611 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_pubnames") == 0)
4612 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_pubtypes") == 0))
4613 1.1.1.1.4.2 yamt hdr->sh_type = SHT_IA_64_VMS_DEBUG;
4614 1.1.1.1.4.2 yamt else if ((strcmp (name, ".debug_line") == 0)
4615 1.1.1.1.4.2 yamt || (strcmp (name, ".debug_ranges") == 0)
4616 1.1.1.1.4.2 yamt || (strcmp (name, ".trace_info") == 0)
4617 1.1.1.1.4.2 yamt || (strcmp (name, ".trace_abbrev") == 0)
4618 1.1.1.1.4.2 yamt || (strcmp (name, ".trace_aranges") == 0))
4619 1.1.1.1.4.2 yamt hdr->sh_type = SHT_IA_64_VMS_TRACE;
4620 1.1.1.1.4.2 yamt else if (strcmp (name, ".debug_str") == 0)
4621 1.1.1.1.4.2 yamt hdr->sh_type = SHT_IA_64_VMS_DEBUG_STR;
4622 1.1.1.1.4.2 yamt }
4623 1.1.1.1.4.2 yamt
4624 1.1.1.1.4.2 yamt return TRUE;
4625 1.1.1.1.4.2 yamt }
4626 1.1.1.1.4.2 yamt
4627 1.1.1.1.4.2 yamt /* The final processing done just before writing out a VMS IA-64 ELF
4628 1.1.1.1.4.2 yamt object file. */
4629 1.1.1.1.4.2 yamt
4630 1.1.1.1.4.2 yamt static void
4631 1.1.1.1.4.2 yamt elf64_vms_final_write_processing (bfd *abfd,
4632 1.1.1.1.4.2 yamt bfd_boolean linker ATTRIBUTE_UNUSED)
4633 1.1.1.1.4.2 yamt {
4634 1.1.1.1.4.2 yamt Elf_Internal_Shdr *hdr;
4635 1.1.1.1.4.2 yamt asection *s;
4636 1.1.1.1.4.2 yamt int unwind_info_sect_idx = 0;
4637 1.1.1.1.4.2 yamt
4638 1.1.1.1.4.2 yamt for (s = abfd->sections; s; s = s->next)
4639 1.1.1.1.4.2 yamt {
4640 1.1.1.1.4.2 yamt hdr = &elf_section_data (s)->this_hdr;
4641 1.1.1.1.4.2 yamt
4642 1.1.1.1.4.2 yamt if (strcmp (bfd_get_section_name (abfd, hdr->bfd_section),
4643 1.1.1.1.4.2 yamt ".IA_64.unwind_info") == 0)
4644 1.1.1.1.4.2 yamt unwind_info_sect_idx = elf_section_data (s)->this_idx;
4645 1.1.1.1.4.2 yamt
4646 1.1.1.1.4.2 yamt switch (hdr->sh_type)
4647 1.1.1.1.4.2 yamt {
4648 1.1.1.1.4.2 yamt case SHT_IA_64_UNWIND:
4649 1.1.1.1.4.2 yamt /* VMS requires sh_info to point to the unwind info section. */
4650 1.1.1.1.4.2 yamt hdr->sh_info = unwind_info_sect_idx;
4651 1.1.1.1.4.2 yamt break;
4652 1.1.1.1.4.2 yamt }
4653 1.1.1.1.4.2 yamt }
4654 1.1.1.1.4.2 yamt
4655 1.1.1.1.4.2 yamt if (! elf_flags_init (abfd))
4656 1.1.1.1.4.2 yamt {
4657 1.1.1.1.4.2 yamt unsigned long flags = 0;
4658 1.1.1.1.4.2 yamt
4659 1.1.1.1.4.2 yamt if (abfd->xvec->byteorder == BFD_ENDIAN_BIG)
4660 1.1.1.1.4.2 yamt flags |= EF_IA_64_BE;
4661 1.1.1.1.4.2 yamt if (bfd_get_mach (abfd) == bfd_mach_ia64_elf64)
4662 1.1.1.1.4.2 yamt flags |= EF_IA_64_ABI64;
4663 1.1.1.1.4.2 yamt
4664 1.1.1.1.4.2 yamt elf_elfheader (abfd)->e_flags = flags;
4665 1.1.1.1.4.2 yamt elf_flags_init (abfd) = TRUE;
4666 1.1.1.1.4.2 yamt }
4667 1.1.1.1.4.2 yamt }
4668 1.1.1.1.4.2 yamt
4669 1.1.1.1.4.2 yamt static bfd_boolean
4670 1.1.1.1.4.2 yamt elf64_vms_write_shdrs_and_ehdr (bfd *abfd)
4671 1.1.1.1.4.2 yamt {
4672 1.1.1.1.4.2 yamt unsigned char needed_count[8];
4673 1.1.1.1.4.2 yamt
4674 1.1.1.1.4.2 yamt if (!bfd_elf64_write_shdrs_and_ehdr (abfd))
4675 1.1.1.1.4.2 yamt return FALSE;
4676 1.1.1.1.4.2 yamt
4677 1.1.1.1.4.2 yamt bfd_putl64 (elf_ia64_vms_tdata (abfd)->needed_count, needed_count);
4678 1.1.1.1.4.2 yamt
4679 1.1.1.1.4.2 yamt if (bfd_seek (abfd, sizeof (Elf64_External_Ehdr), SEEK_SET) != 0
4680 1.1.1.1.4.2 yamt || bfd_bwrite (needed_count, 8, abfd) != 8)
4681 1.1.1.1.4.2 yamt return FALSE;
4682 1.1.1.1.4.2 yamt
4683 1.1.1.1.4.2 yamt return TRUE;
4684 1.1.1.1.4.2 yamt }
4685 1.1.1.1.4.2 yamt
4686 1.1.1.1.4.2 yamt static bfd_boolean
4687 1.1.1.1.4.2 yamt elf64_vms_close_and_cleanup (bfd *abfd)
4688 1.1.1.1.4.2 yamt {
4689 1.1.1.1.4.2 yamt if (bfd_get_format (abfd) == bfd_object)
4690 1.1.1.1.4.2 yamt {
4691 1.1.1.1.4.2 yamt long isize;
4692 1.1.1.1.4.2 yamt
4693 1.1.1.1.4.2 yamt /* Pad to 8 byte boundary for IPF/VMS. */
4694 1.1.1.1.4.2 yamt isize = bfd_get_size (abfd);
4695 1.1.1.1.4.2 yamt if ((isize & 7) != 0)
4696 1.1.1.1.4.2 yamt {
4697 1.1.1.1.4.2 yamt int ishort = 8 - (isize & 7);
4698 1.1.1.1.4.2 yamt bfd_uint64_t pad = 0;
4699 1.1.1.1.4.2 yamt
4700 1.1.1.1.4.2 yamt bfd_seek (abfd, isize, SEEK_SET);
4701 1.1.1.1.4.2 yamt bfd_bwrite (&pad, ishort, abfd);
4702 1.1.1.1.4.2 yamt }
4703 1.1.1.1.4.2 yamt }
4704 1.1.1.1.4.2 yamt
4705 1.1.1.1.4.2 yamt return _bfd_elf_close_and_cleanup (abfd);
4706 1.1.1.1.4.2 yamt }
4707 1.1.1.1.4.2 yamt
4708 1.1.1.1.4.2 yamt /* Add symbols from an ELF object file to the linker hash table. */
4709 1.1.1.1.4.2 yamt
4710 1.1.1.1.4.2 yamt static bfd_boolean
4711 1.1.1.1.4.2 yamt elf64_vms_link_add_object_symbols (bfd *abfd, struct bfd_link_info *info)
4712 1.1.1.1.4.2 yamt {
4713 1.1.1.1.4.2 yamt Elf_Internal_Shdr *hdr;
4714 1.1.1.1.4.2 yamt bfd_size_type symcount;
4715 1.1.1.1.4.2 yamt bfd_size_type extsymcount;
4716 1.1.1.1.4.2 yamt bfd_size_type extsymoff;
4717 1.1.1.1.4.2 yamt struct elf_link_hash_entry **sym_hash;
4718 1.1.1.1.4.2 yamt bfd_boolean dynamic;
4719 1.1.1.1.4.2 yamt Elf_Internal_Sym *isymbuf = NULL;
4720 1.1.1.1.4.2 yamt Elf_Internal_Sym *isym;
4721 1.1.1.1.4.2 yamt Elf_Internal_Sym *isymend;
4722 1.1.1.1.4.2 yamt const struct elf_backend_data *bed;
4723 1.1.1.1.4.2 yamt struct elf_link_hash_table *htab;
4724 1.1.1.1.4.2 yamt bfd_size_type amt;
4725 1.1.1.1.4.2 yamt
4726 1.1.1.1.4.2 yamt htab = elf_hash_table (info);
4727 1.1.1.1.4.2 yamt bed = get_elf_backend_data (abfd);
4728 1.1.1.1.4.2 yamt
4729 1.1.1.1.4.2 yamt if ((abfd->flags & DYNAMIC) == 0)
4730 1.1.1.1.4.2 yamt dynamic = FALSE;
4731 1.1.1.1.4.2 yamt else
4732 1.1.1.1.4.2 yamt {
4733 1.1.1.1.4.2 yamt dynamic = TRUE;
4734 1.1.1.1.4.2 yamt
4735 1.1.1.1.4.2 yamt /* You can't use -r against a dynamic object. Also, there's no
4736 1.1.1.1.4.2 yamt hope of using a dynamic object which does not exactly match
4737 1.1.1.1.4.2 yamt the format of the output file. */
4738 1.1.1.1.4.2 yamt if (info->relocatable
4739 1.1.1.1.4.2 yamt || !is_elf_hash_table (htab)
4740 1.1.1.1.4.2 yamt || info->output_bfd->xvec != abfd->xvec)
4741 1.1.1.1.4.2 yamt {
4742 1.1.1.1.4.2 yamt if (info->relocatable)
4743 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_invalid_operation);
4744 1.1.1.1.4.2 yamt else
4745 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_wrong_format);
4746 1.1.1.1.4.2 yamt goto error_return;
4747 1.1.1.1.4.2 yamt }
4748 1.1.1.1.4.2 yamt }
4749 1.1.1.1.4.2 yamt
4750 1.1.1.1.4.2 yamt if (! dynamic)
4751 1.1.1.1.4.2 yamt {
4752 1.1.1.1.4.2 yamt /* If we are creating a shared library, create all the dynamic
4753 1.1.1.1.4.2 yamt sections immediately. We need to attach them to something,
4754 1.1.1.1.4.2 yamt so we attach them to this BFD, provided it is the right
4755 1.1.1.1.4.2 yamt format. FIXME: If there are no input BFD's of the same
4756 1.1.1.1.4.2 yamt format as the output, we can't make a shared library. */
4757 1.1.1.1.4.2 yamt if (info->shared
4758 1.1.1.1.4.2 yamt && is_elf_hash_table (htab)
4759 1.1.1.1.4.2 yamt && info->output_bfd->xvec == abfd->xvec
4760 1.1.1.1.4.2 yamt && !htab->dynamic_sections_created)
4761 1.1.1.1.4.2 yamt {
4762 1.1.1.1.4.2 yamt if (! elf64_ia64_create_dynamic_sections (abfd, info))
4763 1.1.1.1.4.2 yamt goto error_return;
4764 1.1.1.1.4.2 yamt }
4765 1.1.1.1.4.2 yamt }
4766 1.1.1.1.4.2 yamt else if (!is_elf_hash_table (htab))
4767 1.1.1.1.4.2 yamt goto error_return;
4768 1.1.1.1.4.2 yamt else
4769 1.1.1.1.4.2 yamt {
4770 1.1.1.1.4.2 yamt asection *s;
4771 1.1.1.1.4.2 yamt bfd_byte *dynbuf;
4772 1.1.1.1.4.2 yamt bfd_byte *extdyn;
4773 1.1.1.1.4.2 yamt
4774 1.1.1.1.4.2 yamt /* ld --just-symbols and dynamic objects don't mix very well.
4775 1.1.1.1.4.2 yamt ld shouldn't allow it. */
4776 1.1.1.1.4.2 yamt if ((s = abfd->sections) != NULL
4777 1.1.1.1.4.2 yamt && s->sec_info_type == SEC_INFO_TYPE_JUST_SYMS)
4778 1.1.1.1.4.2 yamt abort ();
4779 1.1.1.1.4.2 yamt
4780 1.1.1.1.4.2 yamt /* Be sure there are dynamic sections. */
4781 1.1.1.1.4.2 yamt if (! elf64_ia64_create_dynamic_sections (htab->dynobj, info))
4782 1.1.1.1.4.2 yamt goto error_return;
4783 1.1.1.1.4.2 yamt
4784 1.1.1.1.4.2 yamt s = bfd_get_section_by_name (abfd, ".dynamic");
4785 1.1.1.1.4.2 yamt if (s == NULL)
4786 1.1.1.1.4.2 yamt {
4787 1.1.1.1.4.2 yamt /* VMS libraries do not have dynamic sections. Create one from
4788 1.1.1.1.4.2 yamt the segment. */
4789 1.1.1.1.4.2 yamt Elf_Internal_Phdr *phdr;
4790 1.1.1.1.4.2 yamt unsigned int i, phnum;
4791 1.1.1.1.4.2 yamt
4792 1.1.1.1.4.2 yamt phdr = elf_tdata (abfd)->phdr;
4793 1.1.1.1.4.2 yamt if (phdr == NULL)
4794 1.1.1.1.4.2 yamt goto error_return;
4795 1.1.1.1.4.2 yamt phnum = elf_elfheader (abfd)->e_phnum;
4796 1.1.1.1.4.2 yamt for (i = 0; i < phnum; phdr++)
4797 1.1.1.1.4.2 yamt if (phdr->p_type == PT_DYNAMIC)
4798 1.1.1.1.4.2 yamt {
4799 1.1.1.1.4.2 yamt s = bfd_make_section (abfd, ".dynamic");
4800 1.1.1.1.4.2 yamt if (s == NULL)
4801 1.1.1.1.4.2 yamt goto error_return;
4802 1.1.1.1.4.2 yamt s->vma = phdr->p_vaddr;
4803 1.1.1.1.4.2 yamt s->lma = phdr->p_paddr;
4804 1.1.1.1.4.2 yamt s->size = phdr->p_filesz;
4805 1.1.1.1.4.2 yamt s->filepos = phdr->p_offset;
4806 1.1.1.1.4.2 yamt s->flags |= SEC_HAS_CONTENTS;
4807 1.1.1.1.4.2 yamt s->alignment_power = bfd_log2 (phdr->p_align);
4808 1.1.1.1.4.2 yamt break;
4809 1.1.1.1.4.2 yamt }
4810 1.1.1.1.4.2 yamt if (s == NULL)
4811 1.1.1.1.4.2 yamt goto error_return;
4812 1.1.1.1.4.2 yamt }
4813 1.1.1.1.4.2 yamt
4814 1.1.1.1.4.2 yamt /* Extract IDENT. */
4815 1.1.1.1.4.2 yamt if (!bfd_malloc_and_get_section (abfd, s, &dynbuf))
4816 1.1.1.1.4.2 yamt {
4817 1.1.1.1.4.2 yamt error_free_dyn:
4818 1.1.1.1.4.2 yamt free (dynbuf);
4819 1.1.1.1.4.2 yamt goto error_return;
4820 1.1.1.1.4.2 yamt }
4821 1.1.1.1.4.2 yamt
4822 1.1.1.1.4.2 yamt for (extdyn = dynbuf;
4823 1.1.1.1.4.2 yamt extdyn < dynbuf + s->size;
4824 1.1.1.1.4.2 yamt extdyn += bed->s->sizeof_dyn)
4825 1.1.1.1.4.2 yamt {
4826 1.1.1.1.4.2 yamt Elf_Internal_Dyn dyn;
4827 1.1.1.1.4.2 yamt
4828 1.1.1.1.4.2 yamt bed->s->swap_dyn_in (abfd, extdyn, &dyn);
4829 1.1.1.1.4.2 yamt if (dyn.d_tag == DT_IA_64_VMS_IDENT)
4830 1.1.1.1.4.2 yamt {
4831 1.1.1.1.4.2 yamt bfd_uint64_t tagv = dyn.d_un.d_val;
4832 1.1.1.1.4.2 yamt elf_ia64_vms_ident (abfd) = tagv;
4833 1.1.1.1.4.2 yamt break;
4834 1.1.1.1.4.2 yamt }
4835 1.1.1.1.4.2 yamt }
4836 1.1.1.1.4.2 yamt if (extdyn >= dynbuf + s->size)
4837 1.1.1.1.4.2 yamt {
4838 1.1.1.1.4.2 yamt /* Ident not found. */
4839 1.1.1.1.4.2 yamt goto error_free_dyn;
4840 1.1.1.1.4.2 yamt }
4841 1.1.1.1.4.2 yamt free (dynbuf);
4842 1.1.1.1.4.2 yamt
4843 1.1.1.1.4.2 yamt /* We do not want to include any of the sections in a dynamic
4844 1.1.1.1.4.2 yamt object in the output file. We hack by simply clobbering the
4845 1.1.1.1.4.2 yamt list of sections in the BFD. This could be handled more
4846 1.1.1.1.4.2 yamt cleanly by, say, a new section flag; the existing
4847 1.1.1.1.4.2 yamt SEC_NEVER_LOAD flag is not the one we want, because that one
4848 1.1.1.1.4.2 yamt still implies that the section takes up space in the output
4849 1.1.1.1.4.2 yamt file. */
4850 1.1.1.1.4.2 yamt bfd_section_list_clear (abfd);
4851 1.1.1.1.4.2 yamt
4852 1.1.1.1.4.2 yamt /* FIXME: should we detect if this library is already included ?
4853 1.1.1.1.4.2 yamt This should be harmless and shouldn't happen in practice. */
4854 1.1.1.1.4.2 yamt }
4855 1.1.1.1.4.2 yamt
4856 1.1.1.1.4.2 yamt hdr = &elf_tdata (abfd)->symtab_hdr;
4857 1.1.1.1.4.2 yamt symcount = hdr->sh_size / bed->s->sizeof_sym;
4858 1.1.1.1.4.2 yamt
4859 1.1.1.1.4.2 yamt /* The sh_info field of the symtab header tells us where the
4860 1.1.1.1.4.2 yamt external symbols start. We don't care about the local symbols at
4861 1.1.1.1.4.2 yamt this point. */
4862 1.1.1.1.4.2 yamt extsymcount = symcount - hdr->sh_info;
4863 1.1.1.1.4.2 yamt extsymoff = hdr->sh_info;
4864 1.1.1.1.4.2 yamt
4865 1.1.1.1.4.2 yamt sym_hash = NULL;
4866 1.1.1.1.4.2 yamt if (extsymcount != 0)
4867 1.1.1.1.4.2 yamt {
4868 1.1.1.1.4.2 yamt isymbuf = bfd_elf_get_elf_syms (abfd, hdr, extsymcount, extsymoff,
4869 1.1.1.1.4.2 yamt NULL, NULL, NULL);
4870 1.1.1.1.4.2 yamt if (isymbuf == NULL)
4871 1.1.1.1.4.2 yamt goto error_return;
4872 1.1.1.1.4.2 yamt
4873 1.1.1.1.4.2 yamt /* We store a pointer to the hash table entry for each external
4874 1.1.1.1.4.2 yamt symbol. */
4875 1.1.1.1.4.2 yamt amt = extsymcount * sizeof (struct elf_link_hash_entry *);
4876 1.1.1.1.4.2 yamt sym_hash = (struct elf_link_hash_entry **) bfd_alloc (abfd, amt);
4877 1.1.1.1.4.2 yamt if (sym_hash == NULL)
4878 1.1.1.1.4.2 yamt goto error_free_sym;
4879 1.1.1.1.4.2 yamt elf_sym_hashes (abfd) = sym_hash;
4880 1.1.1.1.4.2 yamt }
4881 1.1.1.1.4.2 yamt
4882 1.1.1.1.4.2 yamt for (isym = isymbuf, isymend = isymbuf + extsymcount;
4883 1.1.1.1.4.2 yamt isym < isymend;
4884 1.1.1.1.4.2 yamt isym++, sym_hash++)
4885 1.1.1.1.4.2 yamt {
4886 1.1.1.1.4.2 yamt int bind;
4887 1.1.1.1.4.2 yamt bfd_vma value;
4888 1.1.1.1.4.2 yamt asection *sec, *new_sec;
4889 1.1.1.1.4.2 yamt flagword flags;
4890 1.1.1.1.4.2 yamt const char *name;
4891 1.1.1.1.4.2 yamt struct elf_link_hash_entry *h;
4892 1.1.1.1.4.2 yamt bfd_boolean definition;
4893 1.1.1.1.4.2 yamt bfd_boolean size_change_ok;
4894 1.1.1.1.4.2 yamt bfd_boolean type_change_ok;
4895 1.1.1.1.4.2 yamt bfd_boolean common;
4896 1.1.1.1.4.2 yamt unsigned int old_alignment;
4897 1.1.1.1.4.2 yamt bfd *old_bfd;
4898 1.1.1.1.4.2 yamt
4899 1.1.1.1.4.2 yamt flags = BSF_NO_FLAGS;
4900 1.1.1.1.4.2 yamt sec = NULL;
4901 1.1.1.1.4.2 yamt value = isym->st_value;
4902 1.1.1.1.4.2 yamt *sym_hash = NULL;
4903 1.1.1.1.4.2 yamt common = bed->common_definition (isym);
4904 1.1.1.1.4.2 yamt
4905 1.1.1.1.4.2 yamt bind = ELF_ST_BIND (isym->st_info);
4906 1.1.1.1.4.2 yamt switch (bind)
4907 1.1.1.1.4.2 yamt {
4908 1.1.1.1.4.2 yamt case STB_LOCAL:
4909 1.1.1.1.4.2 yamt /* This should be impossible, since ELF requires that all
4910 1.1.1.1.4.2 yamt global symbols follow all local symbols, and that sh_info
4911 1.1.1.1.4.2 yamt point to the first global symbol. Unfortunately, Irix 5
4912 1.1.1.1.4.2 yamt screws this up. */
4913 1.1.1.1.4.2 yamt continue;
4914 1.1.1.1.4.2 yamt
4915 1.1.1.1.4.2 yamt case STB_GLOBAL:
4916 1.1.1.1.4.2 yamt if (isym->st_shndx != SHN_UNDEF && !common)
4917 1.1.1.1.4.2 yamt flags = BSF_GLOBAL;
4918 1.1.1.1.4.2 yamt break;
4919 1.1.1.1.4.2 yamt
4920 1.1.1.1.4.2 yamt case STB_WEAK:
4921 1.1.1.1.4.2 yamt flags = BSF_WEAK;
4922 1.1.1.1.4.2 yamt break;
4923 1.1.1.1.4.2 yamt
4924 1.1.1.1.4.2 yamt case STB_GNU_UNIQUE:
4925 1.1.1.1.4.2 yamt flags = BSF_GNU_UNIQUE;
4926 1.1.1.1.4.2 yamt break;
4927 1.1.1.1.4.2 yamt
4928 1.1.1.1.4.2 yamt default:
4929 1.1.1.1.4.2 yamt /* Leave it up to the processor backend. */
4930 1.1.1.1.4.2 yamt break;
4931 1.1.1.1.4.2 yamt }
4932 1.1.1.1.4.2 yamt
4933 1.1.1.1.4.2 yamt if (isym->st_shndx == SHN_UNDEF)
4934 1.1.1.1.4.2 yamt sec = bfd_und_section_ptr;
4935 1.1.1.1.4.2 yamt else if (isym->st_shndx == SHN_ABS)
4936 1.1.1.1.4.2 yamt sec = bfd_abs_section_ptr;
4937 1.1.1.1.4.2 yamt else if (isym->st_shndx == SHN_COMMON)
4938 1.1.1.1.4.2 yamt {
4939 1.1.1.1.4.2 yamt sec = bfd_com_section_ptr;
4940 1.1.1.1.4.2 yamt /* What ELF calls the size we call the value. What ELF
4941 1.1.1.1.4.2 yamt calls the value we call the alignment. */
4942 1.1.1.1.4.2 yamt value = isym->st_size;
4943 1.1.1.1.4.2 yamt }
4944 1.1.1.1.4.2 yamt else
4945 1.1.1.1.4.2 yamt {
4946 1.1.1.1.4.2 yamt sec = bfd_section_from_elf_index (abfd, isym->st_shndx);
4947 1.1.1.1.4.2 yamt if (sec == NULL)
4948 1.1.1.1.4.2 yamt sec = bfd_abs_section_ptr;
4949 1.1.1.1.4.2 yamt else if (sec->kept_section)
4950 1.1.1.1.4.2 yamt {
4951 1.1.1.1.4.2 yamt /* Symbols from discarded section are undefined. We keep
4952 1.1.1.1.4.2 yamt its visibility. */
4953 1.1.1.1.4.2 yamt sec = bfd_und_section_ptr;
4954 1.1.1.1.4.2 yamt isym->st_shndx = SHN_UNDEF;
4955 1.1.1.1.4.2 yamt }
4956 1.1.1.1.4.2 yamt else if ((abfd->flags & (EXEC_P | DYNAMIC)) != 0)
4957 1.1.1.1.4.2 yamt value -= sec->vma;
4958 1.1.1.1.4.2 yamt }
4959 1.1.1.1.4.2 yamt
4960 1.1.1.1.4.2 yamt name = bfd_elf_string_from_elf_section (abfd, hdr->sh_link,
4961 1.1.1.1.4.2 yamt isym->st_name);
4962 1.1.1.1.4.2 yamt if (name == NULL)
4963 1.1.1.1.4.2 yamt goto error_free_vers;
4964 1.1.1.1.4.2 yamt
4965 1.1.1.1.4.2 yamt if (bed->elf_add_symbol_hook)
4966 1.1.1.1.4.2 yamt {
4967 1.1.1.1.4.2 yamt if (! (*bed->elf_add_symbol_hook) (abfd, info, isym, &name, &flags,
4968 1.1.1.1.4.2 yamt &sec, &value))
4969 1.1.1.1.4.2 yamt goto error_free_vers;
4970 1.1.1.1.4.2 yamt
4971 1.1.1.1.4.2 yamt /* The hook function sets the name to NULL if this symbol
4972 1.1.1.1.4.2 yamt should be skipped for some reason. */
4973 1.1.1.1.4.2 yamt if (name == NULL)
4974 1.1.1.1.4.2 yamt continue;
4975 1.1.1.1.4.2 yamt }
4976 1.1.1.1.4.2 yamt
4977 1.1.1.1.4.2 yamt /* Sanity check that all possibilities were handled. */
4978 1.1.1.1.4.2 yamt if (sec == NULL)
4979 1.1.1.1.4.2 yamt {
4980 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_bad_value);
4981 1.1.1.1.4.2 yamt goto error_free_vers;
4982 1.1.1.1.4.2 yamt }
4983 1.1.1.1.4.2 yamt
4984 1.1.1.1.4.2 yamt if (bfd_is_und_section (sec)
4985 1.1.1.1.4.2 yamt || bfd_is_com_section (sec))
4986 1.1.1.1.4.2 yamt definition = FALSE;
4987 1.1.1.1.4.2 yamt else
4988 1.1.1.1.4.2 yamt definition = TRUE;
4989 1.1.1.1.4.2 yamt
4990 1.1.1.1.4.2 yamt size_change_ok = FALSE;
4991 1.1.1.1.4.2 yamt type_change_ok = bed->type_change_ok;
4992 1.1.1.1.4.2 yamt old_alignment = 0;
4993 1.1.1.1.4.2 yamt old_bfd = NULL;
4994 1.1.1.1.4.2 yamt new_sec = sec;
4995 1.1.1.1.4.2 yamt
4996 1.1.1.1.4.2 yamt if (! bfd_is_und_section (sec))
4997 1.1.1.1.4.2 yamt h = elf_link_hash_lookup (htab, name, TRUE, FALSE, FALSE);
4998 1.1.1.1.4.2 yamt else
4999 1.1.1.1.4.2 yamt h = ((struct elf_link_hash_entry *) bfd_wrapped_link_hash_lookup
5000 1.1.1.1.4.2 yamt (abfd, info, name, TRUE, FALSE, FALSE));
5001 1.1.1.1.4.2 yamt if (h == NULL)
5002 1.1.1.1.4.2 yamt goto error_free_sym;
5003 1.1.1.1.4.2 yamt
5004 1.1.1.1.4.2 yamt *sym_hash = h;
5005 1.1.1.1.4.2 yamt
5006 1.1.1.1.4.2 yamt if (is_elf_hash_table (htab))
5007 1.1.1.1.4.2 yamt {
5008 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
5009 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
5010 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
5011 1.1.1.1.4.2 yamt
5012 1.1.1.1.4.2 yamt /* Remember the old alignment if this is a common symbol, so
5013 1.1.1.1.4.2 yamt that we don't reduce the alignment later on. We can't
5014 1.1.1.1.4.2 yamt check later, because _bfd_generic_link_add_one_symbol
5015 1.1.1.1.4.2 yamt will set a default for the alignment which we want to
5016 1.1.1.1.4.2 yamt override. We also remember the old bfd where the existing
5017 1.1.1.1.4.2 yamt definition comes from. */
5018 1.1.1.1.4.2 yamt switch (h->root.type)
5019 1.1.1.1.4.2 yamt {
5020 1.1.1.1.4.2 yamt default:
5021 1.1.1.1.4.2 yamt break;
5022 1.1.1.1.4.2 yamt
5023 1.1.1.1.4.2 yamt case bfd_link_hash_defined:
5024 1.1.1.1.4.2 yamt if (abfd->selective_search)
5025 1.1.1.1.4.2 yamt continue;
5026 1.1.1.1.4.2 yamt /* Fall-through. */
5027 1.1.1.1.4.2 yamt case bfd_link_hash_defweak:
5028 1.1.1.1.4.2 yamt old_bfd = h->root.u.def.section->owner;
5029 1.1.1.1.4.2 yamt break;
5030 1.1.1.1.4.2 yamt
5031 1.1.1.1.4.2 yamt case bfd_link_hash_common:
5032 1.1.1.1.4.2 yamt old_bfd = h->root.u.c.p->section->owner;
5033 1.1.1.1.4.2 yamt old_alignment = h->root.u.c.p->alignment_power;
5034 1.1.1.1.4.2 yamt break;
5035 1.1.1.1.4.2 yamt }
5036 1.1.1.1.4.2 yamt }
5037 1.1.1.1.4.2 yamt
5038 1.1.1.1.4.2 yamt if (! (_bfd_generic_link_add_one_symbol
5039 1.1.1.1.4.2 yamt (info, abfd, name, flags, sec, value, NULL, FALSE, bed->collect,
5040 1.1.1.1.4.2 yamt (struct bfd_link_hash_entry **) sym_hash)))
5041 1.1.1.1.4.2 yamt goto error_free_vers;
5042 1.1.1.1.4.2 yamt
5043 1.1.1.1.4.2 yamt h = *sym_hash;
5044 1.1.1.1.4.2 yamt while (h->root.type == bfd_link_hash_indirect
5045 1.1.1.1.4.2 yamt || h->root.type == bfd_link_hash_warning)
5046 1.1.1.1.4.2 yamt h = (struct elf_link_hash_entry *) h->root.u.i.link;
5047 1.1.1.1.4.2 yamt
5048 1.1.1.1.4.2 yamt *sym_hash = h;
5049 1.1.1.1.4.2 yamt h->unique_global = (flags & BSF_GNU_UNIQUE) != 0;
5050 1.1.1.1.4.2 yamt
5051 1.1.1.1.4.2 yamt /* Set the alignment of a common symbol. */
5052 1.1.1.1.4.2 yamt if ((common || bfd_is_com_section (sec))
5053 1.1.1.1.4.2 yamt && h->root.type == bfd_link_hash_common)
5054 1.1.1.1.4.2 yamt {
5055 1.1.1.1.4.2 yamt unsigned int align;
5056 1.1.1.1.4.2 yamt
5057 1.1.1.1.4.2 yamt if (common)
5058 1.1.1.1.4.2 yamt align = bfd_log2 (isym->st_value);
5059 1.1.1.1.4.2 yamt else
5060 1.1.1.1.4.2 yamt {
5061 1.1.1.1.4.2 yamt /* The new symbol is a common symbol in a shared object.
5062 1.1.1.1.4.2 yamt We need to get the alignment from the section. */
5063 1.1.1.1.4.2 yamt align = new_sec->alignment_power;
5064 1.1.1.1.4.2 yamt }
5065 1.1.1.1.4.2 yamt if (align > old_alignment
5066 1.1.1.1.4.2 yamt /* Permit an alignment power of zero if an alignment of one
5067 1.1.1.1.4.2 yamt is specified and no other alignments have been specified. */
5068 1.1.1.1.4.2 yamt || (isym->st_value == 1 && old_alignment == 0))
5069 1.1.1.1.4.2 yamt h->root.u.c.p->alignment_power = align;
5070 1.1.1.1.4.2 yamt else
5071 1.1.1.1.4.2 yamt h->root.u.c.p->alignment_power = old_alignment;
5072 1.1.1.1.4.2 yamt }
5073 1.1.1.1.4.2 yamt
5074 1.1.1.1.4.2 yamt if (is_elf_hash_table (htab))
5075 1.1.1.1.4.2 yamt {
5076 1.1.1.1.4.2 yamt /* Check the alignment when a common symbol is involved. This
5077 1.1.1.1.4.2 yamt can change when a common symbol is overridden by a normal
5078 1.1.1.1.4.2 yamt definition or a common symbol is ignored due to the old
5079 1.1.1.1.4.2 yamt normal definition. We need to make sure the maximum
5080 1.1.1.1.4.2 yamt alignment is maintained. */
5081 1.1.1.1.4.2 yamt if ((old_alignment || common)
5082 1.1.1.1.4.2 yamt && h->root.type != bfd_link_hash_common)
5083 1.1.1.1.4.2 yamt {
5084 1.1.1.1.4.2 yamt unsigned int common_align;
5085 1.1.1.1.4.2 yamt unsigned int normal_align;
5086 1.1.1.1.4.2 yamt unsigned int symbol_align;
5087 1.1.1.1.4.2 yamt bfd *normal_bfd;
5088 1.1.1.1.4.2 yamt bfd *common_bfd;
5089 1.1.1.1.4.2 yamt
5090 1.1.1.1.4.2 yamt symbol_align = ffs (h->root.u.def.value) - 1;
5091 1.1.1.1.4.2 yamt if (h->root.u.def.section->owner != NULL
5092 1.1.1.1.4.2 yamt && (h->root.u.def.section->owner->flags & DYNAMIC) == 0)
5093 1.1.1.1.4.2 yamt {
5094 1.1.1.1.4.2 yamt normal_align = h->root.u.def.section->alignment_power;
5095 1.1.1.1.4.2 yamt if (normal_align > symbol_align)
5096 1.1.1.1.4.2 yamt normal_align = symbol_align;
5097 1.1.1.1.4.2 yamt }
5098 1.1.1.1.4.2 yamt else
5099 1.1.1.1.4.2 yamt normal_align = symbol_align;
5100 1.1.1.1.4.2 yamt
5101 1.1.1.1.4.2 yamt if (old_alignment)
5102 1.1.1.1.4.2 yamt {
5103 1.1.1.1.4.2 yamt common_align = old_alignment;
5104 1.1.1.1.4.2 yamt common_bfd = old_bfd;
5105 1.1.1.1.4.2 yamt normal_bfd = abfd;
5106 1.1.1.1.4.2 yamt }
5107 1.1.1.1.4.2 yamt else
5108 1.1.1.1.4.2 yamt {
5109 1.1.1.1.4.2 yamt common_align = bfd_log2 (isym->st_value);
5110 1.1.1.1.4.2 yamt common_bfd = abfd;
5111 1.1.1.1.4.2 yamt normal_bfd = old_bfd;
5112 1.1.1.1.4.2 yamt }
5113 1.1.1.1.4.2 yamt
5114 1.1.1.1.4.2 yamt if (normal_align < common_align)
5115 1.1.1.1.4.2 yamt {
5116 1.1.1.1.4.2 yamt /* PR binutils/2735 */
5117 1.1.1.1.4.2 yamt if (normal_bfd == NULL)
5118 1.1.1.1.4.2 yamt (*_bfd_error_handler)
5119 1.1.1.1.4.2 yamt (_("Warning: alignment %u of common symbol `%s' in %B"
5120 1.1.1.1.4.2 yamt " is greater than the alignment (%u) of its section %A"),
5121 1.1.1.1.4.2 yamt common_bfd, h->root.u.def.section,
5122 1.1.1.1.4.2 yamt 1 << common_align, name, 1 << normal_align);
5123 1.1.1.1.4.2 yamt else
5124 1.1.1.1.4.2 yamt (*_bfd_error_handler)
5125 1.1.1.1.4.2 yamt (_("Warning: alignment %u of symbol `%s' in %B"
5126 1.1.1.1.4.2 yamt " is smaller than %u in %B"),
5127 1.1.1.1.4.2 yamt normal_bfd, common_bfd,
5128 1.1.1.1.4.2 yamt 1 << normal_align, name, 1 << common_align);
5129 1.1.1.1.4.2 yamt }
5130 1.1.1.1.4.2 yamt }
5131 1.1.1.1.4.2 yamt
5132 1.1.1.1.4.2 yamt /* Remember the symbol size if it isn't undefined. */
5133 1.1.1.1.4.2 yamt if ((isym->st_size != 0 && isym->st_shndx != SHN_UNDEF)
5134 1.1.1.1.4.2 yamt && (definition || h->size == 0))
5135 1.1.1.1.4.2 yamt {
5136 1.1.1.1.4.2 yamt if (h->size != 0
5137 1.1.1.1.4.2 yamt && h->size != isym->st_size
5138 1.1.1.1.4.2 yamt && ! size_change_ok)
5139 1.1.1.1.4.2 yamt (*_bfd_error_handler)
5140 1.1.1.1.4.2 yamt (_("Warning: size of symbol `%s' changed"
5141 1.1.1.1.4.2 yamt " from %lu in %B to %lu in %B"),
5142 1.1.1.1.4.2 yamt old_bfd, abfd,
5143 1.1.1.1.4.2 yamt name, (unsigned long) h->size,
5144 1.1.1.1.4.2 yamt (unsigned long) isym->st_size);
5145 1.1.1.1.4.2 yamt
5146 1.1.1.1.4.2 yamt h->size = isym->st_size;
5147 1.1.1.1.4.2 yamt }
5148 1.1.1.1.4.2 yamt
5149 1.1.1.1.4.2 yamt /* If this is a common symbol, then we always want H->SIZE
5150 1.1.1.1.4.2 yamt to be the size of the common symbol. The code just above
5151 1.1.1.1.4.2 yamt won't fix the size if a common symbol becomes larger. We
5152 1.1.1.1.4.2 yamt don't warn about a size change here, because that is
5153 1.1.1.1.4.2 yamt covered by --warn-common. Allow changed between different
5154 1.1.1.1.4.2 yamt function types. */
5155 1.1.1.1.4.2 yamt if (h->root.type == bfd_link_hash_common)
5156 1.1.1.1.4.2 yamt h->size = h->root.u.c.size;
5157 1.1.1.1.4.2 yamt
5158 1.1.1.1.4.2 yamt if (ELF_ST_TYPE (isym->st_info) != STT_NOTYPE
5159 1.1.1.1.4.2 yamt && (definition || h->type == STT_NOTYPE))
5160 1.1.1.1.4.2 yamt {
5161 1.1.1.1.4.2 yamt unsigned int type = ELF_ST_TYPE (isym->st_info);
5162 1.1.1.1.4.2 yamt
5163 1.1.1.1.4.2 yamt if (h->type != type)
5164 1.1.1.1.4.2 yamt {
5165 1.1.1.1.4.2 yamt if (h->type != STT_NOTYPE && ! type_change_ok)
5166 1.1.1.1.4.2 yamt (*_bfd_error_handler)
5167 1.1.1.1.4.2 yamt (_("Warning: type of symbol `%s' changed"
5168 1.1.1.1.4.2 yamt " from %d to %d in %B"),
5169 1.1.1.1.4.2 yamt abfd, name, h->type, type);
5170 1.1.1.1.4.2 yamt
5171 1.1.1.1.4.2 yamt h->type = type;
5172 1.1.1.1.4.2 yamt }
5173 1.1.1.1.4.2 yamt }
5174 1.1.1.1.4.2 yamt
5175 1.1.1.1.4.2 yamt /* Set a flag in the hash table entry indicating the type of
5176 1.1.1.1.4.2 yamt reference or definition we just found. Keep a count of
5177 1.1.1.1.4.2 yamt the number of dynamic symbols we find. A dynamic symbol
5178 1.1.1.1.4.2 yamt is one which is referenced or defined by both a regular
5179 1.1.1.1.4.2 yamt object and a shared object. */
5180 1.1.1.1.4.2 yamt if (! dynamic)
5181 1.1.1.1.4.2 yamt {
5182 1.1.1.1.4.2 yamt if (! definition)
5183 1.1.1.1.4.2 yamt {
5184 1.1.1.1.4.2 yamt h->ref_regular = 1;
5185 1.1.1.1.4.2 yamt if (bind != STB_WEAK)
5186 1.1.1.1.4.2 yamt h->ref_regular_nonweak = 1;
5187 1.1.1.1.4.2 yamt }
5188 1.1.1.1.4.2 yamt else
5189 1.1.1.1.4.2 yamt {
5190 1.1.1.1.4.2 yamt BFD_ASSERT (!h->def_dynamic);
5191 1.1.1.1.4.2 yamt h->def_regular = 1;
5192 1.1.1.1.4.2 yamt }
5193 1.1.1.1.4.2 yamt }
5194 1.1.1.1.4.2 yamt else
5195 1.1.1.1.4.2 yamt {
5196 1.1.1.1.4.2 yamt BFD_ASSERT (definition);
5197 1.1.1.1.4.2 yamt h->def_dynamic = 1;
5198 1.1.1.1.4.2 yamt h->dynindx = -2;
5199 1.1.1.1.4.2 yamt ((struct elf64_ia64_link_hash_entry *)h)->shl = abfd;
5200 1.1.1.1.4.2 yamt }
5201 1.1.1.1.4.2 yamt }
5202 1.1.1.1.4.2 yamt }
5203 1.1.1.1.4.2 yamt
5204 1.1.1.1.4.2 yamt if (isymbuf != NULL)
5205 1.1.1.1.4.2 yamt {
5206 1.1.1.1.4.2 yamt free (isymbuf);
5207 1.1.1.1.4.2 yamt isymbuf = NULL;
5208 1.1.1.1.4.2 yamt }
5209 1.1.1.1.4.2 yamt
5210 1.1.1.1.4.2 yamt /* If this object is the same format as the output object, and it is
5211 1.1.1.1.4.2 yamt not a shared library, then let the backend look through the
5212 1.1.1.1.4.2 yamt relocs.
5213 1.1.1.1.4.2 yamt
5214 1.1.1.1.4.2 yamt This is required to build global offset table entries and to
5215 1.1.1.1.4.2 yamt arrange for dynamic relocs. It is not required for the
5216 1.1.1.1.4.2 yamt particular common case of linking non PIC code, even when linking
5217 1.1.1.1.4.2 yamt against shared libraries, but unfortunately there is no way of
5218 1.1.1.1.4.2 yamt knowing whether an object file has been compiled PIC or not.
5219 1.1.1.1.4.2 yamt Looking through the relocs is not particularly time consuming.
5220 1.1.1.1.4.2 yamt The problem is that we must either (1) keep the relocs in memory,
5221 1.1.1.1.4.2 yamt which causes the linker to require additional runtime memory or
5222 1.1.1.1.4.2 yamt (2) read the relocs twice from the input file, which wastes time.
5223 1.1.1.1.4.2 yamt This would be a good case for using mmap.
5224 1.1.1.1.4.2 yamt
5225 1.1.1.1.4.2 yamt I have no idea how to handle linking PIC code into a file of a
5226 1.1.1.1.4.2 yamt different format. It probably can't be done. */
5227 1.1.1.1.4.2 yamt if (! dynamic
5228 1.1.1.1.4.2 yamt && is_elf_hash_table (htab)
5229 1.1.1.1.4.2 yamt && bed->check_relocs != NULL
5230 1.1.1.1.4.2 yamt && (*bed->relocs_compatible) (abfd->xvec, info->output_bfd->xvec))
5231 1.1.1.1.4.2 yamt {
5232 1.1.1.1.4.2 yamt asection *o;
5233 1.1.1.1.4.2 yamt
5234 1.1.1.1.4.2 yamt for (o = abfd->sections; o != NULL; o = o->next)
5235 1.1.1.1.4.2 yamt {
5236 1.1.1.1.4.2 yamt Elf_Internal_Rela *internal_relocs;
5237 1.1.1.1.4.2 yamt bfd_boolean ok;
5238 1.1.1.1.4.2 yamt
5239 1.1.1.1.4.2 yamt if ((o->flags & SEC_RELOC) == 0
5240 1.1.1.1.4.2 yamt || o->reloc_count == 0
5241 1.1.1.1.4.2 yamt || ((info->strip == strip_all || info->strip == strip_debugger)
5242 1.1.1.1.4.2 yamt && (o->flags & SEC_DEBUGGING) != 0)
5243 1.1.1.1.4.2 yamt || bfd_is_abs_section (o->output_section))
5244 1.1.1.1.4.2 yamt continue;
5245 1.1.1.1.4.2 yamt
5246 1.1.1.1.4.2 yamt internal_relocs = _bfd_elf_link_read_relocs (abfd, o, NULL, NULL,
5247 1.1.1.1.4.2 yamt info->keep_memory);
5248 1.1.1.1.4.2 yamt if (internal_relocs == NULL)
5249 1.1.1.1.4.2 yamt goto error_return;
5250 1.1.1.1.4.2 yamt
5251 1.1.1.1.4.2 yamt ok = (*bed->check_relocs) (abfd, info, o, internal_relocs);
5252 1.1.1.1.4.2 yamt
5253 1.1.1.1.4.2 yamt if (elf_section_data (o)->relocs != internal_relocs)
5254 1.1.1.1.4.2 yamt free (internal_relocs);
5255 1.1.1.1.4.2 yamt
5256 1.1.1.1.4.2 yamt if (! ok)
5257 1.1.1.1.4.2 yamt goto error_return;
5258 1.1.1.1.4.2 yamt }
5259 1.1.1.1.4.2 yamt }
5260 1.1.1.1.4.2 yamt
5261 1.1.1.1.4.2 yamt return TRUE;
5262 1.1.1.1.4.2 yamt
5263 1.1.1.1.4.2 yamt error_free_vers:
5264 1.1.1.1.4.2 yamt error_free_sym:
5265 1.1.1.1.4.2 yamt if (isymbuf != NULL)
5266 1.1.1.1.4.2 yamt free (isymbuf);
5267 1.1.1.1.4.2 yamt error_return:
5268 1.1.1.1.4.2 yamt return FALSE;
5269 1.1.1.1.4.2 yamt }
5270 1.1.1.1.4.2 yamt
5271 1.1.1.1.4.2 yamt static bfd_boolean
5272 1.1.1.1.4.2 yamt elf64_vms_link_add_archive_symbols (bfd *abfd, struct bfd_link_info *info)
5273 1.1.1.1.4.2 yamt {
5274 1.1.1.1.4.2 yamt int pass;
5275 1.1.1.1.4.2 yamt struct bfd_link_hash_entry **pundef;
5276 1.1.1.1.4.2 yamt struct bfd_link_hash_entry **next_pundef;
5277 1.1.1.1.4.2 yamt
5278 1.1.1.1.4.2 yamt /* We only accept VMS libraries. */
5279 1.1.1.1.4.2 yamt if (info->output_bfd->xvec != abfd->xvec)
5280 1.1.1.1.4.2 yamt {
5281 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_wrong_format);
5282 1.1.1.1.4.2 yamt return FALSE;
5283 1.1.1.1.4.2 yamt }
5284 1.1.1.1.4.2 yamt
5285 1.1.1.1.4.2 yamt /* The archive_pass field in the archive itself is used to
5286 1.1.1.1.4.2 yamt initialize PASS, since we may search the same archive multiple
5287 1.1.1.1.4.2 yamt times. */
5288 1.1.1.1.4.2 yamt pass = ++abfd->archive_pass;
5289 1.1.1.1.4.2 yamt
5290 1.1.1.1.4.2 yamt /* Look through the list of undefined symbols. */
5291 1.1.1.1.4.2 yamt for (pundef = &info->hash->undefs; *pundef != NULL; pundef = next_pundef)
5292 1.1.1.1.4.2 yamt {
5293 1.1.1.1.4.2 yamt struct bfd_link_hash_entry *h;
5294 1.1.1.1.4.2 yamt symindex symidx;
5295 1.1.1.1.4.2 yamt bfd *element;
5296 1.1.1.1.4.2 yamt bfd *orig_element;
5297 1.1.1.1.4.2 yamt
5298 1.1.1.1.4.2 yamt h = *pundef;
5299 1.1.1.1.4.2 yamt next_pundef = &(*pundef)->u.undef.next;
5300 1.1.1.1.4.2 yamt
5301 1.1.1.1.4.2 yamt /* When a symbol is defined, it is not necessarily removed from
5302 1.1.1.1.4.2 yamt the list. */
5303 1.1.1.1.4.2 yamt if (h->type != bfd_link_hash_undefined
5304 1.1.1.1.4.2 yamt && h->type != bfd_link_hash_common)
5305 1.1.1.1.4.2 yamt {
5306 1.1.1.1.4.2 yamt /* Remove this entry from the list, for general cleanliness
5307 1.1.1.1.4.2 yamt and because we are going to look through the list again
5308 1.1.1.1.4.2 yamt if we search any more libraries. We can't remove the
5309 1.1.1.1.4.2 yamt entry if it is the tail, because that would lose any
5310 1.1.1.1.4.2 yamt entries we add to the list later on. */
5311 1.1.1.1.4.2 yamt if (*pundef != info->hash->undefs_tail)
5312 1.1.1.1.4.2 yamt {
5313 1.1.1.1.4.2 yamt *pundef = *next_pundef;
5314 1.1.1.1.4.2 yamt next_pundef = pundef;
5315 1.1.1.1.4.2 yamt }
5316 1.1.1.1.4.2 yamt continue;
5317 1.1.1.1.4.2 yamt }
5318 1.1.1.1.4.2 yamt
5319 1.1.1.1.4.2 yamt /* Look for this symbol in the archive hash table. */
5320 1.1.1.1.4.2 yamt symidx = _bfd_vms_lib_find_symbol (abfd, h->root.string);
5321 1.1.1.1.4.2 yamt if (symidx == BFD_NO_MORE_SYMBOLS)
5322 1.1.1.1.4.2 yamt {
5323 1.1.1.1.4.2 yamt /* Nothing in this slot. */
5324 1.1.1.1.4.2 yamt continue;
5325 1.1.1.1.4.2 yamt }
5326 1.1.1.1.4.2 yamt
5327 1.1.1.1.4.2 yamt element = bfd_get_elt_at_index (abfd, symidx);
5328 1.1.1.1.4.2 yamt if (element == NULL)
5329 1.1.1.1.4.2 yamt return FALSE;
5330 1.1.1.1.4.2 yamt
5331 1.1.1.1.4.2 yamt if (element->archive_pass == -1 || element->archive_pass == pass)
5332 1.1.1.1.4.2 yamt {
5333 1.1.1.1.4.2 yamt /* Next symbol if this archive is wrong or already handled. */
5334 1.1.1.1.4.2 yamt continue;
5335 1.1.1.1.4.2 yamt }
5336 1.1.1.1.4.2 yamt
5337 1.1.1.1.4.2 yamt orig_element = element;
5338 1.1.1.1.4.2 yamt if (bfd_is_thin_archive (abfd))
5339 1.1.1.1.4.2 yamt {
5340 1.1.1.1.4.2 yamt element = _bfd_vms_lib_get_imagelib_file (element);
5341 1.1.1.1.4.2 yamt if (element == NULL || !bfd_check_format (element, bfd_object))
5342 1.1.1.1.4.2 yamt {
5343 1.1.1.1.4.2 yamt orig_element->archive_pass = -1;
5344 1.1.1.1.4.2 yamt return FALSE;
5345 1.1.1.1.4.2 yamt }
5346 1.1.1.1.4.2 yamt }
5347 1.1.1.1.4.2 yamt else if (! bfd_check_format (element, bfd_object))
5348 1.1.1.1.4.2 yamt {
5349 1.1.1.1.4.2 yamt element->archive_pass = -1;
5350 1.1.1.1.4.2 yamt return FALSE;
5351 1.1.1.1.4.2 yamt }
5352 1.1.1.1.4.2 yamt
5353 1.1.1.1.4.2 yamt /* Unlike the generic linker, we know that this element provides
5354 1.1.1.1.4.2 yamt a definition for an undefined symbol and we know that we want
5355 1.1.1.1.4.2 yamt to include it. We don't need to check anything. */
5356 1.1.1.1.4.2 yamt if (! (*info->callbacks->add_archive_element) (info, element,
5357 1.1.1.1.4.2 yamt h->root.string, &element))
5358 1.1.1.1.4.2 yamt return FALSE;
5359 1.1.1.1.4.2 yamt if (! elf64_vms_link_add_object_symbols (element, info))
5360 1.1.1.1.4.2 yamt return FALSE;
5361 1.1.1.1.4.2 yamt
5362 1.1.1.1.4.2 yamt orig_element->archive_pass = pass;
5363 1.1.1.1.4.2 yamt }
5364 1.1.1.1.4.2 yamt
5365 1.1.1.1.4.2 yamt return TRUE;
5366 1.1.1.1.4.2 yamt }
5367 1.1.1.1.4.2 yamt
5368 1.1.1.1.4.2 yamt static bfd_boolean
5369 1.1.1.1.4.2 yamt elf64_vms_bfd_link_add_symbols (bfd *abfd, struct bfd_link_info *info)
5370 1.1.1.1.4.2 yamt {
5371 1.1.1.1.4.2 yamt switch (bfd_get_format (abfd))
5372 1.1.1.1.4.2 yamt {
5373 1.1.1.1.4.2 yamt case bfd_object:
5374 1.1.1.1.4.2 yamt return elf64_vms_link_add_object_symbols (abfd, info);
5375 1.1.1.1.4.2 yamt break;
5376 1.1.1.1.4.2 yamt case bfd_archive:
5377 1.1.1.1.4.2 yamt return elf64_vms_link_add_archive_symbols (abfd, info);
5378 1.1.1.1.4.2 yamt break;
5379 1.1.1.1.4.2 yamt default:
5380 1.1.1.1.4.2 yamt bfd_set_error (bfd_error_wrong_format);
5381 1.1.1.1.4.2 yamt return FALSE;
5382 1.1.1.1.4.2 yamt }
5383 1.1.1.1.4.2 yamt }
5384 1.1.1.1.4.2 yamt
5385 1.1.1.1.4.2 yamt static bfd_boolean
5386 1.1.1.1.4.2 yamt elf64_ia64_vms_mkobject (bfd *abfd)
5387 1.1.1.1.4.2 yamt {
5388 1.1.1.1.4.2 yamt return bfd_elf_allocate_object
5389 1.1.1.1.4.2 yamt (abfd, sizeof (struct elf64_ia64_vms_obj_tdata), IA64_ELF_DATA);
5390 1.1.1.1.4.2 yamt }
5391 1.1.1.1.4.2 yamt
5392 1.1.1.1.4.2 yamt
5393 1.1.1.1.4.2 yamt /* Size-dependent data and functions. */
5394 1.1.1.1.4.2 yamt static const struct elf_size_info elf64_ia64_vms_size_info = {
5395 1.1.1.1.4.2 yamt sizeof (Elf64_External_VMS_Ehdr),
5396 1.1.1.1.4.2 yamt sizeof (Elf64_External_Phdr),
5397 1.1.1.1.4.2 yamt sizeof (Elf64_External_Shdr),
5398 1.1.1.1.4.2 yamt sizeof (Elf64_External_Rel),
5399 1.1.1.1.4.2 yamt sizeof (Elf64_External_Rela),
5400 1.1.1.1.4.2 yamt sizeof (Elf64_External_Sym),
5401 1.1.1.1.4.2 yamt sizeof (Elf64_External_Dyn),
5402 1.1.1.1.4.2 yamt sizeof (Elf_External_Note),
5403 1.1.1.1.4.2 yamt 4,
5404 1.1.1.1.4.2 yamt 1,
5405 1.1.1.1.4.2 yamt 64, 3, /* ARCH_SIZE, LOG_FILE_ALIGN */
5406 1.1.1.1.4.2 yamt ELFCLASS64, EV_CURRENT,
5407 1.1.1.1.4.2 yamt bfd_elf64_write_out_phdrs,
5408 1.1.1.1.4.2 yamt elf64_vms_write_shdrs_and_ehdr,
5409 1.1.1.1.4.2 yamt bfd_elf64_checksum_contents,
5410 1.1.1.1.4.2 yamt bfd_elf64_write_relocs,
5411 1.1.1.1.4.2 yamt bfd_elf64_swap_symbol_in,
5412 1.1.1.1.4.2 yamt bfd_elf64_swap_symbol_out,
5413 1.1.1.1.4.2 yamt bfd_elf64_slurp_reloc_table,
5414 1.1.1.1.4.2 yamt bfd_elf64_slurp_symbol_table,
5415 1.1.1.1.4.2 yamt bfd_elf64_swap_dyn_in,
5416 1.1.1.1.4.2 yamt bfd_elf64_swap_dyn_out,
5417 1.1.1.1.4.2 yamt bfd_elf64_swap_reloc_in,
5418 1.1.1.1.4.2 yamt bfd_elf64_swap_reloc_out,
5419 1.1.1.1.4.2 yamt bfd_elf64_swap_reloca_in,
5420 1.1.1.1.4.2 yamt bfd_elf64_swap_reloca_out
5421 1.1.1.1.4.2 yamt };
5422 1.1.1.1.4.2 yamt
5423 1.1.1.1.4.2 yamt #define ELF_ARCH bfd_arch_ia64
5424 1.1.1.1.4.2 yamt #define ELF_MACHINE_CODE EM_IA_64
5425 1.1.1.1.4.2 yamt #define ELF_MAXPAGESIZE 0x10000 /* 64KB */
5426 1.1.1.1.4.2 yamt #define ELF_COMMONPAGESIZE 0x200 /* 16KB */
5427 1.1.1.1.4.2 yamt
5428 1.1.1.1.4.2 yamt #define elf_backend_section_from_shdr \
5429 1.1.1.1.4.2 yamt elf64_ia64_section_from_shdr
5430 1.1.1.1.4.2 yamt #define elf_backend_section_flags \
5431 1.1.1.1.4.2 yamt elf64_ia64_section_flags
5432 1.1.1.1.4.2 yamt #define elf_backend_fake_sections \
5433 1.1.1.1.4.2 yamt elf64_ia64_fake_sections
5434 1.1.1.1.4.2 yamt #define elf_backend_final_write_processing \
5435 1.1.1.1.4.2 yamt elf64_ia64_final_write_processing
5436 1.1.1.1.4.2 yamt #define elf_backend_add_symbol_hook \
5437 1.1.1.1.4.2 yamt elf64_ia64_add_symbol_hook
5438 1.1.1.1.4.2 yamt #define elf_info_to_howto \
5439 1.1.1.1.4.2 yamt elf64_ia64_info_to_howto
5440 1.1.1.1.4.2 yamt
5441 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_reloc_type_lookup \
5442 1.1.1.1.4.2 yamt ia64_elf_reloc_type_lookup
5443 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_reloc_name_lookup \
5444 1.1.1.1.4.2 yamt ia64_elf_reloc_name_lookup
5445 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_is_local_label_name \
5446 1.1.1.1.4.2 yamt elf64_ia64_is_local_label_name
5447 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_relax_section \
5448 1.1.1.1.4.2 yamt elf64_ia64_relax_section
5449 1.1.1.1.4.2 yamt
5450 1.1.1.1.4.2 yamt #define elf_backend_object_p \
5451 1.1.1.1.4.2 yamt elf64_ia64_object_p
5452 1.1.1.1.4.2 yamt
5453 1.1.1.1.4.2 yamt /* Stuff for the BFD linker: */
5454 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_link_hash_table_create \
5455 1.1.1.1.4.2 yamt elf64_ia64_hash_table_create
5456 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_link_hash_table_free \
5457 1.1.1.1.4.2 yamt elf64_ia64_hash_table_free
5458 1.1.1.1.4.2 yamt #define elf_backend_create_dynamic_sections \
5459 1.1.1.1.4.2 yamt elf64_ia64_create_dynamic_sections
5460 1.1.1.1.4.2 yamt #define elf_backend_check_relocs \
5461 1.1.1.1.4.2 yamt elf64_ia64_check_relocs
5462 1.1.1.1.4.2 yamt #define elf_backend_adjust_dynamic_symbol \
5463 1.1.1.1.4.2 yamt elf64_ia64_adjust_dynamic_symbol
5464 1.1.1.1.4.2 yamt #define elf_backend_size_dynamic_sections \
5465 1.1.1.1.4.2 yamt elf64_ia64_size_dynamic_sections
5466 1.1.1.1.4.2 yamt #define elf_backend_omit_section_dynsym \
5467 1.1.1.1.4.2 yamt ((bfd_boolean (*) (bfd *, struct bfd_link_info *, asection *)) bfd_true)
5468 1.1.1.1.4.2 yamt #define elf_backend_relocate_section \
5469 1.1.1.1.4.2 yamt elf64_ia64_relocate_section
5470 1.1.1.1.4.2 yamt #define elf_backend_finish_dynamic_symbol \
5471 1.1.1.1.4.2 yamt elf64_ia64_finish_dynamic_symbol
5472 1.1.1.1.4.2 yamt #define elf_backend_finish_dynamic_sections \
5473 1.1.1.1.4.2 yamt elf64_ia64_finish_dynamic_sections
5474 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_final_link \
5475 1.1.1.1.4.2 yamt elf64_ia64_final_link
5476 1.1.1.1.4.2 yamt
5477 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_merge_private_bfd_data \
5478 1.1.1.1.4.2 yamt elf64_ia64_merge_private_bfd_data
5479 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_set_private_flags \
5480 1.1.1.1.4.2 yamt elf64_ia64_set_private_flags
5481 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_print_private_bfd_data \
5482 1.1.1.1.4.2 yamt elf64_ia64_print_private_bfd_data
5483 1.1.1.1.4.2 yamt
5484 1.1.1.1.4.2 yamt #define elf_backend_plt_readonly 1
5485 1.1.1.1.4.2 yamt #define elf_backend_want_plt_sym 0
5486 1.1.1.1.4.2 yamt #define elf_backend_plt_alignment 5
5487 1.1.1.1.4.2 yamt #define elf_backend_got_header_size 0
5488 1.1.1.1.4.2 yamt #define elf_backend_want_got_plt 1
5489 1.1.1.1.4.2 yamt #define elf_backend_may_use_rel_p 1
5490 1.1.1.1.4.2 yamt #define elf_backend_may_use_rela_p 1
5491 1.1.1.1.4.2 yamt #define elf_backend_default_use_rela_p 1
5492 1.1.1.1.4.2 yamt #define elf_backend_want_dynbss 0
5493 1.1.1.1.4.2 yamt #define elf_backend_hide_symbol elf64_ia64_hash_hide_symbol
5494 1.1.1.1.4.2 yamt #define elf_backend_fixup_symbol _bfd_elf_link_hash_fixup_symbol
5495 1.1.1.1.4.2 yamt #define elf_backend_reloc_type_class elf64_ia64_reloc_type_class
5496 1.1.1.1.4.2 yamt #define elf_backend_rela_normal 1
5497 1.1.1.1.4.2 yamt #define elf_backend_special_sections elf64_ia64_special_sections
5498 1.1.1.1.4.2 yamt #define elf_backend_default_execstack 0
5499 1.1.1.1.4.2 yamt
5500 1.1.1.1.4.2 yamt /* FIXME: PR 290: The Intel C compiler generates SHT_IA_64_UNWIND with
5501 1.1.1.1.4.2 yamt SHF_LINK_ORDER. But it doesn't set the sh_link or sh_info fields.
5502 1.1.1.1.4.2 yamt We don't want to flood users with so many error messages. We turn
5503 1.1.1.1.4.2 yamt off the warning for now. It will be turned on later when the Intel
5504 1.1.1.1.4.2 yamt compiler is fixed. */
5505 1.1.1.1.4.2 yamt #define elf_backend_link_order_error_handler NULL
5506 1.1.1.1.4.2 yamt
5507 1.1.1.1.4.2 yamt /* VMS-specific vectors. */
5508 1.1.1.1.4.2 yamt
5509 1.1.1.1.4.2 yamt #undef TARGET_LITTLE_SYM
5510 1.1.1.1.4.2 yamt #define TARGET_LITTLE_SYM bfd_elf64_ia64_vms_vec
5511 1.1.1.1.4.2 yamt #undef TARGET_LITTLE_NAME
5512 1.1.1.1.4.2 yamt #define TARGET_LITTLE_NAME "elf64-ia64-vms"
5513 1.1.1.1.4.2 yamt #undef TARGET_BIG_SYM
5514 1.1.1.1.4.2 yamt #undef TARGET_BIG_NAME
5515 1.1.1.1.4.2 yamt
5516 1.1.1.1.4.2 yamt /* These are VMS specific functions. */
5517 1.1.1.1.4.2 yamt
5518 1.1.1.1.4.2 yamt #undef elf_backend_object_p
5519 1.1.1.1.4.2 yamt #define elf_backend_object_p elf64_vms_object_p
5520 1.1.1.1.4.2 yamt
5521 1.1.1.1.4.2 yamt #undef elf_backend_section_from_shdr
5522 1.1.1.1.4.2 yamt #define elf_backend_section_from_shdr elf64_vms_section_from_shdr
5523 1.1.1.1.4.2 yamt
5524 1.1.1.1.4.2 yamt #undef elf_backend_post_process_headers
5525 1.1.1.1.4.2 yamt #define elf_backend_post_process_headers elf64_vms_post_process_headers
5526 1.1.1.1.4.2 yamt
5527 1.1.1.1.4.2 yamt #undef elf_backend_section_processing
5528 1.1.1.1.4.2 yamt #define elf_backend_section_processing elf64_vms_section_processing
5529 1.1.1.1.4.2 yamt
5530 1.1.1.1.4.2 yamt #undef elf_backend_final_write_processing
5531 1.1.1.1.4.2 yamt #define elf_backend_final_write_processing elf64_vms_final_write_processing
5532 1.1.1.1.4.2 yamt
5533 1.1.1.1.4.2 yamt #undef bfd_elf64_close_and_cleanup
5534 1.1.1.1.4.2 yamt #define bfd_elf64_close_and_cleanup elf64_vms_close_and_cleanup
5535 1.1.1.1.4.2 yamt
5536 1.1.1.1.4.2 yamt #undef elf_backend_section_from_bfd_section
5537 1.1.1.1.4.2 yamt
5538 1.1.1.1.4.2 yamt #undef elf_backend_symbol_processing
5539 1.1.1.1.4.2 yamt
5540 1.1.1.1.4.2 yamt #undef elf_backend_want_p_paddr_set_to_zero
5541 1.1.1.1.4.2 yamt
5542 1.1.1.1.4.2 yamt #undef ELF_OSABI
5543 1.1.1.1.4.2 yamt #define ELF_OSABI ELFOSABI_OPENVMS
5544 1.1.1.1.4.2 yamt
5545 1.1.1.1.4.2 yamt #undef ELF_MAXPAGESIZE
5546 1.1.1.1.4.2 yamt #define ELF_MAXPAGESIZE 0x10000 /* 64KB */
5547 1.1.1.1.4.2 yamt
5548 1.1.1.1.4.2 yamt #undef elf64_bed
5549 1.1.1.1.4.2 yamt #define elf64_bed elf64_ia64_vms_bed
5550 1.1.1.1.4.2 yamt
5551 1.1.1.1.4.2 yamt #define elf_backend_size_info elf64_ia64_vms_size_info
5552 1.1.1.1.4.2 yamt
5553 1.1.1.1.4.2 yamt /* Use VMS-style archives (in particular, don't use the standard coff
5554 1.1.1.1.4.2 yamt archive format). */
5555 1.1.1.1.4.2 yamt #define bfd_elf64_archive_functions
5556 1.1.1.1.4.2 yamt
5557 1.1.1.1.4.2 yamt #undef bfd_elf64_archive_p
5558 1.1.1.1.4.2 yamt #define bfd_elf64_archive_p _bfd_vms_lib_ia64_archive_p
5559 1.1.1.1.4.2 yamt #undef bfd_elf64_write_archive_contents
5560 1.1.1.1.4.2 yamt #define bfd_elf64_write_archive_contents _bfd_vms_lib_write_archive_contents
5561 1.1.1.1.4.2 yamt #undef bfd_elf64_mkarchive
5562 1.1.1.1.4.2 yamt #define bfd_elf64_mkarchive _bfd_vms_lib_ia64_mkarchive
5563 1.1.1.1.4.2 yamt
5564 1.1.1.1.4.2 yamt #define bfd_elf64_archive_slurp_armap \
5565 1.1.1.1.4.2 yamt _bfd_vms_lib_slurp_armap
5566 1.1.1.1.4.2 yamt #define bfd_elf64_archive_slurp_extended_name_table \
5567 1.1.1.1.4.2 yamt _bfd_vms_lib_slurp_extended_name_table
5568 1.1.1.1.4.2 yamt #define bfd_elf64_archive_construct_extended_name_table \
5569 1.1.1.1.4.2 yamt _bfd_vms_lib_construct_extended_name_table
5570 1.1.1.1.4.2 yamt #define bfd_elf64_archive_truncate_arname \
5571 1.1.1.1.4.2 yamt _bfd_vms_lib_truncate_arname
5572 1.1.1.1.4.2 yamt #define bfd_elf64_archive_write_armap \
5573 1.1.1.1.4.2 yamt _bfd_vms_lib_write_armap
5574 1.1.1.1.4.2 yamt #define bfd_elf64_archive_read_ar_hdr \
5575 1.1.1.1.4.2 yamt _bfd_vms_lib_read_ar_hdr
5576 1.1.1.1.4.2 yamt #define bfd_elf64_archive_write_ar_hdr \
5577 1.1.1.1.4.2 yamt _bfd_vms_lib_write_ar_hdr
5578 1.1.1.1.4.2 yamt #define bfd_elf64_archive_openr_next_archived_file \
5579 1.1.1.1.4.2 yamt _bfd_vms_lib_openr_next_archived_file
5580 1.1.1.1.4.2 yamt #define bfd_elf64_archive_get_elt_at_index \
5581 1.1.1.1.4.2 yamt _bfd_vms_lib_get_elt_at_index
5582 1.1.1.1.4.2 yamt #define bfd_elf64_archive_generic_stat_arch_elt \
5583 1.1.1.1.4.2 yamt _bfd_vms_lib_generic_stat_arch_elt
5584 1.1.1.1.4.2 yamt #define bfd_elf64_archive_update_armap_timestamp \
5585 1.1.1.1.4.2 yamt _bfd_vms_lib_update_armap_timestamp
5586 1.1.1.1.4.2 yamt
5587 1.1.1.1.4.2 yamt /* VMS link methods. */
5588 1.1.1.1.4.2 yamt #undef bfd_elf64_bfd_link_add_symbols
5589 1.1.1.1.4.2 yamt #define bfd_elf64_bfd_link_add_symbols elf64_vms_bfd_link_add_symbols
5590 1.1.1.1.4.2 yamt
5591 1.1.1.1.4.2 yamt #undef elf_backend_want_got_sym
5592 1.1.1.1.4.2 yamt #define elf_backend_want_got_sym 0
5593 1.1.1.1.4.2 yamt
5594 1.1.1.1.4.2 yamt #undef bfd_elf64_mkobject
5595 1.1.1.1.4.2 yamt #define bfd_elf64_mkobject elf64_ia64_vms_mkobject
5596 1.1.1.1.4.2 yamt
5597 1.1.1.1.4.2 yamt /* Redefine to align segments on block size. */
5598 1.1.1.1.4.2 yamt #undef ELF_MAXPAGESIZE
5599 1.1.1.1.4.2 yamt #define ELF_MAXPAGESIZE 0x200 /* 512B */
5600 1.1.1.1.4.2 yamt
5601 1.1.1.1.4.2 yamt #undef elf_backend_want_got_plt
5602 1.1.1.1.4.2 yamt #define elf_backend_want_got_plt 0
5603 1.1.1.1.4.2 yamt
5604 1.1.1.1.4.2 yamt #include "elf64-target.h"
5605