1 /* MIPS-specific support for 64-bit ELF
2    Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
3    Free Software Foundation, Inc.
4    Ian Lance Taylor, Cygnus Support
5    Linker support added by Mark Mitchell, CodeSourcery, LLC.
6    <mark@codesourcery.com>
7 
8 This file is part of BFD, the Binary File Descriptor library.
9 
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
14 
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18 GNU General Public License for more details.
19 
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
23 
24 /* This file supports the 64-bit MIPS ELF ABI.
25 
26    The MIPS 64-bit ELF ABI uses an unusual reloc format.  This file
27    overrides the usual ELF reloc handling, and handles reading and
28    writing the relocations here.  */
29 
30 /* TODO: Many things are unsupported, even if there is some code for it
31  .       (which was mostly stolen from elf32-mips.c and slightly adapted).
32  .
33  .   - Relocation handling for REL relocs is wrong in many cases and
34  .     generally untested.
35  .   - Relocation handling for RELA relocs related to GOT support are
36  .     also likely to be wrong.
37  .   - Support for MIPS16 is untested.
38  .   - Combined relocs with RSS_* entries are unsupported.
39  .   - The whole GOT handling for NewABI is missing, some parts of
40  .     the OldABI version is still lying around and should be removed.
41  */
42 
43 #include "bfd.h"
44 #include "sysdep.h"
45 #include "libbfd.h"
46 #include "aout/ar.h"
47 #include "bfdlink.h"
48 #include "genlink.h"
49 #include "elf-bfd.h"
50 #include "elfxx-mips.h"
51 #include "elf/mips.h"
52 
53 /* Get the ECOFF swapping routines.  The 64-bit ABI is not supposed to
54    use ECOFF.  However, we support it anyhow for an easier changeover.  */
55 #include "coff/sym.h"
56 #include "coff/symconst.h"
57 #include "coff/internal.h"
58 #include "coff/ecoff.h"
59 /* The 64 bit versions of the mdebug data structures are in alpha.h.  */
60 #include "coff/alpha.h"
61 #define ECOFF_SIGNED_64
62 #include "ecoffswap.h"
63 
64 static void mips_elf64_swap_reloc_in
65   (bfd *, const Elf64_Mips_External_Rel *, Elf64_Mips_Internal_Rela *);
66 static void mips_elf64_swap_reloca_in
67   (bfd *, const Elf64_Mips_External_Rela *, Elf64_Mips_Internal_Rela *);
68 static void mips_elf64_swap_reloc_out
69   (bfd *, const Elf64_Mips_Internal_Rela *, Elf64_Mips_External_Rel *);
70 static void mips_elf64_swap_reloca_out
71   (bfd *, const Elf64_Mips_Internal_Rela *, Elf64_Mips_External_Rela *);
72 static void mips_elf64_be_swap_reloc_in
73   (bfd *, const bfd_byte *, Elf_Internal_Rela *);
74 static void mips_elf64_be_swap_reloc_out
75   (bfd *, const Elf_Internal_Rela *, bfd_byte *);
76 static void mips_elf64_be_swap_reloca_in
77   (bfd *, const bfd_byte *, Elf_Internal_Rela *);
78 static void mips_elf64_be_swap_reloca_out
79   (bfd *, const Elf_Internal_Rela *, bfd_byte *);
80 static reloc_howto_type *bfd_elf64_bfd_reloc_type_lookup
81   (bfd *, bfd_reloc_code_real_type);
82 static reloc_howto_type *mips_elf64_rtype_to_howto
83   (unsigned int, bfd_boolean);
84 static void mips_elf64_info_to_howto_rel
85   (bfd *, arelent *, Elf_Internal_Rela *);
86 static void mips_elf64_info_to_howto_rela
87   (bfd *, arelent *, Elf_Internal_Rela *);
88 static long mips_elf64_get_reloc_upper_bound
89   (bfd *, asection *);
90 static long mips_elf64_canonicalize_reloc
91   (bfd *, asection *, arelent **, asymbol **);
92 static long mips_elf64_get_dynamic_reloc_upper_bound
93   (bfd *);
94 static long mips_elf64_canonicalize_dynamic_reloc
95   (bfd *, arelent **, asymbol **);
96 static bfd_boolean mips_elf64_slurp_one_reloc_table
97   (bfd *, asection *, Elf_Internal_Shdr *, bfd_size_type, arelent *,
98    asymbol **, bfd_boolean);
99 static bfd_boolean mips_elf64_slurp_reloc_table
100   (bfd *, asection *, asymbol **, bfd_boolean);
101 static void mips_elf64_write_relocs
102   (bfd *, asection *, void *);
103 static void mips_elf64_write_rel
104   (bfd *, asection *, Elf_Internal_Shdr *, int *, void *);
105 static void mips_elf64_write_rela
106   (bfd *, asection *, Elf_Internal_Shdr *, int *, void *);
107 static bfd_reloc_status_type mips_elf64_gprel16_reloc
108   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
109 static bfd_reloc_status_type mips_elf64_literal_reloc
110   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
111 static bfd_reloc_status_type mips_elf64_gprel32_reloc
112   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
113 static bfd_reloc_status_type mips_elf64_shift6_reloc
114   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
115 static bfd_reloc_status_type mips16_jump_reloc
116   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
117 static bfd_reloc_status_type mips16_gprel_reloc
118   (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
119 static bfd_boolean mips_elf64_assign_gp
120   (bfd *, bfd_vma *);
121 static bfd_reloc_status_type mips_elf64_final_gp
122   (bfd *, asymbol *, bfd_boolean, char **, bfd_vma *);
123 static bfd_boolean mips_elf64_object_p
124   (bfd *);
125 static irix_compat_t elf64_mips_irix_compat
126   (bfd *);
127 static bfd_boolean elf64_mips_grok_prstatus
128   (bfd *, Elf_Internal_Note *);
129 static bfd_boolean elf64_mips_grok_psinfo
130   (bfd *, Elf_Internal_Note *);
131 
132 extern const bfd_target bfd_elf64_bigmips_vec;
133 extern const bfd_target bfd_elf64_littlemips_vec;
134 
135 /* In case we're on a 32-bit machine, construct a 64-bit "-1" value
136    from smaller values.  Start with zero, widen, *then* decrement.  */
137 #define MINUS_ONE	(((bfd_vma)0) - 1)
138 
139 /* The number of local .got entries we reserve.  */
140 #define MIPS_RESERVED_GOTNO (2)
141 
142 /* The relocation table used for SHT_REL sections.  */
143 
144 static reloc_howto_type mips_elf64_howto_table_rel[] =
145 {
146   /* No relocation.  */
147   HOWTO (R_MIPS_NONE,		/* type */
148 	 0,			/* rightshift */
149 	 0,			/* size (0 = byte, 1 = short, 2 = long) */
150 	 0,			/* bitsize */
151 	 FALSE,			/* pc_relative */
152 	 0,			/* bitpos */
153 	 complain_overflow_dont, /* complain_on_overflow */
154 	 _bfd_mips_elf_generic_reloc,	/* special_function */
155 	 "R_MIPS_NONE",		/* name */
156 	 FALSE,			/* partial_inplace */
157 	 0,			/* src_mask */
158 	 0,			/* dst_mask */
159 	 FALSE),		/* pcrel_offset */
160 
161   /* 16 bit relocation.  */
162   HOWTO (R_MIPS_16,		/* type */
163 	 0,			/* rightshift */
164 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
165 	 16,			/* bitsize */
166 	 FALSE,			/* pc_relative */
167 	 0,			/* bitpos */
168 	 complain_overflow_signed, /* complain_on_overflow */
169 	 _bfd_mips_elf_generic_reloc,	/* special_function */
170 	 "R_MIPS_16",		/* name */
171 	 TRUE,			/* partial_inplace */
172 	 0x0000ffff,		/* src_mask */
173 	 0x0000ffff,		/* dst_mask */
174 	 FALSE),		/* pcrel_offset */
175 
176   /* 32 bit relocation.  */
177   HOWTO (R_MIPS_32,		/* type */
178 	 0,			/* rightshift */
179 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
180 	 32,			/* bitsize */
181 	 FALSE,			/* pc_relative */
182 	 0,			/* bitpos */
183 	 complain_overflow_dont, /* complain_on_overflow */
184 	 _bfd_mips_elf_generic_reloc,	/* special_function */
185 	 "R_MIPS_32",		/* name */
186 	 TRUE,			/* partial_inplace */
187 	 0xffffffff,		/* src_mask */
188 	 0xffffffff,		/* dst_mask */
189 	 FALSE),		/* pcrel_offset */
190 
191   /* 32 bit symbol relative relocation.  */
192   HOWTO (R_MIPS_REL32,		/* type */
193 	 0,			/* rightshift */
194 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
195 	 32,			/* bitsize */
196 	 FALSE,			/* pc_relative */
197 	 0,			/* bitpos */
198 	 complain_overflow_dont, /* complain_on_overflow */
199 	 _bfd_mips_elf_generic_reloc,	/* special_function */
200 	 "R_MIPS_REL32",	/* name */
201 	 TRUE,			/* partial_inplace */
202 	 0xffffffff,		/* src_mask */
203 	 0xffffffff,		/* dst_mask */
204 	 FALSE),		/* pcrel_offset */
205 
206   /* 26 bit jump address.  */
207   HOWTO (R_MIPS_26,		/* type */
208 	 2,			/* rightshift */
209 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
210 	 26,			/* bitsize */
211 	 FALSE,			/* pc_relative */
212 	 0,			/* bitpos */
213 	 complain_overflow_dont, /* complain_on_overflow */
214 				/* This needs complex overflow
215 				   detection, because the upper 36
216 				   bits must match the PC + 4.  */
217 	 _bfd_mips_elf_generic_reloc,	/* special_function */
218 	 "R_MIPS_26",		/* name */
219 	 TRUE,			/* partial_inplace */
220 	 0x03ffffff,		/* src_mask */
221 	 0x03ffffff,		/* dst_mask */
222 	 FALSE),		/* pcrel_offset */
223 
224   /* R_MIPS_HI16 and R_MIPS_LO16 are unsupported for NewABI REL.
225      However, the native IRIX6 tools use them, so we try our best. */
226 
227   /* High 16 bits of symbol value.  */
228   HOWTO (R_MIPS_HI16,		/* type */
229 	 16,			/* rightshift */
230 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
231 	 16,			/* bitsize */
232 	 FALSE,			/* pc_relative */
233 	 0,			/* bitpos */
234 	 complain_overflow_dont, /* complain_on_overflow */
235 	 _bfd_mips_elf_hi16_reloc, /* special_function */
236 	 "R_MIPS_HI16",		/* name */
237 	 TRUE,			/* partial_inplace */
238 	 0x0000ffff,		/* src_mask */
239 	 0x0000ffff,		/* dst_mask */
240 	 FALSE),		/* pcrel_offset */
241 
242   /* Low 16 bits of symbol value.  */
243   HOWTO (R_MIPS_LO16,		/* type */
244 	 0,			/* rightshift */
245 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
246 	 16,			/* bitsize */
247 	 FALSE,			/* pc_relative */
248 	 0,			/* bitpos */
249 	 complain_overflow_dont, /* complain_on_overflow */
250 	 _bfd_mips_elf_lo16_reloc, /* special_function */
251 	 "R_MIPS_LO16",		/* name */
252 	 TRUE,			/* partial_inplace */
253 	 0x0000ffff,		/* src_mask */
254 	 0x0000ffff,		/* dst_mask */
255 	 FALSE),		/* pcrel_offset */
256 
257   /* GP relative reference.  */
258   HOWTO (R_MIPS_GPREL16,	/* type */
259 	 0,			/* rightshift */
260 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
261 	 16,			/* bitsize */
262 	 FALSE,			/* pc_relative */
263 	 0,			/* bitpos */
264 	 complain_overflow_signed, /* complain_on_overflow */
265 	 mips_elf64_gprel16_reloc, /* special_function */
266 	 "R_MIPS_GPREL16",	/* name */
267 	 TRUE,			/* partial_inplace */
268 	 0x0000ffff,		/* src_mask */
269 	 0x0000ffff,		/* dst_mask */
270 	 FALSE),		/* pcrel_offset */
271 
272   /* Reference to literal section.  */
273   HOWTO (R_MIPS_LITERAL,	/* type */
274 	 0,			/* rightshift */
275 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
276 	 16,			/* bitsize */
277 	 FALSE,			/* pc_relative */
278 	 0,			/* bitpos */
279 	 complain_overflow_signed, /* complain_on_overflow */
280 	 mips_elf64_literal_reloc, /* special_function */
281 	 "R_MIPS_LITERAL",	/* name */
282 	 TRUE,			/* partial_inplace */
283 	 0x0000ffff,		/* src_mask */
284 	 0x0000ffff,		/* dst_mask */
285 	 FALSE),		/* pcrel_offset */
286 
287   /* Reference to global offset table.  */
288   HOWTO (R_MIPS_GOT16,		/* type */
289 	 0,			/* rightshift */
290 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
291 	 16,			/* bitsize */
292 	 FALSE,			/* pc_relative */
293 	 0,			/* bitpos */
294 	 complain_overflow_signed, /* complain_on_overflow */
295 	 _bfd_mips_elf_got16_reloc, /* special_function */
296 	 "R_MIPS_GOT16",	/* name */
297 	 TRUE,			/* partial_inplace */
298 	 0x0000ffff,		/* src_mask */
299 	 0x0000ffff,		/* dst_mask */
300 	 FALSE),		/* pcrel_offset */
301 
302   /* 16 bit PC relative reference.  */
303   HOWTO (R_MIPS_PC16,		/* type */
304 	 0,			/* rightshift */
305 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
306 	 16,			/* bitsize */
307 	 TRUE,			/* pc_relative */
308 	 0,			/* bitpos */
309 	 complain_overflow_signed, /* complain_on_overflow */
310 	 _bfd_mips_elf_generic_reloc,	/* special_function */
311 	 "R_MIPS_PC16",		/* name */
312 	 TRUE,			/* partial_inplace */
313 	 0x0000ffff,		/* src_mask */
314 	 0x0000ffff,		/* dst_mask */
315 	 TRUE),			/* pcrel_offset */
316 
317   /* 16 bit call through global offset table.  */
318   HOWTO (R_MIPS_CALL16,		/* type */
319 	 0,			/* rightshift */
320 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
321 	 16,			/* bitsize */
322 	 FALSE,			/* pc_relative */
323 	 0,			/* bitpos */
324 	 complain_overflow_signed, /* complain_on_overflow */
325 	 _bfd_mips_elf_generic_reloc,	/* special_function */
326 	 "R_MIPS_CALL16",	/* name */
327 	 TRUE,			/* partial_inplace */
328 	 0x0000ffff,		/* src_mask */
329 	 0x0000ffff,		/* dst_mask */
330 	 FALSE),		/* pcrel_offset */
331 
332   /* 32 bit GP relative reference.  */
333   HOWTO (R_MIPS_GPREL32,	/* type */
334 	 0,			/* rightshift */
335 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
336 	 32,			/* bitsize */
337 	 FALSE,			/* pc_relative */
338 	 0,			/* bitpos */
339 	 complain_overflow_dont, /* complain_on_overflow */
340 	 mips_elf64_gprel32_reloc, /* special_function */
341 	 "R_MIPS_GPREL32",	/* name */
342 	 TRUE,			/* partial_inplace */
343 	 0xffffffff,		/* src_mask */
344 	 0xffffffff,		/* dst_mask */
345 	 FALSE),		/* pcrel_offset */
346 
347   EMPTY_HOWTO (13),
348   EMPTY_HOWTO (14),
349   EMPTY_HOWTO (15),
350 
351   /* A 5 bit shift field.  */
352   HOWTO (R_MIPS_SHIFT5,		/* type */
353 	 0,			/* rightshift */
354 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
355 	 5,			/* bitsize */
356 	 FALSE,			/* pc_relative */
357 	 6,			/* bitpos */
358 	 complain_overflow_bitfield, /* complain_on_overflow */
359 	 _bfd_mips_elf_generic_reloc,	/* special_function */
360 	 "R_MIPS_SHIFT5",	/* name */
361 	 TRUE,			/* partial_inplace */
362 	 0x000007c0,		/* src_mask */
363 	 0x000007c0,		/* dst_mask */
364 	 FALSE),		/* pcrel_offset */
365 
366   /* A 6 bit shift field.  */
367   HOWTO (R_MIPS_SHIFT6,		/* type */
368 	 0,			/* rightshift */
369 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
370 	 6,			/* bitsize */
371 	 FALSE,			/* pc_relative */
372 	 6,			/* bitpos */
373 	 complain_overflow_bitfield, /* complain_on_overflow */
374 	 mips_elf64_shift6_reloc, /* special_function */
375 	 "R_MIPS_SHIFT6",	/* name */
376 	 TRUE,			/* partial_inplace */
377 	 0x000007c4,		/* src_mask */
378 	 0x000007c4,		/* dst_mask */
379 	 FALSE),		/* pcrel_offset */
380 
381   /* 64 bit relocation.  */
382   HOWTO (R_MIPS_64,		/* type */
383 	 0,			/* rightshift */
384 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
385 	 64,			/* bitsize */
386 	 FALSE,			/* pc_relative */
387 	 0,			/* bitpos */
388 	 complain_overflow_dont, /* complain_on_overflow */
389 	 _bfd_mips_elf_generic_reloc,	/* special_function */
390 	 "R_MIPS_64",		/* name */
391 	 TRUE,			/* partial_inplace */
392 	 MINUS_ONE,		/* src_mask */
393 	 MINUS_ONE,		/* dst_mask */
394 	 FALSE),		/* pcrel_offset */
395 
396   /* Displacement in the global offset table.  */
397   HOWTO (R_MIPS_GOT_DISP,	/* type */
398 	 0,			/* rightshift */
399 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
400 	 16,			/* bitsize */
401 	 FALSE,			/* pc_relative */
402 	 0,			/* bitpos */
403 	 complain_overflow_signed, /* complain_on_overflow */
404 	 _bfd_mips_elf_generic_reloc,	/* special_function */
405 	 "R_MIPS_GOT_DISP",	/* name */
406 	 TRUE,			/* partial_inplace */
407 	 0x0000ffff,		/* src_mask */
408 	 0x0000ffff,		/* dst_mask */
409 	 FALSE),		/* pcrel_offset */
410 
411   /* Displacement to page pointer in the global offset table.  */
412   HOWTO (R_MIPS_GOT_PAGE,	/* type */
413 	 0,			/* rightshift */
414 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
415 	 16,			/* bitsize */
416 	 FALSE,			/* pc_relative */
417 	 0,			/* bitpos */
418 	 complain_overflow_signed, /* complain_on_overflow */
419 	 _bfd_mips_elf_generic_reloc,	/* special_function */
420 	 "R_MIPS_GOT_PAGE",	/* name */
421 	 TRUE,			/* partial_inplace */
422 	 0x0000ffff,		/* src_mask */
423 	 0x0000ffff,		/* dst_mask */
424 	 FALSE),		/* pcrel_offset */
425 
426   /* Offset from page pointer in the global offset table.  */
427   HOWTO (R_MIPS_GOT_OFST,	/* type */
428 	 0,			/* rightshift */
429 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
430 	 16,			/* bitsize */
431 	 FALSE,			/* pc_relative */
432 	 0,			/* bitpos */
433 	 complain_overflow_signed, /* complain_on_overflow */
434 	 _bfd_mips_elf_generic_reloc,	/* special_function */
435 	 "R_MIPS_GOT_OFST",	/* name */
436 	 TRUE,			/* partial_inplace */
437 	 0x0000ffff,		/* src_mask */
438 	 0x0000ffff,		/* dst_mask */
439 	 FALSE),		/* pcrel_offset */
440 
441   /* High 16 bits of displacement in global offset table.  */
442   HOWTO (R_MIPS_GOT_HI16,	/* type */
443 	 0,			/* rightshift */
444 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
445 	 16,			/* bitsize */
446 	 FALSE,			/* pc_relative */
447 	 0,			/* bitpos */
448 	 complain_overflow_dont, /* complain_on_overflow */
449 	 _bfd_mips_elf_generic_reloc,	/* special_function */
450 	 "R_MIPS_GOT_HI16",	/* name */
451 	 TRUE,			/* partial_inplace */
452 	 0x0000ffff,		/* src_mask */
453 	 0x0000ffff,		/* dst_mask */
454 	 FALSE),		/* pcrel_offset */
455 
456   /* Low 16 bits of displacement in global offset table.  */
457   HOWTO (R_MIPS_GOT_LO16,	/* type */
458 	 0,			/* rightshift */
459 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
460 	 16,			/* bitsize */
461 	 FALSE,			/* pc_relative */
462 	 0,			/* bitpos */
463 	 complain_overflow_dont, /* complain_on_overflow */
464 	 _bfd_mips_elf_generic_reloc,	/* special_function */
465 	 "R_MIPS_GOT_LO16",	/* name */
466 	 TRUE,			/* partial_inplace */
467 	 0x0000ffff,		/* src_mask */
468 	 0x0000ffff,		/* dst_mask */
469 	 FALSE),		/* pcrel_offset */
470 
471   /* 64 bit subtraction.  */
472   HOWTO (R_MIPS_SUB,		/* type */
473 	 0,			/* rightshift */
474 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
475 	 64,			/* bitsize */
476 	 FALSE,			/* pc_relative */
477 	 0,			/* bitpos */
478 	 complain_overflow_dont, /* complain_on_overflow */
479 	 _bfd_mips_elf_generic_reloc,	/* special_function */
480 	 "R_MIPS_SUB",		/* name */
481 	 TRUE,			/* partial_inplace */
482 	 MINUS_ONE,		/* src_mask */
483 	 MINUS_ONE,		/* dst_mask */
484 	 FALSE),		/* pcrel_offset */
485 
486   /* Insert the addend as an instruction.  */
487   /* FIXME: Not handled correctly.  */
488   HOWTO (R_MIPS_INSERT_A,	/* type */
489 	 0,			/* rightshift */
490 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
491 	 32,			/* bitsize */
492 	 FALSE,			/* pc_relative */
493 	 0,			/* bitpos */
494 	 complain_overflow_dont, /* complain_on_overflow */
495 	 _bfd_mips_elf_generic_reloc,	/* special_function */
496 	 "R_MIPS_INSERT_A",	/* name */
497 	 TRUE,			/* partial_inplace */
498 	 0xffffffff,		/* src_mask */
499 	 0xffffffff,		/* dst_mask */
500 	 FALSE),		/* pcrel_offset */
501 
502   /* Insert the addend as an instruction, and change all relocations
503      to refer to the old instruction at the address.  */
504   /* FIXME: Not handled correctly.  */
505   HOWTO (R_MIPS_INSERT_B,	/* type */
506 	 0,			/* rightshift */
507 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
508 	 32,			/* bitsize */
509 	 FALSE,			/* pc_relative */
510 	 0,			/* bitpos */
511 	 complain_overflow_dont, /* complain_on_overflow */
512 	 _bfd_mips_elf_generic_reloc,	/* special_function */
513 	 "R_MIPS_INSERT_B",	/* name */
514 	 TRUE,			/* partial_inplace */
515 	 0xffffffff,		/* src_mask */
516 	 0xffffffff,		/* dst_mask */
517 	 FALSE),		/* pcrel_offset */
518 
519   /* Delete a 32 bit instruction.  */
520   /* FIXME: Not handled correctly.  */
521   HOWTO (R_MIPS_DELETE,		/* type */
522 	 0,			/* rightshift */
523 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
524 	 32,			/* bitsize */
525 	 FALSE,			/* pc_relative */
526 	 0,			/* bitpos */
527 	 complain_overflow_dont, /* complain_on_overflow */
528 	 _bfd_mips_elf_generic_reloc,	/* special_function */
529 	 "R_MIPS_DELETE",	/* name */
530 	 TRUE,			/* partial_inplace */
531 	 0xffffffff,		/* src_mask */
532 	 0xffffffff,		/* dst_mask */
533 	 FALSE),		/* pcrel_offset */
534 
535   /* The MIPS ELF64 ABI Draft wants us to support these for REL relocations.
536      We don't, because
537        a) It means building the addend from a R_MIPS_HIGHEST/R_MIPS_HIGHER/
538 	  R_MIPS_HI16/R_MIPS_LO16 sequence with varying ordering, using
539 	  fallable heuristics.
540        b) No other NewABI toolchain actually emits such relocations.  */
541   EMPTY_HOWTO (R_MIPS_HIGHER),
542   EMPTY_HOWTO (R_MIPS_HIGHEST),
543 
544   /* High 16 bits of displacement in global offset table.  */
545   HOWTO (R_MIPS_CALL_HI16,	/* type */
546 	 0,			/* rightshift */
547 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
548 	 16,			/* bitsize */
549 	 FALSE,			/* pc_relative */
550 	 0,			/* bitpos */
551 	 complain_overflow_dont, /* complain_on_overflow */
552 	 _bfd_mips_elf_generic_reloc,	/* special_function */
553 	 "R_MIPS_CALL_HI16",	/* name */
554 	 TRUE,			/* partial_inplace */
555 	 0x0000ffff,		/* src_mask */
556 	 0x0000ffff,		/* dst_mask */
557 	 FALSE),		/* pcrel_offset */
558 
559   /* Low 16 bits of displacement in global offset table.  */
560   HOWTO (R_MIPS_CALL_LO16,	/* type */
561 	 0,			/* rightshift */
562 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
563 	 16,			/* bitsize */
564 	 FALSE,			/* pc_relative */
565 	 0,			/* bitpos */
566 	 complain_overflow_dont, /* complain_on_overflow */
567 	 _bfd_mips_elf_generic_reloc,	/* special_function */
568 	 "R_MIPS_CALL_LO16",	/* name */
569 	 TRUE,			/* partial_inplace */
570 	 0x0000ffff,		/* src_mask */
571 	 0x0000ffff,		/* dst_mask */
572 	 FALSE),		/* pcrel_offset */
573 
574   /* Section displacement, used by an associated event location section.  */
575   HOWTO (R_MIPS_SCN_DISP,	/* type */
576 	 0,			/* rightshift */
577 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
578 	 32,			/* bitsize */
579 	 FALSE,			/* pc_relative */
580 	 0,			/* bitpos */
581 	 complain_overflow_dont, /* complain_on_overflow */
582 	 _bfd_mips_elf_generic_reloc,	/* special_function */
583 	 "R_MIPS_SCN_DISP",	/* name */
584 	 TRUE,			/* partial_inplace */
585 	 0xffffffff,		/* src_mask */
586 	 0xffffffff,		/* dst_mask */
587 	 FALSE),		/* pcrel_offset */
588 
589   HOWTO (R_MIPS_REL16,		/* type */
590 	 0,			/* rightshift */
591 	 1,			/* size (0 = byte, 1 = short, 2 = long) */
592 	 16,			/* bitsize */
593 	 FALSE,			/* pc_relative */
594 	 0,			/* bitpos */
595 	 complain_overflow_signed, /* complain_on_overflow */
596 	 _bfd_mips_elf_generic_reloc,	/* special_function */
597 	 "R_MIPS_REL16",	/* name */
598 	 TRUE,			/* partial_inplace */
599 	 0xffff,		/* src_mask */
600 	 0xffff,		/* dst_mask */
601 	 FALSE),		/* pcrel_offset */
602 
603   /* These two are obsolete.  */
604   EMPTY_HOWTO (R_MIPS_ADD_IMMEDIATE),
605   EMPTY_HOWTO (R_MIPS_PJUMP),
606 
607   /* Similiar to R_MIPS_REL32, but used for relocations in a GOT section.
608      It must be used for multigot GOT's (and only there).  */
609   HOWTO (R_MIPS_RELGOT,		/* type */
610 	 0,			/* rightshift */
611 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
612 	 32,			/* bitsize */
613 	 FALSE,			/* pc_relative */
614 	 0,			/* bitpos */
615 	 complain_overflow_dont, /* complain_on_overflow */
616 	 _bfd_mips_elf_generic_reloc,	/* special_function */
617 	 "R_MIPS_RELGOT",	/* name */
618 	 TRUE,			/* partial_inplace */
619 	 0xffffffff,		/* src_mask */
620 	 0xffffffff,		/* dst_mask */
621 	 FALSE),		/* pcrel_offset */
622 
623   /* Protected jump conversion.  This is an optimization hint.  No
624      relocation is required for correctness.  */
625   HOWTO (R_MIPS_JALR,		/* type */
626 	 0,			/* rightshift */
627 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
628 	 32,			/* bitsize */
629 	 FALSE,			/* pc_relative */
630 	 0,			/* bitpos */
631 	 complain_overflow_dont, /* complain_on_overflow */
632 	 _bfd_mips_elf_generic_reloc,	/* special_function */
633 	 "R_MIPS_JALR",		/* name */
634 	 FALSE,			/* partial_inplace */
635 	 0,			/* src_mask */
636 	 0x00000000,		/* dst_mask */
637 	 FALSE),		/* pcrel_offset */
638 
639   /* TLS relocations.  */
640   EMPTY_HOWTO (R_MIPS_TLS_DTPMOD32),
641   EMPTY_HOWTO (R_MIPS_TLS_DTPREL32),
642 
643   HOWTO (R_MIPS_TLS_DTPMOD64,	/* type */
644 	 0,			/* rightshift */
645 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
646 	 64,			/* bitsize */
647 	 FALSE,			/* pc_relative */
648 	 0,			/* bitpos */
649 	 complain_overflow_dont, /* complain_on_overflow */
650 	 _bfd_mips_elf_generic_reloc, /* special_function */
651 	 "R_MIPS_TLS_DTPMOD64",	/* name */
652 	 TRUE,			/* partial_inplace */
653 	 MINUS_ONE,		/* src_mask */
654 	 MINUS_ONE,		/* dst_mask */
655 	 FALSE),		/* pcrel_offset */
656 
657   HOWTO (R_MIPS_TLS_DTPREL64,	/* type */
658 	 0,			/* rightshift */
659 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
660 	 64,			/* bitsize */
661 	 FALSE,			/* pc_relative */
662 	 0,			/* bitpos */
663 	 complain_overflow_dont, /* complain_on_overflow */
664 	 _bfd_mips_elf_generic_reloc, /* special_function */
665 	 "R_MIPS_TLS_DTPREL64",	/* name */
666 	 TRUE,			/* partial_inplace */
667 	 MINUS_ONE,		/* src_mask */
668 	 MINUS_ONE,		/* dst_mask */
669 	 FALSE),		/* pcrel_offset */
670 
671   /* TLS general dynamic variable reference.  */
672   HOWTO (R_MIPS_TLS_GD,		/* type */
673 	 0,			/* rightshift */
674 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
675 	 16,			/* bitsize */
676 	 FALSE,			/* pc_relative */
677 	 0,			/* bitpos */
678 	 complain_overflow_signed, /* complain_on_overflow */
679 	 _bfd_mips_elf_generic_reloc, /* special_function */
680 	 "R_MIPS_TLS_GD",	/* name */
681 	 TRUE,			/* partial_inplace */
682 	 0x0000ffff,		/* src_mask */
683 	 0x0000ffff,		/* dst_mask */
684 	 FALSE),		/* pcrel_offset */
685 
686   /* TLS local dynamic variable reference.  */
687   HOWTO (R_MIPS_TLS_LDM,	/* type */
688 	 0,			/* rightshift */
689 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
690 	 16,			/* bitsize */
691 	 FALSE,			/* pc_relative */
692 	 0,			/* bitpos */
693 	 complain_overflow_signed, /* complain_on_overflow */
694 	 _bfd_mips_elf_generic_reloc, /* special_function */
695 	 "R_MIPS_TLS_LDM",	/* name */
696 	 TRUE,			/* partial_inplace */
697 	 0x0000ffff,		/* src_mask */
698 	 0x0000ffff,		/* dst_mask */
699 	 FALSE),		/* pcrel_offset */
700 
701   /* TLS local dynamic offset.  */
702   HOWTO (R_MIPS_TLS_DTPREL_HI16,	/* type */
703 	 0,			/* rightshift */
704 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
705 	 16,			/* bitsize */
706 	 FALSE,			/* pc_relative */
707 	 0,			/* bitpos */
708 	 complain_overflow_signed, /* complain_on_overflow */
709 	 _bfd_mips_elf_generic_reloc, /* special_function */
710 	 "R_MIPS_TLS_DTPREL_HI16",	/* name */
711 	 TRUE,			/* partial_inplace */
712 	 0x0000ffff,		/* src_mask */
713 	 0x0000ffff,		/* dst_mask */
714 	 FALSE),		/* pcrel_offset */
715 
716   /* TLS local dynamic offset.  */
717   HOWTO (R_MIPS_TLS_DTPREL_LO16,	/* type */
718 	 0,			/* rightshift */
719 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
720 	 16,			/* bitsize */
721 	 FALSE,			/* pc_relative */
722 	 0,			/* bitpos */
723 	 complain_overflow_signed, /* complain_on_overflow */
724 	 _bfd_mips_elf_generic_reloc, /* special_function */
725 	 "R_MIPS_TLS_DTPREL_LO16",	/* name */
726 	 TRUE,			/* partial_inplace */
727 	 0x0000ffff,		/* src_mask */
728 	 0x0000ffff,		/* dst_mask */
729 	 FALSE),		/* pcrel_offset */
730 
731   /* TLS thread pointer offset.  */
732   HOWTO (R_MIPS_TLS_GOTTPREL,	/* type */
733 	 0,			/* rightshift */
734 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
735 	 16,			/* bitsize */
736 	 FALSE,			/* pc_relative */
737 	 0,			/* bitpos */
738 	 complain_overflow_signed, /* complain_on_overflow */
739 	 _bfd_mips_elf_generic_reloc, /* special_function */
740 	 "R_MIPS_TLS_GOTTPREL",	/* name */
741 	 TRUE,			/* partial_inplace */
742 	 0x0000ffff,		/* src_mask */
743 	 0x0000ffff,		/* dst_mask */
744 	 FALSE),		/* pcrel_offset */
745 
746   /* TLS IE dynamic relocations.  */
747   EMPTY_HOWTO (R_MIPS_TLS_TPREL32),
748 
749   HOWTO (R_MIPS_TLS_TPREL64,	/* type */
750 	 0,			/* rightshift */
751 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
752 	 64,			/* bitsize */
753 	 FALSE,			/* pc_relative */
754 	 0,			/* bitpos */
755 	 complain_overflow_dont, /* complain_on_overflow */
756 	 _bfd_mips_elf_generic_reloc, /* special_function */
757 	 "R_MIPS_TLS_TPREL64",	/* name */
758 	 TRUE,			/* partial_inplace */
759 	 MINUS_ONE,		/* src_mask */
760 	 MINUS_ONE,		/* dst_mask */
761 	 FALSE),		/* pcrel_offset */
762 
763   /* TLS thread pointer offset.  */
764   HOWTO (R_MIPS_TLS_TPREL_HI16,	/* type */
765 	 0,			/* rightshift */
766 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
767 	 16,			/* bitsize */
768 	 FALSE,			/* pc_relative */
769 	 0,			/* bitpos */
770 	 complain_overflow_signed, /* complain_on_overflow */
771 	 _bfd_mips_elf_generic_reloc, /* special_function */
772 	 "R_MIPS_TLS_TPREL_HI16", /* name */
773 	 TRUE,			/* partial_inplace */
774 	 0x0000ffff,		/* src_mask */
775 	 0x0000ffff,		/* dst_mask */
776 	 FALSE),		/* pcrel_offset */
777 
778   /* TLS thread pointer offset.  */
779   HOWTO (R_MIPS_TLS_TPREL_LO16,	/* type */
780 	 0,			/* rightshift */
781 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
782 	 16,			/* bitsize */
783 	 FALSE,			/* pc_relative */
784 	 0,			/* bitpos */
785 	 complain_overflow_signed, /* complain_on_overflow */
786 	 _bfd_mips_elf_generic_reloc, /* special_function */
787 	 "R_MIPS_TLS_TPREL_LO16", /* name */
788 	 TRUE,			/* partial_inplace */
789 	 0x0000ffff,		/* src_mask */
790 	 0x0000ffff,		/* dst_mask */
791 	 FALSE),		/* pcrel_offset */
792 };
793 
794 /* The relocation table used for SHT_RELA sections.  */
795 
796 static reloc_howto_type mips_elf64_howto_table_rela[] =
797 {
798   /* No relocation.  */
799   HOWTO (R_MIPS_NONE,		/* type */
800 	 0,			/* rightshift */
801 	 0,			/* size (0 = byte, 1 = short, 2 = long) */
802 	 0,			/* bitsize */
803 	 FALSE,			/* pc_relative */
804 	 0,			/* bitpos */
805 	 complain_overflow_dont, /* complain_on_overflow */
806 	 _bfd_mips_elf_generic_reloc,	/* special_function */
807 	 "R_MIPS_NONE",		/* name */
808 	 FALSE,			/* partial_inplace */
809 	 0,			/* src_mask */
810 	 0,			/* dst_mask */
811 	 FALSE),		/* pcrel_offset */
812 
813   /* 16 bit relocation.  */
814   HOWTO (R_MIPS_16,		/* type */
815 	 0,			/* rightshift */
816 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
817 	 16,			/* bitsize */
818 	 FALSE,			/* pc_relative */
819 	 0,			/* bitpos */
820 	 complain_overflow_signed, /* complain_on_overflow */
821 	 _bfd_mips_elf_generic_reloc,	/* special_function */
822 	 "R_MIPS_16",		/* name */
823 	 FALSE,			/* partial_inplace */
824 	 0,			/* src_mask */
825 	 0x0000ffff,		/* dst_mask */
826 	 FALSE),		/* pcrel_offset */
827 
828   /* 32 bit relocation.  */
829   HOWTO (R_MIPS_32,		/* type */
830 	 0,			/* rightshift */
831 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
832 	 32,			/* bitsize */
833 	 FALSE,			/* pc_relative */
834 	 0,			/* bitpos */
835 	 complain_overflow_dont, /* complain_on_overflow */
836 	 _bfd_mips_elf_generic_reloc,	/* special_function */
837 	 "R_MIPS_32",		/* name */
838 	 FALSE,			/* partial_inplace */
839 	 0,			/* src_mask */
840 	 0xffffffff,		/* dst_mask */
841 	 FALSE),		/* pcrel_offset */
842 
843   /* 32 bit symbol relative relocation.  */
844   HOWTO (R_MIPS_REL32,		/* type */
845 	 0,			/* rightshift */
846 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
847 	 32,			/* bitsize */
848 	 FALSE,			/* pc_relative */
849 	 0,			/* bitpos */
850 	 complain_overflow_dont, /* complain_on_overflow */
851 	 _bfd_mips_elf_generic_reloc,	/* special_function */
852 	 "R_MIPS_REL32",	/* name */
853 	 FALSE,			/* partial_inplace */
854 	 0,			/* src_mask */
855 	 0xffffffff,		/* dst_mask */
856 	 FALSE),		/* pcrel_offset */
857 
858   /* 26 bit jump address.  */
859   HOWTO (R_MIPS_26,		/* type */
860 	 2,			/* rightshift */
861 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
862 	 26,			/* bitsize */
863 	 FALSE,			/* pc_relative */
864 	 0,			/* bitpos */
865 	 complain_overflow_dont, /* complain_on_overflow */
866 				/* This needs complex overflow
867 				   detection, because the upper 36
868 				   bits must match the PC + 4.  */
869 	 _bfd_mips_elf_generic_reloc,	/* special_function */
870 	 "R_MIPS_26",		/* name */
871 	 FALSE,			/* partial_inplace */
872 	 0,			/* src_mask */
873 	 0x03ffffff,		/* dst_mask */
874 	 FALSE),		/* pcrel_offset */
875 
876   /* High 16 bits of symbol value.  */
877   HOWTO (R_MIPS_HI16,		/* type */
878 	 0,			/* rightshift */
879 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
880 	 16,			/* bitsize */
881 	 FALSE,			/* pc_relative */
882 	 0,			/* bitpos */
883 	 complain_overflow_dont, /* complain_on_overflow */
884 	 _bfd_mips_elf_generic_reloc,	/* special_function */
885 	 "R_MIPS_HI16",		/* name */
886 	 FALSE,			/* partial_inplace */
887 	 0,			/* src_mask */
888 	 0x0000ffff,		/* dst_mask */
889 	 FALSE),		/* pcrel_offset */
890 
891   /* Low 16 bits of symbol value.  */
892   HOWTO (R_MIPS_LO16,		/* type */
893 	 0,			/* rightshift */
894 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
895 	 16,			/* bitsize */
896 	 FALSE,			/* pc_relative */
897 	 0,			/* bitpos */
898 	 complain_overflow_dont, /* complain_on_overflow */
899 	 _bfd_mips_elf_generic_reloc,	/* special_function */
900 	 "R_MIPS_LO16",		/* name */
901 	 FALSE,			/* partial_inplace */
902 	 0,			/* src_mask */
903 	 0x0000ffff,		/* dst_mask */
904 	 FALSE),		/* pcrel_offset */
905 
906   /* GP relative reference.  */
907   HOWTO (R_MIPS_GPREL16,	/* type */
908 	 0,			/* rightshift */
909 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
910 	 16,			/* bitsize */
911 	 FALSE,			/* pc_relative */
912 	 0,			/* bitpos */
913 	 complain_overflow_signed, /* complain_on_overflow */
914 	 mips_elf64_gprel16_reloc, /* special_function */
915 	 "R_MIPS_GPREL16",	/* name */
916 	 FALSE,			/* partial_inplace */
917 	 0,			/* src_mask */
918 	 0x0000ffff,		/* dst_mask */
919 	 FALSE),		/* pcrel_offset */
920 
921   /* Reference to literal section.  */
922   HOWTO (R_MIPS_LITERAL,	/* type */
923 	 0,			/* rightshift */
924 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
925 	 16,			/* bitsize */
926 	 FALSE,			/* pc_relative */
927 	 0,			/* bitpos */
928 	 complain_overflow_signed, /* complain_on_overflow */
929 	 mips_elf64_literal_reloc, /* special_function */
930 	 "R_MIPS_LITERAL",	/* name */
931 	 FALSE,			/* partial_inplace */
932 	 0,			/* src_mask */
933 	 0x0000ffff,		/* dst_mask */
934 	 FALSE),		/* pcrel_offset */
935 
936   /* Reference to global offset table.  */
937   HOWTO (R_MIPS_GOT16,		/* type */
938 	 0,			/* rightshift */
939 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
940 	 16,			/* bitsize */
941 	 FALSE,			/* pc_relative */
942 	 0,			/* bitpos */
943 	 complain_overflow_signed, /* complain_on_overflow */
944 	 _bfd_mips_elf_generic_reloc, /* special_function */
945 	 "R_MIPS_GOT16",	/* name */
946 	 FALSE,			/* partial_inplace */
947 	 0,			/* src_mask */
948 	 0x0000ffff,		/* dst_mask */
949 	 FALSE),		/* pcrel_offset */
950 
951   /* 16 bit PC relative reference.  */
952   HOWTO (R_MIPS_PC16,		/* type */
953 	 0,			/* rightshift */
954 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
955 	 16,			/* bitsize */
956 	 TRUE,			/* pc_relative */
957 	 0,			/* bitpos */
958 	 complain_overflow_signed, /* complain_on_overflow */
959 	 _bfd_mips_elf_generic_reloc,	/* special_function */
960 	 "R_MIPS_PC16",		/* name */
961 	 FALSE,			/* partial_inplace */
962 	 0,			/* src_mask */
963 	 0x0000ffff,		/* dst_mask */
964 	 TRUE),			/* pcrel_offset */
965 
966   /* 16 bit call through global offset table.  */
967   HOWTO (R_MIPS_CALL16,		/* type */
968 	 0,			/* rightshift */
969 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
970 	 16,			/* bitsize */
971 	 FALSE,			/* pc_relative */
972 	 0,			/* bitpos */
973 	 complain_overflow_signed, /* complain_on_overflow */
974 	 _bfd_mips_elf_generic_reloc,	/* special_function */
975 	 "R_MIPS_CALL16",	/* name */
976 	 FALSE,			/* partial_inplace */
977 	 0,			/* src_mask */
978 	 0x0000ffff,		/* dst_mask */
979 	 FALSE),		/* pcrel_offset */
980 
981   /* 32 bit GP relative reference.  */
982   HOWTO (R_MIPS_GPREL32,	/* type */
983 	 0,			/* rightshift */
984 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
985 	 32,			/* bitsize */
986 	 FALSE,			/* pc_relative */
987 	 0,			/* bitpos */
988 	 complain_overflow_dont, /* complain_on_overflow */
989 	 mips_elf64_gprel32_reloc, /* special_function */
990 	 "R_MIPS_GPREL32",	/* name */
991 	 FALSE,			/* partial_inplace */
992 	 0,			/* src_mask */
993 	 0xffffffff,		/* dst_mask */
994 	 FALSE),		/* pcrel_offset */
995 
996   EMPTY_HOWTO (13),
997   EMPTY_HOWTO (14),
998   EMPTY_HOWTO (15),
999 
1000   /* A 5 bit shift field.  */
1001   HOWTO (R_MIPS_SHIFT5,		/* type */
1002 	 0,			/* rightshift */
1003 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1004 	 5,			/* bitsize */
1005 	 FALSE,			/* pc_relative */
1006 	 6,			/* bitpos */
1007 	 complain_overflow_bitfield, /* complain_on_overflow */
1008 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1009 	 "R_MIPS_SHIFT5",	/* name */
1010 	 FALSE,			/* partial_inplace */
1011 	 0,			/* src_mask */
1012 	 0x000007c0,		/* dst_mask */
1013 	 FALSE),		/* pcrel_offset */
1014 
1015   /* A 6 bit shift field.  */
1016   HOWTO (R_MIPS_SHIFT6,		/* type */
1017 	 0,			/* rightshift */
1018 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1019 	 6,			/* bitsize */
1020 	 FALSE,			/* pc_relative */
1021 	 6,			/* bitpos */
1022 	 complain_overflow_bitfield, /* complain_on_overflow */
1023 	 mips_elf64_shift6_reloc, /* special_function */
1024 	 "R_MIPS_SHIFT6",	/* name */
1025 	 FALSE,			/* partial_inplace */
1026 	 0,			/* src_mask */
1027 	 0x000007c4,		/* dst_mask */
1028 	 FALSE),		/* pcrel_offset */
1029 
1030   /* 64 bit relocation.  */
1031   HOWTO (R_MIPS_64,		/* type */
1032 	 0,			/* rightshift */
1033 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
1034 	 64,			/* bitsize */
1035 	 FALSE,			/* pc_relative */
1036 	 0,			/* bitpos */
1037 	 complain_overflow_dont, /* complain_on_overflow */
1038 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1039 	 "R_MIPS_64",		/* name */
1040 	 FALSE,			/* partial_inplace */
1041 	 0,			/* src_mask */
1042 	 MINUS_ONE,		/* dst_mask */
1043 	 FALSE),		/* pcrel_offset */
1044 
1045   /* Displacement in the global offset table.  */
1046   HOWTO (R_MIPS_GOT_DISP,	/* type */
1047 	 0,			/* rightshift */
1048 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1049 	 16,			/* bitsize */
1050 	 FALSE,			/* pc_relative */
1051 	 0,			/* bitpos */
1052 	 complain_overflow_signed, /* complain_on_overflow */
1053 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1054 	 "R_MIPS_GOT_DISP",	/* name */
1055 	 FALSE,			/* partial_inplace */
1056 	 0,			/* src_mask */
1057 	 0x0000ffff,		/* dst_mask */
1058 	 FALSE),		/* pcrel_offset */
1059 
1060   /* Displacement to page pointer in the global offset table.  */
1061   HOWTO (R_MIPS_GOT_PAGE,	/* type */
1062 	 0,			/* rightshift */
1063 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1064 	 16,			/* bitsize */
1065 	 FALSE,			/* pc_relative */
1066 	 0,			/* bitpos */
1067 	 complain_overflow_signed, /* complain_on_overflow */
1068 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1069 	 "R_MIPS_GOT_PAGE",	/* name */
1070 	 FALSE,			/* partial_inplace */
1071 	 0,			/* src_mask */
1072 	 0x0000ffff,		/* dst_mask */
1073 	 FALSE),		/* pcrel_offset */
1074 
1075   /* Offset from page pointer in the global offset table.  */
1076   HOWTO (R_MIPS_GOT_OFST,	/* type */
1077 	 0,			/* rightshift */
1078 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1079 	 16,			/* bitsize */
1080 	 FALSE,			/* pc_relative */
1081 	 0,			/* bitpos */
1082 	 complain_overflow_signed, /* complain_on_overflow */
1083 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1084 	 "R_MIPS_GOT_OFST",	/* name */
1085 	 FALSE,			/* partial_inplace */
1086 	 0,			/* src_mask */
1087 	 0x0000ffff,		/* dst_mask */
1088 	 FALSE),		/* pcrel_offset */
1089 
1090   /* High 16 bits of displacement in global offset table.  */
1091   HOWTO (R_MIPS_GOT_HI16,	/* type */
1092 	 0,			/* rightshift */
1093 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1094 	 16,			/* bitsize */
1095 	 FALSE,			/* pc_relative */
1096 	 0,			/* bitpos */
1097 	 complain_overflow_dont, /* complain_on_overflow */
1098 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1099 	 "R_MIPS_GOT_HI16",	/* name */
1100 	 FALSE,			/* partial_inplace */
1101 	 0,			/* src_mask */
1102 	 0x0000ffff,		/* dst_mask */
1103 	 FALSE),		/* pcrel_offset */
1104 
1105   /* Low 16 bits of displacement in global offset table.  */
1106   HOWTO (R_MIPS_GOT_LO16,	/* type */
1107 	 0,			/* rightshift */
1108 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1109 	 16,			/* bitsize */
1110 	 FALSE,			/* pc_relative */
1111 	 0,			/* bitpos */
1112 	 complain_overflow_dont, /* complain_on_overflow */
1113 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1114 	 "R_MIPS_GOT_LO16",	/* name */
1115 	 FALSE,			/* partial_inplace */
1116 	 0,			/* src_mask */
1117 	 0x0000ffff,		/* dst_mask */
1118 	 FALSE),		/* pcrel_offset */
1119 
1120   /* 64 bit subtraction.  */
1121   HOWTO (R_MIPS_SUB,		/* type */
1122 	 0,			/* rightshift */
1123 	 4,			/* size (0 = byte, 1 = short, 2 = long) */
1124 	 64,			/* bitsize */
1125 	 FALSE,			/* pc_relative */
1126 	 0,			/* bitpos */
1127 	 complain_overflow_dont, /* complain_on_overflow */
1128 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1129 	 "R_MIPS_SUB",		/* name */
1130 	 FALSE,			/* partial_inplace */
1131 	 0,			/* src_mask */
1132 	 MINUS_ONE,		/* dst_mask */
1133 	 FALSE),		/* pcrel_offset */
1134 
1135   /* Insert the addend as an instruction.  */
1136   /* FIXME: Not handled correctly.  */
1137   HOWTO (R_MIPS_INSERT_A,	/* type */
1138 	 0,			/* rightshift */
1139 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1140 	 32,			/* bitsize */
1141 	 FALSE,			/* pc_relative */
1142 	 0,			/* bitpos */
1143 	 complain_overflow_dont, /* complain_on_overflow */
1144 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1145 	 "R_MIPS_INSERT_A",	/* name */
1146 	 FALSE,			/* partial_inplace */
1147 	 0,			/* src_mask */
1148 	 0xffffffff,		/* dst_mask */
1149 	 FALSE),		/* pcrel_offset */
1150 
1151   /* Insert the addend as an instruction, and change all relocations
1152      to refer to the old instruction at the address.  */
1153   /* FIXME: Not handled correctly.  */
1154   HOWTO (R_MIPS_INSERT_B,	/* type */
1155 	 0,			/* rightshift */
1156 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1157 	 32,			/* bitsize */
1158 	 FALSE,			/* pc_relative */
1159 	 0,			/* bitpos */
1160 	 complain_overflow_dont, /* complain_on_overflow */
1161 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1162 	 "R_MIPS_INSERT_B",	/* name */
1163 	 FALSE,			/* partial_inplace */
1164 	 0,			/* src_mask */
1165 	 0xffffffff,		/* dst_mask */
1166 	 FALSE),		/* pcrel_offset */
1167 
1168   /* Delete a 32 bit instruction.  */
1169   /* FIXME: Not handled correctly.  */
1170   HOWTO (R_MIPS_DELETE,		/* type */
1171 	 0,			/* rightshift */
1172 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1173 	 32,			/* bitsize */
1174 	 FALSE,			/* pc_relative */
1175 	 0,			/* bitpos */
1176 	 complain_overflow_dont, /* complain_on_overflow */
1177 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1178 	 "R_MIPS_DELETE",	/* name */
1179 	 FALSE,			/* partial_inplace */
1180 	 0,			/* src_mask */
1181 	 0xffffffff,		/* dst_mask */
1182 	 FALSE),		/* pcrel_offset */
1183 
1184   /* Get the higher value of a 64 bit addend.  */
1185   HOWTO (R_MIPS_HIGHER,		/* type */
1186 	 0,			/* rightshift */
1187 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1188 	 16,			/* bitsize */
1189 	 FALSE,			/* pc_relative */
1190 	 0,			/* bitpos */
1191 	 complain_overflow_dont, /* complain_on_overflow */
1192 	 _bfd_mips_elf_generic_reloc, /* special_function */
1193 	 "R_MIPS_HIGHER",	/* name */
1194 	 FALSE,			/* partial_inplace */
1195 	 0,			/* src_mask */
1196 	 0x0000ffff,		/* dst_mask */
1197 	 FALSE),		/* pcrel_offset */
1198 
1199   /* Get the highest value of a 64 bit addend.  */
1200   HOWTO (R_MIPS_HIGHEST,	/* type */
1201 	 0,			/* rightshift */
1202 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1203 	 16,			/* bitsize */
1204 	 FALSE,			/* pc_relative */
1205 	 0,			/* bitpos */
1206 	 complain_overflow_dont, /* complain_on_overflow */
1207 	 _bfd_mips_elf_generic_reloc, /* special_function */
1208 	 "R_MIPS_HIGHEST",	/* name */
1209 	 FALSE,			/* partial_inplace */
1210 	 0,			/* src_mask */
1211 	 0x0000ffff,		/* dst_mask */
1212 	 FALSE),		/* pcrel_offset */
1213 
1214   /* High 16 bits of displacement in global offset table.  */
1215   HOWTO (R_MIPS_CALL_HI16,	/* type */
1216 	 0,			/* rightshift */
1217 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1218 	 16,			/* bitsize */
1219 	 FALSE,			/* pc_relative */
1220 	 0,			/* bitpos */
1221 	 complain_overflow_dont, /* complain_on_overflow */
1222 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1223 	 "R_MIPS_CALL_HI16",	/* name */
1224 	 FALSE,			/* partial_inplace */
1225 	 0,			/* src_mask */
1226 	 0x0000ffff,		/* dst_mask */
1227 	 FALSE),		/* pcrel_offset */
1228 
1229   /* Low 16 bits of displacement in global offset table.  */
1230   HOWTO (R_MIPS_CALL_LO16,	/* type */
1231 	 0,			/* rightshift */
1232 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1233 	 16,			/* bitsize */
1234 	 FALSE,			/* pc_relative */
1235 	 0,			/* bitpos */
1236 	 complain_overflow_dont, /* complain_on_overflow */
1237 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1238 	 "R_MIPS_CALL_LO16",	/* name */
1239 	 FALSE,			/* partial_inplace */
1240 	 0,			/* src_mask */
1241 	 0x0000ffff,		/* dst_mask */
1242 	 FALSE),		/* pcrel_offset */
1243 
1244   /* Section displacement, used by an associated event location section.  */
1245   HOWTO (R_MIPS_SCN_DISP,	/* type */
1246 	 0,			/* rightshift */
1247 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1248 	 32,			/* bitsize */
1249 	 FALSE,			/* pc_relative */
1250 	 0,			/* bitpos */
1251 	 complain_overflow_dont, /* complain_on_overflow */
1252 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1253 	 "R_MIPS_SCN_DISP",	/* name */
1254 	 FALSE,			/* partial_inplace */
1255 	 0,			/* src_mask */
1256 	 0xffffffff,		/* dst_mask */
1257 	 FALSE),		/* pcrel_offset */
1258 
1259   HOWTO (R_MIPS_REL16,		/* type */
1260 	 0,			/* rightshift */
1261 	 1,			/* size (0 = byte, 1 = short, 2 = long) */
1262 	 16,			/* bitsize */
1263 	 FALSE,			/* pc_relative */
1264 	 0,			/* bitpos */
1265 	 complain_overflow_signed, /* complain_on_overflow */
1266 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1267 	 "R_MIPS_REL16",	/* name */
1268 	 FALSE,			/* partial_inplace */
1269 	 0,			/* src_mask */
1270 	 0xffff,		/* dst_mask */
1271 	 FALSE),		/* pcrel_offset */
1272 
1273   /* These two are obsolete.  */
1274   EMPTY_HOWTO (R_MIPS_ADD_IMMEDIATE),
1275   EMPTY_HOWTO (R_MIPS_PJUMP),
1276 
1277   /* Similiar to R_MIPS_REL32, but used for relocations in a GOT section.
1278      It must be used for multigot GOT's (and only there).  */
1279   HOWTO (R_MIPS_RELGOT,		/* type */
1280 	 0,			/* rightshift */
1281 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1282 	 32,			/* bitsize */
1283 	 FALSE,			/* pc_relative */
1284 	 0,			/* bitpos */
1285 	 complain_overflow_dont, /* complain_on_overflow */
1286 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1287 	 "R_MIPS_RELGOT",	/* name */
1288 	 FALSE,			/* partial_inplace */
1289 	 0,			/* src_mask */
1290 	 0xffffffff,		/* dst_mask */
1291 	 FALSE),		/* pcrel_offset */
1292 
1293   /* Protected jump conversion.  This is an optimization hint.  No
1294      relocation is required for correctness.  */
1295   HOWTO (R_MIPS_JALR,		/* type */
1296 	 0,			/* rightshift */
1297 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1298 	 32,			/* bitsize */
1299 	 FALSE,			/* pc_relative */
1300 	 0,			/* bitpos */
1301 	 complain_overflow_dont, /* complain_on_overflow */
1302 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1303 	 "R_MIPS_JALR",		/* name */
1304 	 FALSE,			/* partial_inplace */
1305 	 0,			/* src_mask */
1306 	 0x00000000,		/* dst_mask */
1307 	 FALSE),		/* pcrel_offset */
1308 
1309   /* TLS relocations.  */
1310   EMPTY_HOWTO (R_MIPS_TLS_DTPMOD32),
1311   EMPTY_HOWTO (R_MIPS_TLS_DTPREL32),
1312   EMPTY_HOWTO (R_MIPS_TLS_DTPMOD64),
1313   EMPTY_HOWTO (R_MIPS_TLS_DTPREL64),
1314 
1315   /* TLS general dynamic variable reference.  */
1316   HOWTO (R_MIPS_TLS_GD,		/* type */
1317 	 0,			/* rightshift */
1318 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1319 	 16,			/* bitsize */
1320 	 FALSE,			/* pc_relative */
1321 	 0,			/* bitpos */
1322 	 complain_overflow_signed, /* complain_on_overflow */
1323 	 _bfd_mips_elf_generic_reloc, /* special_function */
1324 	 "R_MIPS_TLS_GD",	/* name */
1325 	 TRUE,			/* partial_inplace */
1326 	 0x0000ffff,		/* src_mask */
1327 	 0x0000ffff,		/* dst_mask */
1328 	 FALSE),		/* pcrel_offset */
1329 
1330   /* TLS local dynamic variable reference.  */
1331   HOWTO (R_MIPS_TLS_LDM,	/* type */
1332 	 0,			/* rightshift */
1333 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1334 	 16,			/* bitsize */
1335 	 FALSE,			/* pc_relative */
1336 	 0,			/* bitpos */
1337 	 complain_overflow_signed, /* complain_on_overflow */
1338 	 _bfd_mips_elf_generic_reloc, /* special_function */
1339 	 "R_MIPS_TLS_LDM",	/* name */
1340 	 TRUE,			/* partial_inplace */
1341 	 0x0000ffff,		/* src_mask */
1342 	 0x0000ffff,		/* dst_mask */
1343 	 FALSE),		/* pcrel_offset */
1344 
1345   /* TLS local dynamic offset.  */
1346   HOWTO (R_MIPS_TLS_DTPREL_HI16,	/* type */
1347 	 0,			/* rightshift */
1348 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1349 	 16,			/* bitsize */
1350 	 FALSE,			/* pc_relative */
1351 	 0,			/* bitpos */
1352 	 complain_overflow_signed, /* complain_on_overflow */
1353 	 _bfd_mips_elf_generic_reloc, /* special_function */
1354 	 "R_MIPS_TLS_DTPREL_HI16",	/* name */
1355 	 TRUE,			/* partial_inplace */
1356 	 0x0000ffff,		/* src_mask */
1357 	 0x0000ffff,		/* dst_mask */
1358 	 FALSE),		/* pcrel_offset */
1359 
1360   /* TLS local dynamic offset.  */
1361   HOWTO (R_MIPS_TLS_DTPREL_LO16,	/* type */
1362 	 0,			/* rightshift */
1363 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1364 	 16,			/* bitsize */
1365 	 FALSE,			/* pc_relative */
1366 	 0,			/* bitpos */
1367 	 complain_overflow_signed, /* complain_on_overflow */
1368 	 _bfd_mips_elf_generic_reloc, /* special_function */
1369 	 "R_MIPS_TLS_DTPREL_LO16",	/* name */
1370 	 TRUE,			/* partial_inplace */
1371 	 0x0000ffff,		/* src_mask */
1372 	 0x0000ffff,		/* dst_mask */
1373 	 FALSE),		/* pcrel_offset */
1374 
1375   /* TLS thread pointer offset.  */
1376   HOWTO (R_MIPS_TLS_GOTTPREL,	/* type */
1377 	 0,			/* rightshift */
1378 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1379 	 16,			/* bitsize */
1380 	 FALSE,			/* pc_relative */
1381 	 0,			/* bitpos */
1382 	 complain_overflow_signed, /* complain_on_overflow */
1383 	 _bfd_mips_elf_generic_reloc, /* special_function */
1384 	 "R_MIPS_TLS_GOTTPREL",	/* name */
1385 	 TRUE,			/* partial_inplace */
1386 	 0x0000ffff,		/* src_mask */
1387 	 0x0000ffff,		/* dst_mask */
1388 	 FALSE),		/* pcrel_offset */
1389 
1390   EMPTY_HOWTO (R_MIPS_TLS_TPREL32),
1391   EMPTY_HOWTO (R_MIPS_TLS_TPREL64),
1392 
1393   /* TLS thread pointer offset.  */
1394   HOWTO (R_MIPS_TLS_TPREL_HI16,	/* type */
1395 	 0,			/* rightshift */
1396 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1397 	 16,			/* bitsize */
1398 	 FALSE,			/* pc_relative */
1399 	 0,			/* bitpos */
1400 	 complain_overflow_signed, /* complain_on_overflow */
1401 	 _bfd_mips_elf_generic_reloc, /* special_function */
1402 	 "R_MIPS_TLS_TPREL_HI16", /* name */
1403 	 TRUE,			/* partial_inplace */
1404 	 0x0000ffff,		/* src_mask */
1405 	 0x0000ffff,		/* dst_mask */
1406 	 FALSE),		/* pcrel_offset */
1407 
1408   /* TLS thread pointer offset.  */
1409   HOWTO (R_MIPS_TLS_TPREL_LO16,	/* type */
1410 	 0,			/* rightshift */
1411 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1412 	 16,			/* bitsize */
1413 	 FALSE,			/* pc_relative */
1414 	 0,			/* bitpos */
1415 	 complain_overflow_signed, /* complain_on_overflow */
1416 	 _bfd_mips_elf_generic_reloc, /* special_function */
1417 	 "R_MIPS_TLS_TPREL_LO16", /* name */
1418 	 TRUE,			/* partial_inplace */
1419 	 0x0000ffff,		/* src_mask */
1420 	 0x0000ffff,		/* dst_mask */
1421 	 FALSE),		/* pcrel_offset */
1422 };
1423 
1424 static reloc_howto_type mips16_elf64_howto_table_rel[] =
1425 {
1426   /* The reloc used for the mips16 jump instruction.  */
1427   HOWTO (R_MIPS16_26,		/* type */
1428 	 2,			/* rightshift */
1429 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1430 	 26,			/* bitsize */
1431 	 FALSE,			/* pc_relative */
1432 	 0,			/* bitpos */
1433 	 complain_overflow_dont, /* complain_on_overflow */
1434 	 			/* This needs complex overflow
1435 				   detection, because the upper four
1436 				   bits must match the PC.  */
1437 	 mips16_jump_reloc,	/* special_function */
1438 	 "R_MIPS16_26",		/* name */
1439 	 TRUE,			/* partial_inplace */
1440 	 0x3ffffff,		/* src_mask */
1441 	 0x3ffffff,		/* dst_mask */
1442 	 FALSE),		/* pcrel_offset */
1443 
1444   /* The reloc used for the mips16 gprel instruction.  */
1445   HOWTO (R_MIPS16_GPREL,	/* type */
1446 	 0,			/* rightshift */
1447 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1448 	 16,			/* bitsize */
1449 	 FALSE,			/* pc_relative */
1450 	 0,			/* bitpos */
1451 	 complain_overflow_signed, /* complain_on_overflow */
1452 	 mips16_gprel_reloc,	/* special_function */
1453 	 "R_MIPS16_GPREL",	/* name */
1454 	 TRUE,			/* partial_inplace */
1455 	 0x0000ffff,		/* src_mask */
1456 	 0x0000ffff,	        /* dst_mask */
1457 	 FALSE),		/* pcrel_offset */
1458 
1459   /* A placeholder for MIPS16 reference to global offset table.  */
1460   EMPTY_HOWTO (R_MIPS16_GOT16),
1461 
1462   /* A placeholder for MIPS16 16 bit call through global offset table.  */
1463   EMPTY_HOWTO (R_MIPS16_CALL16),
1464 
1465   /* MIPS16 high 16 bits of symbol value.  */
1466   HOWTO (R_MIPS16_HI16,		/* type */
1467 	 16,			/* rightshift */
1468 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1469 	 16,			/* bitsize */
1470 	 FALSE,			/* pc_relative */
1471 	 0,			/* bitpos */
1472 	 complain_overflow_dont, /* complain_on_overflow */
1473 	 _bfd_mips_elf_hi16_reloc, /* special_function */
1474 	 "R_MIPS16_HI16",	/* name */
1475 	 TRUE,			/* partial_inplace */
1476 	 0x0000ffff,		/* src_mask */
1477 	 0x0000ffff,		/* dst_mask */
1478 	 FALSE),		/* pcrel_offset */
1479 
1480   /* MIPS16 low 16 bits of symbol value.  */
1481   HOWTO (R_MIPS16_LO16,		/* type */
1482 	 0,			/* rightshift */
1483 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1484 	 16,			/* bitsize */
1485 	 FALSE,			/* pc_relative */
1486 	 0,			/* bitpos */
1487 	 complain_overflow_dont, /* complain_on_overflow */
1488 	 _bfd_mips_elf_lo16_reloc, /* special_function */
1489 	 "R_MIPS16_LO16",	/* name */
1490 	 TRUE,			/* partial_inplace */
1491 	 0x0000ffff,		/* src_mask */
1492 	 0x0000ffff,		/* dst_mask */
1493 	 FALSE),		/* pcrel_offset */
1494 };
1495 
1496 static reloc_howto_type mips16_elf64_howto_table_rela[] =
1497 {
1498   /* The reloc used for the mips16 jump instruction.  */
1499   HOWTO (R_MIPS16_26,		/* type */
1500 	 2,			/* rightshift */
1501 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1502 	 26,			/* bitsize */
1503 	 FALSE,			/* pc_relative */
1504 	 0,			/* bitpos */
1505 	 complain_overflow_dont, /* complain_on_overflow */
1506 	 			/* This needs complex overflow
1507 				   detection, because the upper four
1508 				   bits must match the PC.  */
1509 	 mips16_jump_reloc,	/* special_function */
1510 	 "R_MIPS16_26",		/* name */
1511 	 FALSE,			/* partial_inplace */
1512 	 0x3ffffff,		/* src_mask */
1513 	 0x3ffffff,		/* dst_mask */
1514 	 FALSE),		/* pcrel_offset */
1515 
1516   /* The reloc used for the mips16 gprel instruction.  */
1517   HOWTO (R_MIPS16_GPREL,	/* type */
1518 	 0,			/* rightshift */
1519 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1520 	 16,			/* bitsize */
1521 	 FALSE,			/* pc_relative */
1522 	 0,			/* bitpos */
1523 	 complain_overflow_signed, /* complain_on_overflow */
1524 	 mips16_gprel_reloc,	/* special_function */
1525 	 "R_MIPS16_GPREL",	/* name */
1526 	 FALSE,			/* partial_inplace */
1527 	 0x0000ffff,		/* src_mask */
1528 	 0x0000ffff,	        /* dst_mask */
1529 	 FALSE),		/* pcrel_offset */
1530 
1531   /* A placeholder for MIPS16 reference to global offset table.  */
1532   EMPTY_HOWTO (R_MIPS16_GOT16),
1533 
1534   /* A placeholder for MIPS16 16 bit call through global offset table.  */
1535   EMPTY_HOWTO (R_MIPS16_CALL16),
1536 
1537   /* MIPS16 high 16 bits of symbol value.  */
1538   HOWTO (R_MIPS16_HI16,		/* type */
1539 	 16,			/* rightshift */
1540 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1541 	 16,			/* bitsize */
1542 	 FALSE,			/* pc_relative */
1543 	 0,			/* bitpos */
1544 	 complain_overflow_dont, /* complain_on_overflow */
1545 	 _bfd_mips_elf_hi16_reloc, /* special_function */
1546 	 "R_MIPS16_HI16",	/* name */
1547 	 FALSE,			/* partial_inplace */
1548 	 0x0000ffff,		/* src_mask */
1549 	 0x0000ffff,		/* dst_mask */
1550 	 FALSE),		/* pcrel_offset */
1551 
1552   /* MIPS16 low 16 bits of symbol value.  */
1553   HOWTO (R_MIPS16_LO16,		/* type */
1554 	 0,			/* rightshift */
1555 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1556 	 16,			/* bitsize */
1557 	 FALSE,			/* pc_relative */
1558 	 0,			/* bitpos */
1559 	 complain_overflow_dont, /* complain_on_overflow */
1560 	 _bfd_mips_elf_lo16_reloc, /* special_function */
1561 	 "R_MIPS16_LO16",	/* name */
1562 	 FALSE,			/* partial_inplace */
1563 	 0x0000ffff,		/* src_mask */
1564 	 0x0000ffff,		/* dst_mask */
1565 	 FALSE),		/* pcrel_offset */
1566 };
1567 
1568 /* GNU extension to record C++ vtable hierarchy */
1569 static reloc_howto_type elf_mips_gnu_vtinherit_howto =
1570   HOWTO (R_MIPS_GNU_VTINHERIT,	/* type */
1571 	 0,			/* rightshift */
1572 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1573 	 0,			/* bitsize */
1574 	 FALSE,			/* pc_relative */
1575 	 0,			/* bitpos */
1576 	 complain_overflow_dont, /* complain_on_overflow */
1577 	 NULL,			/* special_function */
1578 	 "R_MIPS_GNU_VTINHERIT", /* name */
1579 	 FALSE,			/* partial_inplace */
1580 	 0,			/* src_mask */
1581 	 0,			/* dst_mask */
1582 	 FALSE);		/* pcrel_offset */
1583 
1584 /* GNU extension to record C++ vtable member usage */
1585 static reloc_howto_type elf_mips_gnu_vtentry_howto =
1586   HOWTO (R_MIPS_GNU_VTENTRY,	/* type */
1587 	 0,			/* rightshift */
1588 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1589 	 0,			/* bitsize */
1590 	 FALSE,			/* pc_relative */
1591 	 0,			/* bitpos */
1592 	 complain_overflow_dont, /* complain_on_overflow */
1593 	 _bfd_elf_rel_vtable_reloc_fn, /* special_function */
1594 	 "R_MIPS_GNU_VTENTRY",	/* name */
1595 	 FALSE,			/* partial_inplace */
1596 	 0,			/* src_mask */
1597 	 0,			/* dst_mask */
1598 	 FALSE);		/* pcrel_offset */
1599 
1600 /* 16 bit offset for pc-relative branches.  */
1601 static reloc_howto_type elf_mips_gnu_rel16_s2 =
1602   HOWTO (R_MIPS_GNU_REL16_S2,	/* type */
1603 	 2,			/* rightshift */
1604 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1605 	 16,			/* bitsize */
1606 	 TRUE,			/* pc_relative */
1607 	 0,			/* bitpos */
1608 	 complain_overflow_signed, /* complain_on_overflow */
1609 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1610 	 "R_MIPS_GNU_REL16_S2",	/* name */
1611 	 TRUE,			/* partial_inplace */
1612 	 0x0000ffff,		/* src_mask */
1613 	 0x0000ffff,		/* dst_mask */
1614 	 TRUE);			/* pcrel_offset */
1615 
1616 /* 16 bit offset for pc-relative branches.  */
1617 static reloc_howto_type elf_mips_gnu_rela16_s2 =
1618   HOWTO (R_MIPS_GNU_REL16_S2,	/* type */
1619 	 2,			/* rightshift */
1620 	 2,			/* size (0 = byte, 1 = short, 2 = long) */
1621 	 16,			/* bitsize */
1622 	 TRUE,			/* pc_relative */
1623 	 0,			/* bitpos */
1624 	 complain_overflow_signed, /* complain_on_overflow */
1625 	 _bfd_mips_elf_generic_reloc,	/* special_function */
1626 	 "R_MIPS_GNU_REL16_S2",	/* name */
1627 	 FALSE,			/* partial_inplace */
1628 	 0,			/* src_mask */
1629 	 0x0000ffff,		/* dst_mask */
1630 	 TRUE);			/* pcrel_offset */
1631 
1632 /* Swap in a MIPS 64-bit Rel reloc.  */
1633 
1634 static void
mips_elf64_swap_reloc_in(bfd * abfd,const Elf64_Mips_External_Rel * src,Elf64_Mips_Internal_Rela * dst)1635 mips_elf64_swap_reloc_in (bfd *abfd, const Elf64_Mips_External_Rel *src,
1636 			  Elf64_Mips_Internal_Rela *dst)
1637 {
1638   dst->r_offset = H_GET_64 (abfd, src->r_offset);
1639   dst->r_sym = H_GET_32 (abfd, src->r_sym);
1640   dst->r_ssym = H_GET_8 (abfd, src->r_ssym);
1641   dst->r_type3 = H_GET_8 (abfd, src->r_type3);
1642   dst->r_type2 = H_GET_8 (abfd, src->r_type2);
1643   dst->r_type = H_GET_8 (abfd, src->r_type);
1644   dst->r_addend = 0;
1645 }
1646 
1647 /* Swap in a MIPS 64-bit Rela reloc.  */
1648 
1649 static void
mips_elf64_swap_reloca_in(bfd * abfd,const Elf64_Mips_External_Rela * src,Elf64_Mips_Internal_Rela * dst)1650 mips_elf64_swap_reloca_in (bfd *abfd, const Elf64_Mips_External_Rela *src,
1651 			   Elf64_Mips_Internal_Rela *dst)
1652 {
1653   dst->r_offset = H_GET_64 (abfd, src->r_offset);
1654   dst->r_sym = H_GET_32 (abfd, src->r_sym);
1655   dst->r_ssym = H_GET_8 (abfd, src->r_ssym);
1656   dst->r_type3 = H_GET_8 (abfd, src->r_type3);
1657   dst->r_type2 = H_GET_8 (abfd, src->r_type2);
1658   dst->r_type = H_GET_8 (abfd, src->r_type);
1659   dst->r_addend = H_GET_S64 (abfd, src->r_addend);
1660 }
1661 
1662 /* Swap out a MIPS 64-bit Rel reloc.  */
1663 
1664 static void
mips_elf64_swap_reloc_out(bfd * abfd,const Elf64_Mips_Internal_Rela * src,Elf64_Mips_External_Rel * dst)1665 mips_elf64_swap_reloc_out (bfd *abfd, const Elf64_Mips_Internal_Rela *src,
1666 			   Elf64_Mips_External_Rel *dst)
1667 {
1668   H_PUT_64 (abfd, src->r_offset, dst->r_offset);
1669   H_PUT_32 (abfd, src->r_sym, dst->r_sym);
1670   H_PUT_8 (abfd, src->r_ssym, dst->r_ssym);
1671   H_PUT_8 (abfd, src->r_type3, dst->r_type3);
1672   H_PUT_8 (abfd, src->r_type2, dst->r_type2);
1673   H_PUT_8 (abfd, src->r_type, dst->r_type);
1674 }
1675 
1676 /* Swap out a MIPS 64-bit Rela reloc.  */
1677 
1678 static void
mips_elf64_swap_reloca_out(bfd * abfd,const Elf64_Mips_Internal_Rela * src,Elf64_Mips_External_Rela * dst)1679 mips_elf64_swap_reloca_out (bfd *abfd, const Elf64_Mips_Internal_Rela *src,
1680 			    Elf64_Mips_External_Rela *dst)
1681 {
1682   H_PUT_64 (abfd, src->r_offset, dst->r_offset);
1683   H_PUT_32 (abfd, src->r_sym, dst->r_sym);
1684   H_PUT_8 (abfd, src->r_ssym, dst->r_ssym);
1685   H_PUT_8 (abfd, src->r_type3, dst->r_type3);
1686   H_PUT_8 (abfd, src->r_type2, dst->r_type2);
1687   H_PUT_8 (abfd, src->r_type, dst->r_type);
1688   H_PUT_S64 (abfd, src->r_addend, dst->r_addend);
1689 }
1690 
1691 /* Swap in a MIPS 64-bit Rel reloc.  */
1692 
1693 static void
mips_elf64_be_swap_reloc_in(bfd * abfd,const bfd_byte * src,Elf_Internal_Rela * dst)1694 mips_elf64_be_swap_reloc_in (bfd *abfd, const bfd_byte *src,
1695 			     Elf_Internal_Rela *dst)
1696 {
1697   Elf64_Mips_Internal_Rela mirel;
1698 
1699   mips_elf64_swap_reloc_in (abfd,
1700 			    (const Elf64_Mips_External_Rel *) src,
1701 			    &mirel);
1702 
1703   dst[0].r_offset = mirel.r_offset;
1704   dst[0].r_info = ELF64_R_INFO (mirel.r_sym, mirel.r_type);
1705   dst[0].r_addend = 0;
1706   dst[1].r_offset = mirel.r_offset;
1707   dst[1].r_info = ELF64_R_INFO (mirel.r_ssym, mirel.r_type2);
1708   dst[1].r_addend = 0;
1709   dst[2].r_offset = mirel.r_offset;
1710   dst[2].r_info = ELF64_R_INFO (STN_UNDEF, mirel.r_type3);
1711   dst[2].r_addend = 0;
1712 }
1713 
1714 /* Swap in a MIPS 64-bit Rela reloc.  */
1715 
1716 static void
mips_elf64_be_swap_reloca_in(bfd * abfd,const bfd_byte * src,Elf_Internal_Rela * dst)1717 mips_elf64_be_swap_reloca_in (bfd *abfd, const bfd_byte *src,
1718 			      Elf_Internal_Rela *dst)
1719 {
1720   Elf64_Mips_Internal_Rela mirela;
1721 
1722   mips_elf64_swap_reloca_in (abfd,
1723 			     (const Elf64_Mips_External_Rela *) src,
1724 			     &mirela);
1725 
1726   dst[0].r_offset = mirela.r_offset;
1727   dst[0].r_info = ELF64_R_INFO (mirela.r_sym, mirela.r_type);
1728   dst[0].r_addend = mirela.r_addend;
1729   dst[1].r_offset = mirela.r_offset;
1730   dst[1].r_info = ELF64_R_INFO (mirela.r_ssym, mirela.r_type2);
1731   dst[1].r_addend = 0;
1732   dst[2].r_offset = mirela.r_offset;
1733   dst[2].r_info = ELF64_R_INFO (STN_UNDEF, mirela.r_type3);
1734   dst[2].r_addend = 0;
1735 }
1736 
1737 /* Swap out a MIPS 64-bit Rel reloc.  */
1738 
1739 static void
mips_elf64_be_swap_reloc_out(bfd * abfd,const Elf_Internal_Rela * src,bfd_byte * dst)1740 mips_elf64_be_swap_reloc_out (bfd *abfd, const Elf_Internal_Rela *src,
1741 			      bfd_byte *dst)
1742 {
1743   Elf64_Mips_Internal_Rela mirel;
1744 
1745   mirel.r_offset = src[0].r_offset;
1746   BFD_ASSERT(src[0].r_offset == src[1].r_offset);
1747 
1748   mirel.r_type = ELF64_MIPS_R_TYPE (src[0].r_info);
1749   mirel.r_sym = ELF64_R_SYM (src[0].r_info);
1750   mirel.r_type2 = ELF64_MIPS_R_TYPE (src[1].r_info);
1751   mirel.r_ssym = ELF64_MIPS_R_SSYM (src[1].r_info);
1752   mirel.r_type3 = ELF64_MIPS_R_TYPE (src[2].r_info);
1753 
1754   mips_elf64_swap_reloc_out (abfd, &mirel,
1755 			     (Elf64_Mips_External_Rel *) dst);
1756 }
1757 
1758 /* Swap out a MIPS 64-bit Rela reloc.  */
1759 
1760 static void
mips_elf64_be_swap_reloca_out(bfd * abfd,const Elf_Internal_Rela * src,bfd_byte * dst)1761 mips_elf64_be_swap_reloca_out (bfd *abfd, const Elf_Internal_Rela *src,
1762 			       bfd_byte *dst)
1763 {
1764   Elf64_Mips_Internal_Rela mirela;
1765 
1766   mirela.r_offset = src[0].r_offset;
1767   BFD_ASSERT(src[0].r_offset == src[1].r_offset);
1768   BFD_ASSERT(src[0].r_offset == src[2].r_offset);
1769 
1770   mirela.r_type = ELF64_MIPS_R_TYPE (src[0].r_info);
1771   mirela.r_sym = ELF64_R_SYM (src[0].r_info);
1772   mirela.r_addend = src[0].r_addend;
1773   BFD_ASSERT(src[1].r_addend == 0);
1774   BFD_ASSERT(src[2].r_addend == 0);
1775 
1776   mirela.r_type2 = ELF64_MIPS_R_TYPE (src[1].r_info);
1777   mirela.r_ssym = ELF64_MIPS_R_SSYM (src[1].r_info);
1778   mirela.r_type3 = ELF64_MIPS_R_TYPE (src[2].r_info);
1779 
1780   mips_elf64_swap_reloca_out (abfd, &mirela,
1781 			      (Elf64_Mips_External_Rela *) dst);
1782 }
1783 
1784 /* Set the GP value for OUTPUT_BFD.  Returns FALSE if this is a
1785    dangerous relocation.  */
1786 
1787 static bfd_boolean
mips_elf64_assign_gp(bfd * output_bfd,bfd_vma * pgp)1788 mips_elf64_assign_gp (bfd *output_bfd, bfd_vma *pgp)
1789 {
1790   unsigned int count;
1791   asymbol **sym;
1792   unsigned int i;
1793 
1794   /* If we've already figured out what GP will be, just return it.  */
1795   *pgp = _bfd_get_gp_value (output_bfd);
1796   if (*pgp)
1797     return TRUE;
1798 
1799   count = bfd_get_symcount (output_bfd);
1800   sym = bfd_get_outsymbols (output_bfd);
1801 
1802   /* The linker script will have created a symbol named `_gp' with the
1803      appropriate value.  */
1804   if (sym == NULL)
1805     i = count;
1806   else
1807     {
1808       for (i = 0; i < count; i++, sym++)
1809 	{
1810 	  register const char *name;
1811 
1812 	  name = bfd_asymbol_name (*sym);
1813 	  if (*name == '_' && strcmp (name, "_gp") == 0)
1814 	    {
1815 	      *pgp = bfd_asymbol_value (*sym);
1816 	      _bfd_set_gp_value (output_bfd, *pgp);
1817 	      break;
1818 	    }
1819 	}
1820     }
1821 
1822   if (i >= count)
1823     {
1824       /* Only get the error once.  */
1825       *pgp = 4;
1826       _bfd_set_gp_value (output_bfd, *pgp);
1827       return FALSE;
1828     }
1829 
1830   return TRUE;
1831 }
1832 
1833 /* We have to figure out the gp value, so that we can adjust the
1834    symbol value correctly.  We look up the symbol _gp in the output
1835    BFD.  If we can't find it, we're stuck.  We cache it in the ELF
1836    target data.  We don't need to adjust the symbol value for an
1837    external symbol if we are producing relocatable output.  */
1838 
1839 static bfd_reloc_status_type
mips_elf64_final_gp(bfd * output_bfd,asymbol * symbol,bfd_boolean relocatable,char ** error_message,bfd_vma * pgp)1840 mips_elf64_final_gp (bfd *output_bfd, asymbol *symbol, bfd_boolean relocatable,
1841 		     char **error_message, bfd_vma *pgp)
1842 {
1843   if (bfd_is_und_section (symbol->section)
1844       && ! relocatable)
1845     {
1846       *pgp = 0;
1847       return bfd_reloc_undefined;
1848     }
1849 
1850   *pgp = _bfd_get_gp_value (output_bfd);
1851   if (*pgp == 0
1852       && (! relocatable
1853 	  || (symbol->flags & BSF_SECTION_SYM) != 0))
1854     {
1855       if (relocatable)
1856 	{
1857 	  /* Make up a value.  */
1858 	  *pgp = symbol->section->output_section->vma /*+ 0x4000*/;
1859 	  _bfd_set_gp_value (output_bfd, *pgp);
1860 	}
1861       else if (!mips_elf64_assign_gp (output_bfd, pgp))
1862 	{
1863 	  *error_message =
1864 	    (char *) _("GP relative relocation when _gp not defined");
1865 	  return bfd_reloc_dangerous;
1866 	}
1867     }
1868 
1869   return bfd_reloc_ok;
1870 }
1871 
1872 /* Do a R_MIPS_GPREL16 relocation.  This is a 16 bit value which must
1873    become the offset from the gp register.  */
1874 
1875 static bfd_reloc_status_type
mips_elf64_gprel16_reloc(bfd * abfd,arelent * reloc_entry,asymbol * symbol,void * data,asection * input_section,bfd * output_bfd,char ** error_message)1876 mips_elf64_gprel16_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
1877 			  void *data, asection *input_section, bfd *output_bfd,
1878 			  char **error_message)
1879 {
1880   bfd_boolean relocatable;
1881   bfd_reloc_status_type ret;
1882   bfd_vma gp;
1883 
1884   /* If we're relocating, and this is an external symbol, we don't want
1885      to change anything.  */
1886   if (output_bfd != NULL
1887       && (symbol->flags & BSF_SECTION_SYM) == 0
1888       && (symbol->flags & BSF_LOCAL) != 0)
1889     {
1890       reloc_entry->address += input_section->output_offset;
1891       return bfd_reloc_ok;
1892     }
1893 
1894   if (output_bfd != NULL)
1895     relocatable = TRUE;
1896   else
1897     {
1898       relocatable = FALSE;
1899       output_bfd = symbol->section->output_section->owner;
1900     }
1901 
1902   ret = mips_elf64_final_gp (output_bfd, symbol, relocatable, error_message,
1903 			     &gp);
1904   if (ret != bfd_reloc_ok)
1905     return ret;
1906 
1907   return _bfd_mips_elf_gprel16_with_gp (abfd, symbol, reloc_entry,
1908 					input_section, relocatable,
1909 					data, gp);
1910 }
1911 
1912 /* Do a R_MIPS_LITERAL relocation.  */
1913 
1914 static bfd_reloc_status_type
mips_elf64_literal_reloc(bfd * abfd,arelent * reloc_entry,asymbol * symbol,void * data,asection * input_section,bfd * output_bfd,char ** error_message)1915 mips_elf64_literal_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
1916 			  void *data, asection *input_section, bfd *output_bfd,
1917 			  char **error_message)
1918 {
1919   bfd_boolean relocatable;
1920   bfd_reloc_status_type ret;
1921   bfd_vma gp;
1922 
1923   /* R_MIPS_LITERAL relocations are defined for local symbols only.  */
1924   if (output_bfd != NULL
1925       && (symbol->flags & BSF_SECTION_SYM) == 0
1926       && (symbol->flags & BSF_LOCAL) != 0)
1927     {
1928       *error_message = (char *)
1929 	_("literal relocation occurs for an external symbol");
1930       return bfd_reloc_outofrange;
1931     }
1932 
1933   /* FIXME: The entries in the .lit8 and .lit4 sections should be merged.  */
1934   if (output_bfd != NULL)
1935     relocatable = TRUE;
1936   else
1937     {
1938       relocatable = FALSE;
1939       output_bfd = symbol->section->output_section->owner;
1940     }
1941 
1942   ret = mips_elf64_final_gp (output_bfd, symbol, relocatable, error_message,
1943 			     &gp);
1944   if (ret != bfd_reloc_ok)
1945     return ret;
1946 
1947   return _bfd_mips_elf_gprel16_with_gp (abfd, symbol, reloc_entry,
1948 					input_section, relocatable,
1949 					data, gp);
1950 }
1951 
1952 /* Do a R_MIPS_GPREL32 relocation.  This is a 32 bit value which must
1953    become the offset from the gp register.  */
1954 
1955 static bfd_reloc_status_type
mips_elf64_gprel32_reloc(bfd * abfd,arelent * reloc_entry,asymbol * symbol,void * data,asection * input_section,bfd * output_bfd,char ** error_message)1956 mips_elf64_gprel32_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
1957 			  void *data, asection *input_section, bfd *output_bfd,
1958 			  char **error_message)
1959 {
1960   bfd_boolean relocatable;
1961   bfd_reloc_status_type ret;
1962   bfd_vma gp;
1963   bfd_vma relocation;
1964   bfd_vma val;
1965 
1966   /* R_MIPS_GPREL32 relocations are defined for local symbols only.  */
1967   if (output_bfd != NULL
1968       && (symbol->flags & BSF_SECTION_SYM) == 0
1969       && (symbol->flags & BSF_LOCAL) != 0)
1970     {
1971       *error_message = (char *)
1972 	_("32bits gp relative relocation occurs for an external symbol");
1973       return bfd_reloc_outofrange;
1974     }
1975 
1976   if (output_bfd != NULL)
1977     relocatable = TRUE;
1978   else
1979     {
1980       relocatable = FALSE;
1981       output_bfd = symbol->section->output_section->owner;
1982     }
1983 
1984   ret = mips_elf64_final_gp (output_bfd, symbol, relocatable,
1985 			     error_message, &gp);
1986   if (ret != bfd_reloc_ok)
1987     return ret;
1988 
1989   if (bfd_is_com_section (symbol->section))
1990     relocation = 0;
1991   else
1992     relocation = symbol->value;
1993 
1994   relocation += symbol->section->output_section->vma;
1995   relocation += symbol->section->output_offset;
1996 
1997   if (reloc_entry->address > bfd_get_section_limit (abfd, input_section))
1998     return bfd_reloc_outofrange;
1999 
2000   /* Set val to the offset into the section or symbol.  */
2001   val = reloc_entry->addend;
2002 
2003   if (reloc_entry->howto->partial_inplace)
2004     val += bfd_get_32 (abfd, (bfd_byte *) data + reloc_entry->address);
2005 
2006   /* Adjust val for the final section location and GP value.  If we
2007      are producing relocatable output, we don't want to do this for
2008      an external symbol.  */
2009   if (! relocatable
2010       || (symbol->flags & BSF_SECTION_SYM) != 0)
2011     val += relocation - gp;
2012 
2013   if (reloc_entry->howto->partial_inplace)
2014     bfd_put_32 (abfd, val, (bfd_byte *) data + reloc_entry->address);
2015   else
2016     reloc_entry->addend = val;
2017 
2018   if (relocatable)
2019     reloc_entry->address += input_section->output_offset;
2020 
2021   return bfd_reloc_ok;
2022 }
2023 
2024 /* Do a R_MIPS_SHIFT6 relocation. The MSB of the shift is stored at bit 2,
2025    the rest is at bits 6-10. The bitpos already got right by the howto.  */
2026 
2027 static bfd_reloc_status_type
mips_elf64_shift6_reloc(bfd * abfd,arelent * reloc_entry,asymbol * symbol,void * data,asection * input_section,bfd * output_bfd,char ** error_message)2028 mips_elf64_shift6_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
2029 			 void *data, asection *input_section, bfd *output_bfd,
2030 			 char **error_message)
2031 {
2032   if (reloc_entry->howto->partial_inplace)
2033     {
2034       reloc_entry->addend = ((reloc_entry->addend & 0x00007c0)
2035 			     | (reloc_entry->addend & 0x00000800) >> 9);
2036     }
2037 
2038   return _bfd_mips_elf_generic_reloc (abfd, reloc_entry, symbol, data,
2039 				      input_section, output_bfd,
2040 				      error_message);
2041 }
2042 
2043 /* Handle a mips16 jump.  */
2044 
2045 static bfd_reloc_status_type
mips16_jump_reloc(bfd * abfd ATTRIBUTE_UNUSED,arelent * reloc_entry,asymbol * symbol,void * data ATTRIBUTE_UNUSED,asection * input_section,bfd * output_bfd,char ** error_message ATTRIBUTE_UNUSED)2046 mips16_jump_reloc (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc_entry,
2047 		   asymbol *symbol, void *data ATTRIBUTE_UNUSED,
2048 		   asection *input_section, bfd *output_bfd,
2049 		   char **error_message ATTRIBUTE_UNUSED)
2050 {
2051   if (output_bfd != NULL
2052       && (symbol->flags & BSF_SECTION_SYM) == 0
2053       && (! reloc_entry->howto->partial_inplace
2054 	  || reloc_entry->addend == 0))
2055     {
2056       reloc_entry->address += input_section->output_offset;
2057       return bfd_reloc_ok;
2058     }
2059 
2060   /* FIXME.  */
2061   {
2062     static bfd_boolean warned;
2063 
2064     if (! warned)
2065       (*_bfd_error_handler)
2066 	(_("Linking mips16 objects into %s format is not supported"),
2067 	 bfd_get_target (input_section->output_section->owner));
2068     warned = TRUE;
2069   }
2070 
2071   return bfd_reloc_undefined;
2072 }
2073 
2074 /* Handle a mips16 GP relative reloc.  */
2075 
2076 static bfd_reloc_status_type
mips16_gprel_reloc(bfd * abfd,arelent * reloc_entry,asymbol * symbol,void * data,asection * input_section,bfd * output_bfd,char ** error_message)2077 mips16_gprel_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol,
2078 		    void *data, asection *input_section, bfd *output_bfd,
2079 		    char **error_message)
2080 {
2081   bfd_boolean relocatable;
2082   bfd_reloc_status_type ret;
2083   bfd_byte *location;
2084   bfd_vma gp;
2085 
2086   /* If we're relocating, and this is an external symbol, we don't want
2087      to change anything.  */
2088   if (output_bfd != NULL
2089       && (symbol->flags & BSF_SECTION_SYM) == 0
2090       && (symbol->flags & BSF_LOCAL) != 0)
2091     {
2092       reloc_entry->address += input_section->output_offset;
2093       return bfd_reloc_ok;
2094     }
2095 
2096   if (output_bfd != NULL)
2097     relocatable = TRUE;
2098   else
2099     {
2100       relocatable = FALSE;
2101       output_bfd = symbol->section->output_section->owner;
2102     }
2103 
2104   ret = mips_elf64_final_gp (output_bfd, symbol, relocatable, error_message,
2105 			     &gp);
2106   if (ret != bfd_reloc_ok)
2107     return ret;
2108 
2109   location = (bfd_byte *) data + reloc_entry->address;
2110   _bfd_mips16_elf_reloc_unshuffle (abfd, reloc_entry->howto->type, FALSE,
2111 				   location);
2112   ret = _bfd_mips_elf_gprel16_with_gp (abfd, symbol, reloc_entry,
2113 				       input_section, relocatable,
2114 				       data, gp);
2115   _bfd_mips16_elf_reloc_shuffle (abfd, reloc_entry->howto->type, !relocatable,
2116 				 location);
2117 
2118   return ret;
2119 }
2120 
2121 /* A mapping from BFD reloc types to MIPS ELF reloc types.  */
2122 
2123 struct elf_reloc_map {
2124   bfd_reloc_code_real_type bfd_val;
2125   enum elf_mips_reloc_type elf_val;
2126 };
2127 
2128 static const struct elf_reloc_map mips_reloc_map[] =
2129 {
2130   { BFD_RELOC_NONE, R_MIPS_NONE },
2131   { BFD_RELOC_16, R_MIPS_16 },
2132   { BFD_RELOC_32, R_MIPS_32 },
2133   /* There is no BFD reloc for R_MIPS_REL32.  */
2134   { BFD_RELOC_64, R_MIPS_64 },
2135   { BFD_RELOC_CTOR, R_MIPS_64 },
2136   { BFD_RELOC_16_PCREL, R_MIPS_PC16 },
2137   { BFD_RELOC_HI16_S, R_MIPS_HI16 },
2138   { BFD_RELOC_LO16, R_MIPS_LO16 },
2139   { BFD_RELOC_GPREL16, R_MIPS_GPREL16 },
2140   { BFD_RELOC_GPREL32, R_MIPS_GPREL32 },
2141   { BFD_RELOC_MIPS_JMP, R_MIPS_26 },
2142   { BFD_RELOC_MIPS_LITERAL, R_MIPS_LITERAL },
2143   { BFD_RELOC_MIPS_GOT16, R_MIPS_GOT16 },
2144   { BFD_RELOC_MIPS_CALL16, R_MIPS_CALL16 },
2145   { BFD_RELOC_MIPS_SHIFT5, R_MIPS_SHIFT5 },
2146   { BFD_RELOC_MIPS_SHIFT6, R_MIPS_SHIFT6 },
2147   { BFD_RELOC_MIPS_GOT_DISP, R_MIPS_GOT_DISP },
2148   { BFD_RELOC_MIPS_GOT_PAGE, R_MIPS_GOT_PAGE },
2149   { BFD_RELOC_MIPS_GOT_OFST, R_MIPS_GOT_OFST },
2150   { BFD_RELOC_MIPS_GOT_HI16, R_MIPS_GOT_HI16 },
2151   { BFD_RELOC_MIPS_GOT_LO16, R_MIPS_GOT_LO16 },
2152   { BFD_RELOC_MIPS_SUB, R_MIPS_SUB },
2153   { BFD_RELOC_MIPS_INSERT_A, R_MIPS_INSERT_A },
2154   { BFD_RELOC_MIPS_INSERT_B, R_MIPS_INSERT_B },
2155   { BFD_RELOC_MIPS_DELETE, R_MIPS_DELETE },
2156   { BFD_RELOC_MIPS_HIGHEST, R_MIPS_HIGHEST },
2157   { BFD_RELOC_MIPS_HIGHER, R_MIPS_HIGHER },
2158   { BFD_RELOC_MIPS_CALL_HI16, R_MIPS_CALL_HI16 },
2159   { BFD_RELOC_MIPS_CALL_LO16, R_MIPS_CALL_LO16 },
2160   { BFD_RELOC_MIPS_SCN_DISP, R_MIPS_SCN_DISP },
2161   { BFD_RELOC_MIPS_REL16, R_MIPS_REL16 },
2162   /* Use of R_MIPS_ADD_IMMEDIATE and R_MIPS_PJUMP is deprecated.  */
2163   { BFD_RELOC_MIPS_RELGOT, R_MIPS_RELGOT },
2164   { BFD_RELOC_MIPS_JALR, R_MIPS_JALR },
2165   { BFD_RELOC_MIPS_TLS_DTPMOD32, R_MIPS_TLS_DTPMOD32 },
2166   { BFD_RELOC_MIPS_TLS_DTPREL32, R_MIPS_TLS_DTPREL32 },
2167   { BFD_RELOC_MIPS_TLS_DTPMOD64, R_MIPS_TLS_DTPMOD64 },
2168   { BFD_RELOC_MIPS_TLS_DTPREL64, R_MIPS_TLS_DTPREL64 },
2169   { BFD_RELOC_MIPS_TLS_GD, R_MIPS_TLS_GD },
2170   { BFD_RELOC_MIPS_TLS_LDM, R_MIPS_TLS_LDM },
2171   { BFD_RELOC_MIPS_TLS_DTPREL_HI16, R_MIPS_TLS_DTPREL_HI16 },
2172   { BFD_RELOC_MIPS_TLS_DTPREL_LO16, R_MIPS_TLS_DTPREL_LO16 },
2173   { BFD_RELOC_MIPS_TLS_GOTTPREL, R_MIPS_TLS_GOTTPREL },
2174   { BFD_RELOC_MIPS_TLS_TPREL32, R_MIPS_TLS_TPREL32 },
2175   { BFD_RELOC_MIPS_TLS_TPREL64, R_MIPS_TLS_TPREL64 },
2176   { BFD_RELOC_MIPS_TLS_TPREL_HI16, R_MIPS_TLS_TPREL_HI16 },
2177   { BFD_RELOC_MIPS_TLS_TPREL_LO16, R_MIPS_TLS_TPREL_LO16 }
2178 };
2179 
2180 static const struct elf_reloc_map mips16_reloc_map[] =
2181 {
2182   { BFD_RELOC_MIPS16_JMP, R_MIPS16_26 - R_MIPS16_min },
2183   { BFD_RELOC_MIPS16_GPREL, R_MIPS16_GPREL - R_MIPS16_min },
2184   { BFD_RELOC_MIPS16_HI16_S, R_MIPS16_HI16 - R_MIPS16_min },
2185   { BFD_RELOC_MIPS16_LO16, R_MIPS16_LO16 - R_MIPS16_min },
2186 };
2187 
2188 /* Given a BFD reloc type, return a howto structure.  */
2189 
2190 static reloc_howto_type *
bfd_elf64_bfd_reloc_type_lookup(bfd * abfd ATTRIBUTE_UNUSED,bfd_reloc_code_real_type code)2191 bfd_elf64_bfd_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
2192 				 bfd_reloc_code_real_type code)
2193 {
2194   unsigned int i;
2195   /* FIXME: We default to RELA here instead of choosing the right
2196      relocation variant.  */
2197   reloc_howto_type *howto_table = mips_elf64_howto_table_rela;
2198   reloc_howto_type *howto16_table = mips16_elf64_howto_table_rela;
2199 
2200   for (i = 0; i < sizeof (mips_reloc_map) / sizeof (struct elf_reloc_map);
2201        i++)
2202     {
2203       if (mips_reloc_map[i].bfd_val == code)
2204 	return &howto_table[(int) mips_reloc_map[i].elf_val];
2205     }
2206 
2207   for (i = 0; i < sizeof (mips16_reloc_map) / sizeof (struct elf_reloc_map);
2208        i++)
2209     {
2210       if (mips16_reloc_map[i].bfd_val == code)
2211 	return &howto16_table[(int) mips16_reloc_map[i].elf_val];
2212     }
2213 
2214   switch (code)
2215     {
2216     case BFD_RELOC_VTABLE_INHERIT:
2217       return &elf_mips_gnu_vtinherit_howto;
2218     case BFD_RELOC_VTABLE_ENTRY:
2219       return &elf_mips_gnu_vtentry_howto;
2220     case BFD_RELOC_16_PCREL_S2:
2221       return &elf_mips_gnu_rela16_s2;
2222     default:
2223       bfd_set_error (bfd_error_bad_value);
2224       return NULL;
2225     }
2226 }
2227 
2228 /* Given a MIPS Elf_Internal_Rel, fill in an arelent structure.  */
2229 
2230 static reloc_howto_type *
mips_elf64_rtype_to_howto(unsigned int r_type,bfd_boolean rela_p)2231 mips_elf64_rtype_to_howto (unsigned int r_type, bfd_boolean rela_p)
2232 {
2233   switch (r_type)
2234     {
2235     case R_MIPS_GNU_VTINHERIT:
2236       return &elf_mips_gnu_vtinherit_howto;
2237     case R_MIPS_GNU_VTENTRY:
2238       return &elf_mips_gnu_vtentry_howto;
2239     case R_MIPS_GNU_REL16_S2:
2240       if (rela_p)
2241 	return &elf_mips_gnu_rela16_s2;
2242       else
2243 	return &elf_mips_gnu_rel16_s2;
2244     default:
2245       if (r_type >= R_MIPS16_min && r_type < R_MIPS16_max)
2246 	{
2247 	  if (rela_p)
2248 	    return &mips16_elf64_howto_table_rela[r_type - R_MIPS16_min];
2249 	  else
2250 	    return &mips16_elf64_howto_table_rel[r_type - R_MIPS16_min];
2251 	}
2252       BFD_ASSERT (r_type < (unsigned int) R_MIPS_max);
2253       if (rela_p)
2254 	return &mips_elf64_howto_table_rela[r_type];
2255       else
2256 	return &mips_elf64_howto_table_rel[r_type];
2257       break;
2258     }
2259 }
2260 
2261 /* Prevent relocation handling by bfd for MIPS ELF64.  */
2262 
2263 static void
mips_elf64_info_to_howto_rel(bfd * abfd ATTRIBUTE_UNUSED,arelent * cache_ptr ATTRIBUTE_UNUSED,Elf_Internal_Rela * dst ATTRIBUTE_UNUSED)2264 mips_elf64_info_to_howto_rel (bfd *abfd ATTRIBUTE_UNUSED,
2265 			      arelent *cache_ptr ATTRIBUTE_UNUSED,
2266 			      Elf_Internal_Rela *dst ATTRIBUTE_UNUSED)
2267 {
2268   BFD_ASSERT (0);
2269 }
2270 
2271 static void
mips_elf64_info_to_howto_rela(bfd * abfd ATTRIBUTE_UNUSED,arelent * cache_ptr ATTRIBUTE_UNUSED,Elf_Internal_Rela * dst ATTRIBUTE_UNUSED)2272 mips_elf64_info_to_howto_rela (bfd *abfd ATTRIBUTE_UNUSED,
2273 			       arelent *cache_ptr ATTRIBUTE_UNUSED,
2274 			       Elf_Internal_Rela *dst ATTRIBUTE_UNUSED)
2275 {
2276   BFD_ASSERT (0);
2277 }
2278 
2279 /* Since each entry in an SHT_REL or SHT_RELA section can represent up
2280    to three relocs, we must tell the user to allocate more space.  */
2281 
2282 static long
mips_elf64_get_reloc_upper_bound(bfd * abfd ATTRIBUTE_UNUSED,asection * sec)2283 mips_elf64_get_reloc_upper_bound (bfd *abfd ATTRIBUTE_UNUSED, asection *sec)
2284 {
2285   return (sec->reloc_count * 3 + 1) * sizeof (arelent *);
2286 }
2287 
2288 static long
mips_elf64_get_dynamic_reloc_upper_bound(bfd * abfd)2289 mips_elf64_get_dynamic_reloc_upper_bound (bfd *abfd)
2290 {
2291   return _bfd_elf_get_dynamic_reloc_upper_bound (abfd) * 3;
2292 }
2293 
2294 /* We must also copy more relocations than the corresponding functions
2295    in elf.c would, so the two following functions are slightly
2296    modified from elf.c, that multiply the external relocation count by
2297    3 to obtain the internal relocation count.  */
2298 
2299 static long
mips_elf64_canonicalize_reloc(bfd * abfd,sec_ptr section,arelent ** relptr,asymbol ** symbols)2300 mips_elf64_canonicalize_reloc (bfd *abfd, sec_ptr section,
2301 			       arelent **relptr, asymbol **symbols)
2302 {
2303   arelent *tblptr;
2304   unsigned int i;
2305   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
2306 
2307   if (! bed->s->slurp_reloc_table (abfd, section, symbols, FALSE))
2308     return -1;
2309 
2310   tblptr = section->relocation;
2311   for (i = 0; i < section->reloc_count * 3; i++)
2312     *relptr++ = tblptr++;
2313 
2314   *relptr = NULL;
2315 
2316   return section->reloc_count * 3;
2317 }
2318 
2319 static long
mips_elf64_canonicalize_dynamic_reloc(bfd * abfd,arelent ** storage,asymbol ** syms)2320 mips_elf64_canonicalize_dynamic_reloc (bfd *abfd, arelent **storage,
2321 				       asymbol **syms)
2322 {
2323   bfd_boolean (*slurp_relocs) (bfd *, asection *, asymbol **, bfd_boolean);
2324   asection *s;
2325   long ret;
2326 
2327   if (elf_dynsymtab (abfd) == 0)
2328     {
2329       bfd_set_error (bfd_error_invalid_operation);
2330       return -1;
2331     }
2332 
2333   slurp_relocs = get_elf_backend_data (abfd)->s->slurp_reloc_table;
2334   ret = 0;
2335   for (s = abfd->sections; s != NULL; s = s->next)
2336     {
2337       if (elf_section_data (s)->this_hdr.sh_link == elf_dynsymtab (abfd)
2338 	  && (elf_section_data (s)->this_hdr.sh_type == SHT_REL
2339 	      || elf_section_data (s)->this_hdr.sh_type == SHT_RELA))
2340 	{
2341 	  arelent *p;
2342 	  long count, i;
2343 
2344 	  if (! (*slurp_relocs) (abfd, s, syms, TRUE))
2345 	    return -1;
2346 	  count = s->size / elf_section_data (s)->this_hdr.sh_entsize * 3;
2347 	  p = s->relocation;
2348 	  for (i = 0; i < count; i++)
2349 	    *storage++ = p++;
2350 	  ret += count;
2351 	}
2352     }
2353 
2354   *storage = NULL;
2355 
2356   return ret;
2357 }
2358 
2359 /* Read the relocations from one reloc section.  This is mostly copied
2360    from elfcode.h, except for the changes to expand one external
2361    relocation to 3 internal ones.  We must unfortunately set
2362    reloc_count to the number of external relocations, because a lot of
2363    generic code seems to depend on this.  */
2364 
2365 static bfd_boolean
mips_elf64_slurp_one_reloc_table(bfd * abfd,asection * asect,Elf_Internal_Shdr * rel_hdr,bfd_size_type reloc_count,arelent * relents,asymbol ** symbols,bfd_boolean dynamic)2366 mips_elf64_slurp_one_reloc_table (bfd *abfd, asection *asect,
2367 				  Elf_Internal_Shdr *rel_hdr,
2368 				  bfd_size_type reloc_count,
2369 				  arelent *relents, asymbol **symbols,
2370 				  bfd_boolean dynamic)
2371 {
2372   void *allocated;
2373   bfd_byte *native_relocs;
2374   arelent *relent;
2375   bfd_vma i;
2376   int entsize;
2377   bfd_boolean rela_p;
2378 
2379   allocated = bfd_malloc (rel_hdr->sh_size);
2380   if (allocated == NULL)
2381     return FALSE;
2382 
2383   if (bfd_seek (abfd, rel_hdr->sh_offset, SEEK_SET) != 0
2384       || (bfd_bread (allocated, rel_hdr->sh_size, abfd)
2385 	  != rel_hdr->sh_size))
2386     goto error_return;
2387 
2388   native_relocs = allocated;
2389 
2390   entsize = rel_hdr->sh_entsize;
2391   BFD_ASSERT (entsize == sizeof (Elf64_Mips_External_Rel)
2392 	      || entsize == sizeof (Elf64_Mips_External_Rela));
2393 
2394   if (entsize == sizeof (Elf64_Mips_External_Rel))
2395     rela_p = FALSE;
2396   else
2397     rela_p = TRUE;
2398 
2399   for (i = 0, relent = relents;
2400        i < reloc_count;
2401        i++, native_relocs += entsize)
2402     {
2403       Elf64_Mips_Internal_Rela rela;
2404       bfd_boolean used_sym, used_ssym;
2405       int ir;
2406 
2407       if (entsize == sizeof (Elf64_Mips_External_Rela))
2408 	mips_elf64_swap_reloca_in (abfd,
2409 				   (Elf64_Mips_External_Rela *) native_relocs,
2410 				   &rela);
2411       else
2412 	mips_elf64_swap_reloc_in (abfd,
2413 				  (Elf64_Mips_External_Rel *) native_relocs,
2414 				  &rela);
2415 
2416       /* Each entry represents exactly three actual relocations.  */
2417 
2418       used_sym = FALSE;
2419       used_ssym = FALSE;
2420       for (ir = 0; ir < 3; ir++)
2421 	{
2422 	  enum elf_mips_reloc_type type;
2423 
2424 	  switch (ir)
2425 	    {
2426 	    default:
2427 	      abort ();
2428 	    case 0:
2429 	      type = (enum elf_mips_reloc_type) rela.r_type;
2430 	      break;
2431 	    case 1:
2432 	      type = (enum elf_mips_reloc_type) rela.r_type2;
2433 	      break;
2434 	    case 2:
2435 	      type = (enum elf_mips_reloc_type) rela.r_type3;
2436 	      break;
2437 	    }
2438 
2439 	  /* Some types require symbols, whereas some do not.  */
2440 	  switch (type)
2441 	    {
2442 	    case R_MIPS_NONE:
2443 	    case R_MIPS_LITERAL:
2444 	    case R_MIPS_INSERT_A:
2445 	    case R_MIPS_INSERT_B:
2446 	    case R_MIPS_DELETE:
2447 	      relent->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr;
2448 	      break;
2449 
2450 	    default:
2451 	      if (! used_sym)
2452 		{
2453 		  if (rela.r_sym == 0)
2454 		    relent->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr;
2455 		  else
2456 		    {
2457 		      asymbol **ps, *s;
2458 
2459 		      ps = symbols + rela.r_sym - 1;
2460 		      s = *ps;
2461 		      if ((s->flags & BSF_SECTION_SYM) == 0)
2462 			relent->sym_ptr_ptr = ps;
2463 		      else
2464 			relent->sym_ptr_ptr = s->section->symbol_ptr_ptr;
2465 		    }
2466 
2467 		  used_sym = TRUE;
2468 		}
2469 	      else if (! used_ssym)
2470 		{
2471 		  switch (rela.r_ssym)
2472 		    {
2473 		    case RSS_UNDEF:
2474 		      relent->sym_ptr_ptr =
2475 			bfd_abs_section_ptr->symbol_ptr_ptr;
2476 		      break;
2477 
2478 		    case RSS_GP:
2479 		    case RSS_GP0:
2480 		    case RSS_LOC:
2481 		      /* FIXME: I think these need to be handled using
2482 			 special howto structures.  */
2483 		      BFD_ASSERT (0);
2484 		      break;
2485 
2486 		    default:
2487 		      BFD_ASSERT (0);
2488 		      break;
2489 		    }
2490 
2491 		  used_ssym = TRUE;
2492 		}
2493 	      else
2494 		relent->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr;
2495 
2496 	      break;
2497 	    }
2498 
2499 	  /* The address of an ELF reloc is section relative for an
2500 	     object file, and absolute for an executable file or
2501 	     shared library.  The address of a BFD reloc is always
2502 	     section relative.  */
2503 	  if ((abfd->flags & (EXEC_P | DYNAMIC)) == 0 || dynamic)
2504 	    relent->address = rela.r_offset;
2505 	  else
2506 	    relent->address = rela.r_offset - asect->vma;
2507 
2508 	  relent->addend = rela.r_addend;
2509 
2510 	  relent->howto = mips_elf64_rtype_to_howto (type, rela_p);
2511 
2512 	  ++relent;
2513 	}
2514     }
2515 
2516   asect->reloc_count += (relent - relents) / 3;
2517 
2518   if (allocated != NULL)
2519     free (allocated);
2520 
2521   return TRUE;
2522 
2523  error_return:
2524   if (allocated != NULL)
2525     free (allocated);
2526   return FALSE;
2527 }
2528 
2529 /* Read the relocations.  On Irix 6, there can be two reloc sections
2530    associated with a single data section.  This is copied from
2531    elfcode.h as well, with changes as small as accounting for 3
2532    internal relocs per external reloc and resetting reloc_count to
2533    zero before processing the relocs of a section.  */
2534 
2535 static bfd_boolean
mips_elf64_slurp_reloc_table(bfd * abfd,asection * asect,asymbol ** symbols,bfd_boolean dynamic)2536 mips_elf64_slurp_reloc_table (bfd *abfd, asection *asect,
2537 			      asymbol **symbols, bfd_boolean dynamic)
2538 {
2539   struct bfd_elf_section_data * const d = elf_section_data (asect);
2540   Elf_Internal_Shdr *rel_hdr;
2541   Elf_Internal_Shdr *rel_hdr2;
2542   bfd_size_type reloc_count;
2543   bfd_size_type reloc_count2;
2544   arelent *relents;
2545   bfd_size_type amt;
2546 
2547   if (asect->relocation != NULL)
2548     return TRUE;
2549 
2550   if (! dynamic)
2551     {
2552       if ((asect->flags & SEC_RELOC) == 0
2553 	  || asect->reloc_count == 0)
2554 	return TRUE;
2555 
2556       rel_hdr = &d->rel_hdr;
2557       reloc_count = NUM_SHDR_ENTRIES (rel_hdr);
2558       rel_hdr2 = d->rel_hdr2;
2559       reloc_count2 = (rel_hdr2 ? NUM_SHDR_ENTRIES (rel_hdr2) : 0);
2560 
2561       BFD_ASSERT (asect->reloc_count == reloc_count + reloc_count2);
2562       BFD_ASSERT (asect->rel_filepos == rel_hdr->sh_offset
2563 		  || (rel_hdr2 && asect->rel_filepos == rel_hdr2->sh_offset));
2564 
2565     }
2566   else
2567     {
2568       /* Note that ASECT->RELOC_COUNT tends not to be accurate in this
2569 	 case because relocations against this section may use the
2570 	 dynamic symbol table, and in that case bfd_section_from_shdr
2571 	 in elf.c does not update the RELOC_COUNT.  */
2572       if (asect->size == 0)
2573 	return TRUE;
2574 
2575       rel_hdr = &d->this_hdr;
2576       reloc_count = NUM_SHDR_ENTRIES (rel_hdr);
2577       rel_hdr2 = NULL;
2578       reloc_count2 = 0;
2579     }
2580 
2581   /* Allocate space for 3 arelent structures for each Rel structure.  */
2582   amt = (reloc_count + reloc_count2) * 3 * sizeof (arelent);
2583   relents = bfd_alloc (abfd, amt);
2584   if (relents == NULL)
2585     return FALSE;
2586 
2587   /* The slurp_one_reloc_table routine increments reloc_count.  */
2588   asect->reloc_count = 0;
2589 
2590   if (! mips_elf64_slurp_one_reloc_table (abfd, asect,
2591 					  rel_hdr, reloc_count,
2592 					  relents,
2593 					  symbols, dynamic))
2594     return FALSE;
2595   if (d->rel_hdr2 != NULL)
2596     {
2597       if (! mips_elf64_slurp_one_reloc_table (abfd, asect,
2598 					      rel_hdr2, reloc_count2,
2599 					      relents + reloc_count * 3,
2600 					      symbols, dynamic))
2601 	return FALSE;
2602     }
2603 
2604   asect->relocation = relents;
2605   return TRUE;
2606 }
2607 
2608 /* Write out the relocations.  */
2609 
2610 static void
mips_elf64_write_relocs(bfd * abfd,asection * sec,void * data)2611 mips_elf64_write_relocs (bfd *abfd, asection *sec, void *data)
2612 {
2613   bfd_boolean *failedp = data;
2614   int count;
2615   Elf_Internal_Shdr *rel_hdr;
2616   unsigned int idx;
2617 
2618   /* If we have already failed, don't do anything.  */
2619   if (*failedp)
2620     return;
2621 
2622   if ((sec->flags & SEC_RELOC) == 0)
2623     return;
2624 
2625   /* The linker backend writes the relocs out itself, and sets the
2626      reloc_count field to zero to inhibit writing them here.  Also,
2627      sometimes the SEC_RELOC flag gets set even when there aren't any
2628      relocs.  */
2629   if (sec->reloc_count == 0)
2630     return;
2631 
2632   /* We can combine up to three relocs that refer to the same address
2633      if the latter relocs have no associated symbol.  */
2634   count = 0;
2635   for (idx = 0; idx < sec->reloc_count; idx++)
2636     {
2637       bfd_vma addr;
2638       unsigned int i;
2639 
2640       ++count;
2641 
2642       addr = sec->orelocation[idx]->address;
2643       for (i = 0; i < 2; i++)
2644 	{
2645 	  arelent *r;
2646 
2647 	  if (idx + 1 >= sec->reloc_count)
2648 	    break;
2649 	  r = sec->orelocation[idx + 1];
2650 	  if (r->address != addr
2651 	      || ! bfd_is_abs_section ((*r->sym_ptr_ptr)->section)
2652 	      || (*r->sym_ptr_ptr)->value != 0)
2653 	    break;
2654 
2655 	  /* We can merge the reloc at IDX + 1 with the reloc at IDX.  */
2656 
2657 	  ++idx;
2658 	}
2659     }
2660 
2661   rel_hdr = &elf_section_data (sec)->rel_hdr;
2662 
2663   /* Do the actual relocation.  */
2664 
2665   if (rel_hdr->sh_entsize == sizeof(Elf64_Mips_External_Rel))
2666     mips_elf64_write_rel (abfd, sec, rel_hdr, &count, data);
2667   else if (rel_hdr->sh_entsize == sizeof(Elf64_Mips_External_Rela))
2668     mips_elf64_write_rela (abfd, sec, rel_hdr, &count, data);
2669   else
2670     BFD_ASSERT (0);
2671 }
2672 
2673 static void
mips_elf64_write_rel(bfd * abfd,asection * sec,Elf_Internal_Shdr * rel_hdr,int * count,void * data)2674 mips_elf64_write_rel (bfd *abfd, asection *sec,
2675 		      Elf_Internal_Shdr *rel_hdr,
2676 		      int *count, void *data)
2677 {
2678   bfd_boolean *failedp = data;
2679   Elf64_Mips_External_Rel *ext_rel;
2680   unsigned int idx;
2681   asymbol *last_sym = 0;
2682   int last_sym_idx = 0;
2683 
2684   rel_hdr->sh_size = rel_hdr->sh_entsize * *count;
2685   rel_hdr->contents = bfd_alloc (abfd, rel_hdr->sh_size);
2686   if (rel_hdr->contents == NULL)
2687     {
2688       *failedp = TRUE;
2689       return;
2690     }
2691 
2692   ext_rel = (Elf64_Mips_External_Rel *) rel_hdr->contents;
2693   for (idx = 0; idx < sec->reloc_count; idx++, ext_rel++)
2694     {
2695       arelent *ptr;
2696       Elf64_Mips_Internal_Rela int_rel;
2697       asymbol *sym;
2698       int n;
2699       unsigned int i;
2700 
2701       ptr = sec->orelocation[idx];
2702 
2703       /* The address of an ELF reloc is section relative for an object
2704 	 file, and absolute for an executable file or shared library.
2705 	 The address of a BFD reloc is always section relative.  */
2706       if ((abfd->flags & (EXEC_P | DYNAMIC)) == 0)
2707 	int_rel.r_offset = ptr->address;
2708       else
2709 	int_rel.r_offset = ptr->address + sec->vma;
2710 
2711       sym = *ptr->sym_ptr_ptr;
2712       if (sym == last_sym)
2713 	n = last_sym_idx;
2714       else if (bfd_is_abs_section (sym->section) && sym->value == 0)
2715 	n = STN_UNDEF;
2716       else
2717 	{
2718 	  last_sym = sym;
2719 	  n = _bfd_elf_symbol_from_bfd_symbol (abfd, &sym);
2720 	  if (n < 0)
2721 	    {
2722 	      *failedp = TRUE;
2723 	      return;
2724 	    }
2725 	  last_sym_idx = n;
2726 	}
2727 
2728       int_rel.r_sym = n;
2729       int_rel.r_ssym = RSS_UNDEF;
2730 
2731       if ((*ptr->sym_ptr_ptr)->the_bfd->xvec != abfd->xvec
2732 	  && ! _bfd_elf_validate_reloc (abfd, ptr))
2733 	{
2734 	  *failedp = TRUE;
2735 	  return;
2736 	}
2737 
2738       int_rel.r_type = ptr->howto->type;
2739       int_rel.r_type2 = (int) R_MIPS_NONE;
2740       int_rel.r_type3 = (int) R_MIPS_NONE;
2741 
2742       for (i = 0; i < 2; i++)
2743 	{
2744 	  arelent *r;
2745 
2746 	  if (idx + 1 >= sec->reloc_count)
2747 	    break;
2748 	  r = sec->orelocation[idx + 1];
2749 	  if (r->address != ptr->address
2750 	      || ! bfd_is_abs_section ((*r->sym_ptr_ptr)->section)
2751 	      || (*r->sym_ptr_ptr)->value != 0)
2752 	    break;
2753 
2754 	  /* We can merge the reloc at IDX + 1 with the reloc at IDX.  */
2755 
2756 	  if (i == 0)
2757 	    int_rel.r_type2 = r->howto->type;
2758 	  else
2759 	    int_rel.r_type3 = r->howto->type;
2760 
2761 	  ++idx;
2762 	}
2763 
2764       mips_elf64_swap_reloc_out (abfd, &int_rel, ext_rel);
2765     }
2766 
2767   BFD_ASSERT (ext_rel - (Elf64_Mips_External_Rel *) rel_hdr->contents
2768 	      == *count);
2769 }
2770 
2771 static void
mips_elf64_write_rela(bfd * abfd,asection * sec,Elf_Internal_Shdr * rela_hdr,int * count,void * data)2772 mips_elf64_write_rela (bfd *abfd, asection *sec,
2773 		       Elf_Internal_Shdr *rela_hdr,
2774 		       int *count, void *data)
2775 {
2776   bfd_boolean *failedp = data;
2777   Elf64_Mips_External_Rela *ext_rela;
2778   unsigned int idx;
2779   asymbol *last_sym = 0;
2780   int last_sym_idx = 0;
2781 
2782   rela_hdr->sh_size = rela_hdr->sh_entsize * *count;
2783   rela_hdr->contents = bfd_alloc (abfd, rela_hdr->sh_size);
2784   if (rela_hdr->contents == NULL)
2785     {
2786       *failedp = TRUE;
2787       return;
2788     }
2789 
2790   ext_rela = (Elf64_Mips_External_Rela *) rela_hdr->contents;
2791   for (idx = 0; idx < sec->reloc_count; idx++, ext_rela++)
2792     {
2793       arelent *ptr;
2794       Elf64_Mips_Internal_Rela int_rela;
2795       asymbol *sym;
2796       int n;
2797       unsigned int i;
2798 
2799       ptr = sec->orelocation[idx];
2800 
2801       /* The address of an ELF reloc is section relative for an object
2802 	 file, and absolute for an executable file or shared library.
2803 	 The address of a BFD reloc is always section relative.  */
2804       if ((abfd->flags & (EXEC_P | DYNAMIC)) == 0)
2805 	int_rela.r_offset = ptr->address;
2806       else
2807 	int_rela.r_offset = ptr->address + sec->vma;
2808 
2809       sym = *ptr->sym_ptr_ptr;
2810       if (sym == last_sym)
2811 	n = last_sym_idx;
2812       else if (bfd_is_abs_section (sym->section) && sym->value == 0)
2813 	n = STN_UNDEF;
2814       else
2815 	{
2816 	  last_sym = sym;
2817 	  n = _bfd_elf_symbol_from_bfd_symbol (abfd, &sym);
2818 	  if (n < 0)
2819 	    {
2820 	      *failedp = TRUE;
2821 	      return;
2822 	    }
2823 	  last_sym_idx = n;
2824 	}
2825 
2826       int_rela.r_sym = n;
2827       int_rela.r_addend = ptr->addend;
2828       int_rela.r_ssym = RSS_UNDEF;
2829 
2830       if ((*ptr->sym_ptr_ptr)->the_bfd->xvec != abfd->xvec
2831 	  && ! _bfd_elf_validate_reloc (abfd, ptr))
2832 	{
2833 	  *failedp = TRUE;
2834 	  return;
2835 	}
2836 
2837       int_rela.r_type = ptr->howto->type;
2838       int_rela.r_type2 = (int) R_MIPS_NONE;
2839       int_rela.r_type3 = (int) R_MIPS_NONE;
2840 
2841       for (i = 0; i < 2; i++)
2842 	{
2843 	  arelent *r;
2844 
2845 	  if (idx + 1 >= sec->reloc_count)
2846 	    break;
2847 	  r = sec->orelocation[idx + 1];
2848 	  if (r->address != ptr->address
2849 	      || ! bfd_is_abs_section ((*r->sym_ptr_ptr)->section)
2850 	      || (*r->sym_ptr_ptr)->value != 0)
2851 	    break;
2852 
2853 	  /* We can merge the reloc at IDX + 1 with the reloc at IDX.  */
2854 
2855 	  if (i == 0)
2856 	    int_rela.r_type2 = r->howto->type;
2857 	  else
2858 	    int_rela.r_type3 = r->howto->type;
2859 
2860 	  ++idx;
2861 	}
2862 
2863       mips_elf64_swap_reloca_out (abfd, &int_rela, ext_rela);
2864     }
2865 
2866   BFD_ASSERT (ext_rela - (Elf64_Mips_External_Rela *) rela_hdr->contents
2867 	      == *count);
2868 }
2869 
2870 /* Set the right machine number for a MIPS ELF file.  */
2871 
2872 static bfd_boolean
mips_elf64_object_p(bfd * abfd)2873 mips_elf64_object_p (bfd *abfd)
2874 {
2875   unsigned long mach;
2876 
2877   /* Irix 6 is broken.  Object file symbol tables are not always
2878      sorted correctly such that local symbols precede global symbols,
2879      and the sh_info field in the symbol table is not always right.  */
2880   if (elf64_mips_irix_compat (abfd) != ict_none)
2881     elf_bad_symtab (abfd) = TRUE;
2882 
2883   mach = _bfd_elf_mips_mach (elf_elfheader (abfd)->e_flags);
2884   bfd_default_set_arch_mach (abfd, bfd_arch_mips, mach);
2885   return TRUE;
2886 }
2887 
2888 /* Depending on the target vector we generate some version of Irix
2889    executables or "normal" MIPS ELF ABI executables.  */
2890 static irix_compat_t
elf64_mips_irix_compat(bfd * abfd)2891 elf64_mips_irix_compat (bfd *abfd)
2892 {
2893   if ((abfd->xvec == &bfd_elf64_bigmips_vec)
2894       || (abfd->xvec == &bfd_elf64_littlemips_vec))
2895     return ict_irix6;
2896   else
2897     return ict_none;
2898 }
2899 
2900 /* Support for core dump NOTE sections.  */
2901 static bfd_boolean
elf64_mips_grok_prstatus(bfd * abfd,Elf_Internal_Note * note)2902 elf64_mips_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
2903 {
2904   int offset;
2905   unsigned int size;
2906 
2907   switch (note->descsz)
2908     {
2909       default:
2910 	return FALSE;
2911 
2912       case 480:		/* Linux/MIPS - N64 kernel */
2913 	/* pr_cursig */
2914 	elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);
2915 
2916 	/* pr_pid */
2917 	elf_tdata (abfd)->core_pid = bfd_get_32 (abfd, note->descdata + 32);
2918 
2919 	/* pr_reg */
2920 	offset = 112;
2921 	size = 360;
2922 
2923 	break;
2924     }
2925 
2926   /* Make a ".reg/999" section.  */
2927   return _bfd_elfcore_make_pseudosection (abfd, ".reg",
2928 					  size, note->descpos + offset);
2929 }
2930 
2931 static bfd_boolean
elf64_mips_grok_psinfo(bfd * abfd,Elf_Internal_Note * note)2932 elf64_mips_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
2933 {
2934   switch (note->descsz)
2935     {
2936       default:
2937 	return FALSE;
2938 
2939       case 136:		/* Linux/MIPS - N64 kernel elf_prpsinfo */
2940 	elf_tdata (abfd)->core_program
2941 	 = _bfd_elfcore_strndup (abfd, note->descdata + 40, 16);
2942 	elf_tdata (abfd)->core_command
2943 	 = _bfd_elfcore_strndup (abfd, note->descdata + 56, 80);
2944     }
2945 
2946   /* Note that for some reason, a spurious space is tacked
2947      onto the end of the args in some (at least one anyway)
2948      implementations, so strip it off if it exists.  */
2949 
2950   {
2951     char *command = elf_tdata (abfd)->core_command;
2952     int n = strlen (command);
2953 
2954     if (0 < n && command[n - 1] == ' ')
2955       command[n - 1] = '\0';
2956   }
2957 
2958   return TRUE;
2959 }
2960 
2961 /* ECOFF swapping routines.  These are used when dealing with the
2962    .mdebug section, which is in the ECOFF debugging format.  */
2963 static const struct ecoff_debug_swap mips_elf64_ecoff_debug_swap =
2964 {
2965   /* Symbol table magic number.  */
2966   magicSym2,
2967   /* Alignment of debugging information.  E.g., 4.  */
2968   8,
2969   /* Sizes of external symbolic information.  */
2970   sizeof (struct hdr_ext),
2971   sizeof (struct dnr_ext),
2972   sizeof (struct pdr_ext),
2973   sizeof (struct sym_ext),
2974   sizeof (struct opt_ext),
2975   sizeof (struct fdr_ext),
2976   sizeof (struct rfd_ext),
2977   sizeof (struct ext_ext),
2978   /* Functions to swap in external symbolic data.  */
2979   ecoff_swap_hdr_in,
2980   ecoff_swap_dnr_in,
2981   ecoff_swap_pdr_in,
2982   ecoff_swap_sym_in,
2983   ecoff_swap_opt_in,
2984   ecoff_swap_fdr_in,
2985   ecoff_swap_rfd_in,
2986   ecoff_swap_ext_in,
2987   _bfd_ecoff_swap_tir_in,
2988   _bfd_ecoff_swap_rndx_in,
2989   /* Functions to swap out external symbolic data.  */
2990   ecoff_swap_hdr_out,
2991   ecoff_swap_dnr_out,
2992   ecoff_swap_pdr_out,
2993   ecoff_swap_sym_out,
2994   ecoff_swap_opt_out,
2995   ecoff_swap_fdr_out,
2996   ecoff_swap_rfd_out,
2997   ecoff_swap_ext_out,
2998   _bfd_ecoff_swap_tir_out,
2999   _bfd_ecoff_swap_rndx_out,
3000   /* Function to read in symbolic data.  */
3001   _bfd_mips_elf_read_ecoff_info
3002 };
3003 
3004 /* Relocations in the 64 bit MIPS ELF ABI are more complex than in
3005    standard ELF.  This structure is used to redirect the relocation
3006    handling routines.  */
3007 
3008 const struct elf_size_info mips_elf64_size_info =
3009 {
3010   sizeof (Elf64_External_Ehdr),
3011   sizeof (Elf64_External_Phdr),
3012   sizeof (Elf64_External_Shdr),
3013   sizeof (Elf64_Mips_External_Rel),
3014   sizeof (Elf64_Mips_External_Rela),
3015   sizeof (Elf64_External_Sym),
3016   sizeof (Elf64_External_Dyn),
3017   sizeof (Elf_External_Note),
3018   4,		/* hash-table entry size */
3019   3,		/* internal relocations per external relocations */
3020   64,		/* arch_size */
3021   3,		/* log_file_align */
3022   ELFCLASS64,
3023   EV_CURRENT,
3024   bfd_elf64_write_out_phdrs,
3025   bfd_elf64_write_shdrs_and_ehdr,
3026   mips_elf64_write_relocs,
3027   bfd_elf64_swap_symbol_in,
3028   bfd_elf64_swap_symbol_out,
3029   mips_elf64_slurp_reloc_table,
3030   bfd_elf64_slurp_symbol_table,
3031   bfd_elf64_swap_dyn_in,
3032   bfd_elf64_swap_dyn_out,
3033   mips_elf64_be_swap_reloc_in,
3034   mips_elf64_be_swap_reloc_out,
3035   mips_elf64_be_swap_reloca_in,
3036   mips_elf64_be_swap_reloca_out
3037 };
3038 
3039 #define ELF_ARCH			bfd_arch_mips
3040 #define ELF_MACHINE_CODE		EM_MIPS
3041 
3042 #define elf_backend_collect		TRUE
3043 #define elf_backend_type_change_ok	TRUE
3044 #define elf_backend_can_gc_sections	TRUE
3045 #define elf_info_to_howto		mips_elf64_info_to_howto_rela
3046 #define elf_info_to_howto_rel		mips_elf64_info_to_howto_rel
3047 #define elf_backend_object_p		mips_elf64_object_p
3048 #define elf_backend_symbol_processing	_bfd_mips_elf_symbol_processing
3049 #define elf_backend_section_processing	_bfd_mips_elf_section_processing
3050 #define elf_backend_section_from_shdr	_bfd_mips_elf_section_from_shdr
3051 #define elf_backend_fake_sections	_bfd_mips_elf_fake_sections
3052 #define elf_backend_section_from_bfd_section \
3053 				_bfd_mips_elf_section_from_bfd_section
3054 #define elf_backend_add_symbol_hook	_bfd_mips_elf_add_symbol_hook
3055 #define elf_backend_link_output_symbol_hook \
3056 				_bfd_mips_elf_link_output_symbol_hook
3057 #define elf_backend_create_dynamic_sections \
3058 				_bfd_mips_elf_create_dynamic_sections
3059 #define elf_backend_check_relocs	_bfd_mips_elf_check_relocs
3060 #define elf_backend_adjust_dynamic_symbol \
3061 				_bfd_mips_elf_adjust_dynamic_symbol
3062 #define elf_backend_always_size_sections \
3063 				_bfd_mips_elf_always_size_sections
3064 #define elf_backend_size_dynamic_sections \
3065 				_bfd_mips_elf_size_dynamic_sections
3066 #define elf_backend_relocate_section    _bfd_mips_elf_relocate_section
3067 #define elf_backend_finish_dynamic_symbol \
3068 				_bfd_mips_elf_finish_dynamic_symbol
3069 #define elf_backend_finish_dynamic_sections \
3070 				_bfd_mips_elf_finish_dynamic_sections
3071 #define elf_backend_final_write_processing \
3072 				_bfd_mips_elf_final_write_processing
3073 #define elf_backend_additional_program_headers \
3074 				_bfd_mips_elf_additional_program_headers
3075 #define elf_backend_modify_segment_map	_bfd_mips_elf_modify_segment_map
3076 #define elf_backend_gc_mark_hook	_bfd_mips_elf_gc_mark_hook
3077 #define elf_backend_gc_sweep_hook	_bfd_mips_elf_gc_sweep_hook
3078 #define elf_backend_copy_indirect_symbol \
3079 					_bfd_mips_elf_copy_indirect_symbol
3080 #define elf_backend_hide_symbol		_bfd_mips_elf_hide_symbol
3081 #define elf_backend_ignore_discarded_relocs \
3082 					_bfd_mips_elf_ignore_discarded_relocs
3083 #define elf_backend_mips_irix_compat	elf64_mips_irix_compat
3084 #define elf_backend_mips_rtype_to_howto	mips_elf64_rtype_to_howto
3085 #define elf_backend_ecoff_debug_swap	&mips_elf64_ecoff_debug_swap
3086 #define elf_backend_size_info		mips_elf64_size_info
3087 
3088 #define elf_backend_grok_prstatus	elf64_mips_grok_prstatus
3089 #define elf_backend_grok_psinfo		elf64_mips_grok_psinfo
3090 
3091 #define elf_backend_got_header_size	(4 * MIPS_RESERVED_GOTNO)
3092 
3093 /* MIPS ELF64 can use a mixture of REL and RELA, but some Relocations
3094    work better/work only in RELA, so we default to this.  */
3095 #define elf_backend_may_use_rel_p	1
3096 #define elf_backend_may_use_rela_p	1
3097 #define elf_backend_default_use_rela_p	1
3098 
3099 #define elf_backend_write_section	_bfd_mips_elf_write_section
3100 
3101 /* We don't set bfd_elf64_bfd_is_local_label_name because the 32-bit
3102    MIPS-specific function only applies to IRIX5, which had no 64-bit
3103    ABI.  */
3104 #define bfd_elf64_find_nearest_line	_bfd_mips_elf_find_nearest_line
3105 #define bfd_elf64_new_section_hook	_bfd_mips_elf_new_section_hook
3106 #define bfd_elf64_set_section_contents	_bfd_mips_elf_set_section_contents
3107 #define bfd_elf64_bfd_get_relocated_section_contents \
3108 				_bfd_elf_mips_get_relocated_section_contents
3109 #define bfd_elf64_bfd_link_hash_table_create \
3110 				_bfd_mips_elf_link_hash_table_create
3111 #define bfd_elf64_bfd_final_link	_bfd_mips_elf_final_link
3112 #define bfd_elf64_bfd_merge_private_bfd_data \
3113 				_bfd_mips_elf_merge_private_bfd_data
3114 #define bfd_elf64_bfd_set_private_flags	_bfd_mips_elf_set_private_flags
3115 #define bfd_elf64_bfd_print_private_bfd_data \
3116 				_bfd_mips_elf_print_private_bfd_data
3117 
3118 #define bfd_elf64_get_reloc_upper_bound mips_elf64_get_reloc_upper_bound
3119 #define bfd_elf64_canonicalize_reloc mips_elf64_canonicalize_reloc
3120 #define bfd_elf64_get_dynamic_reloc_upper_bound mips_elf64_get_dynamic_reloc_upper_bound
3121 #define bfd_elf64_canonicalize_dynamic_reloc mips_elf64_canonicalize_dynamic_reloc
3122 #define bfd_elf64_bfd_relax_section     _bfd_mips_relax_section
3123 
3124 /* MIPS ELF64 archive functions.  */
3125 #define bfd_elf64_archive_functions
3126 extern bfd_boolean bfd_elf64_archive_slurp_armap
3127   (bfd *);
3128 extern bfd_boolean bfd_elf64_archive_write_armap
3129   (bfd *, unsigned int, struct orl *, unsigned int, int);
3130 #define bfd_elf64_archive_slurp_extended_name_table \
3131 			_bfd_archive_coff_slurp_extended_name_table
3132 #define bfd_elf64_archive_construct_extended_name_table \
3133 			_bfd_archive_coff_construct_extended_name_table
3134 #define bfd_elf64_archive_truncate_arname \
3135 			_bfd_archive_coff_truncate_arname
3136 #define bfd_elf64_archive_read_ar_hdr	_bfd_archive_coff_read_ar_hdr
3137 #define bfd_elf64_archive_openr_next_archived_file \
3138 			_bfd_archive_coff_openr_next_archived_file
3139 #define bfd_elf64_archive_get_elt_at_index \
3140 			_bfd_archive_coff_get_elt_at_index
3141 #define bfd_elf64_archive_generic_stat_arch_elt \
3142 			_bfd_archive_coff_generic_stat_arch_elt
3143 #define bfd_elf64_archive_update_armap_timestamp \
3144 			_bfd_archive_coff_update_armap_timestamp
3145 
3146 /* The SGI style (n)64 NewABI.  */
3147 #define TARGET_LITTLE_SYM		bfd_elf64_littlemips_vec
3148 #define TARGET_LITTLE_NAME		"elf64-littlemips"
3149 #define TARGET_BIG_SYM			bfd_elf64_bigmips_vec
3150 #define TARGET_BIG_NAME			"elf64-bigmips"
3151 
3152 /* The SVR4 MIPS ABI says that this should be 0x10000, but Irix 5 uses
3153    a value of 0x1000, and we are compatible.
3154    FIXME: How does this affect NewABI?  */
3155 #define ELF_MAXPAGESIZE			0x1000
3156 
3157 #include "elf64-target.h"
3158 
3159 /* The SYSV-style 'traditional' (n)64 NewABI.  */
3160 #undef TARGET_LITTLE_SYM
3161 #undef TARGET_LITTLE_NAME
3162 #undef TARGET_BIG_SYM
3163 #undef TARGET_BIG_NAME
3164 
3165 #undef ELF_MAXPAGESIZE
3166 
3167 #define TARGET_LITTLE_SYM		bfd_elf64_tradlittlemips_vec
3168 #define TARGET_LITTLE_NAME		"elf64-tradlittlemips"
3169 #define TARGET_BIG_SYM			bfd_elf64_tradbigmips_vec
3170 #define TARGET_BIG_NAME			"elf64-tradbigmips"
3171 
3172 /* The SVR4 MIPS ABI says that this should be 0x10000, and Linux uses
3173    page sizes of up to that limit, so we need to respect it.  */
3174 #define ELF_MAXPAGESIZE			0x10000
3175 #define elf64_bed			elf64_tradbed
3176 
3177 /* Include the target file again for this target.  */
3178 #include "elf64-target.h"
3179