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