OSDN Git Service

bfd/
[pf3gnuchains/pf3gnuchains3x.git] / bfd / elf32-frv.c
1 /* FRV-specific support for 32-bit ELF.
2    Copyright 2002, 2003, 2004 Free Software Foundation, Inc.
3
4 This file is part of BFD, the Binary File Descriptor library.
5
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2 of the License, or
9 (at your option) any later version.
10
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with this program; if not, write to the Free Software
18 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
19
20 #include "bfd.h"
21 #include "sysdep.h"
22 #include "libbfd.h"
23 #include "elf-bfd.h"
24 #include "elf/frv.h"
25 #include "elf/dwarf2.h"
26 #include "hashtab.h"
27
28 /* Forward declarations.  */
29 static bfd_reloc_status_type elf32_frv_relocate_lo16
30   PARAMS ((bfd *,  Elf_Internal_Rela *, bfd_byte *, bfd_vma));
31 static bfd_reloc_status_type elf32_frv_relocate_hi16
32   PARAMS ((bfd *,  Elf_Internal_Rela *, bfd_byte *, bfd_vma));
33 static bfd_reloc_status_type elf32_frv_relocate_label24
34   PARAMS ((bfd *, asection *, Elf_Internal_Rela *, bfd_byte *, bfd_vma));
35 static bfd_reloc_status_type elf32_frv_relocate_gprel12
36   PARAMS ((struct bfd_link_info *, bfd *, asection *, Elf_Internal_Rela *,
37            bfd_byte *, bfd_vma));
38 static bfd_reloc_status_type elf32_frv_relocate_gprelu12
39   PARAMS ((struct bfd_link_info *, bfd *, asection *, Elf_Internal_Rela *,
40            bfd_byte *, bfd_vma));
41 static bfd_reloc_status_type elf32_frv_relocate_gprello
42   PARAMS ((struct bfd_link_info *, bfd *, asection *, Elf_Internal_Rela *,
43            bfd_byte *, bfd_vma));
44 static bfd_reloc_status_type elf32_frv_relocate_gprelhi
45   PARAMS ((struct bfd_link_info *, bfd *, asection *, Elf_Internal_Rela *,
46            bfd_byte *, bfd_vma));
47 static reloc_howto_type *frv_reloc_type_lookup
48   PARAMS ((bfd *, bfd_reloc_code_real_type));
49 static void frv_info_to_howto_rela
50   PARAMS ((bfd *, arelent *, Elf_Internal_Rela *));
51 static bfd_boolean elf32_frv_relocate_section
52   PARAMS ((bfd *, struct bfd_link_info *, bfd *, asection *, bfd_byte *,
53            Elf_Internal_Rela *, Elf_Internal_Sym *, asection **));
54 static bfd_boolean elf32_frv_add_symbol_hook
55   PARAMS (( bfd *, struct bfd_link_info *, Elf_Internal_Sym *,
56             const char **, flagword *, asection **, bfd_vma *));
57 static bfd_reloc_status_type frv_final_link_relocate
58   PARAMS ((reloc_howto_type *, bfd *, asection *, bfd_byte *,
59            Elf_Internal_Rela *, bfd_vma));
60 static bfd_boolean elf32_frv_gc_sweep_hook
61   PARAMS ((bfd *, struct bfd_link_info *, asection *, const
62            Elf_Internal_Rela *));
63 static asection * elf32_frv_gc_mark_hook
64   PARAMS ((asection *, struct bfd_link_info *, Elf_Internal_Rela *,
65            struct elf_link_hash_entry *, Elf_Internal_Sym *));
66 static bfd_boolean elf32_frv_check_relocs
67   PARAMS ((bfd *, struct bfd_link_info *, asection *,
68            const Elf_Internal_Rela *));
69 static int elf32_frv_machine
70   PARAMS ((bfd *));
71 static bfd_boolean elf32_frv_object_p
72   PARAMS ((bfd *));
73 static bfd_boolean frv_elf_set_private_flags
74   PARAMS ((bfd *, flagword));
75 static bfd_boolean frv_elf_copy_private_bfd_data
76   PARAMS ((bfd *, bfd *));
77 static bfd_boolean frv_elf_merge_private_bfd_data
78   PARAMS ((bfd *, bfd *));
79 static bfd_boolean frv_elf_print_private_bfd_data
80   PARAMS ((bfd *, PTR));
81
82 static reloc_howto_type elf32_frv_howto_table [] =
83 {
84   /* This reloc does nothing.  */
85   HOWTO (R_FRV_NONE,            /* type */
86          0,                     /* rightshift */
87          2,                     /* size (0 = byte, 1 = short, 2 = long) */
88          32,                    /* bitsize */
89          FALSE,                 /* pc_relative */
90          0,                     /* bitpos */
91          complain_overflow_bitfield, /* complain_on_overflow */
92          bfd_elf_generic_reloc, /* special_function */
93          "R_FRV_NONE",          /* name */
94          FALSE,                 /* partial_inplace */
95          0,                     /* src_mask */
96          0,                     /* dst_mask */
97          FALSE),                /* pcrel_offset */
98
99   /* A 32 bit absolute relocation.  */
100   HOWTO (R_FRV_32,              /* type */
101          0,                     /* rightshift */
102          2,                     /* size (0 = byte, 1 = short, 2 = long) */
103          32,                    /* bitsize */
104          FALSE,                 /* pc_relative */
105          0,                     /* bitpos */
106          complain_overflow_bitfield, /* complain_on_overflow */
107          bfd_elf_generic_reloc, /* special_function */
108          "R_FRV_32",            /* name */
109          FALSE,                 /* partial_inplace */
110          0xffffffff,            /* src_mask */
111          0xffffffff,            /* dst_mask */
112          FALSE),                /* pcrel_offset */
113
114   /* A 16 bit pc-relative relocation.  */
115   HOWTO (R_FRV_LABEL16,         /* type */
116          2,                     /* rightshift */
117          2,                     /* size (0 = byte, 1 = short, 2 = long) */
118          16,                    /* bitsize */
119          TRUE,                  /* pc_relative */
120          0,                     /* bitpos */
121          complain_overflow_signed, /* complain_on_overflow */
122          bfd_elf_generic_reloc, /* special_function */
123          "R_FRV_LABEL16",       /* name */
124          FALSE,                 /* partial_inplace */
125          0xffff,                /* src_mask */
126          0xffff,                /* dst_mask */
127          TRUE),                 /* pcrel_offset */
128
129   /* A 24-bit pc-relative relocation.  */
130   HOWTO (R_FRV_LABEL24, /* type */
131          2,                     /* rightshift */
132          2,                     /* size (0 = byte, 1 = short, 2 = long) */
133          26,                    /* bitsize */
134          TRUE,                  /* pc_relative */
135          0,                     /* bitpos */
136          complain_overflow_bitfield, /* complain_on_overflow */
137          bfd_elf_generic_reloc, /* special_function */
138          "R_FRV_LABEL24",       /* name */
139          FALSE,                 /* partial_inplace */
140          0x7e03ffff,            /* src_mask */
141          0x7e03ffff,            /* dst_mask */
142          TRUE),                 /* pcrel_offset */
143
144   HOWTO (R_FRV_LO16,            /* type */
145          0,                     /* rightshift */
146          2,                     /* size (0 = byte, 1 = short, 2 = long) */
147          16,                    /* bitsize */
148          FALSE,                 /* pc_relative */
149          0,                     /* bitpos */
150          complain_overflow_dont, /* complain_on_overflow */
151          bfd_elf_generic_reloc, /* special_function */
152          "R_FRV_LO16",          /* name */
153          FALSE,                 /* partial_inplace */
154          0xffff,                /* src_mask */
155          0xffff,                /* dst_mask */
156          FALSE),                /* pcrel_offset */
157
158   HOWTO (R_FRV_HI16,            /* type */
159          0,                     /* rightshift */
160          2,                     /* size (0 = byte, 1 = short, 2 = long) */
161          16,                    /* bitsize */
162          FALSE,                 /* pc_relative */
163          0,                     /* bitpos */
164          complain_overflow_dont, /* complain_on_overflow */
165          bfd_elf_generic_reloc, /* special_function */
166          "R_FRV_HI16",          /* name */
167          FALSE,                 /* partial_inplace */
168          0xffff,                /* src_mask */
169          0xffff,                /* dst_mask */
170          FALSE),                /* pcrel_offset */
171
172   HOWTO (R_FRV_GPREL12,         /* type */
173          0,                     /* rightshift */
174          2,                     /* size (0 = byte, 1 = short, 2 = long) */
175          12,                    /* bitsize */
176          FALSE,                 /* pc_relative */
177          0,                     /* bitpos */
178          complain_overflow_dont, /* complain_on_overflow */
179          bfd_elf_generic_reloc, /* special_function */
180          "R_FRV_GPREL12",       /* name */
181          FALSE,                 /* partial_inplace */
182          0xfff,                 /* src_mask */
183          0xfff,                 /* dst_mask */
184          FALSE),                /* pcrel_offset */
185
186   HOWTO (R_FRV_GPRELU12,        /* type */
187          0,                     /* rightshift */
188          2,                     /* size (0 = byte, 1 = short, 2 = long) */
189          12,                    /* bitsize */
190          FALSE,                 /* pc_relative */
191          0,                     /* bitpos */
192          complain_overflow_dont, /* complain_on_overflow */
193          bfd_elf_generic_reloc, /* special_function */
194          "R_FRV_GPRELU12",      /* name */
195          FALSE,                 /* partial_inplace */
196          0xfff,                 /* src_mask */
197          0x3f03f,               /* dst_mask */
198          FALSE),                /* pcrel_offset */
199
200   HOWTO (R_FRV_GPREL32,         /* type */
201          0,                     /* rightshift */
202          2,                     /* size (0 = byte, 1 = short, 2 = long) */
203          32,                    /* bitsize */
204          FALSE,                 /* pc_relative */
205          0,                     /* bitpos */
206          complain_overflow_dont, /* complain_on_overflow */
207          bfd_elf_generic_reloc, /* special_function */
208          "R_FRV_GPREL32",       /* name */
209          FALSE,                 /* partial_inplace */
210          0xffffffff,            /* src_mask */
211          0xffffffff,            /* dst_mask */
212          FALSE),                /* pcrel_offset */
213
214   HOWTO (R_FRV_GPRELHI,         /* type */
215          0,                     /* rightshift */
216          2,                     /* size (0 = byte, 1 = short, 2 = long) */
217          16,                    /* bitsize */
218          FALSE,                 /* pc_relative */
219          0,                     /* bitpos */
220          complain_overflow_dont, /* complain_on_overflow */
221          bfd_elf_generic_reloc, /* special_function */
222          "R_FRV_GPRELHI",       /* name */
223          FALSE,                 /* partial_inplace */
224          0xffff,                        /* src_mask */
225          0xffff,                /* dst_mask */
226          FALSE),                /* pcrel_offset */
227
228   HOWTO (R_FRV_GPRELLO,         /* type */
229          0,                     /* rightshift */
230          2,                     /* size (0 = byte, 1 = short, 2 = long) */
231          16,                    /* bitsize */
232          FALSE,                 /* pc_relative */
233          0,                     /* bitpos */
234          complain_overflow_dont, /* complain_on_overflow */
235          bfd_elf_generic_reloc, /* special_function */
236          "R_FRV_GPRELLO",       /* name */
237          FALSE,                 /* partial_inplace */
238          0xffff,                        /* src_mask */
239          0xffff,                /* dst_mask */
240          FALSE),                /* pcrel_offset */
241
242   /* A 12-bit signed operand with the GOT offset for the address of
243      the symbol.  */
244   HOWTO (R_FRV_GOT12,           /* type */
245          0,                     /* rightshift */
246          2,                     /* size (0 = byte, 1 = short, 2 = long) */
247          12,                    /* bitsize */
248          FALSE,                 /* pc_relative */
249          0,                     /* bitpos */
250          complain_overflow_signed, /* complain_on_overflow */
251          bfd_elf_generic_reloc, /* special_function */
252          "R_FRV_GOT12",         /* name */
253          FALSE,                 /* partial_inplace */
254          0xfff,                 /* src_mask */
255          0xfff,                 /* dst_mask */
256          FALSE),                /* pcrel_offset */
257
258   /* The upper 16 bits of the GOT offset for the address of the
259      symbol.  */
260   HOWTO (R_FRV_GOTHI,           /* type */
261          0,                     /* rightshift */
262          2,                     /* size (0 = byte, 1 = short, 2 = long) */
263          16,                    /* bitsize */
264          FALSE,                 /* pc_relative */
265          0,                     /* bitpos */
266          complain_overflow_dont, /* complain_on_overflow */
267          bfd_elf_generic_reloc, /* special_function */
268          "R_FRV_GOTHI",         /* name */
269          FALSE,                 /* partial_inplace */
270          0xffff,                        /* src_mask */
271          0xffff,                /* dst_mask */
272          FALSE),                /* pcrel_offset */
273
274   /* The lower 16 bits of the GOT offset for the address of the
275      symbol.  */
276   HOWTO (R_FRV_GOTLO,           /* type */
277          0,                     /* rightshift */
278          2,                     /* size (0 = byte, 1 = short, 2 = long) */
279          16,                    /* bitsize */
280          FALSE,                 /* pc_relative */
281          0,                     /* bitpos */
282          complain_overflow_dont, /* complain_on_overflow */
283          bfd_elf_generic_reloc, /* special_function */
284          "R_FRV_GOTLO",         /* name */
285          FALSE,                 /* partial_inplace */
286          0xffff,                /* src_mask */
287          0xffff,                /* dst_mask */
288          FALSE),                /* pcrel_offset */
289
290   /* The 32-bit address of the canonical descriptor of a function.  */
291   HOWTO (R_FRV_FUNCDESC,        /* type */
292          0,                     /* rightshift */
293          2,                     /* size (0 = byte, 1 = short, 2 = long) */
294          32,                    /* bitsize */
295          FALSE,                 /* pc_relative */
296          0,                     /* bitpos */
297          complain_overflow_bitfield, /* complain_on_overflow */
298          bfd_elf_generic_reloc, /* special_function */
299          "R_FRV_FUNCDESC",      /* name */
300          FALSE,                 /* partial_inplace */
301          0xffffffff,            /* src_mask */
302          0xffffffff,            /* dst_mask */
303          FALSE),                /* pcrel_offset */
304
305   /* A 12-bit signed operand with the GOT offset for the address of
306      canonical descriptor of a function.  */
307   HOWTO (R_FRV_FUNCDESC_GOT12,  /* type */
308          0,                     /* rightshift */
309          2,                     /* size (0 = byte, 1 = short, 2 = long) */
310          12,                    /* bitsize */
311          FALSE,                 /* pc_relative */
312          0,                     /* bitpos */
313          complain_overflow_signed, /* complain_on_overflow */
314          bfd_elf_generic_reloc, /* special_function */
315          "R_FRV_FUNCDESC_GOT12", /* name */
316          FALSE,                 /* partial_inplace */
317          0xfff,                 /* src_mask */
318          0xfff,                 /* dst_mask */
319          FALSE),                /* pcrel_offset */
320
321   /* The upper 16 bits of the GOT offset for the address of the
322      canonical descriptor of a function.  */
323   HOWTO (R_FRV_FUNCDESC_GOTHI,  /* type */
324          0,                     /* rightshift */
325          2,                     /* size (0 = byte, 1 = short, 2 = long) */
326          16,                    /* bitsize */
327          FALSE,                 /* pc_relative */
328          0,                     /* bitpos */
329          complain_overflow_dont, /* complain_on_overflow */
330          bfd_elf_generic_reloc, /* special_function */
331          "R_FRV_FUNCDESC_GOTHI", /* name */
332          FALSE,                 /* partial_inplace */
333          0xffff,                /* src_mask */
334          0xffff,                /* dst_mask */
335          FALSE),                /* pcrel_offset */
336
337   /* The lower 16 bits of the GOT offset for the address of the
338      canonical descriptor of a function.  */
339   HOWTO (R_FRV_FUNCDESC_GOTLO,  /* type */
340          0,                     /* rightshift */
341          2,                     /* size (0 = byte, 1 = short, 2 = long) */
342          16,                    /* bitsize */
343          FALSE,                 /* pc_relative */
344          0,                     /* bitpos */
345          complain_overflow_dont, /* complain_on_overflow */
346          bfd_elf_generic_reloc, /* special_function */
347          "R_FRV_FUNCDESC_GOTLO", /* name */
348          FALSE,                 /* partial_inplace */
349          0xffff,                /* src_mask */
350          0xffff,                /* dst_mask */
351          FALSE),                /* pcrel_offset */
352
353   /* The 32-bit address of the canonical descriptor of a function.  */
354   HOWTO (R_FRV_FUNCDESC_VALUE,  /* type */
355          0,                     /* rightshift */
356          2,                     /* size (0 = byte, 1 = short, 2 = long) */
357          64,                    /* bitsize */
358          FALSE,                 /* pc_relative */
359          0,                     /* bitpos */
360          complain_overflow_bitfield, /* complain_on_overflow */
361          bfd_elf_generic_reloc, /* special_function */
362          "R_FRV_FUNCDESC_VALUE", /* name */
363          FALSE,                 /* partial_inplace */
364          0xffffffff,            /* src_mask */
365          0xffffffff,            /* dst_mask */
366          FALSE),                /* pcrel_offset */
367
368   /* A 12-bit signed operand with the GOT offset for the address of
369      canonical descriptor of a function.  */
370   HOWTO (R_FRV_FUNCDESC_GOTOFF12, /* type */
371          0,                     /* rightshift */
372          2,                     /* size (0 = byte, 1 = short, 2 = long) */
373          12,                    /* bitsize */
374          FALSE,                 /* pc_relative */
375          0,                     /* bitpos */
376          complain_overflow_signed, /* complain_on_overflow */
377          bfd_elf_generic_reloc, /* special_function */
378          "R_FRV_FUNCDESC_GOTOFF12", /* name */
379          FALSE,                 /* partial_inplace */
380          0xfff,                 /* src_mask */
381          0xfff,                 /* dst_mask */
382          FALSE),                /* pcrel_offset */
383
384   /* The upper 16 bits of the GOT offset for the address of the
385      canonical descriptor of a function.  */
386   HOWTO (R_FRV_FUNCDESC_GOTOFFHI, /* type */
387          0,                     /* rightshift */
388          2,                     /* size (0 = byte, 1 = short, 2 = long) */
389          16,                    /* bitsize */
390          FALSE,                 /* pc_relative */
391          0,                     /* bitpos */
392          complain_overflow_dont, /* complain_on_overflow */
393          bfd_elf_generic_reloc, /* special_function */
394          "R_FRV_FUNCDESC_GOTOFFHI", /* name */
395          FALSE,                 /* partial_inplace */
396          0xffff,                /* src_mask */
397          0xffff,                /* dst_mask */
398          FALSE),                /* pcrel_offset */
399
400   /* The lower 16 bits of the GOT offset for the address of the
401      canonical descriptor of a function.  */
402   HOWTO (R_FRV_FUNCDESC_GOTOFFLO, /* type */
403          0,                     /* rightshift */
404          2,                     /* size (0 = byte, 1 = short, 2 = long) */
405          16,                    /* bitsize */
406          FALSE,                 /* pc_relative */
407          0,                     /* bitpos */
408          complain_overflow_dont, /* complain_on_overflow */
409          bfd_elf_generic_reloc, /* special_function */
410          "R_FRV_FUNCDESC_GOTOFFLO", /* name */
411          FALSE,                 /* partial_inplace */
412          0xffff,                /* src_mask */
413          0xffff,                /* dst_mask */
414          FALSE),                /* pcrel_offset */
415
416   /* A 12-bit signed operand with the GOT offset for the address of
417      the symbol.  */
418   HOWTO (R_FRV_GOTOFF12,        /* type */
419          0,                     /* rightshift */
420          2,                     /* size (0 = byte, 1 = short, 2 = long) */
421          12,                    /* bitsize */
422          FALSE,                 /* pc_relative */
423          0,                     /* bitpos */
424          complain_overflow_signed, /* complain_on_overflow */
425          bfd_elf_generic_reloc, /* special_function */
426          "R_FRV_GOTOFF12",      /* name */
427          FALSE,                 /* partial_inplace */
428          0xfff,                 /* src_mask */
429          0xfff,                 /* dst_mask */
430          FALSE),                /* pcrel_offset */
431
432   /* The upper 16 bits of the GOT offset for the address of the
433      symbol.  */
434   HOWTO (R_FRV_GOTOFFHI,        /* 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_FRV_GOTOFFHI",      /* name */
443          FALSE,                 /* partial_inplace */
444          0xffff,                /* src_mask */
445          0xffff,                /* dst_mask */
446          FALSE),                /* pcrel_offset */
447
448   /* The lower 16 bits of the GOT offset for the address of the
449      symbol.  */
450   HOWTO (R_FRV_GOTOFFLO,        /* type */
451          0,                     /* rightshift */
452          2,                     /* size (0 = byte, 1 = short, 2 = long) */
453          16,                    /* bitsize */
454          FALSE,                 /* pc_relative */
455          0,                     /* bitpos */
456          complain_overflow_dont, /* complain_on_overflow */
457          bfd_elf_generic_reloc, /* special_function */
458          "R_FRV_GOTOFFLO",      /* name */
459          FALSE,                 /* partial_inplace */
460          0xffff,                /* src_mask */
461          0xffff,                /* dst_mask */
462          FALSE),                /* pcrel_offset */
463
464 };
465
466 /* GNU extension to record C++ vtable hierarchy.  */
467 static reloc_howto_type elf32_frv_vtinherit_howto =
468   HOWTO (R_FRV_GNU_VTINHERIT,   /* type */
469          0,                     /* rightshift */
470          2,                     /* size (0 = byte, 1 = short, 2 = long) */
471          0,                     /* bitsize */
472          FALSE,                 /* pc_relative */
473          0,                     /* bitpos */
474          complain_overflow_dont, /* complain_on_overflow */
475          NULL,                  /* special_function */
476          "R_FRV_GNU_VTINHERIT", /* name */
477          FALSE,                 /* partial_inplace */
478          0,                     /* src_mask */
479          0,                     /* dst_mask */
480          FALSE);                /* pcrel_offset */
481
482   /* GNU extension to record C++ vtable member usage.  */
483 static reloc_howto_type elf32_frv_vtentry_howto =
484   HOWTO (R_FRV_GNU_VTENTRY,     /* type */
485          0,                     /* rightshift */
486          2,                     /* size (0 = byte, 1 = short, 2 = long) */
487          0,                     /* bitsize */
488          FALSE,                 /* pc_relative */
489          0,                     /* bitpos */
490          complain_overflow_dont, /* complain_on_overflow */
491          _bfd_elf_rel_vtable_reloc_fn,  /* special_function */
492          "R_FRV_GNU_VTENTRY",   /* name */
493          FALSE,                 /* partial_inplace */
494          0,                     /* src_mask */
495          0,                     /* dst_mask */
496          FALSE);                /* pcrel_offset */
497
498 /* The following 3 relocations are REL.  The only difference to the
499    entries in the table above are that partial_inplace is TRUE.  */
500 static reloc_howto_type elf32_frv_rel_32_howto =
501   HOWTO (R_FRV_32,              /* type */
502          0,                     /* rightshift */
503          2,                     /* size (0 = byte, 1 = short, 2 = long) */
504          32,                    /* bitsize */
505          FALSE,                 /* pc_relative */
506          0,                     /* bitpos */
507          complain_overflow_bitfield, /* complain_on_overflow */
508          bfd_elf_generic_reloc, /* special_function */
509          "R_FRV_32",            /* name */
510          TRUE,                  /* partial_inplace */
511          0xffffffff,            /* src_mask */
512          0xffffffff,            /* dst_mask */
513          FALSE);                /* pcrel_offset */
514
515 static reloc_howto_type elf32_frv_rel_funcdesc_howto =
516   HOWTO (R_FRV_FUNCDESC,        /* type */
517          0,                     /* rightshift */
518          2,                     /* size (0 = byte, 1 = short, 2 = long) */
519          32,                    /* bitsize */
520          FALSE,                 /* pc_relative */
521          0,                     /* bitpos */
522          complain_overflow_bitfield, /* complain_on_overflow */
523          bfd_elf_generic_reloc, /* special_function */
524          "R_FRV_FUNCDESC",      /* name */
525          TRUE,                  /* partial_inplace */
526          0xffffffff,            /* src_mask */
527          0xffffffff,            /* dst_mask */
528          FALSE);                /* pcrel_offset */
529
530 static reloc_howto_type elf32_frv_rel_funcdesc_value_howto =
531   HOWTO (R_FRV_FUNCDESC_VALUE,  /* type */
532          0,                     /* rightshift */
533          2,                     /* size (0 = byte, 1 = short, 2 = long) */
534          64,                    /* bitsize */
535          FALSE,                 /* pc_relative */
536          0,                     /* bitpos */
537          complain_overflow_bitfield, /* complain_on_overflow */
538          bfd_elf_generic_reloc, /* special_function */
539          "R_FRV_FUNCDESC_VALUE", /* name */
540          TRUE,                  /* partial_inplace */
541          0xffffffff,            /* src_mask */
542          0xffffffff,            /* dst_mask */
543          FALSE);                /* pcrel_offset */
544
545 \f
546 /* Map BFD reloc types to FRV ELF reloc types.  */
547 #if 0
548 struct frv_reloc_map
549 {
550   unsigned int bfd_reloc_val;
551   unsigned int frv_reloc_val;
552 };
553
554 static const struct frv_reloc_map frv_reloc_map [] =
555 {
556   { BFD_RELOC_NONE,           R_FRV_NONE },
557   { BFD_RELOC_32,             R_FRV_32 },
558   { BFD_RELOC_FRV_LABEL16,    R_FRV_LABEL16 },
559   { BFD_RELOC_FRV_LABEL24,    R_FRV_LABEL24 },
560   { BFD_RELOC_FRV_LO16,       R_FRV_LO16 },
561   { BFD_RELOC_FRV_HI16,       R_FRV_HI16 },
562   { BFD_RELOC_FRV_GPREL12,    R_FRV_GPREL12 },
563   { BFD_RELOC_FRV_GPRELU12,   R_FRV_GPRELU12 },
564   { BFD_RELOC_FRV_GPREL32,    R_FRV_GPREL32 },
565   { BFD_RELOC_FRV_GPRELHI,    R_FRV_GPRELHI },
566   { BFD_RELOC_FRV_GPRELLO,    R_FRV_GPRELLO },
567   { BFD_RELOC_FRV_GOT12,      R_FRV_GOT12 },
568   { BFD_RELOC_FRV_GOTHI,      R_FRV_GOTHI },
569   { BFD_RELOC_FRV_GOTLO,      R_FRV_GOTLO },
570   { BFD_RELOC_FRV_FUNCDESC,   R_FRV_FUNCDESC },
571   { BFD_RELOC_FRV_FUNCDESC_GOT12, R_FRV_FUNCDESC_GOT12 },
572   { BFD_RELOC_FRV_FUNCDESC_GOTHI, R_FRV_FUNCDESC_GOTHI },
573   { BFD_RELOC_FRV_FUNCDESC_GOTLO, R_FRV_FUNCDESC_GOTLO },
574   { BFD_RELOC_FRV_FUNCDESC_VALUE, R_FRV_FUNCDESC_VALUE },
575   { BFD_RELOC_FRV_FUNCDESC_GOTOFF12, R_FRV_FUNCDESC_GOTOFF12 },
576   { BFD_RELOC_FRV_FUNCDESC_GOTOFFHI, R_FRV_FUNCDESC_GOTOFFHI },
577   { BFD_RELOC_FRV_FUNCDESC_GOTOFFLO, R_FRV_FUNCDESC_GOTOFFLO },
578   { BFD_RELOC_FRV_GOTOFF12,   R_FRV_GOTOFF12 },
579   { BFD_RELOC_FRV_GOTOFFHI,   R_FRV_GOTOFFHI },
580   { BFD_RELOC_FRV_GOTOFFLO,   R_FRV_GOTOFFLO },
581   { BFD_RELOC_VTABLE_INHERIT, R_FRV_GNU_VTINHERIT },
582   { BFD_RELOC_VTABLE_ENTRY,   R_FRV_GNU_VTENTRY },
583 };
584 #endif
585
586 extern const bfd_target bfd_elf32_frvfdpic_vec;
587 #define IS_FDPIC(bfd) ((bfd)->xvec == &bfd_elf32_frvfdpic_vec)
588
589 /* An extension of the elf hash table data structure, containing some
590    additional FRV-specific data.  */
591 struct frvfdpic_elf_link_hash_table
592 {
593   struct elf_link_hash_table elf;
594
595   /* A pointer to the .got section.  */
596   asection *sgot;
597   /* A pointer to the .rel.got section.  */
598   asection *sgotrel;
599   /* A pointer to the .rofixup section.  */
600   asection *sgotfixup;
601   /* A pointer to the .plt section.  */
602   asection *splt;
603   /* A pointer to the .rel.plt section.  */
604   asection *spltrel;
605   /* GOT base offset.  */
606   bfd_vma got0;
607   /* Location of the first non-lazy PLT entry, i.e., the number of
608      bytes taken by lazy PLT entries.  */
609   bfd_vma plt0;
610   /* A hash table holding information about which symbols were
611      referenced with which PIC-related relocations.  */
612   struct htab *relocs_info;
613 };
614
615 /* Get the FRV ELF linker hash table from a link_info structure.  */
616
617 #define frvfdpic_hash_table(info) \
618   ((struct frvfdpic_elf_link_hash_table *) ((info)->hash))
619
620 #define frvfdpic_got_section(info) \
621   (frvfdpic_hash_table (info)->sgot)
622 #define frvfdpic_gotrel_section(info) \
623   (frvfdpic_hash_table (info)->sgotrel)
624 #define frvfdpic_gotfixup_section(info) \
625   (frvfdpic_hash_table (info)->sgotfixup)
626 #define frvfdpic_plt_section(info) \
627   (frvfdpic_hash_table (info)->splt)
628 #define frvfdpic_pltrel_section(info) \
629   (frvfdpic_hash_table (info)->spltrel)
630 #define frvfdpic_relocs_info(info) \
631   (frvfdpic_hash_table (info)->relocs_info)
632 #define frvfdpic_got_initial_offset(info) \
633   (frvfdpic_hash_table (info)->got0)
634 #define frvfdpic_plt_initial_offset(info) \
635   (frvfdpic_hash_table (info)->plt0)
636
637 /* Create an FRV ELF linker hash table.  */
638
639 static struct bfd_link_hash_table *
640 frvfdpic_elf_link_hash_table_create (bfd *abfd)
641 {
642   struct frvfdpic_elf_link_hash_table *ret;
643   bfd_size_type amt = sizeof (struct frvfdpic_elf_link_hash_table);
644
645   ret = bfd_zalloc (abfd, amt);
646   if (ret == NULL)
647     return NULL;
648
649   if (! _bfd_elf_link_hash_table_init (&ret->elf, abfd,
650                                        _bfd_elf_link_hash_newfunc))
651     {
652       free (ret);
653       return NULL;
654     }
655
656   return &ret->elf.root;
657 }
658
659 /* Decide whether a reference to a symbol can be resolved locally or
660    not.  If the symbol is protected, we want the local address, but
661    its function descriptor must be assigned by the dynamic linker.  */
662 #define FRVFDPIC_SYM_LOCAL(INFO, H) \
663   (_bfd_elf_symbol_refs_local_p ((H), (INFO), 1) \
664    || ! elf_hash_table (INFO)->dynamic_sections_created \
665    || (/* The condition below is an ugly hack to get .scommon data to
666           be regarded as local.  For some reason the
667           ELF_LINK_HASH_DEF_REGULAR bit is not set on such common
668           symbols, and the SEC_IS_COMMON bit is not set any longer
669           when we need to perform this test.  Hopefully this
670           approximation is good enough.  */ \
671        ((H)->root.type == bfd_link_hash_defined \
672         || (H)->root.type == bfd_link_hash_defweak) \
673        && (H)->root.u.def.section->output_section \
674        && ((H)->root.u.def.section->flags & SEC_LINKER_CREATED)))
675 #define FRVFDPIC_FUNCDESC_LOCAL(INFO, H) \
676   ((H)->dynindx == -1 || ! elf_hash_table (INFO)->dynamic_sections_created)
677
678 /* This structure collects information on what kind of GOT, PLT or
679    function descriptors are required by relocations that reference a
680    certain symbol.  */
681 struct frvfdpic_relocs_info
682 {
683   /* The index of the symbol, as stored in the relocation r_info, if
684      we have a local symbol; -1 otherwise.  */
685   long symndx;
686   union
687   {
688     /* The input bfd in which the symbol is defined, if it's a local
689        symbol.  */
690     bfd *abfd;
691     /* If symndx == -1, the hash table entry corresponding to a global
692        symbol (even if it turns out to bind locally, in which case it
693        should ideally be replaced with section's symndx + addend).  */
694     struct elf_link_hash_entry *h;
695   } d;
696   /* The addend of the relocation that references the symbol.  */
697   bfd_vma addend;
698
699   /* The fields above are used to identify an entry.  The fields below
700      contain information on how an entry is used and, later on, which
701      locations it was assigned.  */
702   /* The following 3 fields record whether the symbol+addend above was
703      ever referenced with a GOT relocation.  The 12 suffix indicates a
704      GOT12 relocation; los is used for GOTLO relocations that are not
705      matched by a GOTHI relocation; hilo is used for GOTLO/GOTHI
706      pairs.  */
707   unsigned got12:1;
708   unsigned gotlos:1;
709   unsigned gothilo:1;
710   /* Whether a FUNCDESC relocation references symbol+addend.  */
711   unsigned fd:1;
712   /* Whether a FUNCDESC_GOT relocation references symbol+addend.  */
713   unsigned fdgot12:1;
714   unsigned fdgotlos:1;
715   unsigned fdgothilo:1;
716   /* Whether a FUNCDESC_GOTOFF relocation references symbol+addend.  */
717   unsigned fdgoff12:1;
718   unsigned fdgofflos:1;
719   unsigned fdgoffhilo:1;
720   /* Whether symbol+addend is referenced with GOTOFF12, GOTOFFLO or
721      GOTOFFHI relocations.  The addend doesn't really matter, since we
722      envision that this will only be used to check whether the symbol
723      is mapped to the same segment as the got.  */
724   unsigned gotoff:1;
725   /* Whether symbol+addend is referenced by a LABEL24 relocation.  */
726   unsigned call:1;
727   /* Whether symbol+addend is referenced by a 32 or FUNCDESC_VALUE
728      relocation.  */
729   unsigned sym:1;
730   /* Whether we need a PLT entry for a symbol.  Should be implied by
731      something like:
732      (call && symndx == -1 && ! FRVFDPIC_SYM_LOCAL (info, d.h))  */
733   unsigned plt:1;
734   /* Whether a function descriptor should be created in this link unit
735      for symbol+addend.  Should be implied by something like:
736      (plt || fdgotoff12 || fdgotofflos || fdgotofflohi
737       || ((fd || fdgot12 || fdgotlos || fdgothilo)
738           && (symndx != -1 || FRVFDPIC_FUNCDESC_LOCAL (info, d.h))))  */
739   unsigned privfd:1;
740   /* Whether a lazy PLT entry is needed for this symbol+addend.
741      Should be implied by something like:
742      (privfd && symndx == -1 && ! FRVFDPIC_SYM_LOCAL (info, d.h)
743       && ! (info->flags & DF_BIND_NOW))  */
744   unsigned lazyplt:1;
745   /* Whether we've already emitted GOT relocations and PLT entries as
746      needed for this symbol.  */
747   unsigned done:1;
748
749   /* The number of R_FRV_32, R_FRV_FUNCDESC and R_FRV_FUNCDESC_VALUE
750      relocations referencing the symbol.  */
751   unsigned relocs32, relocsfd, relocsfdv;
752
753   /* The number of .rofixups entries and dynamic relocations allocated
754      for this symbol, minus any that might have already been used.  */
755   unsigned fixups, dynrelocs;
756
757   /* The offsets of the GOT entries assigned to symbol+addend, to the
758      function descriptor's address, and to a function descriptor,
759      respectively.  Should be zero if unassigned.  The offsets are
760      counted from the value that will be assigned to the PIC register,
761      not from the beginning of the .got section.  */
762   bfd_signed_vma got_entry, fdgot_entry, fd_entry;
763   /* The offsets of the PLT entries assigned to symbol+addend,
764      non-lazy and lazy, respectively.  If unassigned, should be
765      (bfd_vma)-1.  */
766   bfd_vma plt_entry, lzplt_entry;
767 };
768
769 /* Compute a hash with the key fields of an frvfdpic_relocs_info entry.  */
770 static hashval_t
771 frvfdpic_relocs_info_hash (const void *entry_)
772 {
773   const struct frvfdpic_relocs_info *entry = entry_;
774
775   return (entry->symndx == -1
776           ? entry->d.h->root.root.hash
777           : entry->symndx + entry->d.abfd->id * 257) + entry->addend;
778 }
779
780 /* Test whether the key fields of two frvfdpic_relocs_info entries are
781    identical.  */
782 static int
783 frvfdpic_relocs_info_eq (const void *entry1, const void *entry2)
784 {
785   const struct frvfdpic_relocs_info *e1 = entry1;
786   const struct frvfdpic_relocs_info *e2 = entry2;
787
788   return e1->symndx == e2->symndx && e1->addend == e2->addend
789     && (e1->symndx == -1 ? e1->d.h == e2->d.h : e1->d.abfd == e2->d.abfd);
790 }
791
792 /* Find or create an entry in a hash table HT that matches the key
793    fields of the given ENTRY.  If it's not found, memory for a new
794    entry is allocated in ABFD's obstack.  */
795 static struct frvfdpic_relocs_info *
796 frvfdpic_relocs_info_find (struct htab *ht,
797                            bfd *abfd,
798                            const struct frvfdpic_relocs_info *entry,
799                            enum insert_option insert)
800 {
801   struct frvfdpic_relocs_info **loc =
802     (struct frvfdpic_relocs_info **) htab_find_slot (ht, entry, insert);
803
804   if (! loc)
805     return NULL;
806
807   if (*loc)
808     return *loc;
809
810   *loc = bfd_zalloc (abfd, sizeof (**loc));
811
812   if (! *loc)
813     return *loc;
814
815   (*loc)->symndx = entry->symndx;
816   (*loc)->d = entry->d;
817   (*loc)->addend = entry->addend;
818   (*loc)->plt_entry = (bfd_vma)-1;
819   (*loc)->lzplt_entry = (bfd_vma)-1;
820
821   return *loc;
822 }
823
824 /* Obtain the address of the entry in HT associated with H's symbol +
825    addend, creating a new entry if none existed.  ABFD is only used
826    for memory allocation purposes.  */
827 inline static struct frvfdpic_relocs_info *
828 frvfdpic_relocs_info_for_global (struct htab *ht,
829                                  bfd *abfd,
830                                  struct elf_link_hash_entry *h,
831                                  bfd_vma addend,
832                                  enum insert_option insert)
833 {
834   struct frvfdpic_relocs_info entry;
835
836   entry.symndx = -1;
837   entry.d.h = h;
838   entry.addend = addend;
839
840   return frvfdpic_relocs_info_find (ht, abfd, &entry, insert);
841 }
842
843 /* Obtain the address of the entry in HT associated with the SYMNDXth
844    local symbol of the input bfd ABFD, plus the addend, creating a new
845    entry if none existed.  */  
846 inline static struct frvfdpic_relocs_info *
847 frvfdpic_relocs_info_for_local (struct htab *ht,
848                                 bfd *abfd,
849                                 long symndx,
850                                 bfd_vma addend,
851                                 enum insert_option insert)
852 {
853   struct frvfdpic_relocs_info entry;
854
855   entry.symndx = symndx;
856   entry.d.abfd = abfd;
857   entry.addend = addend;
858
859   return frvfdpic_relocs_info_find (ht, abfd, &entry, insert);
860 }
861
862 /* Merge fields set by check_relocs() of two entries that end up being
863    mapped to the same (presumably global) symbol.  */
864
865 inline static void
866 frvfdpic_pic_merge_early_relocs_info (struct frvfdpic_relocs_info *e2,
867                                       struct frvfdpic_relocs_info const *e1)
868 {
869   e2->got12 |= e1->got12;
870   e2->gotlos |= e1->gotlos;
871   e2->gothilo |= e1->gothilo;
872   e2->fd |= e1->fd;
873   e2->fdgot12 |= e1->fdgot12;
874   e2->fdgotlos |= e1->fdgotlos;
875   e2->fdgothilo |= e1->fdgothilo;
876   e2->fdgoff12 |= e1->fdgoff12;
877   e2->fdgofflos |= e1->fdgofflos;
878   e2->fdgoffhilo |= e1->fdgoffhilo;
879   e2->gotoff |= e1->gotoff;
880   e2->call |= e1->call;
881   e2->sym |= e1->sym;
882
883 #if 0
884   /* These are set in _frvfdpic_count_got_plt_entries() or later, and this
885      function is only called in _frvfdpic_resolve_final_relocs_info(), that
886      runs just before it, so we don't have to worry about the fields
887      below.  */
888
889   e2->plt |= e1->plt;
890   e2->privfd |= e1->privfd;
891   e2->lazyplt |= e1->lazyplt;
892   e2->done |= e1->done;
893
894   e2->relocs32 += e1->relocs32;
895   e2->relocsfd += e1->relocsfd;
896   e2->relocsfdv += e1->relocsfdv;
897   e2->fixups += e1->fixups;
898   e2->dynrelocs += e1->dynrelocs;
899
900   if (abs (e1->got_entry) < abs (e2->got_entry))
901     e2->got_entry = e1->got_entry;
902   if (abs (e1->fdgot_entry) < abs (e2->fdgot_entry))
903     e2->fdgot_entry = e1->fdgot_entry;
904   if (abs (e1->fd_entry) < abs (e2->fd_entry))
905     e2->fd_entry = e1->fd_entry;
906
907   if (e1->plt_entry < e2->plt_entry)
908     e2->plt_entry = e1->plt_entry;
909   if (e1->lzplt_entry < e2->lzplt_entry)
910     e2->lzplt_entry = e1->lzplt_entry;
911 #endif
912 }
913
914 /* Every block of 65535 lazy PLT entries shares a single call to the
915    resolver, inserted in the 32768th lazy PLT entry (i.e., entry #
916    32767, counting from 0).  All other lazy PLT entries branch to it
917    in a single instruction.  */
918
919 #define FRVFDPIC_LZPLT_BLOCK_SIZE ((bfd_vma) 8 * 65535 + 4)
920 #define FRVFDPIC_LZPLT_RESOLV_LOC (8 * 32767)
921
922 /* Add a dynamic relocation to the SRELOC section.  */
923
924 inline static bfd_vma
925 _frvfdpic_add_dyn_reloc (bfd *output_bfd, asection *sreloc, bfd_vma offset,
926                          int reloc_type, long dynindx, bfd_vma addend,
927                          struct frvfdpic_relocs_info *entry)
928 {
929   Elf_Internal_Rela outrel;
930   bfd_vma reloc_offset;
931
932   outrel.r_offset = offset;
933   outrel.r_info = ELF32_R_INFO (dynindx, reloc_type);
934   outrel.r_addend = addend;
935
936   reloc_offset = sreloc->reloc_count * sizeof (Elf32_External_Rel);
937   BFD_ASSERT (reloc_offset < sreloc->size);
938   bfd_elf32_swap_reloc_out (output_bfd, &outrel,
939                             sreloc->contents + reloc_offset);
940   sreloc->reloc_count++;
941
942   /* If the entry's index is zero, this relocation was probably to a
943      linkonce section that got discarded.  We reserved a dynamic
944      relocation, but it was for another entry than the one we got at
945      the time of emitting the relocation.  Unfortunately there's no
946      simple way for us to catch this situation, since the relocation
947      is cleared right before calling relocate_section, at which point
948      we no longer know what the relocation used to point to.  */
949   if (entry->symndx)
950     {
951       BFD_ASSERT (entry->dynrelocs > 0);
952       entry->dynrelocs--;
953     }
954
955   return reloc_offset;
956 }
957
958 /* Add a fixup to the ROFIXUP section.  */
959
960 static bfd_vma
961 _frvfdpic_add_rofixup (bfd *output_bfd, asection *rofixup, bfd_vma offset,
962                        struct frvfdpic_relocs_info *entry)
963 {
964   bfd_vma fixup_offset;
965
966   if (rofixup->flags & SEC_EXCLUDE)
967     return -1;
968
969   fixup_offset = rofixup->reloc_count * 4;
970   if (rofixup->contents)
971     {
972       BFD_ASSERT (fixup_offset < rofixup->size);
973       bfd_put_32 (output_bfd, offset, rofixup->contents + fixup_offset);
974     }
975   rofixup->reloc_count++;
976
977   if (entry && entry->symndx)
978     {
979       /* See discussion about symndx == 0 in _frvfdpic_add_dyn_reloc
980          above.  */
981       BFD_ASSERT (entry->fixups > 0);
982       entry->fixups--;
983     }
984
985   return fixup_offset;
986 }
987
988 /* Find the segment number in which OSEC, and output section, is
989    located.  */
990
991 static unsigned
992 _frvfdpic_osec_to_segment (bfd *output_bfd, asection *osec)
993 {
994   struct elf_segment_map *m;
995   Elf_Internal_Phdr *p;
996
997   /* Find the segment that contains the output_section.  */
998   for (m = elf_tdata (output_bfd)->segment_map,
999          p = elf_tdata (output_bfd)->phdr;
1000        m != NULL;
1001        m = m->next, p++)
1002     {
1003       int i;
1004
1005       for (i = m->count - 1; i >= 0; i--)
1006         if (m->sections[i] == osec)
1007           break;
1008
1009       if (i >= 0)
1010         break;
1011     }
1012
1013   return p - elf_tdata (output_bfd)->phdr;
1014 }
1015
1016 inline static bfd_boolean
1017 _frvfdpic_osec_readonly_p (bfd *output_bfd, asection *osec)
1018 {
1019   unsigned seg = _frvfdpic_osec_to_segment (output_bfd, osec);
1020
1021   return ! (elf_tdata (output_bfd)->phdr[seg].p_flags & PF_W);
1022 }
1023
1024 /* Generate relocations for GOT entries, function descriptors, and
1025    code for PLT and lazy PLT entries.  */
1026
1027 inline static bfd_boolean
1028 _frvfdpic_emit_got_relocs_plt_entries (struct frvfdpic_relocs_info *entry,
1029                                        bfd *output_bfd,
1030                                        struct bfd_link_info *info,
1031                                        asection *sec,
1032                                        Elf_Internal_Sym *sym,
1033                                        bfd_vma addend)
1034                                   
1035 {
1036   bfd_vma fd_lazy_rel_offset = (bfd_vma)-1;
1037   int dynindx = -1;
1038
1039   if (entry->done)
1040     return TRUE;
1041   entry->done = 1;
1042
1043   if (entry->got_entry || entry->fdgot_entry || entry->fd_entry)
1044     {
1045       /* If the symbol is dynamic, consider it for dynamic
1046          relocations, otherwise decay to section + offset.  */
1047       if (entry->symndx == -1 && entry->d.h->dynindx != -1)
1048         dynindx = entry->d.h->dynindx;
1049       else
1050         {
1051           if (sec->output_section
1052               && ! bfd_is_abs_section (sec->output_section)
1053               && ! bfd_is_und_section (sec->output_section))
1054             dynindx = elf_section_data (sec->output_section)->dynindx;
1055           else
1056             dynindx = 0;
1057         }
1058     }
1059
1060   /* Generate relocation for GOT entry pointing to the symbol.  */
1061   if (entry->got_entry)
1062     {
1063       int idx = dynindx;
1064       bfd_vma ad = addend;
1065
1066       /* If the symbol is dynamic but binds locally, use
1067          section+offset.  */
1068       if (sec && (entry->symndx != -1
1069                   || FRVFDPIC_SYM_LOCAL (info, entry->d.h)))
1070         {
1071           if (entry->symndx == -1)
1072             ad += entry->d.h->root.u.def.value;
1073           else
1074             ad += sym->st_value;
1075           ad += sec->output_offset;
1076           if (sec->output_section && elf_section_data (sec->output_section))
1077             idx = elf_section_data (sec->output_section)->dynindx;
1078           else
1079             idx = 0;
1080         }
1081
1082       /* If we're linking an executable at a fixed address, we can
1083          omit the dynamic relocation as long as the symbol is local to
1084          this module.  */
1085       if (info->executable && !info->pie
1086           && (entry->symndx != -1
1087               || FRVFDPIC_SYM_LOCAL (info, entry->d.h)))
1088         {
1089           if (sec)
1090             ad += sec->output_section->vma;
1091           if (entry->symndx != -1
1092               || entry->d.h->root.type != bfd_link_hash_undefweak)
1093             _frvfdpic_add_rofixup (output_bfd,
1094                                    frvfdpic_gotfixup_section (info),
1095                                    frvfdpic_got_section (info)->output_section
1096                                    ->vma
1097                                    + frvfdpic_got_section (info)->output_offset
1098                                    + frvfdpic_got_initial_offset (info)
1099                                    + entry->got_entry, entry);
1100         }
1101       else
1102         _frvfdpic_add_dyn_reloc (output_bfd, frvfdpic_gotrel_section (info),
1103                                  _bfd_elf_section_offset
1104                                  (output_bfd, info,
1105                                   frvfdpic_got_section (info),
1106                                   frvfdpic_got_initial_offset (info)
1107                                   + entry->got_entry)
1108                                  + frvfdpic_got_section (info)
1109                                  ->output_section->vma
1110                                  + frvfdpic_got_section (info)->output_offset,
1111                                  R_FRV_32, idx, ad, entry);
1112         
1113       bfd_put_32 (output_bfd, ad,
1114                   frvfdpic_got_section (info)->contents
1115                   + frvfdpic_got_initial_offset (info)
1116                   + entry->got_entry);
1117     }
1118
1119   /* Generate relocation for GOT entry pointing to a canonical
1120      function descriptor.  */
1121   if (entry->fdgot_entry)
1122     {
1123       int reloc, idx;
1124       bfd_vma ad = 0;
1125       
1126       if (! (entry->symndx == -1
1127              && entry->d.h->root.type == bfd_link_hash_undefweak
1128              && FRVFDPIC_SYM_LOCAL (info, entry->d.h)))
1129         {
1130           /* If the symbol is dynamic and there may be dynamic symbol
1131              resolution because we are, or are linked with, a shared
1132              library, emit a FUNCDESC relocation such that the dynamic
1133              linker will allocate the function descriptor.  If the
1134              symbol needs a non-local function descriptor but binds
1135              locally (e.g., its visibility is protected, emit a
1136              dynamic relocation decayed to section+offset.  */
1137           if (entry->symndx == -1
1138               && ! FRVFDPIC_FUNCDESC_LOCAL (info, entry->d.h)
1139               && FRVFDPIC_SYM_LOCAL (info, entry->d.h)
1140               && !(info->executable && !info->pie))
1141             {
1142               reloc = R_FRV_FUNCDESC;
1143               idx = elf_section_data (entry->d.h->root.u.def.section
1144                                       ->output_section)->dynindx;
1145               ad = entry->d.h->root.u.def.section->output_offset
1146                 + entry->d.h->root.u.def.value;
1147             }
1148           else if (entry->symndx == -1
1149                    && ! FRVFDPIC_FUNCDESC_LOCAL (info, entry->d.h))
1150             {
1151               reloc = R_FRV_FUNCDESC;
1152               idx = dynindx;
1153               ad = addend;
1154               if (ad)
1155                 return FALSE;
1156             }
1157           else
1158             {
1159               /* Otherwise, we know we have a private function descriptor,
1160                  so reference it directly.  */
1161               if (elf_hash_table (info)->dynamic_sections_created)
1162                 BFD_ASSERT (entry->privfd);
1163               reloc = R_FRV_32;
1164               idx = elf_section_data (frvfdpic_got_section (info)
1165                                       ->output_section)->dynindx;
1166               ad = frvfdpic_got_section (info)->output_offset
1167                 + frvfdpic_got_initial_offset (info) + entry->fd_entry;
1168             }
1169
1170           /* If there is room for dynamic symbol resolution, emit the
1171              dynamic relocation.  However, if we're linking an
1172              executable at a fixed location, we won't have emitted a
1173              dynamic symbol entry for the got section, so idx will be
1174              zero, which means we can and should compute the address
1175              of the private descriptor ourselves.  */
1176           if (info->executable && !info->pie
1177               && (entry->symndx != -1
1178                   || FRVFDPIC_FUNCDESC_LOCAL (info, entry->d.h)))
1179             {
1180               ad += frvfdpic_got_section (info)->output_section->vma;
1181               _frvfdpic_add_rofixup (output_bfd,
1182                                      frvfdpic_gotfixup_section (info),
1183                                      frvfdpic_got_section (info)
1184                                      ->output_section->vma
1185                                      + frvfdpic_got_section (info)
1186                                      ->output_offset
1187                                      + frvfdpic_got_initial_offset (info)
1188                                      + entry->fdgot_entry, entry);
1189             }
1190           else
1191             _frvfdpic_add_dyn_reloc (output_bfd,
1192                                      frvfdpic_gotrel_section (info),
1193                                      _bfd_elf_section_offset
1194                                      (output_bfd, info,
1195                                       frvfdpic_got_section (info),
1196                                       frvfdpic_got_initial_offset (info)
1197                                       + entry->fdgot_entry)
1198                                      + frvfdpic_got_section (info)
1199                                      ->output_section->vma
1200                                      + frvfdpic_got_section (info)
1201                                      ->output_offset,
1202                                      reloc, idx, ad, entry);
1203         }
1204
1205       bfd_put_32 (output_bfd, ad,
1206                   frvfdpic_got_section (info)->contents
1207                   + frvfdpic_got_initial_offset (info)
1208                   + entry->fdgot_entry);
1209     }
1210
1211   /* Generate relocation to fill in a private function descriptor in
1212      the GOT.  */
1213   if (entry->fd_entry)
1214     {
1215       int idx = dynindx;
1216       bfd_vma ad = addend;
1217       bfd_vma ofst;
1218       long lowword, highword;
1219
1220       /* If the symbol is dynamic but binds locally, use
1221          section+offset.  */
1222       if (sec && (entry->symndx != -1
1223                   || FRVFDPIC_SYM_LOCAL (info, entry->d.h)))
1224         {
1225           if (entry->symndx == -1)
1226             ad += entry->d.h->root.u.def.value;
1227           else
1228             ad += sym->st_value;
1229           ad += sec->output_offset;
1230           if (sec->output_section && elf_section_data (sec->output_section))
1231             idx = elf_section_data (sec->output_section)->dynindx;
1232           else
1233             idx = 0;
1234         }
1235
1236       /* If we're linking an executable at a fixed address, we can
1237          omit the dynamic relocation as long as the symbol is local to
1238          this module.  */
1239       if (info->executable && !info->pie
1240           && (entry->symndx != -1 || FRVFDPIC_SYM_LOCAL (info, entry->d.h)))
1241         {
1242           if (sec)
1243             ad += sec->output_section->vma;
1244           ofst = 0;
1245           if (entry->symndx != -1
1246               || entry->d.h->root.type != bfd_link_hash_undefweak)
1247             {
1248               _frvfdpic_add_rofixup (output_bfd,
1249                                      frvfdpic_gotfixup_section (info),
1250                                      frvfdpic_got_section (info)
1251                                      ->output_section->vma
1252                                      + frvfdpic_got_section (info)
1253                                      ->output_offset
1254                                      + frvfdpic_got_initial_offset (info)
1255                                      + entry->fd_entry, entry);
1256               _frvfdpic_add_rofixup (output_bfd,
1257                                      frvfdpic_gotfixup_section (info),
1258                                      frvfdpic_got_section (info)
1259                                      ->output_section->vma
1260                                      + frvfdpic_got_section (info)
1261                                      ->output_offset
1262                                      + frvfdpic_got_initial_offset (info)
1263                                      + entry->fd_entry + 4, entry);
1264             }
1265         }
1266       else
1267         {
1268           ofst =
1269             _frvfdpic_add_dyn_reloc (output_bfd,
1270                                      entry->lazyplt
1271                                      ? frvfdpic_pltrel_section (info)
1272                                      : frvfdpic_gotrel_section (info),
1273                                      _bfd_elf_section_offset
1274                                      (output_bfd, info,
1275                                       frvfdpic_got_section (info),
1276                                       frvfdpic_got_initial_offset (info)
1277                                       + entry->fd_entry)
1278                                      + frvfdpic_got_section (info)
1279                                      ->output_section->vma
1280                                      + frvfdpic_got_section (info)
1281                                      ->output_offset,
1282                                      R_FRV_FUNCDESC_VALUE, idx, ad, entry);
1283         }
1284
1285       /* If we've omitted the dynamic relocation, just emit the fixed
1286          addresses of the symbol and of the local GOT base offset.  */
1287       if (info->executable && !info->pie && sec && sec->output_section)
1288         {
1289           lowword = ad;
1290           highword = frvfdpic_got_section (info)->output_section->vma
1291             + frvfdpic_got_section (info)->output_offset
1292             + frvfdpic_got_initial_offset (info);
1293         }
1294       else if (entry->lazyplt)
1295         {
1296           if (ad)
1297             return FALSE;
1298           
1299           fd_lazy_rel_offset = ofst;
1300
1301           /* A function descriptor used for lazy or local resolving is
1302              initialized such that its high word contains the output
1303              section index in which the PLT entries are located, and
1304              the low word contains the address of the lazy PLT entry
1305              entry point, that must be within the memory region
1306              assigned to that section.  */
1307           lowword = entry->lzplt_entry + 4
1308             + frvfdpic_plt_section (info)->output_offset
1309             + frvfdpic_plt_section (info)->output_section->vma;
1310           highword = _frvfdpic_osec_to_segment 
1311             (output_bfd, frvfdpic_plt_section (info)->output_section);
1312         }
1313       else
1314         {
1315           /* A function descriptor for a local function gets the index
1316              of the section.  For a non-local function, it's
1317              disregarded.  */
1318           lowword = ad;
1319           if (entry->symndx == -1 && entry->d.h->dynindx != -1
1320               && entry->d.h->dynindx == idx)
1321             highword = 0;
1322           else
1323             highword = _frvfdpic_osec_to_segment
1324               (output_bfd, sec->output_section);
1325         }
1326
1327       bfd_put_32 (output_bfd, lowword,
1328                   frvfdpic_got_section (info)->contents
1329                   + frvfdpic_got_initial_offset (info)
1330                   + entry->fd_entry);
1331       bfd_put_32 (output_bfd, highword,
1332                   frvfdpic_got_section (info)->contents
1333                   + frvfdpic_got_initial_offset (info)
1334                   + entry->fd_entry + 4);
1335     }
1336
1337   /* Generate code for the PLT entry.  */
1338   if (entry->plt_entry != (bfd_vma) -1)
1339     {
1340       bfd_byte *plt_code = frvfdpic_plt_section (info)->contents
1341         + entry->plt_entry;
1342
1343       BFD_ASSERT (entry->fd_entry);
1344
1345       /* Figure out what kind of PLT entry we need, depending on the
1346          location of the function descriptor within the GOT.  */
1347       if (entry->fd_entry >= -(1 << (12 - 1))
1348           && entry->fd_entry < (1 << (12 - 1)))
1349         {
1350           /* lddi @(gr15, fd_entry), gr14 */
1351           bfd_put_32 (output_bfd,
1352                       0x9cccf000 | (entry->fd_entry & ((1 << 12) - 1)),
1353                       plt_code);
1354           plt_code += 4;
1355         }
1356       else
1357         {
1358           if (entry->fd_entry >= -(1 << (16 - 1))
1359               && entry->fd_entry < (1 << (16 - 1)))
1360             {
1361               /* setlos lo(fd_entry), gr14 */
1362               bfd_put_32 (output_bfd,
1363                           0x9cfc0000
1364                           | (entry->fd_entry & (((bfd_vma)1 << 16) - 1)),
1365                           plt_code);
1366               plt_code += 4;
1367             }
1368           else
1369             {
1370               /* sethi.p hi(fd_entry), gr14
1371                  setlo lo(fd_entry), gr14 */
1372               bfd_put_32 (output_bfd,
1373                           0x1cf80000
1374                           | ((entry->fd_entry >> 16)
1375                              & (((bfd_vma)1 << 16) - 1)),
1376                           plt_code);
1377               bfd_put_32 (output_bfd,
1378                           0x9cf40000
1379                           | (entry->fd_entry & (((bfd_vma)1 << 16) - 1)),
1380                           plt_code);
1381               plt_code += 8;
1382             }
1383           /* ldd @(gr14,gr15),gr14 */
1384           bfd_put_32 (output_bfd, 0x9c08e14f, plt_code);
1385           plt_code += 4;
1386         }
1387       /* jmpl @(gr14,gr0) */
1388       bfd_put_32 (output_bfd, 0x8030e000, plt_code);
1389     }
1390
1391   /* Generate code for the lazy PLT entry.  */
1392   if (entry->lzplt_entry != (bfd_vma) -1)
1393     {
1394       bfd_byte *lzplt_code = frvfdpic_plt_section (info)->contents
1395         + entry->lzplt_entry;
1396       bfd_vma resolverStub_addr;
1397
1398       bfd_put_32 (output_bfd, fd_lazy_rel_offset, lzplt_code);
1399       lzplt_code += 4;
1400
1401       resolverStub_addr = entry->lzplt_entry / FRVFDPIC_LZPLT_BLOCK_SIZE
1402         * FRVFDPIC_LZPLT_BLOCK_SIZE + FRVFDPIC_LZPLT_RESOLV_LOC;
1403       if (resolverStub_addr >= frvfdpic_plt_initial_offset (info))
1404         resolverStub_addr = frvfdpic_plt_initial_offset (info) - 12;
1405
1406       if (entry->lzplt_entry == resolverStub_addr)
1407         {
1408           /* This is a lazy PLT entry that includes a resolver call.  */
1409           /* ldd @(gr15,gr0), gr4
1410              jmpl @(gr4,gr0)  */
1411           bfd_put_32 (output_bfd, 0x8808f140, lzplt_code);
1412           bfd_put_32 (output_bfd, 0x80304000, lzplt_code + 4);
1413         }
1414       else
1415         {
1416           /* bra  resolverStub */
1417           bfd_put_32 (output_bfd,
1418                       0xc01a0000
1419                       | (((resolverStub_addr - entry->lzplt_entry)
1420                           / 4) & (((bfd_vma)1 << 16) - 1)),
1421                       lzplt_code);
1422         }
1423     }
1424
1425   return TRUE;
1426 }
1427
1428 /* Handle an FRV small data reloc.  */
1429
1430 static bfd_reloc_status_type
1431 elf32_frv_relocate_gprel12 (info, input_bfd, input_section, relocation,
1432                             contents, value)
1433      struct bfd_link_info *info;
1434      bfd *input_bfd;
1435      asection *input_section;
1436      Elf_Internal_Rela *relocation;
1437      bfd_byte *contents;
1438      bfd_vma value;
1439 {
1440   bfd_vma insn;
1441   bfd_vma gp;
1442   struct bfd_link_hash_entry *h;
1443
1444   h = bfd_link_hash_lookup (info->hash, "_gp", FALSE, FALSE, TRUE);
1445
1446   gp = (h->u.def.value
1447         + h->u.def.section->output_section->vma
1448         + h->u.def.section->output_offset);
1449
1450   value -= input_section->output_section->vma;
1451   value -= (gp - input_section->output_section->vma);
1452
1453   insn = bfd_get_32 (input_bfd, contents + relocation->r_offset);
1454
1455   value += relocation->r_addend;
1456
1457   if ((long) value > 0x7ff || (long) value < -0x800)
1458     return bfd_reloc_overflow;
1459
1460   bfd_put_32 (input_bfd,
1461               (insn & 0xfffff000) | (value & 0xfff),
1462               contents + relocation->r_offset);
1463
1464   return bfd_reloc_ok;
1465 }
1466
1467 /* Handle an FRV small data reloc. for the u12 field.  */
1468
1469 static bfd_reloc_status_type
1470 elf32_frv_relocate_gprelu12 (info, input_bfd, input_section, relocation,
1471                              contents, value)
1472      struct bfd_link_info *info;
1473      bfd *input_bfd;
1474      asection *input_section;
1475      Elf_Internal_Rela *relocation;
1476      bfd_byte *contents;
1477      bfd_vma value;
1478 {
1479   bfd_vma insn;
1480   bfd_vma gp;
1481   struct bfd_link_hash_entry *h;
1482   bfd_vma mask;
1483
1484   h = bfd_link_hash_lookup (info->hash, "_gp", FALSE, FALSE, TRUE);
1485
1486   gp = (h->u.def.value
1487         + h->u.def.section->output_section->vma
1488         + h->u.def.section->output_offset);
1489
1490   value -= input_section->output_section->vma;
1491   value -= (gp - input_section->output_section->vma);
1492
1493   insn = bfd_get_32 (input_bfd, contents + relocation->r_offset);
1494
1495   value += relocation->r_addend;
1496
1497   if ((long) value > 0x7ff || (long) value < -0x800)
1498     return bfd_reloc_overflow;
1499
1500   /* The high 6 bits go into bits 17-12. The low 6 bits go into bits 5-0.  */
1501   mask = 0x3f03f;
1502   insn = (insn & ~mask) | ((value & 0xfc0) << 12) | (value & 0x3f);
1503
1504   bfd_put_32 (input_bfd, insn, contents + relocation->r_offset);
1505
1506   return bfd_reloc_ok;
1507 }
1508
1509 /* Handle an FRV ELF HI16 reloc.  */
1510
1511 static bfd_reloc_status_type
1512 elf32_frv_relocate_hi16 (input_bfd, relhi, contents, value)
1513      bfd *input_bfd;
1514      Elf_Internal_Rela *relhi;
1515      bfd_byte *contents;
1516      bfd_vma value;
1517 {
1518   bfd_vma insn;
1519
1520   insn = bfd_get_32 (input_bfd, contents + relhi->r_offset);
1521
1522   value += relhi->r_addend;
1523   value = ((value >> 16) & 0xffff);
1524
1525   insn = (insn & 0xffff0000) | value;
1526
1527   if ((long) value > 0xffff || (long) value < -0x10000)
1528     return bfd_reloc_overflow;
1529
1530   bfd_put_32 (input_bfd, insn, contents + relhi->r_offset);
1531   return bfd_reloc_ok;
1532
1533 }
1534 static bfd_reloc_status_type
1535 elf32_frv_relocate_lo16 (input_bfd, rello, contents, value)
1536      bfd *input_bfd;
1537      Elf_Internal_Rela *rello;
1538      bfd_byte *contents;
1539      bfd_vma value;
1540 {
1541   bfd_vma insn;
1542
1543   insn = bfd_get_32 (input_bfd, contents + rello->r_offset);
1544
1545   value += rello->r_addend;
1546   value = value & 0xffff;
1547
1548   insn = (insn & 0xffff0000) | value;
1549
1550   if ((long) value > 0xffff || (long) value < -0x10000)
1551     return bfd_reloc_overflow;
1552
1553   bfd_put_32 (input_bfd, insn, contents + rello->r_offset);
1554   return bfd_reloc_ok;
1555 }
1556
1557 /* Perform the relocation for the CALL label24 instruction.  */
1558
1559 static bfd_reloc_status_type
1560 elf32_frv_relocate_label24 (input_bfd, input_section, rello, contents, value)
1561      bfd *input_bfd;
1562      asection *input_section;
1563      Elf_Internal_Rela *rello;
1564      bfd_byte *contents;
1565      bfd_vma value;
1566 {
1567   bfd_vma insn;
1568   bfd_vma label6;
1569   bfd_vma label18;
1570
1571   /* The format for the call instruction is:
1572
1573     0 000000 0001111 000000000000000000
1574       label6 opcode  label18
1575
1576     The branch calculation is: pc + (4*label24)
1577     where label24 is the concatenation of label6 and label18.  */
1578
1579   /* Grab the instruction.  */
1580   insn = bfd_get_32 (input_bfd, contents + rello->r_offset);
1581
1582   value -= input_section->output_section->vma + input_section->output_offset;
1583   value -= rello->r_offset;
1584   value += rello->r_addend;
1585
1586   value = value >> 2;
1587
1588   label6  = value & 0xfc0000;
1589   label6  = label6 << 7;
1590
1591   label18 = value & 0x3ffff;
1592
1593   insn = insn & 0x803c0000;
1594   insn = insn | label6;
1595   insn = insn | label18;
1596
1597   bfd_put_32 (input_bfd, insn, contents + rello->r_offset);
1598
1599   return bfd_reloc_ok;
1600 }
1601
1602 static bfd_reloc_status_type
1603 elf32_frv_relocate_gprelhi (info, input_bfd, input_section, relocation,
1604                             contents, value)
1605      struct bfd_link_info *info;
1606      bfd *input_bfd;
1607      asection *input_section;
1608      Elf_Internal_Rela *relocation;
1609      bfd_byte *contents;
1610      bfd_vma value;
1611 {
1612   bfd_vma insn;
1613   bfd_vma gp;
1614   struct bfd_link_hash_entry *h;
1615
1616   h = bfd_link_hash_lookup (info->hash, "_gp", FALSE, FALSE, TRUE);
1617
1618   gp = (h->u.def.value
1619         + h->u.def.section->output_section->vma
1620         + h->u.def.section->output_offset);
1621
1622   value -= input_section->output_section->vma;
1623   value -= (gp - input_section->output_section->vma);
1624   value += relocation->r_addend;
1625   value = ((value >> 16) & 0xffff);
1626
1627   if ((long) value > 0xffff || (long) value < -0x10000)
1628     return bfd_reloc_overflow;
1629
1630   insn = bfd_get_32 (input_bfd, contents + relocation->r_offset);
1631   insn = (insn & 0xffff0000) | value;
1632
1633   bfd_put_32 (input_bfd, insn, contents + relocation->r_offset);
1634   return bfd_reloc_ok;
1635 }
1636
1637 static bfd_reloc_status_type
1638 elf32_frv_relocate_gprello (info, input_bfd, input_section, relocation,
1639                             contents, value)
1640      struct bfd_link_info *info;
1641      bfd *input_bfd;
1642      asection *input_section;
1643      Elf_Internal_Rela *relocation;
1644      bfd_byte *contents;
1645      bfd_vma value;
1646 {
1647   bfd_vma insn;
1648   bfd_vma gp;
1649   struct bfd_link_hash_entry *h;
1650
1651   h = bfd_link_hash_lookup (info->hash, "_gp", FALSE, FALSE, TRUE);
1652
1653   gp = (h->u.def.value
1654         + h->u.def.section->output_section->vma
1655         + h->u.def.section->output_offset);
1656
1657   value -= input_section->output_section->vma;
1658   value -= (gp - input_section->output_section->vma);
1659   value += relocation->r_addend;
1660   value = value & 0xffff;
1661
1662   if ((long) value > 0xffff || (long) value < -0x10000)
1663     return bfd_reloc_overflow;
1664
1665   insn = bfd_get_32 (input_bfd, contents + relocation->r_offset);
1666   insn = (insn & 0xffff0000) | value;
1667
1668   bfd_put_32 (input_bfd, insn, contents + relocation->r_offset);
1669
1670  return bfd_reloc_ok;
1671 }
1672
1673 static reloc_howto_type *
1674 frv_reloc_type_lookup (abfd, code)
1675      bfd *abfd ATTRIBUTE_UNUSED;
1676      bfd_reloc_code_real_type code;
1677 {
1678   switch (code)
1679     {
1680     default:
1681       break;
1682
1683     case BFD_RELOC_NONE:
1684       return &elf32_frv_howto_table[ (int) R_FRV_NONE];
1685
1686     case BFD_RELOC_32:
1687       if (elf_elfheader (abfd)->e_type == ET_EXEC
1688           || elf_elfheader (abfd)->e_type == ET_DYN)
1689         return &elf32_frv_rel_32_howto;
1690       /* Fall through.  */
1691     case BFD_RELOC_CTOR:
1692       return &elf32_frv_howto_table[ (int) R_FRV_32];
1693
1694     case BFD_RELOC_FRV_LABEL16:
1695       return &elf32_frv_howto_table[ (int) R_FRV_LABEL16];
1696
1697     case BFD_RELOC_FRV_LABEL24:
1698       return &elf32_frv_howto_table[ (int) R_FRV_LABEL24];
1699
1700     case BFD_RELOC_FRV_LO16:
1701       return &elf32_frv_howto_table[ (int) R_FRV_LO16];
1702
1703     case BFD_RELOC_FRV_HI16:
1704       return &elf32_frv_howto_table[ (int) R_FRV_HI16];
1705
1706     case BFD_RELOC_FRV_GPREL12:
1707       return &elf32_frv_howto_table[ (int) R_FRV_GPREL12];
1708
1709     case BFD_RELOC_FRV_GPRELU12:
1710       return &elf32_frv_howto_table[ (int) R_FRV_GPRELU12];
1711
1712     case BFD_RELOC_FRV_GPREL32:
1713       return &elf32_frv_howto_table[ (int) R_FRV_GPREL32];
1714
1715     case BFD_RELOC_FRV_GPRELHI:
1716       return &elf32_frv_howto_table[ (int) R_FRV_GPRELHI];
1717
1718     case BFD_RELOC_FRV_GPRELLO:
1719       return &elf32_frv_howto_table[ (int) R_FRV_GPRELLO];
1720
1721     case BFD_RELOC_FRV_GOT12:
1722       return &elf32_frv_howto_table[ (int) R_FRV_GOT12];
1723
1724     case BFD_RELOC_FRV_GOTHI:
1725       return &elf32_frv_howto_table[ (int) R_FRV_GOTHI];
1726
1727     case BFD_RELOC_FRV_GOTLO:
1728       return &elf32_frv_howto_table[ (int) R_FRV_GOTLO];
1729
1730     case BFD_RELOC_FRV_FUNCDESC:
1731       if (elf_elfheader (abfd)->e_type == ET_EXEC
1732           || elf_elfheader (abfd)->e_type == ET_DYN)
1733         return &elf32_frv_rel_funcdesc_howto;
1734       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC];
1735
1736     case BFD_RELOC_FRV_FUNCDESC_GOT12:
1737       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOT12];
1738
1739     case BFD_RELOC_FRV_FUNCDESC_GOTHI:
1740       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOTHI];
1741
1742     case BFD_RELOC_FRV_FUNCDESC_GOTLO:
1743       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOTLO];
1744
1745     case BFD_RELOC_FRV_FUNCDESC_VALUE:
1746       if (elf_elfheader (abfd)->e_type == ET_EXEC
1747           || elf_elfheader (abfd)->e_type == ET_DYN)
1748         return &elf32_frv_rel_funcdesc_value_howto;
1749       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_VALUE];
1750
1751     case BFD_RELOC_FRV_FUNCDESC_GOTOFF12:
1752       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOTOFF12];
1753
1754     case BFD_RELOC_FRV_FUNCDESC_GOTOFFHI:
1755       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOTOFFHI];
1756
1757     case BFD_RELOC_FRV_FUNCDESC_GOTOFFLO:
1758       return &elf32_frv_howto_table[ (int) R_FRV_FUNCDESC_GOTOFFLO];
1759
1760     case BFD_RELOC_FRV_GOTOFF12:
1761       return &elf32_frv_howto_table[ (int) R_FRV_GOTOFF12];
1762
1763     case BFD_RELOC_FRV_GOTOFFHI:
1764       return &elf32_frv_howto_table[ (int) R_FRV_GOTOFFHI];
1765
1766     case BFD_RELOC_FRV_GOTOFFLO:
1767       return &elf32_frv_howto_table[ (int) R_FRV_GOTOFFLO];
1768
1769     case BFD_RELOC_VTABLE_INHERIT:
1770       return &elf32_frv_vtinherit_howto;
1771
1772     case BFD_RELOC_VTABLE_ENTRY:
1773       return &elf32_frv_vtentry_howto;
1774     }
1775
1776   return NULL;
1777 }
1778
1779 /* Set the howto pointer for an FRV ELF reloc.  */
1780
1781 static void
1782 frv_info_to_howto_rela (abfd, cache_ptr, dst)
1783      bfd *abfd ATTRIBUTE_UNUSED;
1784      arelent *cache_ptr;
1785      Elf_Internal_Rela *dst;
1786 {
1787   unsigned int r_type;
1788
1789   r_type = ELF32_R_TYPE (dst->r_info);
1790   switch (r_type)
1791     {
1792     case R_FRV_GNU_VTINHERIT:
1793       cache_ptr->howto = &elf32_frv_vtinherit_howto;
1794       break;
1795
1796     case R_FRV_GNU_VTENTRY:
1797       cache_ptr->howto = &elf32_frv_vtentry_howto;
1798       break;
1799
1800     default:
1801       cache_ptr->howto = & elf32_frv_howto_table [r_type];
1802       break;
1803     }
1804 }
1805
1806 /* Set the howto pointer for an FRV ELF REL reloc.  */
1807 static void
1808 frvfdpic_info_to_howto_rel (bfd *abfd ATTRIBUTE_UNUSED,
1809                             arelent *cache_ptr, Elf_Internal_Rela *dst)
1810 {
1811   unsigned int r_type;
1812
1813   r_type = ELF32_R_TYPE (dst->r_info);
1814   switch (r_type)
1815     {
1816     case R_FRV_32:
1817       cache_ptr->howto = &elf32_frv_rel_32_howto;
1818       break;
1819
1820     case R_FRV_FUNCDESC:
1821       cache_ptr->howto = &elf32_frv_rel_funcdesc_howto;
1822       break;
1823
1824     case R_FRV_FUNCDESC_VALUE:
1825       cache_ptr->howto = &elf32_frv_rel_funcdesc_value_howto;
1826       break;
1827
1828     default:
1829       cache_ptr->howto = NULL;
1830       break;
1831     }
1832 }
1833 \f
1834 /* Perform a single relocation.  By default we use the standard BFD
1835    routines, but a few relocs, we have to do them ourselves.  */
1836
1837 static bfd_reloc_status_type
1838 frv_final_link_relocate (howto, input_bfd, input_section, contents, rel,
1839                          relocation)
1840      reloc_howto_type *howto;
1841      bfd *input_bfd;
1842      asection *input_section;
1843      bfd_byte *contents;
1844      Elf_Internal_Rela *rel;
1845      bfd_vma relocation;
1846 {
1847   return _bfd_final_link_relocate (howto, input_bfd, input_section,
1848                                    contents, rel->r_offset, relocation,
1849                                    rel->r_addend);
1850 }
1851
1852 \f
1853 /* Relocate an FRV ELF section.
1854
1855    The RELOCATE_SECTION function is called by the new ELF backend linker
1856    to handle the relocations for a section.
1857
1858    The relocs are always passed as Rela structures; if the section
1859    actually uses Rel structures, the r_addend field will always be
1860    zero.
1861
1862    This function is responsible for adjusting the section contents as
1863    necessary, and (if using Rela relocs and generating a relocatable
1864    output file) adjusting the reloc addend as necessary.
1865
1866    This function does not have to worry about setting the reloc
1867    address or the reloc symbol index.
1868
1869    LOCAL_SYMS is a pointer to the swapped in local symbols.
1870
1871    LOCAL_SECTIONS is an array giving the section in the input file
1872    corresponding to the st_shndx field of each local symbol.
1873
1874    The global hash table entry for the global symbols can be found
1875    via elf_sym_hashes (input_bfd).
1876
1877    When generating relocatable output, this function must handle
1878    STB_LOCAL/STT_SECTION symbols specially.  The output symbol is
1879    going to be the section symbol corresponding to the output
1880    section, which means that the addend must be adjusted
1881    accordingly.  */
1882
1883 static bfd_boolean
1884 elf32_frv_relocate_section (output_bfd, info, input_bfd, input_section,
1885                             contents, relocs, local_syms, local_sections)
1886      bfd *output_bfd ATTRIBUTE_UNUSED;
1887      struct bfd_link_info *info;
1888      bfd *input_bfd;
1889      asection *input_section;
1890      bfd_byte *contents;
1891      Elf_Internal_Rela *relocs;
1892      Elf_Internal_Sym *local_syms;
1893      asection **local_sections;
1894 {
1895   Elf_Internal_Shdr *symtab_hdr;
1896   struct elf_link_hash_entry **sym_hashes;
1897   Elf_Internal_Rela *rel;
1898   Elf_Internal_Rela *relend;
1899   unsigned isec_segment, got_segment, plt_segment, gprel_segment,
1900     check_segment[2];
1901   int silence_segment_error = !(info->shared || info->pie);
1902
1903   if (info->relocatable)
1904     return TRUE;
1905
1906   symtab_hdr = & elf_tdata (input_bfd)->symtab_hdr;
1907   sym_hashes = elf_sym_hashes (input_bfd);
1908   relend     = relocs + input_section->reloc_count;
1909
1910   isec_segment = _frvfdpic_osec_to_segment (output_bfd,
1911                                             input_section->output_section);
1912   if (IS_FDPIC (output_bfd) && frvfdpic_got_section (info))
1913     got_segment = _frvfdpic_osec_to_segment (output_bfd,
1914                                              frvfdpic_got_section (info)
1915                                              ->output_section);
1916   else
1917     got_segment = -1;
1918   if (IS_FDPIC (output_bfd) && frvfdpic_gotfixup_section (info))
1919     gprel_segment = _frvfdpic_osec_to_segment (output_bfd,
1920                                                frvfdpic_gotfixup_section (info)
1921                                                ->output_section);
1922   else
1923     gprel_segment = -1;
1924   if (IS_FDPIC (output_bfd) && elf_hash_table (info)->dynamic_sections_created)
1925     plt_segment = _frvfdpic_osec_to_segment (output_bfd,
1926                                              frvfdpic_plt_section (info)
1927                                              ->output_section);
1928   else
1929     plt_segment = -1;
1930
1931   for (rel = relocs; rel < relend; rel ++)
1932     {
1933       reloc_howto_type *howto;
1934       unsigned long r_symndx;
1935       Elf_Internal_Sym *sym;
1936       asection *sec;
1937       struct elf_link_hash_entry *h;
1938       bfd_vma relocation;
1939       bfd_reloc_status_type r;
1940       const char * name = NULL;
1941       int r_type;
1942       asection *osec;
1943       struct frvfdpic_relocs_info *picrel;
1944       bfd_vma orig_addend = rel->r_addend;
1945
1946       r_type = ELF32_R_TYPE (rel->r_info);
1947
1948       if (   r_type == R_FRV_GNU_VTINHERIT
1949           || r_type == R_FRV_GNU_VTENTRY)
1950         continue;
1951
1952       /* This is a final link.  */
1953       r_symndx = ELF32_R_SYM (rel->r_info);
1954       howto  = elf32_frv_howto_table + ELF32_R_TYPE (rel->r_info);
1955       h      = NULL;
1956       sym    = NULL;
1957       sec    = NULL;
1958
1959       if (r_symndx < symtab_hdr->sh_info)
1960         {
1961           sym = local_syms + r_symndx;
1962           osec = sec = local_sections [r_symndx];
1963           relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
1964
1965           name = bfd_elf_string_from_elf_section
1966             (input_bfd, symtab_hdr->sh_link, sym->st_name);
1967           name = (name == NULL) ? bfd_section_name (input_bfd, sec) : name;
1968         }
1969       else
1970         {
1971           h = sym_hashes [r_symndx - symtab_hdr->sh_info];
1972
1973           while (h->root.type == bfd_link_hash_indirect
1974                  || h->root.type == bfd_link_hash_warning)
1975             h = (struct elf_link_hash_entry *) h->root.u.i.link;
1976
1977           name = h->root.root.string;
1978
1979           if ((h->root.type == bfd_link_hash_defined
1980                || h->root.type == bfd_link_hash_defweak)
1981               && ! FRVFDPIC_SYM_LOCAL (info, h))
1982             {
1983               sec = NULL;
1984               relocation = 0;
1985             }
1986           else
1987           if (h->root.type == bfd_link_hash_defined
1988               || h->root.type == bfd_link_hash_defweak)
1989             {
1990               sec = h->root.u.def.section;
1991               relocation = (h->root.u.def.value
1992                             + sec->output_section->vma
1993                             + sec->output_offset);
1994             }
1995           else if (h->root.type == bfd_link_hash_undefweak)
1996             {
1997               relocation = 0;
1998             }
1999           else if (info->unresolved_syms_in_objects == RM_IGNORE
2000                    && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
2001             relocation = 0;
2002           else
2003             {
2004               if (! ((*info->callbacks->undefined_symbol)
2005                      (info, h->root.root.string, input_bfd,
2006                       input_section, rel->r_offset,
2007                       (info->unresolved_syms_in_objects == RM_GENERATE_ERROR
2008                        || ELF_ST_VISIBILITY (h->other)))))
2009                 return FALSE;
2010               relocation = 0;
2011             }
2012           osec = sec;
2013         }
2014
2015       switch (r_type)
2016         {
2017         case R_FRV_LABEL24:
2018         case R_FRV_32:
2019           if (! IS_FDPIC (output_bfd))
2020             goto non_fdpic;
2021
2022         case R_FRV_GOT12:
2023         case R_FRV_GOTHI:
2024         case R_FRV_GOTLO:
2025         case R_FRV_FUNCDESC_GOT12:
2026         case R_FRV_FUNCDESC_GOTHI:
2027         case R_FRV_FUNCDESC_GOTLO:
2028         case R_FRV_GOTOFF12:
2029         case R_FRV_GOTOFFHI:
2030         case R_FRV_GOTOFFLO:
2031         case R_FRV_FUNCDESC_GOTOFF12:
2032         case R_FRV_FUNCDESC_GOTOFFHI:
2033         case R_FRV_FUNCDESC_GOTOFFLO:
2034         case R_FRV_FUNCDESC:
2035         case R_FRV_FUNCDESC_VALUE:
2036           if (h != NULL)
2037             picrel = frvfdpic_relocs_info_for_global (frvfdpic_relocs_info
2038                                                       (info), input_bfd, h,
2039                                                       orig_addend, INSERT);
2040           else
2041             /* In order to find the entry we created before, we must
2042                use the original addend, not the one that may have been
2043                modified by _bfd_elf_rela_local_sym().  */
2044             picrel = frvfdpic_relocs_info_for_local (frvfdpic_relocs_info
2045                                                      (info), input_bfd, r_symndx,
2046                                                      orig_addend, INSERT);
2047           if (! picrel)
2048             return FALSE;
2049
2050           if (!_frvfdpic_emit_got_relocs_plt_entries (picrel, output_bfd, info,
2051                                                       osec, sym,
2052                                                       rel->r_addend))
2053             {
2054               (*_bfd_error_handler)
2055                 (_("%s: relocation at `%s+0x%x' references symbol `%s' with nonzero addend"),
2056                  bfd_archive_filename (input_bfd), input_section->name,
2057                  rel->r_offset, name);
2058               return FALSE;
2059
2060             }
2061
2062           break;
2063
2064         default:
2065         non_fdpic:
2066           picrel = NULL;
2067           if (h && ! FRVFDPIC_SYM_LOCAL (info, h))
2068             {
2069               info->callbacks->warning
2070                 (info, _("relocation references symbol not defined in the module"),
2071                  name, input_bfd, input_section, rel->r_offset);
2072               return FALSE;
2073             }
2074           break;
2075         }
2076
2077       switch (r_type)
2078         {
2079         case R_FRV_LABEL24:
2080           check_segment[0] = isec_segment;
2081           if (! IS_FDPIC (output_bfd))
2082             check_segment[1] = isec_segment;
2083           else if (picrel->plt)
2084             {
2085               relocation = frvfdpic_plt_section (info)->output_section->vma
2086                 + frvfdpic_plt_section (info)->output_offset
2087                 + picrel->plt_entry;
2088               check_segment[1] = plt_segment;
2089             }
2090           /* We don't want to warn on calls to undefined weak symbols,
2091              as calls to them must be protected by non-NULL tests
2092              anyway, and unprotected calls would invoke undefined
2093              behavior.  */
2094           else if (picrel->symndx == -1
2095                    && picrel->d.h->root.type == bfd_link_hash_undefweak)
2096             check_segment[1] = check_segment[0];
2097           else
2098             check_segment[1] = sec
2099               ? _frvfdpic_osec_to_segment (output_bfd, sec->output_section)
2100               : (unsigned)-1;
2101           break;
2102
2103         case R_FRV_GOT12:
2104         case R_FRV_GOTHI:
2105         case R_FRV_GOTLO:
2106           relocation = picrel->got_entry;
2107           check_segment[0] = check_segment[1] = got_segment;
2108           break;
2109           
2110         case R_FRV_FUNCDESC_GOT12:
2111         case R_FRV_FUNCDESC_GOTHI:
2112         case R_FRV_FUNCDESC_GOTLO:
2113           relocation = picrel->fdgot_entry;
2114           check_segment[0] = check_segment[1] = got_segment;
2115           break;
2116           
2117         case R_FRV_GOTOFFHI:
2118         case R_FRV_GOTOFF12:
2119         case R_FRV_GOTOFFLO:
2120           relocation -= frvfdpic_got_section (info)->output_section->vma
2121             + frvfdpic_got_section (info)->output_offset
2122             + frvfdpic_got_initial_offset (info);
2123           check_segment[0] = got_segment;
2124           check_segment[1] = sec
2125             ? _frvfdpic_osec_to_segment (output_bfd, sec->output_section)
2126             : (unsigned)-1;
2127           break;
2128
2129         case R_FRV_FUNCDESC_GOTOFF12:
2130         case R_FRV_FUNCDESC_GOTOFFHI:
2131         case R_FRV_FUNCDESC_GOTOFFLO:
2132           relocation = picrel->fd_entry;
2133           check_segment[0] = check_segment[1] = got_segment;
2134           break;
2135
2136         case R_FRV_FUNCDESC:
2137           {
2138             int dynindx;
2139             bfd_vma addend = rel->r_addend;
2140
2141             if (! (h && h->root.type == bfd_link_hash_undefweak
2142                    && FRVFDPIC_SYM_LOCAL (info, h)))
2143               {
2144                 /* If the symbol is dynamic and there may be dynamic
2145                    symbol resolution because we are or are linked with a
2146                    shared library, emit a FUNCDESC relocation such that
2147                    the dynamic linker will allocate the function
2148                    descriptor.  If the symbol needs a non-local function
2149                    descriptor but binds locally (e.g., its visibility is
2150                    protected, emit a dynamic relocation decayed to
2151                    section+offset.  */
2152                 if (h && ! FRVFDPIC_FUNCDESC_LOCAL (info, h)
2153                     && FRVFDPIC_SYM_LOCAL (info, h)
2154                     && !(info->executable && !info->pie))
2155                   {
2156                     dynindx = elf_section_data (h->root.u.def.section
2157                                                 ->output_section)->dynindx;
2158                     addend += h->root.u.def.section->output_offset
2159                       + h->root.u.def.value;
2160                   }
2161                 else if (h && ! FRVFDPIC_FUNCDESC_LOCAL (info, h))
2162                   {
2163                     if (addend)
2164                       {
2165                         info->callbacks->warning
2166                           (info, _("R_FRV_FUNCDESC references dynamic symbol with nonzero addend"),
2167                            name, input_bfd, input_section, rel->r_offset);
2168                         return FALSE;
2169                       }
2170                     dynindx = h->dynindx;
2171                   }
2172                 else
2173                   {
2174                     /* Otherwise, we know we have a private function
2175                        descriptor, so reference it directly.  */
2176                     BFD_ASSERT (picrel->privfd);
2177                     r_type = R_FRV_32;
2178                     dynindx = elf_section_data (frvfdpic_got_section (info)
2179                                                 ->output_section)->dynindx;
2180                     addend = frvfdpic_got_section (info)->output_offset
2181                       + frvfdpic_got_initial_offset (info)
2182                       + picrel->fd_entry;
2183                   }
2184
2185                 /* If there is room for dynamic symbol resolution, emit
2186                    the dynamic relocation.  However, if we're linking an
2187                    executable at a fixed location, we won't have emitted a
2188                    dynamic symbol entry for the got section, so idx will
2189                    be zero, which means we can and should compute the
2190                    address of the private descriptor ourselves.  */
2191                 if (info->executable && !info->pie
2192                     && (!h || FRVFDPIC_FUNCDESC_LOCAL (info, h)))
2193                   {
2194                     addend += frvfdpic_got_section (info)->output_section->vma;
2195                     if ((bfd_get_section_flags (output_bfd,
2196                                                 input_section->output_section)
2197                          & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2198                       {
2199                         if (_frvfdpic_osec_readonly_p (output_bfd,
2200                                                        input_section
2201                                                        ->output_section))
2202                           {
2203                             info->callbacks->warning
2204                               (info,
2205                                _("cannot emit fixups in read-only section"),
2206                                name, input_bfd, input_section, rel->r_offset);
2207                             return FALSE;
2208                           }
2209                         _frvfdpic_add_rofixup (output_bfd,
2210                                                frvfdpic_gotfixup_section
2211                                                (info),
2212                                                _bfd_elf_section_offset
2213                                                (output_bfd, info,
2214                                                 input_section, rel->r_offset)
2215                                                + input_section
2216                                                ->output_section->vma
2217                                                + input_section->output_offset,
2218                                                picrel);
2219                       }
2220                   }
2221                 else if ((bfd_get_section_flags (output_bfd,
2222                                                  input_section->output_section)
2223                           & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2224                   {
2225                     if (_frvfdpic_osec_readonly_p (output_bfd,
2226                                                    input_section
2227                                                    ->output_section))
2228                       {
2229                         info->callbacks->warning
2230                           (info,
2231                            _("cannot emit dynamic relocations in read-only section"),
2232                            name, input_bfd, input_section, rel->r_offset);
2233                         return FALSE;
2234                       }
2235                     _frvfdpic_add_dyn_reloc (output_bfd,
2236                                              frvfdpic_gotrel_section (info),
2237                                              _bfd_elf_section_offset
2238                                              (output_bfd, info,
2239                                               input_section, rel->r_offset)
2240                                              + input_section
2241                                              ->output_section->vma
2242                                              + input_section->output_offset,
2243                                              r_type, dynindx, addend, picrel);
2244                   }
2245                 else
2246                   addend += frvfdpic_got_section (info)->output_section->vma;
2247               }
2248
2249             /* We want the addend in-place because dynamic
2250                relocations are REL.  Setting relocation to it should
2251                arrange for it to be installed.  */
2252             relocation = addend - rel->r_addend;
2253           }
2254           check_segment[0] = check_segment[1] = got_segment;
2255           break;
2256
2257         case R_FRV_32:
2258           if (! IS_FDPIC (output_bfd))
2259             {
2260               check_segment[0] = check_segment[1] = -1;
2261               break;
2262             }
2263           /* Fall through.  */
2264         case R_FRV_FUNCDESC_VALUE:
2265           {
2266             int dynindx;
2267             bfd_vma addend = rel->r_addend;
2268
2269             /* If the symbol is dynamic but binds locally, use
2270                section+offset.  */
2271             if (h && ! FRVFDPIC_SYM_LOCAL (info, h))
2272               {
2273                 if (addend && r_type == R_FRV_FUNCDESC_VALUE)
2274                   {
2275                     info->callbacks->warning
2276                       (info, _("R_FRV_FUNCDESC_VALUE references dynamic symbol with nonzero addend"),
2277                        name, input_bfd, input_section, rel->r_offset);
2278                     return FALSE;
2279                   }
2280                 dynindx = h->dynindx;
2281               }
2282             else
2283               {
2284                 if (h)
2285                   addend += h->root.u.def.value;
2286                 else
2287                   addend += sym->st_value;
2288                 if (osec)
2289                   addend += osec->output_offset;
2290                 if (osec && osec->output_section
2291                     && ! bfd_is_abs_section (osec->output_section)
2292                     && ! bfd_is_und_section (osec->output_section))
2293                   dynindx = elf_section_data (osec->output_section)->dynindx;
2294                 else
2295                   dynindx = 0;
2296               }
2297
2298             /* If we're linking an executable at a fixed address, we
2299                can omit the dynamic relocation as long as the symbol
2300                is defined in the current link unit (which is implied
2301                by its output section not being NULL).  */
2302             if (info->executable && !info->pie
2303                 && (!h || FRVFDPIC_SYM_LOCAL (info, h)))
2304               {
2305                 if (osec)
2306                   addend += osec->output_section->vma;
2307                 if (IS_FDPIC (input_bfd)
2308                     && (bfd_get_section_flags (output_bfd,
2309                                                input_section->output_section)
2310                         & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2311                   {
2312                     if (_frvfdpic_osec_readonly_p (output_bfd,
2313                                                    input_section
2314                                                    ->output_section))
2315                       {
2316                         info->callbacks->warning
2317                           (info,
2318                            _("cannot emit fixups in read-only section"),
2319                            name, input_bfd, input_section, rel->r_offset);
2320                         return FALSE;
2321                       }
2322                     if (!h || h->root.type != bfd_link_hash_undefweak)
2323                       {
2324                         _frvfdpic_add_rofixup (output_bfd,
2325                                                frvfdpic_gotfixup_section
2326                                                (info),
2327                                                _bfd_elf_section_offset
2328                                                (output_bfd, info,
2329                                                 input_section, rel->r_offset)
2330                                                + input_section
2331                                                ->output_section->vma
2332                                                + input_section->output_offset,
2333                                                picrel);
2334                         if (r_type == R_FRV_FUNCDESC_VALUE)
2335                           _frvfdpic_add_rofixup
2336                             (output_bfd,
2337                              frvfdpic_gotfixup_section (info),
2338                              _bfd_elf_section_offset
2339                              (output_bfd, info,
2340                               input_section, rel->r_offset)
2341                              + input_section->output_section->vma
2342                              + input_section->output_offset + 4, picrel);
2343                       }
2344                   }
2345               }
2346             else
2347               {
2348                 if ((bfd_get_section_flags (output_bfd,
2349                                             input_section->output_section)
2350                      & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
2351                   {
2352                     if (_frvfdpic_osec_readonly_p (output_bfd,
2353                                                    input_section
2354                                                    ->output_section))
2355                       {
2356                         info->callbacks->warning
2357                           (info,
2358                            _("cannot emit dynamic relocations in read-only section"),
2359                            name, input_bfd, input_section, rel->r_offset);
2360                         return FALSE;
2361                       }
2362                     _frvfdpic_add_dyn_reloc (output_bfd,
2363                                              frvfdpic_gotrel_section (info),
2364                                              _bfd_elf_section_offset
2365                                              (output_bfd, info,
2366                                               input_section, rel->r_offset)
2367                                              + input_section
2368                                              ->output_section->vma
2369                                              + input_section->output_offset,
2370                                              r_type, dynindx, addend, picrel);
2371                   }
2372                 else if (osec)
2373                   addend += osec->output_section->vma;
2374                 /* We want the addend in-place because dynamic
2375                    relocations are REL.  Setting relocation to it
2376                    should arrange for it to be installed.  */
2377                 relocation = addend - rel->r_addend;
2378               }
2379
2380             if (r_type == R_FRV_FUNCDESC_VALUE)
2381               {
2382                 /* If we've omitted the dynamic relocation, just emit
2383                    the fixed addresses of the symbol and of the local
2384                    GOT base offset.  */
2385                 if (info->executable && !info->pie
2386                     && (!h || FRVFDPIC_SYM_LOCAL (info, h)))
2387                   bfd_put_32 (output_bfd,
2388                               frvfdpic_got_section (info)->output_section->vma
2389                               + frvfdpic_got_section (info)->output_offset
2390                               + frvfdpic_got_initial_offset (info),
2391                               contents + rel->r_offset + 4);
2392                 else
2393                   /* A function descriptor used for lazy or local
2394                      resolving is initialized such that its high word
2395                      contains the output section index in which the
2396                      PLT entries are located, and the low word
2397                      contains the offset of the lazy PLT entry entry
2398                      point into that section.  */
2399                   bfd_put_32 (output_bfd,
2400                               h && ! FRVFDPIC_SYM_LOCAL (info, h)
2401                               ? 0
2402                               : _frvfdpic_osec_to_segment (output_bfd,
2403                                                            sec
2404                                                            ->output_section),
2405                               contents + rel->r_offset + 4);
2406               }
2407           }
2408           check_segment[0] = check_segment[1] = got_segment;
2409           break;
2410
2411         case R_FRV_GPREL12:
2412         case R_FRV_GPRELU12:
2413         case R_FRV_GPREL32:
2414         case R_FRV_GPRELHI:
2415         case R_FRV_GPRELLO:
2416           check_segment[0] = gprel_segment;
2417           check_segment[1] = sec
2418             ? _frvfdpic_osec_to_segment (output_bfd, sec->output_section)
2419             : (unsigned)-1;
2420           break;
2421
2422         default:
2423           check_segment[0] = isec_segment;
2424           check_segment[1] = sec
2425             ? _frvfdpic_osec_to_segment (output_bfd, sec->output_section)
2426             : (unsigned)-1;
2427           break;
2428         }
2429
2430       if (check_segment[0] != check_segment[1] && IS_FDPIC (output_bfd))
2431         {
2432 #if 1 /* If you take this out, remove the #error from fdpic-static-6.d
2433          in the ld testsuite.  */
2434           /* This helps catch problems in GCC while we can't do more
2435              than static linking.  The idea is to test whether the
2436              input file basename is crt0.o only once.  */
2437           if (silence_segment_error == 1)
2438             silence_segment_error =
2439               (strlen (input_bfd->filename) == 6
2440                && strcmp (input_bfd->filename, "crt0.o") == 0)
2441               || (strlen (input_bfd->filename) > 6
2442                   && strcmp (input_bfd->filename
2443                              + strlen (input_bfd->filename) - 7,
2444                              "/crt0.o") == 0)
2445               ? -1 : 0;
2446 #endif
2447           if (!silence_segment_error
2448               /* We don't want duplicate errors for undefined
2449                  symbols.  */
2450               && !(picrel && picrel->symndx == -1
2451                    && picrel->d.h->root.type == bfd_link_hash_undefined))
2452             info->callbacks->warning
2453               (info,
2454                (info->shared || info->pie)
2455                ? _("relocations between different segments are not supported")
2456                : _("warning: relocation references a different segment"),
2457                name, input_bfd, input_section, rel->r_offset);
2458           if (!silence_segment_error && (info->shared || info->pie))
2459             return FALSE;
2460           elf_elfheader (output_bfd)->e_flags |= EF_FRV_PIC;
2461         }
2462
2463       switch (r_type)
2464         {
2465         case R_FRV_GOTOFFHI:
2466           /* We need the addend to be applied before we shift the
2467              value right.  */
2468           relocation += rel->r_addend;
2469           /* Fall through.  */
2470         case R_FRV_GOTHI:
2471         case R_FRV_FUNCDESC_GOTHI:
2472         case R_FRV_FUNCDESC_GOTOFFHI:
2473           relocation >>= 16;
2474           /* Fall through.  */
2475
2476         case R_FRV_GOTLO:
2477         case R_FRV_FUNCDESC_GOTLO:
2478         case R_FRV_GOTOFFLO:
2479         case R_FRV_FUNCDESC_GOTOFFLO:
2480           relocation &= 0xffff;
2481           break;
2482
2483         default:
2484           break;
2485         }
2486
2487       switch (r_type)
2488         {
2489         case R_FRV_LABEL24:
2490           if (! IS_FDPIC (output_bfd) || ! picrel->plt)
2491             break;
2492           /* Fall through.  */
2493           
2494           /* When referencing a GOT entry, a function descriptor or a
2495              PLT, we don't want the addend to apply to the reference,
2496              but rather to the referenced symbol.  The actual entry
2497              will have already been created taking the addend into
2498              account, so cancel it out here.  */
2499         case R_FRV_GOT12:
2500         case R_FRV_GOTHI:
2501         case R_FRV_GOTLO:
2502         case R_FRV_FUNCDESC_GOT12:
2503         case R_FRV_FUNCDESC_GOTHI:
2504         case R_FRV_FUNCDESC_GOTLO:
2505         case R_FRV_FUNCDESC_GOTOFF12:
2506         case R_FRV_FUNCDESC_GOTOFFHI:
2507         case R_FRV_FUNCDESC_GOTOFFLO:
2508           /* Note that we only want GOTOFFHI, not GOTOFFLO or GOTOFF12
2509              here, since we do want to apply the addend to the others.
2510              Note that we've applied the addend to GOTOFFHI before we
2511              shifted it right.  */ 
2512         case R_FRV_GOTOFFHI:
2513           relocation -= rel->r_addend;
2514           break;
2515
2516         default:
2517           break;
2518         }
2519
2520      if (r_type == R_FRV_HI16)
2521        r = elf32_frv_relocate_hi16 (input_bfd, rel, contents, relocation);
2522
2523      else if (r_type == R_FRV_LO16)
2524        r = elf32_frv_relocate_lo16 (input_bfd, rel, contents, relocation);
2525
2526      else if (r_type == R_FRV_LABEL24)
2527        r = elf32_frv_relocate_label24 (input_bfd, input_section, rel,
2528                                        contents, relocation);
2529
2530      else if (r_type == R_FRV_GPREL12)
2531        r = elf32_frv_relocate_gprel12 (info, input_bfd, input_section, rel,
2532                                        contents, relocation);
2533
2534      else if (r_type == R_FRV_GPRELU12)
2535        r = elf32_frv_relocate_gprelu12 (info, input_bfd, input_section, rel,
2536                                         contents, relocation);
2537
2538      else if (r_type == R_FRV_GPRELLO)
2539        r = elf32_frv_relocate_gprello (info, input_bfd, input_section, rel,
2540                                        contents, relocation);
2541
2542      else if (r_type == R_FRV_GPRELHI)
2543        r = elf32_frv_relocate_gprelhi (info, input_bfd, input_section, rel,
2544                                        contents, relocation);
2545
2546      else
2547        r = frv_final_link_relocate (howto, input_bfd, input_section, contents,
2548                                     rel, relocation);
2549
2550       if (r != bfd_reloc_ok)
2551         {
2552           const char * msg = (const char *) NULL;
2553
2554           switch (r)
2555             {
2556             case bfd_reloc_overflow:
2557               r = info->callbacks->reloc_overflow
2558                 (info, name, howto->name, (bfd_vma) 0,
2559                  input_bfd, input_section, rel->r_offset);
2560               break;
2561
2562             case bfd_reloc_undefined:
2563               r = info->callbacks->undefined_symbol
2564                 (info, name, input_bfd, input_section, rel->r_offset, TRUE);
2565               break;
2566
2567             case bfd_reloc_outofrange:
2568               msg = _("internal error: out of range error");
2569               break;
2570
2571             case bfd_reloc_notsupported:
2572               msg = _("internal error: unsupported relocation error");
2573               break;
2574
2575             case bfd_reloc_dangerous:
2576               msg = _("internal error: dangerous relocation");
2577               break;
2578
2579             default:
2580               msg = _("internal error: unknown error");
2581               break;
2582             }
2583
2584           if (msg)
2585             r = info->callbacks->warning
2586               (info, msg, name, input_bfd, input_section, rel->r_offset);
2587
2588           if (! r)
2589             return FALSE;
2590         }
2591     }
2592
2593   return TRUE;
2594 }
2595 \f
2596 /* Return the section that should be marked against GC for a given
2597    relocation.  */
2598
2599 static asection *
2600 elf32_frv_gc_mark_hook (sec, info, rel, h, sym)
2601      asection *sec;
2602      struct bfd_link_info *info ATTRIBUTE_UNUSED;
2603      Elf_Internal_Rela *rel;
2604      struct elf_link_hash_entry *h;
2605      Elf_Internal_Sym *sym;
2606 {
2607   if (h != NULL)
2608     {
2609       switch (ELF32_R_TYPE (rel->r_info))
2610         {
2611         case R_FRV_GNU_VTINHERIT:
2612         case R_FRV_GNU_VTENTRY:
2613           break;
2614
2615         default:
2616           switch (h->root.type)
2617             {
2618             default:
2619               break;
2620
2621             case bfd_link_hash_defined:
2622             case bfd_link_hash_defweak:
2623               return h->root.u.def.section;
2624
2625             case bfd_link_hash_common:
2626               return h->root.u.c.p->section;
2627             }
2628         }
2629     }
2630   else
2631     return bfd_section_from_elf_index (sec->owner, sym->st_shndx);
2632
2633   return NULL;
2634 }
2635
2636 /* Update the got entry reference counts for the section being removed.  */
2637
2638 static bfd_boolean
2639 elf32_frv_gc_sweep_hook (abfd, info, sec, relocs)
2640      bfd *abfd ATTRIBUTE_UNUSED;
2641      struct bfd_link_info *info ATTRIBUTE_UNUSED;
2642      asection *sec ATTRIBUTE_UNUSED;
2643      const Elf_Internal_Rela *relocs ATTRIBUTE_UNUSED;
2644 {
2645   return TRUE;
2646 }
2647
2648 \f
2649 /* Hook called by the linker routine which adds symbols from an object
2650    file.  We use it to put .comm items in .scomm, and not .comm.  */
2651
2652 static bfd_boolean
2653 elf32_frv_add_symbol_hook (abfd, info, sym, namep, flagsp, secp, valp)
2654      bfd *abfd;
2655      struct bfd_link_info *info;
2656      Elf_Internal_Sym *sym;
2657      const char **namep ATTRIBUTE_UNUSED;
2658      flagword *flagsp ATTRIBUTE_UNUSED;
2659      asection **secp;
2660      bfd_vma *valp;
2661 {
2662   if (sym->st_shndx == SHN_COMMON
2663       && !info->relocatable
2664       && (int)sym->st_size <= (int)bfd_get_gp_size (abfd))
2665     {
2666       /* Common symbols less than or equal to -G nn bytes are
2667          automatically put into .sbss.  */
2668
2669       asection *scomm = bfd_get_section_by_name (abfd, ".scommon");
2670
2671       if (scomm == NULL)
2672         {
2673           scomm = bfd_make_section (abfd, ".scommon");
2674           if (scomm == NULL
2675               || !bfd_set_section_flags (abfd, scomm, (SEC_ALLOC
2676                                                        | SEC_IS_COMMON
2677                                                        | SEC_LINKER_CREATED)))
2678             return FALSE;
2679         }
2680
2681       *secp = scomm;
2682       *valp = sym->st_size;
2683     }
2684
2685   return TRUE;
2686 }
2687
2688 /* We need dynamic symbols for every section, since segments can
2689    relocate independently.  */
2690 static bfd_boolean
2691 _frvfdpic_link_omit_section_dynsym (bfd *output_bfd ATTRIBUTE_UNUSED,
2692                                     struct bfd_link_info *info
2693                                     ATTRIBUTE_UNUSED,
2694                                     asection *p ATTRIBUTE_UNUSED)
2695 {
2696   switch (elf_section_data (p)->this_hdr.sh_type)
2697     {
2698     case SHT_PROGBITS:
2699     case SHT_NOBITS:
2700       /* If sh_type is yet undecided, assume it could be
2701          SHT_PROGBITS/SHT_NOBITS.  */
2702     case SHT_NULL:
2703       return FALSE;
2704
2705       /* There shouldn't be section relative relocations
2706          against any other section.  */
2707     default:
2708       return TRUE;
2709     }
2710 }
2711
2712 /* Create  a .got section, as well as its additional info field.  This
2713    is almost entirely copied from
2714    elflink.c:_bfd_elf_create_got_section().  */
2715
2716 static bfd_boolean
2717 _frv_create_got_section (bfd *abfd, struct bfd_link_info *info)
2718 {
2719   flagword flags;
2720   asection *s;
2721   struct elf_link_hash_entry *h;
2722   struct bfd_link_hash_entry *bh;
2723   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
2724   int ptralign;
2725   int offset;
2726
2727   /* This function may be called more than once.  */
2728   s = bfd_get_section_by_name (abfd, ".got");
2729   if (s != NULL && (s->flags & SEC_LINKER_CREATED) != 0)
2730     return TRUE;
2731
2732   /* Machine specific: although pointers are 32-bits wide, we want the
2733      GOT to be aligned to a 64-bit boundary, such that function
2734      descriptors in it can be accessed with 64-bit loads and
2735      stores.  */
2736   ptralign = 3;
2737
2738   flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
2739            | SEC_LINKER_CREATED);
2740
2741   s = bfd_make_section (abfd, ".got");
2742   if (s == NULL
2743       || !bfd_set_section_flags (abfd, s, flags)
2744       || !bfd_set_section_alignment (abfd, s, ptralign))
2745     return FALSE;
2746
2747   if (bed->want_got_plt)
2748     {
2749       s = bfd_make_section (abfd, ".got.plt");
2750       if (s == NULL
2751           || !bfd_set_section_flags (abfd, s, flags)
2752           || !bfd_set_section_alignment (abfd, s, ptralign))
2753         return FALSE;
2754     }
2755
2756   if (bed->want_got_sym)
2757     {
2758       /* Define the symbol _GLOBAL_OFFSET_TABLE_ at the start of the .got
2759          (or .got.plt) section.  We don't do this in the linker script
2760          because we don't want to define the symbol if we are not creating
2761          a global offset table.  */
2762       bh = NULL;
2763       if (!(_bfd_generic_link_add_one_symbol
2764             (info, abfd, "_GLOBAL_OFFSET_TABLE_", BSF_GLOBAL, s,
2765              bed->got_symbol_offset, (const char *) NULL, FALSE,
2766              bed->collect, &bh)))
2767         return FALSE;
2768       h = (struct elf_link_hash_entry *) bh;
2769       h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
2770       h->type = STT_OBJECT;
2771
2772       /* Machine-specific: we want the symbol for executables as
2773          well.  */
2774       if (! bfd_elf_link_record_dynamic_symbol (info, h))
2775         return FALSE;
2776
2777       elf_hash_table (info)->hgot = h;
2778     }
2779
2780   /* The first bit of the global offset table is the header.  */
2781   s->size += bed->got_header_size + bed->got_symbol_offset;
2782
2783   /* This is the machine-specific part.  Create and initialize section
2784      data for the got.  */
2785   if (IS_FDPIC (abfd))
2786     {
2787       frvfdpic_got_section (info) = s;
2788       frvfdpic_relocs_info (info) = htab_try_create (1, frvfdpic_relocs_info_hash,
2789                                                      frvfdpic_relocs_info_eq,
2790                                                      (htab_del) NULL);
2791       if (! frvfdpic_relocs_info (info))
2792         return FALSE;
2793
2794       s = bfd_make_section (abfd, ".rel.got");
2795       if (s == NULL
2796           || ! bfd_set_section_flags (abfd, s, (flags | SEC_READONLY))
2797           || ! bfd_set_section_alignment (abfd, s, 2))
2798         return FALSE;
2799
2800       frvfdpic_gotrel_section (info) = s;
2801
2802       /* Machine-specific.  */
2803       s = bfd_make_section (abfd, ".rofixup");
2804       if (s == NULL
2805           || ! bfd_set_section_flags (abfd, s, (flags | SEC_READONLY))
2806           || ! bfd_set_section_alignment (abfd, s, 2))
2807         return FALSE;
2808
2809       frvfdpic_gotfixup_section (info) = s;
2810       offset = -2048;
2811       flags = BSF_GLOBAL;
2812     }
2813   else
2814     {
2815       offset = 2048;
2816       flags = BSF_GLOBAL | BSF_WEAK;
2817     }
2818
2819   /* Define _gp in .rofixup, for FDPIC, or .got otherwise.  If it
2820      turns out that we're linking with a different linker script, the
2821      linker script will override it.  */
2822   bh = NULL;
2823   if (!(_bfd_generic_link_add_one_symbol
2824         (info, abfd, "_gp", flags, s, offset, (const char *) NULL, FALSE,
2825          bed->collect, &bh)))
2826     return FALSE;
2827   h = (struct elf_link_hash_entry *) bh;
2828   h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
2829   h->type = STT_OBJECT;
2830
2831   /* Machine-specific: we want the symbol for executables as well.  */
2832   if (IS_FDPIC (abfd) && ! bfd_elf_link_record_dynamic_symbol (info, h))
2833     return FALSE;
2834
2835   return TRUE;
2836 }
2837
2838 /* Make sure the got and plt sections exist, and that our pointers in
2839    the link hash table point to them.  */
2840
2841 static bfd_boolean
2842 elf32_frvfdpic_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
2843 {
2844   /* This is mostly copied from
2845      elflink.c:_bfd_elf_create_dynamic_sections().  */
2846   flagword flags, pltflags;
2847   asection *s;
2848   const struct elf_backend_data *bed = get_elf_backend_data (abfd);
2849
2850   /* We need to create .plt, .rel[a].plt, .got, .got.plt, .dynbss, and
2851      .rel[a].bss sections.  */
2852
2853   flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
2854            | SEC_LINKER_CREATED);
2855
2856   pltflags = flags;
2857   pltflags |= SEC_CODE;
2858   if (bed->plt_not_loaded)
2859     pltflags &= ~ (SEC_CODE | SEC_LOAD | SEC_HAS_CONTENTS);
2860   if (bed->plt_readonly)
2861     pltflags |= SEC_READONLY;
2862
2863   s = bfd_make_section (abfd, ".plt");
2864   if (s == NULL
2865       || ! bfd_set_section_flags (abfd, s, pltflags)
2866       || ! bfd_set_section_alignment (abfd, s, bed->plt_alignment))
2867     return FALSE;
2868   /* FRV-specific: remember it.  */
2869   frvfdpic_plt_section (info) = s;
2870
2871   if (bed->want_plt_sym)
2872     {
2873       /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
2874          .plt section.  */
2875       struct elf_link_hash_entry *h;
2876       struct bfd_link_hash_entry *bh = NULL;
2877
2878       if (! (_bfd_generic_link_add_one_symbol
2879              (info, abfd, "_PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s, 0, NULL,
2880               FALSE, get_elf_backend_data (abfd)->collect, &bh)))
2881         return FALSE;
2882       h = (struct elf_link_hash_entry *) bh;
2883       h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
2884       h->type = STT_OBJECT;
2885
2886       if (! info->executable
2887           && ! bfd_elf_link_record_dynamic_symbol (info, h))
2888         return FALSE;
2889     }
2890
2891   /* FRV-specific: we want rel relocations for the plt.  */
2892   s = bfd_make_section (abfd, ".rel.plt");
2893   if (s == NULL
2894       || ! bfd_set_section_flags (abfd, s, flags | SEC_READONLY)
2895       || ! bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
2896     return FALSE;
2897   /* FRV-specific: remember it.  */
2898   frvfdpic_pltrel_section (info) = s;
2899
2900   /* FRV-specific: we want to create the GOT in the FRV way.  */
2901   if (! _frv_create_got_section (abfd, info))
2902     return FALSE;
2903
2904   /* FRV-specific: make sure we created everything we wanted.  */
2905   BFD_ASSERT (frvfdpic_got_section (info) && frvfdpic_gotrel_section (info)
2906               && frvfdpic_gotfixup_section (info)
2907               && frvfdpic_plt_section (info)
2908               && frvfdpic_pltrel_section (info));
2909
2910   if (bed->want_dynbss)
2911     {
2912       /* The .dynbss section is a place to put symbols which are defined
2913          by dynamic objects, are referenced by regular objects, and are
2914          not functions.  We must allocate space for them in the process
2915          image and use a R_*_COPY reloc to tell the dynamic linker to
2916          initialize them at run time.  The linker script puts the .dynbss
2917          section into the .bss section of the final image.  */
2918       s = bfd_make_section (abfd, ".dynbss");
2919       if (s == NULL
2920           || ! bfd_set_section_flags (abfd, s, SEC_ALLOC | SEC_LINKER_CREATED))
2921         return FALSE;
2922
2923       /* The .rel[a].bss section holds copy relocs.  This section is not
2924      normally needed.  We need to create it here, though, so that the
2925      linker will map it to an output section.  We can't just create it
2926      only if we need it, because we will not know whether we need it
2927      until we have seen all the input files, and the first time the
2928      main linker code calls BFD after examining all the input files
2929      (size_dynamic_sections) the input sections have already been
2930      mapped to the output sections.  If the section turns out not to
2931      be needed, we can discard it later.  We will never need this
2932      section when generating a shared object, since they do not use
2933      copy relocs.  */
2934       if (! info->shared)
2935         {
2936           s = bfd_make_section (abfd,
2937                                 (bed->default_use_rela_p
2938                                  ? ".rela.bss" : ".rel.bss"));
2939           if (s == NULL
2940               || ! bfd_set_section_flags (abfd, s, flags | SEC_READONLY)
2941               || ! bfd_set_section_alignment (abfd, s, bed->s->log_file_align))
2942             return FALSE;
2943         }
2944     }
2945
2946   return TRUE;
2947 }
2948
2949 /* The name of the dynamic interpreter.  This is put in the .interp
2950    section.  */
2951
2952 #define ELF_DYNAMIC_INTERPRETER "/lib/ld.so.1"
2953
2954 #define DEFAULT_STACK_SIZE 0x20000
2955
2956 /* This structure is used to collect the number of entries present in
2957    each addressable range of the got.  */
2958 struct _frvfdpic_dynamic_got_info
2959 {
2960   /* Several bits of information about the current link.  */
2961   struct bfd_link_info *info;
2962   /* Total size needed for GOT entries within the 12-, 16- or 32-bit
2963      ranges.  */
2964   bfd_vma got12, gotlos, gothilo;
2965   /* Total size needed for function descriptor entries within the 12-,
2966      16- or 32-bit ranges.  */
2967   bfd_vma fd12, fdlos, fdhilo;
2968   /* Total size needed function descriptor entries referenced in PLT
2969      entries, that would be profitable to place in offsets close to
2970      the PIC register.  */
2971   bfd_vma fdplt;
2972   /* Total size needed by lazy PLT entries.  */
2973   bfd_vma lzplt;
2974   /* Number of relocations carried over from input object files.  */
2975   unsigned long relocs;
2976   /* Number of fixups introduced by relocations in input object files.  */
2977   unsigned long fixups;
2978 };
2979
2980 /* Compute the total GOT size required by each symbol in each range.
2981    Symbols may require up to 4 words in the GOT: an entry pointing to
2982    the symbol, an entry pointing to its function descriptor, and a
2983    private function descriptors taking two words.  */
2984
2985 static int
2986 _frvfdpic_count_got_plt_entries (void **entryp, void *dinfo_)
2987 {
2988   struct frvfdpic_relocs_info *entry = *entryp;
2989   struct _frvfdpic_dynamic_got_info *dinfo = dinfo_;
2990   unsigned relocs = 0, fixups = 0;
2991
2992   /* Allocate space for a GOT entry pointing to the symbol.  */
2993   if (entry->got12)
2994     dinfo->got12 += 4;
2995   else if (entry->gotlos)
2996     dinfo->gotlos += 4;
2997   else if (entry->gothilo)
2998     dinfo->gothilo += 4;
2999   else
3000     entry->relocs32--;
3001   entry->relocs32++;
3002
3003   /* Allocate space for a GOT entry pointing to the function
3004      descriptor.  */
3005   if (entry->fdgot12)
3006     dinfo->got12 += 4;
3007   else if (entry->fdgotlos)
3008     dinfo->gotlos += 4;
3009   else if (entry->fdgothilo)
3010     dinfo->gothilo += 4;
3011   else
3012     entry->relocsfd--;
3013   entry->relocsfd++;
3014
3015   /* Decide whether we need a PLT entry, a function descriptor in the
3016      GOT, and a lazy PLT entry for this symbol.  */
3017   entry->plt = entry->call
3018     && entry->symndx == -1 && ! FRVFDPIC_SYM_LOCAL (dinfo->info, entry->d.h)
3019     && elf_hash_table (dinfo->info)->dynamic_sections_created;
3020   entry->privfd = entry->plt
3021     || entry->fdgoff12 || entry->fdgofflos || entry->fdgoffhilo
3022     || ((entry->fd || entry->fdgot12 || entry->fdgotlos || entry->fdgothilo)
3023         && (entry->symndx != -1
3024             || FRVFDPIC_FUNCDESC_LOCAL (dinfo->info, entry->d.h)));
3025   entry->lazyplt = entry->privfd
3026     && entry->symndx == -1 && ! FRVFDPIC_SYM_LOCAL (dinfo->info, entry->d.h)
3027     && ! (dinfo->info->flags & DF_BIND_NOW)
3028     && elf_hash_table (dinfo->info)->dynamic_sections_created;
3029
3030   /* Allocate space for a function descriptor.  */
3031   if (entry->fdgoff12)
3032     dinfo->fd12 += 8;
3033   else if (entry->fdgofflos)
3034     dinfo->fdlos += 8;
3035   else if (entry->privfd && entry->plt)
3036     dinfo->fdplt += 8;
3037   else if (entry->privfd)
3038     dinfo->fdhilo += 8;
3039   else
3040     entry->relocsfdv--;
3041   entry->relocsfdv++;
3042
3043   if (entry->lazyplt)
3044     dinfo->lzplt += 8;
3045
3046   if (!dinfo->info->executable || dinfo->info->pie)
3047     relocs = entry->relocs32 + entry->relocsfd + entry->relocsfdv;
3048   else
3049     {
3050       if (entry->symndx != -1 || FRVFDPIC_SYM_LOCAL (dinfo->info, entry->d.h))
3051         {
3052           if (entry->symndx != -1
3053               || entry->d.h->root.type != bfd_link_hash_undefweak)
3054             fixups += entry->relocs32 + 2 * entry->relocsfdv;
3055         }
3056       else
3057         relocs += entry->relocs32 + entry->relocsfdv;
3058
3059       if (entry->symndx != -1
3060           || FRVFDPIC_FUNCDESC_LOCAL (dinfo->info, entry->d.h))
3061         {
3062           if (entry->symndx != -1
3063               || entry->d.h->root.type != bfd_link_hash_undefweak)
3064             fixups += entry->relocsfd;
3065         }
3066       else
3067         relocs += entry->relocsfd;
3068     }
3069
3070   entry->dynrelocs += relocs;
3071   entry->fixups += fixups;
3072   dinfo->relocs += relocs;
3073   dinfo->fixups += fixups;
3074
3075   return 1;
3076 }
3077
3078 /* This structure is used to assign offsets to got entries, function
3079    descriptors, plt entries and lazy plt entries.  */
3080
3081 struct _frvfdpic_dynamic_got_plt_info
3082 {
3083   /* Summary information collected with _frvfdpic_count_got_plt_entries.  */
3084   struct _frvfdpic_dynamic_got_info g;
3085
3086   /* For each addressable range, we record a MAX (positive) and MIN
3087      (negative) value.  CUR is used to assign got entries, and it's
3088      incremented from an initial positive value to MAX, then from MIN
3089      to FDCUR (unless FDCUR wraps around first).  FDCUR is used to
3090      assign function descriptors, and it's decreased from an initial
3091      non-positive value to MIN, then from MAX down to CUR (unless CUR
3092      wraps around first).  All of MIN, MAX, CUR and FDCUR always point
3093      to even words.  ODD, if non-zero, indicates an odd word to be
3094      used for the next got entry, otherwise CUR is used and
3095      incremented by a pair of words, wrapping around when it reaches
3096      MAX.  FDCUR is decremented (and wrapped) before the next function
3097      descriptor is chosen.  FDPLT indicates the number of remaining
3098      slots that can be used for function descriptors used only by PLT
3099      entries.  */
3100   struct _frvfdpic_dynamic_got_alloc_data
3101   {
3102     bfd_signed_vma max, cur, odd, fdcur, min;
3103     bfd_vma fdplt;
3104   } got12, gotlos, gothilo;
3105 };
3106
3107 /* Determine the positive and negative ranges to be used by each
3108    offset range in the GOT.  FDCUR and CUR, that must be aligned to a
3109    double-word boundary, are the minimum (negative) and maximum
3110    (positive) GOT offsets already used by previous ranges, except for
3111    an ODD entry that may have been left behind.  GOT and FD indicate
3112    the size of GOT entries and function descriptors that must be
3113    placed within the range from -WRAP to WRAP.  If there's room left,
3114    up to FDPLT bytes should be reserved for additional function
3115    descriptors.  */
3116
3117 inline static bfd_signed_vma
3118 _frvfdpic_compute_got_alloc_data (struct _frvfdpic_dynamic_got_alloc_data *gad,
3119                                   bfd_signed_vma fdcur,
3120                                   bfd_signed_vma odd,
3121                                   bfd_signed_vma cur,
3122                                   bfd_vma got,
3123                                   bfd_vma fd,
3124                                   bfd_vma fdplt,
3125                                   bfd_vma wrap)
3126 {
3127   bfd_signed_vma wrapmin = -wrap;
3128
3129   /* Start at the given initial points.  */
3130   gad->fdcur = fdcur;
3131   gad->cur = cur;
3132
3133   /* If we had an incoming odd word and we have any got entries that
3134      are going to use it, consume it, otherwise leave gad->odd at
3135      zero.  We might force gad->odd to zero and return the incoming
3136      odd such that it is used by the next range, but then GOT entries
3137      might appear to be out of order and we wouldn't be able to
3138      shorten the GOT by one word if it turns out to end with an
3139      unpaired GOT entry.  */
3140   if (odd && got)
3141     {
3142       gad->odd = odd;
3143       got -= 4;
3144       odd = 0;
3145     }
3146   else
3147     gad->odd = 0;
3148
3149   /* If we're left with an unpaired GOT entry, compute its location
3150      such that we can return it.  Otherwise, if got doesn't require an
3151      odd number of words here, either odd was already zero in the
3152      block above, or it was set to zero because got was non-zero, or
3153      got was already zero.  In the latter case, we want the value of
3154      odd to carry over to the return statement, so we don't want to
3155      reset odd unless the condition below is true.  */
3156   if (got & 4)
3157     {
3158       odd = cur + got;
3159       got += 4;
3160     }
3161   
3162   /* Compute the tentative boundaries of this range.  */
3163   gad->max = cur + got;
3164   gad->min = fdcur - fd;
3165   gad->fdplt = 0;
3166
3167   /* If function descriptors took too much space, wrap some of them
3168      around.  */
3169   if (gad->min < wrapmin)
3170     {
3171       gad->max += wrapmin - gad->min;
3172       gad->min = wrapmin;
3173     }
3174   /* If there is space left and we have function descriptors
3175      referenced in PLT entries that could take advantage of shorter
3176      offsets, place them here.  */
3177   else if (fdplt && gad->min > wrapmin)
3178     {
3179       bfd_vma fds;
3180       if ((bfd_vma) (gad->min - wrapmin) < fdplt)
3181         fds = gad->min - wrapmin;
3182       else
3183         fds = fdplt;
3184
3185       fdplt -= fds;
3186       gad->min -= fds;
3187       gad->fdplt += fds;
3188     }
3189
3190   /* If GOT entries took too much space, wrap some of them around.
3191      This may well cause gad->min to become lower than wrapmin.  This
3192      will cause a relocation overflow later on, so we don't have to
3193      report it here . */
3194   if ((bfd_vma) gad->max > wrap)
3195     {
3196       gad->min -= gad->max - wrap;
3197       gad->max = wrap;
3198     }
3199   /* If there is more space left, try to place some more function
3200      descriptors for PLT entries.  */
3201   else if (fdplt && (bfd_vma) gad->max < wrap)
3202     {
3203       bfd_vma fds;
3204       if ((bfd_vma) (wrap - gad->max) < fdplt)
3205         fds = wrap - gad->max;
3206       else
3207         fds = fdplt;
3208
3209       fdplt -= fds;
3210       gad->max += fds;
3211       gad->fdplt += fds;
3212     }
3213
3214   /* If odd was initially computed as an offset past the wrap point,
3215      wrap it around.  */
3216   if (odd > gad->max)
3217     odd = gad->min + odd - gad->max;
3218
3219   /* _frvfdpic_get_got_entry() below will always wrap gad->cur if needed
3220      before returning, so do it here too.  This guarantees that,
3221      should cur and fdcur meet at the wrap point, they'll both be
3222      equal to min.  */
3223   if (gad->cur == gad->max)
3224     gad->cur = gad->min;
3225
3226   return odd;
3227 }
3228
3229 /* Compute the location of the next GOT entry, given the allocation
3230    data for a range.  */
3231
3232 inline static bfd_signed_vma
3233 _frvfdpic_get_got_entry (struct _frvfdpic_dynamic_got_alloc_data *gad)
3234 {
3235   bfd_signed_vma ret;
3236   
3237   if (gad->odd)
3238     {
3239       /* If there was an odd word left behind, use it.  */
3240       ret = gad->odd;
3241       gad->odd = 0;
3242     }
3243   else
3244     {
3245       /* Otherwise, use the word pointed to by cur, reserve the next
3246          as an odd word, and skip to the next pair of words, possibly
3247          wrapping around.  */
3248       ret = gad->cur;
3249       gad->odd = gad->cur + 4;
3250       gad->cur += 8;
3251       if (gad->cur == gad->max)
3252         gad->cur = gad->min;
3253     }
3254
3255   return ret;
3256 }
3257
3258 /* Compute the location of the next function descriptor entry in the
3259    GOT, given the allocation data for a range.  */
3260
3261 inline static bfd_signed_vma
3262 _frvfdpic_get_fd_entry (struct _frvfdpic_dynamic_got_alloc_data *gad)
3263 {
3264   /* If we're at the bottom, wrap around, and only then allocate the
3265      next pair of words.  */
3266   if (gad->fdcur == gad->min)
3267     gad->fdcur = gad->max;
3268   return gad->fdcur -= 8;
3269 }
3270
3271 /* Assign GOT offsets for every GOT entry and function descriptor.
3272    Doing everything in a single pass is tricky.  */
3273
3274 static int
3275 _frvfdpic_assign_got_entries (void **entryp, void *info_)
3276 {
3277   struct frvfdpic_relocs_info *entry = *entryp;
3278   struct _frvfdpic_dynamic_got_plt_info *dinfo = info_;
3279
3280   if (entry->got12)
3281     entry->got_entry = _frvfdpic_get_got_entry (&dinfo->got12);
3282   else if (entry->gotlos)
3283     entry->got_entry = _frvfdpic_get_got_entry (&dinfo->gotlos);
3284   else if (entry->gothilo)
3285     entry->got_entry = _frvfdpic_get_got_entry (&dinfo->gothilo);
3286
3287   if (entry->fdgot12)
3288     entry->fdgot_entry = _frvfdpic_get_got_entry (&dinfo->got12);
3289   else if (entry->fdgotlos)
3290     entry->fdgot_entry = _frvfdpic_get_got_entry (&dinfo->gotlos);
3291   else if (entry->fdgothilo)
3292     entry->fdgot_entry = _frvfdpic_get_got_entry (&dinfo->gothilo);
3293
3294   if (entry->fdgoff12)
3295     entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->got12);
3296   else if (entry->plt && dinfo->got12.fdplt)
3297     {
3298       dinfo->got12.fdplt -= 8;
3299       entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->got12);
3300     }
3301   else if (entry->fdgofflos)
3302     entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gotlos);
3303   else if (entry->plt && dinfo->gotlos.fdplt)
3304     {
3305       dinfo->gotlos.fdplt -= 8;
3306       entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gotlos);
3307     }
3308   else if (entry->plt)
3309     {
3310       dinfo->gothilo.fdplt -= 8;
3311       entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gothilo);
3312     }
3313   else if (entry->privfd)
3314     entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gothilo);
3315   
3316   return 1;
3317 }
3318
3319 /* Assign GOT offsets to private function descriptors used by PLT
3320    entries (or referenced by 32-bit offsets), as well as PLT entries
3321    and lazy PLT entries.  */
3322
3323 static int
3324 _frvfdpic_assign_plt_entries (void **entryp, void *info_)
3325 {
3326   struct frvfdpic_relocs_info *entry = *entryp;
3327   struct _frvfdpic_dynamic_got_plt_info *dinfo = info_;
3328
3329   /* If this symbol requires a local function descriptor, allocate
3330      one.  */
3331   if (entry->privfd && entry->fd_entry == 0)
3332     {
3333       if (dinfo->got12.fdplt)
3334         {
3335           entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->got12);
3336           dinfo->got12.fdplt -= 8;
3337         }
3338       else if (dinfo->gotlos.fdplt)
3339         {
3340           entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gotlos);
3341           dinfo->gotlos.fdplt -= 8;
3342         }
3343       else
3344         {
3345           BFD_ASSERT (dinfo->gothilo.fdplt)
3346           entry->fd_entry = _frvfdpic_get_fd_entry (&dinfo->gothilo);
3347           dinfo->gothilo.fdplt -= 8;
3348         }
3349     }
3350
3351   if (entry->plt)
3352     {
3353       int size;
3354
3355       /* We use the section's raw size to mark the location of the
3356          next PLT entry.  */
3357       entry->plt_entry = frvfdpic_plt_section (dinfo->g.info)->size;
3358
3359       /* Figure out the length of this PLT entry based on the
3360          addressing mode we need to reach the function descriptor.  */
3361       BFD_ASSERT (entry->fd_entry);
3362       if (entry->fd_entry >= -(1 << (12 - 1))
3363           && entry->fd_entry < (1 << (12 - 1)))
3364         size = 8;
3365       else if (entry->fd_entry >= -(1 << (16 - 1))
3366                && entry->fd_entry < (1 << (16 - 1)))
3367         size = 12;
3368       else
3369         size = 16;
3370
3371       frvfdpic_plt_section (dinfo->g.info)->size += size;
3372     }
3373
3374   if (entry->lazyplt)
3375     {
3376       entry->lzplt_entry = dinfo->g.lzplt;
3377       dinfo->g.lzplt += 8;
3378       /* If this entry is the one that gets the resolver stub, account
3379          for the additional instruction.  */
3380       if (entry->lzplt_entry % FRVFDPIC_LZPLT_BLOCK_SIZE
3381           == FRVFDPIC_LZPLT_RESOLV_LOC)
3382         dinfo->g.lzplt += 4;
3383     }
3384       
3385   return 1;
3386 }  
3387
3388 /* Follow indirect and warning hash entries so that each got entry
3389    points to the final symbol definition.  P must point to a pointer
3390    to the hash table we're traversing.  Since this traversal may
3391    modify the hash table, we set this pointer to NULL to indicate
3392    we've made a potentially-destructive change to the hash table, so
3393    the traversal must be restarted.  */
3394 static int
3395 _frvfdpic_resolve_final_relocs_info (void **entryp, void *p)
3396 {
3397   struct frvfdpic_relocs_info *entry = *entryp;
3398   htab_t *htab = p;
3399
3400   if (entry->symndx == -1)
3401     {
3402       struct elf_link_hash_entry *h = entry->d.h;
3403       struct frvfdpic_relocs_info *oentry;
3404
3405       while (h->root.type == bfd_link_hash_indirect
3406              || h->root.type == bfd_link_hash_warning)
3407         h = (struct elf_link_hash_entry *)h->root.u.i.link;
3408
3409       if (entry->d.h == h)
3410         return 1;
3411
3412       oentry = frvfdpic_relocs_info_for_global (*htab, 0, h, entry->addend,
3413                                                 NO_INSERT);
3414
3415       if (oentry)
3416         {
3417           /* Merge the two entries.  */
3418           frvfdpic_pic_merge_early_relocs_info (oentry, entry);
3419           htab_clear_slot (*htab, entryp);
3420           return 1;
3421         }
3422
3423       entry->d.h = h;
3424
3425       /* If we can't find this entry with the new bfd hash, re-insert
3426          it, and get the traversal restarted.  */
3427       if (! htab_find (*htab, entry))
3428         {
3429           htab_clear_slot (*htab, entryp);
3430           entryp = htab_find_slot (*htab, entry, INSERT);
3431           if (! *entryp)
3432             *entryp = entry;
3433           /* Abort the traversal, since the whole table may have
3434              moved, and leave it up to the parent to restart the
3435              process.  */
3436           *(htab_t *)p = NULL;
3437           return 0;
3438         }
3439     }
3440
3441   return 1;
3442 }
3443
3444 /* Set the sizes of the dynamic sections.  */
3445
3446 static bfd_boolean
3447 elf32_frvfdpic_size_dynamic_sections (bfd *output_bfd,
3448                                       struct bfd_link_info *info)
3449 {
3450   bfd *dynobj;
3451   asection *s;
3452   struct _frvfdpic_dynamic_got_plt_info gpinfo;
3453   bfd_signed_vma odd;
3454   bfd_vma limit;
3455
3456   dynobj = elf_hash_table (info)->dynobj;
3457   BFD_ASSERT (dynobj != NULL);
3458
3459   if (elf_hash_table (info)->dynamic_sections_created)
3460     {
3461       /* Set the contents of the .interp section to the interpreter.  */
3462       if (info->executable)
3463         {
3464           s = bfd_get_section_by_name (dynobj, ".interp");
3465           BFD_ASSERT (s != NULL);
3466           s->size = sizeof ELF_DYNAMIC_INTERPRETER;
3467           s->contents = (bfd_byte *) ELF_DYNAMIC_INTERPRETER;
3468         }
3469     }
3470
3471   memset (&gpinfo, 0, sizeof (gpinfo));
3472   gpinfo.g.info = info;
3473
3474   for (;;)
3475     {
3476       htab_t relocs = frvfdpic_relocs_info (info);
3477
3478       htab_traverse (relocs, _frvfdpic_resolve_final_relocs_info, &relocs);
3479
3480       if (relocs == frvfdpic_relocs_info (info))
3481         break;
3482     }
3483
3484   htab_traverse (frvfdpic_relocs_info (info), _frvfdpic_count_got_plt_entries,
3485                  &gpinfo.g);
3486
3487   odd = 12;
3488   /* Compute the total size taken by entries in the 12-bit and 16-bit
3489      ranges, to tell how many PLT function descriptors we can bring
3490      into the 12-bit range without causing the 16-bit range to
3491      overflow.  */
3492   limit = odd + gpinfo.g.got12 + gpinfo.g.gotlos
3493     + gpinfo.g.fd12 + gpinfo.g.fdlos;
3494   if (limit < (bfd_vma)1 << 16)
3495     limit = ((bfd_vma)1 << 16) - limit;
3496   else
3497     limit = 0;
3498   if (gpinfo.g.fdplt < limit)
3499     limit = gpinfo.g.fdplt;
3500
3501   /* Determine the ranges of GOT offsets that we can use for each
3502      range of addressing modes.  */
3503   odd = _frvfdpic_compute_got_alloc_data (&gpinfo.got12,
3504                                           0,
3505                                           odd,
3506                                           16,
3507                                           gpinfo.g.got12,
3508                                           gpinfo.g.fd12,
3509                                           limit,
3510                                           (bfd_vma)1 << (12-1));
3511   odd = _frvfdpic_compute_got_alloc_data (&gpinfo.gotlos,
3512                                           gpinfo.got12.min,
3513                                           odd,
3514                                           gpinfo.got12.max,
3515                                           gpinfo.g.gotlos,
3516                                           gpinfo.g.fdlos,
3517                                           gpinfo.g.fdplt - gpinfo.got12.fdplt,
3518                                           (bfd_vma)1 << (16-1));
3519   odd = _frvfdpic_compute_got_alloc_data (&gpinfo.gothilo,
3520                                           gpinfo.gotlos.min,
3521                                           odd,
3522                                           gpinfo.gotlos.max,
3523                                           gpinfo.g.gothilo,
3524                                           gpinfo.g.fdhilo,
3525                                           gpinfo.g.fdplt - gpinfo.got12.fdplt
3526                                           - gpinfo.gotlos.fdplt,
3527                                           (bfd_vma)1 << (32-1));
3528
3529   /* Now assign (most) GOT offsets.  */
3530   htab_traverse (frvfdpic_relocs_info (info), _frvfdpic_assign_got_entries,
3531                  &gpinfo);
3532
3533   frvfdpic_got_section (info)->size = gpinfo.gothilo.max
3534     - gpinfo.gothilo.min
3535     /* If an odd word is the last word of the GOT, we don't need this
3536        word to be part of the GOT.  */
3537     - (odd + 4 == gpinfo.gothilo.max ? 4 : 0);
3538   if (frvfdpic_got_section (info)->size == 0)
3539     frvfdpic_got_section (info)->flags |= SEC_EXCLUDE;
3540   else if (frvfdpic_got_section (info)->size == 12
3541            && ! elf_hash_table (info)->dynamic_sections_created)
3542     {
3543       frvfdpic_got_section (info)->flags |= SEC_EXCLUDE;
3544       frvfdpic_got_section (info)->size = 0;
3545     }
3546   else
3547     {
3548       frvfdpic_got_section (info)->contents =
3549         (bfd_byte *) bfd_zalloc (dynobj,
3550                                  frvfdpic_got_section (info)->size);
3551       if (frvfdpic_got_section (info)->contents == NULL)
3552         return FALSE;
3553     }
3554   
3555   if (elf_hash_table (info)->dynamic_sections_created)
3556     /* Subtract the number of lzplt entries, since those will generate
3557        relocations in the pltrel section.  */
3558     frvfdpic_gotrel_section (info)->size =
3559       (gpinfo.g.relocs - gpinfo.g.lzplt / 8)
3560       * get_elf_backend_data (output_bfd)->s->sizeof_rel;
3561   else
3562     BFD_ASSERT (gpinfo.g.relocs == 0);
3563   if (frvfdpic_gotrel_section (info)->size == 0)
3564     frvfdpic_gotrel_section (info)->flags |= SEC_EXCLUDE;
3565   else
3566     {
3567       frvfdpic_gotrel_section (info)->contents =
3568         (bfd_byte *) bfd_zalloc (dynobj,
3569                                  frvfdpic_gotrel_section (info)->size);
3570       if (frvfdpic_gotrel_section (info)->contents == NULL)
3571         return FALSE;
3572     }
3573
3574   frvfdpic_gotfixup_section (info)->size = (gpinfo.g.fixups + 1) * 4;
3575   if (frvfdpic_gotfixup_section (info)->size == 0)
3576     frvfdpic_gotfixup_section (info)->flags |= SEC_EXCLUDE;
3577   else
3578     {
3579       frvfdpic_gotfixup_section (info)->contents =
3580         (bfd_byte *) bfd_zalloc (dynobj,
3581                                  frvfdpic_gotfixup_section (info)->size);
3582       if (frvfdpic_gotfixup_section (info)->contents == NULL)
3583         return FALSE;
3584     }
3585   
3586   if (elf_hash_table (info)->dynamic_sections_created)
3587     {
3588       frvfdpic_pltrel_section (info)->size =
3589         gpinfo.g.lzplt / 8 * get_elf_backend_data (output_bfd)->s->sizeof_rel;
3590       if (frvfdpic_pltrel_section (info)->size == 0)
3591         frvfdpic_pltrel_section (info)->flags |= SEC_EXCLUDE;
3592       else
3593         {
3594           frvfdpic_pltrel_section (info)->contents =
3595             (bfd_byte *) bfd_zalloc (dynobj,
3596                                      frvfdpic_pltrel_section (info)->size);
3597           if (frvfdpic_pltrel_section (info)->contents == NULL)
3598             return FALSE;
3599         }
3600     }
3601   
3602   /* Add 4 bytes for every block of at most 65535 lazy PLT entries,
3603      such that there's room for the additional instruction needed to
3604      call the resolver.  Since _frvfdpic_assign_got_entries didn't
3605      account for them, our block size is 4 bytes smaller than the real
3606      block size.  */
3607   if (elf_hash_table (info)->dynamic_sections_created)
3608     {
3609       frvfdpic_plt_section (info)->size = gpinfo.g.lzplt
3610         + ((gpinfo.g.lzplt + (FRVFDPIC_LZPLT_BLOCK_SIZE - 4) - 8)
3611            / (FRVFDPIC_LZPLT_BLOCK_SIZE - 4) * 4);
3612     }
3613
3614   /* Reset it, such that _frvfdpic_assign_plt_entries() can use it to
3615      actually assign lazy PLT entries addresses.  */
3616   gpinfo.g.lzplt = 0;
3617
3618   /* Save information that we're going to need to generate GOT and PLT
3619      entries.  */
3620   frvfdpic_got_initial_offset (info) = -gpinfo.gothilo.min;
3621
3622   if (get_elf_backend_data (output_bfd)->want_got_sym)
3623     elf_hash_table (info)->hgot->root.u.def.value
3624       += frvfdpic_got_initial_offset (info);
3625
3626   if (elf_hash_table (info)->dynamic_sections_created)
3627     frvfdpic_plt_initial_offset (info) =
3628       frvfdpic_plt_section (info)->size;
3629
3630   htab_traverse (frvfdpic_relocs_info (info), _frvfdpic_assign_plt_entries,
3631                  &gpinfo);
3632
3633   /* Allocate the PLT section contents only after
3634      _frvfdpic_assign_plt_entries has a chance to add the size of the
3635      non-lazy PLT entries.  */
3636   if (elf_hash_table (info)->dynamic_sections_created)
3637     {
3638       if (frvfdpic_plt_section (info)->size == 0)
3639         frvfdpic_plt_section (info)->flags |= SEC_EXCLUDE;
3640       else
3641         {
3642           frvfdpic_plt_section (info)->contents =
3643             (bfd_byte *) bfd_zalloc (dynobj,
3644                                      frvfdpic_plt_section (info)->size);
3645           if (frvfdpic_plt_section (info)->contents == NULL)
3646             return FALSE;
3647         }
3648     }
3649
3650   if (elf_hash_table (info)->dynamic_sections_created)
3651     {
3652       if (frvfdpic_got_section (info)->size)
3653         if (!_bfd_elf_add_dynamic_entry (info, DT_PLTGOT, 0))
3654           return FALSE;
3655
3656       if (frvfdpic_pltrel_section (info)->size)
3657         if (!_bfd_elf_add_dynamic_entry (info, DT_PLTRELSZ, 0)
3658             || !_bfd_elf_add_dynamic_entry (info, DT_PLTREL, DT_REL)
3659             || !_bfd_elf_add_dynamic_entry (info, DT_JMPREL, 0))
3660           return FALSE;
3661
3662       if (frvfdpic_gotrel_section (info)->size)
3663         if (!_bfd_elf_add_dynamic_entry (info, DT_REL, 0)
3664             || !_bfd_elf_add_dynamic_entry (info, DT_RELSZ, 0)
3665             || !_bfd_elf_add_dynamic_entry (info, DT_RELENT,
3666                                             sizeof (Elf32_External_Rel)))
3667           return FALSE;
3668     }
3669
3670   return TRUE;
3671 }
3672
3673 static bfd_boolean
3674 elf32_frvfdpic_always_size_sections (bfd *output_bfd,
3675                                      struct bfd_link_info *info)
3676 {
3677   if (!info->relocatable)
3678     {
3679       struct elf_link_hash_entry *h;
3680       asection *sec;
3681
3682       /* Force a PT_GNU_STACK segment to be created.  */
3683       if (! elf_tdata (output_bfd)->stack_flags)
3684         elf_tdata (output_bfd)->stack_flags = PF_R | PF_W | PF_X;
3685
3686       /* Define __stacksize if it's not defined yet.  */
3687       h = elf_link_hash_lookup (elf_hash_table (info), "__stacksize",
3688                                 FALSE, FALSE, FALSE);
3689       if (! h || h->root.type != bfd_link_hash_defined
3690           || h->type != STT_OBJECT
3691           || !(h->elf_link_hash_flags & ELF_LINK_HASH_DEF_REGULAR))
3692         {
3693           struct bfd_link_hash_entry *bh = NULL;
3694
3695           if (!(_bfd_generic_link_add_one_symbol
3696                 (info, output_bfd, "__stacksize",
3697                  BSF_GLOBAL, bfd_abs_section_ptr, DEFAULT_STACK_SIZE,
3698                  (const char *) NULL, FALSE,
3699                  get_elf_backend_data (output_bfd)->collect, &bh)))
3700             return FALSE;
3701
3702           h = (struct elf_link_hash_entry *) bh;
3703           h->elf_link_hash_flags |= ELF_LINK_HASH_DEF_REGULAR;
3704           h->type = STT_OBJECT;
3705         }
3706
3707       /* Create a stack section, and set its alignment.  */
3708       sec = bfd_make_section (output_bfd, ".stack");
3709
3710       if (sec == NULL
3711           || ! bfd_set_section_alignment (output_bfd, sec, 3))
3712         return FALSE;
3713     }
3714
3715   return TRUE;
3716 }
3717
3718 static bfd_boolean
3719 elf32_frvfdpic_modify_segment_map (bfd *output_bfd,
3720                                    struct bfd_link_info *info)
3721 {
3722   struct elf_segment_map *m;
3723
3724   /* objcopy and strip preserve what's already there using
3725      elf32_frvfdpic_copy_private_bfd_data ().  */
3726   if (! info)
3727     return TRUE;
3728
3729   for (m = elf_tdata (output_bfd)->segment_map; m != NULL; m = m->next)
3730     if (m->p_type == PT_GNU_STACK)
3731       break;
3732
3733   if (m)
3734     {
3735       asection *sec = bfd_get_section_by_name (output_bfd, ".stack");
3736       struct elf_link_hash_entry *h;
3737
3738       if (sec)
3739         {
3740           /* Obtain the pointer to the __stacksize symbol.  */
3741           h = elf_link_hash_lookup (elf_hash_table (info), "__stacksize",
3742                                     FALSE, FALSE, FALSE);
3743           while (h->root.type == bfd_link_hash_indirect
3744                  || h->root.type == bfd_link_hash_warning)
3745             h = (struct elf_link_hash_entry *)h->root.u.i.link;
3746           BFD_ASSERT (h->root.type == bfd_link_hash_defined);
3747
3748           /* Set the section size from the symbol value.  We
3749              intentionally ignore the symbol section.  */
3750           if (h->root.type == bfd_link_hash_defined)
3751             sec->size = h->root.u.def.value;
3752           else
3753             sec->size = DEFAULT_STACK_SIZE;
3754
3755           /* Add the stack section to the PT_GNU_STACK segment,
3756              such that its size and alignment requirements make it
3757              to the segment.  */
3758           m->sections[m->count] = sec;
3759           m->count++;
3760         }
3761     }
3762
3763   return TRUE;
3764 }
3765
3766 /* Fill in code and data in dynamic sections.  */
3767
3768 static bfd_boolean
3769 elf32_frv_finish_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
3770                                    struct bfd_link_info *info ATTRIBUTE_UNUSED)
3771 {
3772   /* Nothing to be done for non-FDPIC.  */
3773   return TRUE;
3774 }
3775
3776 static bfd_boolean
3777 elf32_frvfdpic_finish_dynamic_sections (bfd *output_bfd,
3778                                         struct bfd_link_info *info)
3779 {
3780   bfd *dynobj;
3781   asection *sdyn;
3782
3783   dynobj = elf_hash_table (info)->dynobj;
3784
3785   if (frvfdpic_got_section (info))
3786     {
3787       BFD_ASSERT (frvfdpic_gotrel_section (info)->size
3788                   == (frvfdpic_gotrel_section (info)->reloc_count
3789                       * sizeof (Elf32_External_Rel)));
3790
3791       if (frvfdpic_gotfixup_section (info))
3792         {
3793           struct elf_link_hash_entry *hgot = elf_hash_table (info)->hgot;
3794           bfd_vma got_value = hgot->root.u.def.value
3795             + hgot->root.u.def.section->output_section->vma
3796             + hgot->root.u.def.section->output_offset;
3797
3798           _frvfdpic_add_rofixup (output_bfd, frvfdpic_gotfixup_section (info),
3799                                  got_value, 0);
3800
3801           if (frvfdpic_gotfixup_section (info)->size
3802               != (frvfdpic_gotfixup_section (info)->reloc_count * 4))
3803             {
3804               (*_bfd_error_handler)
3805                 ("LINKER BUG: .rofixup section size mismatch");
3806               return FALSE;
3807             }
3808         }
3809     }
3810   if (elf_hash_table (info)->dynamic_sections_created)
3811     {
3812       BFD_ASSERT (frvfdpic_pltrel_section (info)->size
3813                   == (frvfdpic_pltrel_section (info)->reloc_count
3814                       * sizeof (Elf32_External_Rel)));
3815     }
3816
3817   sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
3818
3819   if (elf_hash_table (info)->dynamic_sections_created)
3820     {
3821       Elf32_External_Dyn * dyncon;
3822       Elf32_External_Dyn * dynconend;
3823
3824       BFD_ASSERT (sdyn != NULL);
3825
3826       dyncon = (Elf32_External_Dyn *) sdyn->contents;
3827       dynconend = (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
3828
3829       for (; dyncon < dynconend; dyncon++)
3830         {
3831           Elf_Internal_Dyn dyn;
3832
3833           bfd_elf32_swap_dyn_in (dynobj, dyncon, &dyn);
3834
3835           switch (dyn.d_tag)
3836             {
3837             default:
3838               break;
3839
3840             case DT_PLTGOT:
3841               dyn.d_un.d_ptr = frvfdpic_got_section (info)->output_section->vma
3842                 + frvfdpic_got_section (info)->output_offset
3843                 + frvfdpic_got_initial_offset (info);
3844               bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
3845               break;
3846
3847             case DT_JMPREL:
3848               dyn.d_un.d_ptr = frvfdpic_pltrel_section (info)
3849                 ->output_section->vma
3850                 + frvfdpic_pltrel_section (info)->output_offset;
3851               bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
3852               break;
3853
3854             case DT_PLTRELSZ:
3855               dyn.d_un.d_val = frvfdpic_pltrel_section (info)->size;
3856               bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
3857               break;
3858             }
3859         }
3860     }
3861
3862   return TRUE;
3863 }
3864
3865 /* Adjust a symbol defined by a dynamic object and referenced by a
3866    regular object.  */
3867
3868 static bfd_boolean
3869 elf32_frvfdpic_adjust_dynamic_symbol
3870 (struct bfd_link_info *info ATTRIBUTE_UNUSED,
3871  struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
3872 {
3873   bfd * dynobj;
3874
3875   dynobj = elf_hash_table (info)->dynobj;
3876
3877   /* Make sure we know what is going on here.  */
3878   BFD_ASSERT (dynobj != NULL
3879               && (h->weakdef != NULL
3880                   || ((h->elf_link_hash_flags
3881                        & ELF_LINK_HASH_DEF_DYNAMIC) != 0
3882                       && (h->elf_link_hash_flags
3883                           & ELF_LINK_HASH_REF_REGULAR) != 0
3884                       && (h->elf_link_hash_flags
3885                           & ELF_LINK_HASH_DEF_REGULAR) == 0)));
3886
3887   /* If this is a weak symbol, and there is a real definition, the
3888      processor independent code will have arranged for us to see the
3889      real definition first, and we can just use the same value.  */
3890   if (h->weakdef != NULL)
3891     {
3892       BFD_ASSERT (h->weakdef->root.type == bfd_link_hash_defined
3893                   || h->weakdef->root.type == bfd_link_hash_defweak);
3894       h->root.u.def.section = h->weakdef->root.u.def.section;
3895       h->root.u.def.value = h->weakdef->root.u.def.value;
3896     }
3897
3898   return TRUE;
3899 }
3900
3901 /* Perform any actions needed for dynamic symbols.  */
3902
3903 static bfd_boolean
3904 elf32_frvfdpic_finish_dynamic_symbol
3905 (bfd *output_bfd ATTRIBUTE_UNUSED,
3906  struct bfd_link_info *info ATTRIBUTE_UNUSED,
3907  struct elf_link_hash_entry *h ATTRIBUTE_UNUSED,
3908  Elf_Internal_Sym *sym ATTRIBUTE_UNUSED)
3909 {
3910   return TRUE;
3911 }
3912
3913 /* Decide whether to attempt to turn absptr or lsda encodings in
3914    shared libraries into pcrel within the given input section.  */
3915
3916 static bfd_boolean
3917 frvfdpic_elf_use_relative_eh_frame
3918 (bfd *input_bfd ATTRIBUTE_UNUSED,
3919  struct bfd_link_info *info ATTRIBUTE_UNUSED,
3920  asection *eh_frame_section ATTRIBUTE_UNUSED)
3921 {
3922   /* We can't use PC-relative encodings in FDPIC binaries, in general.  */
3923   return FALSE;
3924 }
3925
3926 /* Adjust the contents of an eh_frame_hdr section before they're output.  */
3927
3928 static bfd_byte
3929 frvfdpic_elf_encode_eh_address (bfd *abfd,
3930                                 struct bfd_link_info *info,
3931                                 asection *osec, bfd_vma offset,
3932                                 asection *loc_sec, bfd_vma loc_offset,
3933                                 bfd_vma *encoded)
3934 {
3935   struct elf_link_hash_entry *h;
3936
3937   h = elf_hash_table (info)->hgot;
3938   BFD_ASSERT (h && h->root.type == bfd_link_hash_defined);
3939
3940   if (! h || (_frvfdpic_osec_to_segment (abfd, osec)
3941               == _frvfdpic_osec_to_segment (abfd, loc_sec->output_section)))
3942     return _bfd_elf_encode_eh_address (abfd, info, osec, offset,
3943                                        loc_sec, loc_offset, encoded);
3944
3945   BFD_ASSERT (_frvfdpic_osec_to_segment (abfd, osec)
3946               == (_frvfdpic_osec_to_segment
3947                   (abfd, h->root.u.def.section->output_section)));
3948
3949   *encoded = osec->vma + offset
3950     - (h->root.u.def.value
3951        + h->root.u.def.section->output_section->vma
3952        + h->root.u.def.section->output_offset);
3953
3954   return DW_EH_PE_datarel | DW_EH_PE_sdata4;
3955 }
3956
3957 /* Look through the relocs for a section during the first phase.
3958
3959    Besides handling virtual table relocs for gc, we have to deal with
3960    all sorts of PIC-related relocations.  We describe below the
3961    general plan on how to handle such relocations, even though we only
3962    collect information at this point, storing them in hash tables for
3963    perusal of later passes.
3964
3965    32 relocations are propagated to the linker output when creating
3966    position-independent output.  LO16 and HI16 relocations are not
3967    supposed to be encountered in this case.
3968
3969    LABEL16 should always be resolvable by the linker, since it's only
3970    used by branches.
3971
3972    LABEL24, on the other hand, is used by calls.  If it turns out that
3973    the target of a call is a dynamic symbol, a PLT entry must be
3974    created for it, which triggers the creation of a private function
3975    descriptor and, unless lazy binding is disabled, a lazy PLT entry.
3976
3977    GPREL relocations require the referenced symbol to be in the same
3978    segment as _gp, but this can only be checked later.
3979
3980    All GOT, GOTOFF and FUNCDESC relocations require a .got section to
3981    exist.  LABEL24 might as well, since it may require a PLT entry,
3982    that will require a got.
3983
3984    Non-FUNCDESC GOT relocations require a GOT entry to be created
3985    regardless of whether the symbol is dynamic.  However, since a
3986    global symbol that turns out to not be exported may have the same
3987    address of a non-dynamic symbol, we don't assign GOT entries at
3988    this point, such that we can share them in this case.  A relocation
3989    for the GOT entry always has to be created, be it to offset a
3990    private symbol by the section load address, be it to get the symbol
3991    resolved dynamically.
3992
3993    FUNCDESC GOT relocations require a GOT entry to be created, and
3994    handled as if a FUNCDESC relocation was applied to the GOT entry in
3995    an object file.
3996
3997    FUNCDESC relocations referencing a symbol that turns out to NOT be
3998    dynamic cause a private function descriptor to be created.  The
3999    FUNCDESC relocation then decays to a 32 relocation that points at
4000    the private descriptor.  If the symbol is dynamic, the FUNCDESC
4001    relocation is propagated to the linker output, such that the
4002    dynamic linker creates the canonical descriptor, pointing to the
4003    dynamically-resolved definition of the function.
4004
4005    Non-FUNCDESC GOTOFF relocations must always refer to non-dynamic
4006    symbols that are assigned to the same segment as the GOT, but we
4007    can only check this later, after we know the complete set of
4008    symbols defined and/or exported.
4009
4010    FUNCDESC GOTOFF relocations require a function descriptor to be
4011    created and, unless lazy binding is disabled or the symbol is not
4012    dynamic, a lazy PLT entry.  Since we can't tell at this point
4013    whether a symbol is going to be dynamic, we have to decide later
4014    whether to create a lazy PLT entry or bind the descriptor directly
4015    to the private function.
4016
4017    FUNCDESC_VALUE relocations are not supposed to be present in object
4018    files, but they may very well be simply propagated to the linker
4019    output, since they have no side effect.
4020
4021
4022    A function descriptor always requires a FUNCDESC_VALUE relocation.
4023    Whether it's in .plt.rel or not depends on whether lazy binding is
4024    enabled and on whether the referenced symbol is dynamic.
4025
4026    The existence of a lazy PLT requires the resolverStub lazy PLT
4027    entry to be present.
4028
4029
4030    As for assignment of GOT, PLT and lazy PLT entries, and private
4031    descriptors, we might do them all sequentially, but we can do
4032    better than that.  For example, we can place GOT entries and
4033    private function descriptors referenced using 12-bit operands
4034    closer to the PIC register value, such that these relocations don't
4035    overflow.  Those that are only referenced with LO16 relocations
4036    could come next, but we may as well place PLT-required function
4037    descriptors in the 12-bit range to make them shorter.  Symbols
4038    referenced with LO16/HI16 may come next, but we may place
4039    additional function descriptors in the 16-bit range if we can
4040    reliably tell that we've already placed entries that are ever
4041    referenced with only LO16.  PLT entries are therefore generated as
4042    small as possible, while not introducing relocation overflows in
4043    GOT or FUNCDESC_GOTOFF relocations.  Lazy PLT entries could be
4044    generated before or after PLT entries, but not intermingled with
4045    them, such that we can have more lazy PLT entries in range for a
4046    branch to the resolverStub.  The resolverStub should be emitted at
4047    the most distant location from the first lazy PLT entry such that
4048    it's still in range for a branch, or closer, if there isn't a need
4049    for so many lazy PLT entries.  Additional lazy PLT entries may be
4050    emitted after the resolverStub, as long as branches are still in
4051    range.  If the branch goes out of range, longer lazy PLT entries
4052    are emitted.
4053
4054    We could further optimize PLT and lazy PLT entries by giving them
4055    priority in assignment to closer-to-gr17 locations depending on the
4056    number of occurrences of references to them (assuming a function
4057    that's called more often is more important for performance, so its
4058    PLT entry should be faster), or taking hints from the compiler.
4059    Given infinite time and money... :-)  */
4060
4061 static bfd_boolean
4062 elf32_frv_check_relocs (abfd, info, sec, relocs)
4063      bfd *abfd;
4064      struct bfd_link_info *info;
4065      asection *sec;
4066      const Elf_Internal_Rela *relocs;
4067 {
4068   Elf_Internal_Shdr *symtab_hdr;
4069   struct elf_link_hash_entry **sym_hashes, **sym_hashes_end;
4070   const Elf_Internal_Rela *rel;
4071   const Elf_Internal_Rela *rel_end;
4072   bfd *dynobj;
4073   struct frvfdpic_relocs_info *picrel;
4074
4075   if (info->relocatable)
4076     return TRUE;
4077
4078   symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
4079   sym_hashes = elf_sym_hashes (abfd);
4080   sym_hashes_end = sym_hashes + symtab_hdr->sh_size/sizeof(Elf32_External_Sym);
4081   if (!elf_bad_symtab (abfd))
4082     sym_hashes_end -= symtab_hdr->sh_info;
4083
4084   dynobj = elf_hash_table (info)->dynobj;
4085   rel_end = relocs + sec->reloc_count;
4086   for (rel = relocs; rel < rel_end; rel++)
4087     {
4088       struct elf_link_hash_entry *h;
4089       unsigned long r_symndx;
4090
4091       r_symndx = ELF32_R_SYM (rel->r_info);
4092       if (r_symndx < symtab_hdr->sh_info)
4093         h = NULL;
4094       else
4095         h = sym_hashes[r_symndx - symtab_hdr->sh_info];
4096
4097       switch (ELF32_R_TYPE (rel->r_info))
4098         {
4099         case R_FRV_GOT12:
4100         case R_FRV_GOTHI:
4101         case R_FRV_GOTLO:
4102         case R_FRV_FUNCDESC_GOT12:
4103         case R_FRV_FUNCDESC_GOTHI:
4104         case R_FRV_FUNCDESC_GOTLO:
4105         case R_FRV_GOTOFF12:
4106         case R_FRV_GOTOFFHI:
4107         case R_FRV_GOTOFFLO:
4108         case R_FRV_FUNCDESC_GOTOFF12:
4109         case R_FRV_FUNCDESC_GOTOFFHI:
4110         case R_FRV_FUNCDESC_GOTOFFLO:
4111         case R_FRV_FUNCDESC:
4112         case R_FRV_FUNCDESC_VALUE:
4113           if (! IS_FDPIC (abfd))
4114             goto bad_reloc;
4115           /* Fall through.  */
4116         case R_FRV_GPREL12:
4117         case R_FRV_GPRELU12:
4118         case R_FRV_GPRELHI:
4119         case R_FRV_GPRELLO:
4120         case R_FRV_LABEL24:
4121         case R_FRV_32:
4122           if (! dynobj)
4123             {
4124               elf_hash_table (info)->dynobj = dynobj = abfd;
4125               if (! _frv_create_got_section (abfd, info))
4126                 return FALSE;
4127             }
4128           if (! IS_FDPIC (abfd))
4129             {
4130               picrel = NULL;
4131               break;
4132             }
4133           if (h != NULL)
4134             {
4135               if (h->dynindx == -1)
4136                 switch (ELF_ST_VISIBILITY (h->other))
4137                   {
4138                   case STV_INTERNAL:
4139                   case STV_HIDDEN:
4140                     break;
4141                   default:
4142                     bfd_elf_link_record_dynamic_symbol (info, h);
4143                     break;
4144                   }
4145               picrel
4146                 = frvfdpic_relocs_info_for_global (frvfdpic_relocs_info (info),
4147                                                    abfd, h,
4148                                                    rel->r_addend, INSERT);
4149             }
4150           else
4151             picrel = frvfdpic_relocs_info_for_local (frvfdpic_relocs_info
4152                                                      (info), abfd, r_symndx,
4153                                                      rel->r_addend, INSERT);
4154           if (! picrel)
4155             return FALSE;
4156           break;
4157
4158         default:
4159           picrel = NULL;
4160           break;
4161         }
4162       
4163       switch (ELF32_R_TYPE (rel->r_info))
4164         {
4165         case R_FRV_LABEL24:
4166           if (IS_FDPIC (abfd))
4167             picrel->call = 1;
4168           break;
4169                 
4170         case R_FRV_FUNCDESC_VALUE:
4171           picrel->relocsfdv++;
4172           if (bfd_get_section_flags (abfd, sec) & SEC_ALLOC)
4173             picrel->relocs32--;
4174           /* Fall through.  */
4175
4176         case R_FRV_32:
4177           if (! IS_FDPIC (abfd))
4178             break;
4179
4180           picrel->sym = 1;
4181           if (bfd_get_section_flags (abfd, sec) & SEC_ALLOC)
4182             picrel->relocs32++;
4183           break;
4184             
4185         case R_FRV_GOT12:
4186           picrel->got12 = 1;
4187           break;
4188             
4189         case R_FRV_GOTHI:
4190         case R_FRV_GOTLO:
4191           picrel->gothilo = 1;
4192           break;
4193
4194         case R_FRV_FUNCDESC_GOT12:
4195           picrel->fdgot12 = 1;
4196           break;
4197             
4198         case R_FRV_FUNCDESC_GOTHI:
4199         case R_FRV_FUNCDESC_GOTLO:
4200           picrel->fdgothilo = 1;
4201           break;
4202             
4203         case R_FRV_GOTOFF12:
4204         case R_FRV_GOTOFFHI:
4205         case R_FRV_GOTOFFLO:
4206           picrel->gotoff = 1;
4207           break;
4208             
4209         case R_FRV_FUNCDESC_GOTOFF12:
4210           picrel->fdgoff12 = 1;
4211           break;
4212             
4213         case R_FRV_FUNCDESC_GOTOFFHI:
4214         case R_FRV_FUNCDESC_GOTOFFLO:
4215           picrel->fdgoffhilo = 1;
4216           break;
4217             
4218         case R_FRV_FUNCDESC:
4219           picrel->fd = 1;
4220           picrel->relocsfd++;
4221           break;
4222           
4223         /* This relocation describes the C++ object vtable hierarchy.
4224            Reconstruct it for later use during GC.  */
4225         case R_FRV_GNU_VTINHERIT:
4226           if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
4227             return FALSE;
4228           break;
4229
4230         /* This relocation describes which C++ vtable entries are actually
4231            used.  Record for later use during GC.  */
4232         case R_FRV_GNU_VTENTRY:
4233           if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
4234             return FALSE;
4235           break;
4236
4237         case R_FRV_LABEL16:
4238         case R_FRV_LO16:
4239         case R_FRV_HI16:
4240         case R_FRV_GPREL12:
4241         case R_FRV_GPRELU12:
4242         case R_FRV_GPREL32:
4243         case R_FRV_GPRELHI:
4244         case R_FRV_GPRELLO:
4245           break;
4246
4247         default:
4248         bad_reloc:
4249           (*_bfd_error_handler)
4250             (_("%s: unsupported relocation type %i"),
4251              bfd_archive_filename (abfd), ELF32_R_TYPE (rel->r_info));
4252           return FALSE;
4253         }
4254     }
4255
4256   return TRUE;
4257 }
4258
4259 \f
4260 /* Return the machine subcode from the ELF e_flags header.  */
4261
4262 static int
4263 elf32_frv_machine (abfd)
4264      bfd *abfd;
4265 {
4266   switch (elf_elfheader (abfd)->e_flags & EF_FRV_CPU_MASK)
4267     {
4268     default:                break;
4269     case EF_FRV_CPU_FR550:  return bfd_mach_fr550;
4270     case EF_FRV_CPU_FR500:  return bfd_mach_fr500;
4271     case EF_FRV_CPU_FR450:  return bfd_mach_fr450;
4272     case EF_FRV_CPU_FR405:  return bfd_mach_fr400;
4273     case EF_FRV_CPU_FR400:  return bfd_mach_fr400;
4274     case EF_FRV_CPU_FR300:  return bfd_mach_fr300;
4275     case EF_FRV_CPU_SIMPLE: return bfd_mach_frvsimple;
4276     case EF_FRV_CPU_TOMCAT: return bfd_mach_frvtomcat;
4277     }
4278
4279   return bfd_mach_frv;
4280 }
4281
4282 /* Set the right machine number for a FRV ELF file.  */
4283
4284 static bfd_boolean
4285 elf32_frv_object_p (abfd)
4286      bfd *abfd;
4287 {
4288   bfd_default_set_arch_mach (abfd, bfd_arch_frv, elf32_frv_machine (abfd));
4289   return (((elf_elfheader (abfd)->e_flags & EF_FRV_FDPIC) != 0)
4290           == (IS_FDPIC (abfd)));
4291 }
4292 \f
4293 /* Function to set the ELF flag bits.  */
4294
4295 static bfd_boolean
4296 frv_elf_set_private_flags (abfd, flags)
4297      bfd *abfd;
4298      flagword flags;
4299 {
4300   elf_elfheader (abfd)->e_flags = flags;
4301   elf_flags_init (abfd) = TRUE;
4302   return TRUE;
4303 }
4304
4305 /* Copy backend specific data from one object module to another.  */
4306
4307 static bfd_boolean
4308 frv_elf_copy_private_bfd_data (ibfd, obfd)
4309      bfd *ibfd;
4310      bfd *obfd;
4311 {
4312   if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
4313       || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
4314     return TRUE;
4315
4316   BFD_ASSERT (!elf_flags_init (obfd)
4317               || elf_elfheader (obfd)->e_flags == elf_elfheader (ibfd)->e_flags);
4318
4319   elf_elfheader (obfd)->e_flags = elf_elfheader (ibfd)->e_flags;
4320   elf_flags_init (obfd) = TRUE;
4321   return TRUE;
4322 }
4323
4324 /* Return true if the architecture described by elf header flag
4325    EXTENSION is an extension of the architecture described by BASE.  */
4326
4327 static bfd_boolean
4328 frv_elf_arch_extension_p (flagword base, flagword extension)
4329 {
4330   if (base == extension)
4331     return TRUE;
4332
4333   /* CPU_GENERIC code can be merged with code for a specific
4334      architecture, in which case the result is marked as being
4335      for the specific architecture.  Everything is therefore
4336      an extension of CPU_GENERIC.  */
4337   if (base == EF_FRV_CPU_GENERIC)
4338     return TRUE;
4339
4340   if (extension == EF_FRV_CPU_FR450)
4341     if (base == EF_FRV_CPU_FR400 || base == EF_FRV_CPU_FR405)
4342       return TRUE;
4343
4344   if (extension == EF_FRV_CPU_FR405)
4345     if (base == EF_FRV_CPU_FR400)
4346       return TRUE;
4347
4348   return FALSE;
4349 }
4350
4351 static bfd_boolean
4352 elf32_frvfdpic_copy_private_bfd_data (bfd *ibfd, bfd *obfd)
4353 {
4354   unsigned i;
4355
4356   if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
4357       || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
4358     return TRUE;
4359
4360   if (! frv_elf_copy_private_bfd_data (ibfd, obfd))
4361     return FALSE;
4362
4363   if (! elf_tdata (ibfd) || ! elf_tdata (ibfd)->phdr
4364       || ! elf_tdata (obfd) || ! elf_tdata (obfd)->phdr)
4365     return TRUE;
4366
4367   /* Copy the stack size.  */
4368   for (i = 0; i < elf_elfheader (ibfd)->e_phnum; i++)
4369     if (elf_tdata (ibfd)->phdr[i].p_type == PT_GNU_STACK)
4370       {
4371         Elf_Internal_Phdr *iphdr = &elf_tdata (ibfd)->phdr[i];
4372
4373         for (i = 0; i < elf_elfheader (obfd)->e_phnum; i++)
4374           if (elf_tdata (obfd)->phdr[i].p_type == PT_GNU_STACK)
4375             {
4376               memcpy (&elf_tdata (obfd)->phdr[i], iphdr, sizeof (*iphdr));
4377
4378               /* Rewrite the phdrs, since we're only called after they
4379                  were first written.  */
4380               if (bfd_seek (obfd, (bfd_signed_vma) get_elf_backend_data (obfd)
4381                             ->s->sizeof_ehdr, SEEK_SET) != 0
4382                   || get_elf_backend_data (obfd)->s
4383                   ->write_out_phdrs (obfd, elf_tdata (obfd)->phdr,
4384                                      elf_elfheader (obfd)->e_phnum) != 0)
4385                 return FALSE;
4386               break;
4387             }
4388
4389         break;
4390       }
4391
4392   return TRUE;
4393 }
4394
4395 /* Merge backend specific data from an object file to the output
4396    object file when linking.  */
4397
4398 static bfd_boolean
4399 frv_elf_merge_private_bfd_data (ibfd, obfd)
4400      bfd *ibfd;
4401      bfd *obfd;
4402 {
4403   flagword old_flags, old_partial;
4404   flagword new_flags, new_partial;
4405   bfd_boolean error = FALSE;
4406   char new_opt[80];
4407   char old_opt[80];
4408
4409   new_opt[0] = old_opt[0] = '\0';
4410   new_flags = elf_elfheader (ibfd)->e_flags;
4411   old_flags = elf_elfheader (obfd)->e_flags;
4412
4413   if (new_flags & EF_FRV_FDPIC)
4414     new_flags &= ~EF_FRV_PIC;
4415
4416 #ifdef DEBUG
4417   (*_bfd_error_handler) ("old_flags = 0x%.8lx, new_flags = 0x%.8lx, init = %s, filename = %s",
4418                          old_flags, new_flags, elf_flags_init (obfd) ? "yes" : "no",
4419                          bfd_get_filename (ibfd));
4420 #endif
4421
4422   if (!elf_flags_init (obfd))                   /* First call, no flags set.  */
4423     {
4424       elf_flags_init (obfd) = TRUE;
4425       old_flags = new_flags;
4426     }
4427
4428   else if (new_flags == old_flags)              /* Compatible flags are ok.  */
4429     ;
4430
4431   else                                          /* Possibly incompatible flags.  */
4432     {
4433       /* Warn if different # of gprs are used.  Note, 0 means nothing is
4434          said about the size of gprs.  */
4435       new_partial = (new_flags & EF_FRV_GPR_MASK);
4436       old_partial = (old_flags & EF_FRV_GPR_MASK);
4437       if (new_partial == old_partial)
4438         ;
4439
4440       else if (new_partial == 0)
4441         ;
4442
4443       else if (old_partial == 0)
4444         old_flags |= new_partial;
4445
4446       else
4447         {
4448           switch (new_partial)
4449             {
4450             default:            strcat (new_opt, " -mgpr-??"); break;
4451             case EF_FRV_GPR_32: strcat (new_opt, " -mgpr-32"); break;
4452             case EF_FRV_GPR_64: strcat (new_opt, " -mgpr-64"); break;
4453             }
4454
4455           switch (old_partial)
4456             {
4457             default:            strcat (old_opt, " -mgpr-??"); break;
4458             case EF_FRV_GPR_32: strcat (old_opt, " -mgpr-32"); break;
4459             case EF_FRV_GPR_64: strcat (old_opt, " -mgpr-64"); break;
4460             }
4461         }
4462
4463       /* Warn if different # of fprs are used.  Note, 0 means nothing is
4464          said about the size of fprs.  */
4465       new_partial = (new_flags & EF_FRV_FPR_MASK);
4466       old_partial = (old_flags & EF_FRV_FPR_MASK);
4467       if (new_partial == old_partial)
4468         ;
4469
4470       else if (new_partial == 0)
4471         ;
4472
4473       else if (old_partial == 0)
4474         old_flags |= new_partial;
4475
4476       else
4477         {
4478           switch (new_partial)
4479             {
4480             default:              strcat (new_opt, " -mfpr-?");      break;
4481             case EF_FRV_FPR_32:   strcat (new_opt, " -mfpr-32");     break;
4482             case EF_FRV_FPR_64:   strcat (new_opt, " -mfpr-64");     break;
4483             case EF_FRV_FPR_NONE: strcat (new_opt, " -msoft-float"); break;
4484             }
4485
4486           switch (old_partial)
4487             {
4488             default:              strcat (old_opt, " -mfpr-?");      break;
4489             case EF_FRV_FPR_32:   strcat (old_opt, " -mfpr-32");     break;
4490             case EF_FRV_FPR_64:   strcat (old_opt, " -mfpr-64");     break;
4491             case EF_FRV_FPR_NONE: strcat (old_opt, " -msoft-float"); break;
4492             }
4493         }
4494
4495       /* Warn if different dword support was used.  Note, 0 means nothing is
4496          said about the dword support.  */
4497       new_partial = (new_flags & EF_FRV_DWORD_MASK);
4498       old_partial = (old_flags & EF_FRV_DWORD_MASK);
4499       if (new_partial == old_partial)
4500         ;
4501
4502       else if (new_partial == 0)
4503         ;
4504
4505       else if (old_partial == 0)
4506         old_flags |= new_partial;
4507
4508       else
4509         {
4510           switch (new_partial)
4511             {
4512             default:               strcat (new_opt, " -mdword-?");  break;
4513             case EF_FRV_DWORD_YES: strcat (new_opt, " -mdword");    break;
4514             case EF_FRV_DWORD_NO:  strcat (new_opt, " -mno-dword"); break;
4515             }
4516
4517           switch (old_partial)
4518             {
4519             default:               strcat (old_opt, " -mdword-?");  break;
4520             case EF_FRV_DWORD_YES: strcat (old_opt, " -mdword");    break;
4521             case EF_FRV_DWORD_NO:  strcat (old_opt, " -mno-dword"); break;
4522             }
4523         }
4524
4525       /* Or in flags that accumulate (ie, if one module uses it, mark that the
4526          feature is used.  */
4527       old_flags |= new_flags & (EF_FRV_DOUBLE
4528                                 | EF_FRV_MEDIA
4529                                 | EF_FRV_MULADD
4530                                 | EF_FRV_NON_PIC_RELOCS);
4531
4532       /* If any module was compiled without -G0, clear the G0 bit.  */
4533       old_flags = ((old_flags & ~ EF_FRV_G0)
4534                    | (old_flags & new_flags & EF_FRV_G0));
4535
4536       /* If any module was compiled without -mnopack, clear the mnopack bit.  */
4537       old_flags = ((old_flags & ~ EF_FRV_NOPACK)
4538                    | (old_flags & new_flags & EF_FRV_NOPACK));
4539
4540       /* We don't have to do anything if the pic flags are the same, or the new
4541          module(s) were compiled with -mlibrary-pic.  */
4542       new_partial = (new_flags & EF_FRV_PIC_FLAGS);
4543       old_partial = (old_flags & EF_FRV_PIC_FLAGS);
4544       if ((new_partial == old_partial) || ((new_partial & EF_FRV_LIBPIC) != 0))
4545         ;
4546
4547       /* If the old module(s) were compiled with -mlibrary-pic, copy in the pic
4548          flags if any from the new module.  */
4549       else if ((old_partial & EF_FRV_LIBPIC) != 0)
4550         old_flags = (old_flags & ~ EF_FRV_PIC_FLAGS) | new_partial;
4551
4552       /* If we have mixtures of -fpic and -fPIC, or in both bits.  */
4553       else if (new_partial != 0 && old_partial != 0)
4554         old_flags |= new_partial;
4555
4556       /* One module was compiled for pic and the other was not, see if we have
4557          had any relocations that are not pic-safe.  */
4558       else
4559         {
4560           if ((old_flags & EF_FRV_NON_PIC_RELOCS) == 0)
4561             old_flags |= new_partial;
4562           else
4563             {
4564               old_flags &= ~ EF_FRV_PIC_FLAGS;
4565 #ifndef FRV_NO_PIC_ERROR
4566               error = TRUE;
4567               (*_bfd_error_handler)
4568                 (_("%s: compiled with %s and linked with modules that use non-pic relocations"),
4569                  bfd_get_filename (ibfd),
4570                  (new_flags & EF_FRV_BIGPIC) ? "-fPIC" : "-fpic");
4571 #endif
4572             }
4573         }
4574
4575       /* Warn if different cpu is used (allow a specific cpu to override
4576          the generic cpu).  */
4577       new_partial = (new_flags & EF_FRV_CPU_MASK);
4578       old_partial = (old_flags & EF_FRV_CPU_MASK);
4579       if (frv_elf_arch_extension_p (new_partial, old_partial))
4580         ;
4581
4582       else if (frv_elf_arch_extension_p (old_partial, new_partial))
4583         old_flags = (old_flags & ~EF_FRV_CPU_MASK) | new_partial;
4584
4585       else
4586         {
4587           switch (new_partial)
4588             {
4589             default:                 strcat (new_opt, " -mcpu=?");      break;
4590             case EF_FRV_CPU_GENERIC: strcat (new_opt, " -mcpu=frv");    break;
4591             case EF_FRV_CPU_SIMPLE:  strcat (new_opt, " -mcpu=simple"); break;
4592             case EF_FRV_CPU_FR550:   strcat (new_opt, " -mcpu=fr550");  break;
4593             case EF_FRV_CPU_FR500:   strcat (new_opt, " -mcpu=fr500");  break;
4594             case EF_FRV_CPU_FR450:   strcat (new_opt, " -mcpu=fr450");  break;
4595             case EF_FRV_CPU_FR405:   strcat (new_opt, " -mcpu=fr405");  break;
4596             case EF_FRV_CPU_FR400:   strcat (new_opt, " -mcpu=fr400");  break;
4597             case EF_FRV_CPU_FR300:   strcat (new_opt, " -mcpu=fr300");  break;
4598             case EF_FRV_CPU_TOMCAT:  strcat (new_opt, " -mcpu=tomcat"); break;
4599             }
4600
4601           switch (old_partial)
4602             {
4603             default:                 strcat (old_opt, " -mcpu=?");      break;
4604             case EF_FRV_CPU_GENERIC: strcat (old_opt, " -mcpu=frv");    break;
4605             case EF_FRV_CPU_SIMPLE:  strcat (old_opt, " -mcpu=simple"); break;
4606             case EF_FRV_CPU_FR550:   strcat (old_opt, " -mcpu=fr550");  break;
4607             case EF_FRV_CPU_FR500:   strcat (old_opt, " -mcpu=fr500");  break;
4608             case EF_FRV_CPU_FR450:   strcat (old_opt, " -mcpu=fr450");  break;
4609             case EF_FRV_CPU_FR405:   strcat (old_opt, " -mcpu=fr405");  break;
4610             case EF_FRV_CPU_FR400:   strcat (old_opt, " -mcpu=fr400");  break;
4611             case EF_FRV_CPU_FR300:   strcat (old_opt, " -mcpu=fr300");  break;
4612             case EF_FRV_CPU_TOMCAT:  strcat (old_opt, " -mcpu=tomcat"); break;
4613             }
4614         }
4615
4616       /* Print out any mismatches from above.  */
4617       if (new_opt[0])
4618         {
4619           error = TRUE;
4620           (*_bfd_error_handler)
4621             (_("%s: compiled with %s and linked with modules compiled with %s"),
4622              bfd_get_filename (ibfd), new_opt, old_opt);
4623         }
4624
4625       /* Warn about any other mismatches */
4626       new_partial = (new_flags & ~ EF_FRV_ALL_FLAGS);
4627       old_partial = (old_flags & ~ EF_FRV_ALL_FLAGS);
4628       if (new_partial != old_partial)
4629         {
4630           old_flags |= new_partial;
4631           error = TRUE;
4632           (*_bfd_error_handler)
4633             (_("%s: uses different unknown e_flags (0x%lx) fields than previous modules (0x%lx)"),
4634              bfd_get_filename (ibfd), (long)new_partial, (long)old_partial);
4635         }
4636     }
4637
4638   /* If the cpu is -mcpu=simple, then set the -mnopack bit.  */
4639   if ((old_flags & EF_FRV_CPU_MASK) == EF_FRV_CPU_SIMPLE)
4640     old_flags |= EF_FRV_NOPACK;
4641
4642   /* Update the old flags now with changes made above.  */
4643   old_partial = elf_elfheader (obfd)->e_flags & EF_FRV_CPU_MASK;
4644   elf_elfheader (obfd)->e_flags = old_flags;
4645   if (old_partial != (old_flags & EF_FRV_CPU_MASK))
4646     bfd_default_set_arch_mach (obfd, bfd_arch_frv, elf32_frv_machine (obfd));
4647
4648   if (((new_flags & EF_FRV_FDPIC) == 0)
4649       != (! IS_FDPIC (ibfd)))
4650     {
4651       error = TRUE;
4652       if (IS_FDPIC (obfd))
4653         (*_bfd_error_handler)
4654           (_("%s: cannot link non-fdpic object file into fdpic executable"),
4655            bfd_get_filename (ibfd));
4656       else
4657         (*_bfd_error_handler)
4658           (_("%s: cannot link fdpic object file into non-fdpic executable"),
4659            bfd_get_filename (ibfd));
4660     }
4661
4662   if (error)
4663     bfd_set_error (bfd_error_bad_value);
4664
4665   return !error;
4666 }
4667
4668 \f
4669 bfd_boolean
4670 frv_elf_print_private_bfd_data (abfd, ptr)
4671      bfd *abfd;
4672      PTR ptr;
4673 {
4674   FILE *file = (FILE *) ptr;
4675   flagword flags;
4676
4677   BFD_ASSERT (abfd != NULL && ptr != NULL);
4678
4679   /* Print normal ELF private data.  */
4680   _bfd_elf_print_private_bfd_data (abfd, ptr);
4681
4682   flags = elf_elfheader (abfd)->e_flags;
4683   fprintf (file, _("private flags = 0x%lx:"), (long)flags);
4684
4685   switch (flags & EF_FRV_CPU_MASK)
4686     {
4687     default:                                                    break;
4688     case EF_FRV_CPU_SIMPLE: fprintf (file, " -mcpu=simple");    break;
4689     case EF_FRV_CPU_FR550:  fprintf (file, " -mcpu=fr550");     break;
4690     case EF_FRV_CPU_FR500:  fprintf (file, " -mcpu=fr500");     break;
4691     case EF_FRV_CPU_FR450:  fprintf (file, " -mcpu=fr450");     break;
4692     case EF_FRV_CPU_FR405:  fprintf (file, " -mcpu=fr405");     break;
4693     case EF_FRV_CPU_FR400:  fprintf (file, " -mcpu=fr400");     break;
4694     case EF_FRV_CPU_FR300:  fprintf (file, " -mcpu=fr300");     break;
4695     case EF_FRV_CPU_TOMCAT: fprintf (file, " -mcpu=tomcat");    break;
4696     }
4697
4698   switch (flags & EF_FRV_GPR_MASK)
4699     {
4700     default:                                                    break;
4701     case EF_FRV_GPR_32: fprintf (file, " -mgpr-32");            break;
4702     case EF_FRV_GPR_64: fprintf (file, " -mgpr-64");            break;
4703     }
4704
4705   switch (flags & EF_FRV_FPR_MASK)
4706     {
4707     default:                                                    break;
4708     case EF_FRV_FPR_32:   fprintf (file, " -mfpr-32");          break;
4709     case EF_FRV_FPR_64:   fprintf (file, " -mfpr-64");          break;
4710     case EF_FRV_FPR_NONE: fprintf (file, " -msoft-float");      break;
4711     }
4712
4713   switch (flags & EF_FRV_DWORD_MASK)
4714     {
4715     default:                                                    break;
4716     case EF_FRV_DWORD_YES: fprintf (file, " -mdword");          break;
4717     case EF_FRV_DWORD_NO:  fprintf (file, " -mno-dword");       break;
4718     }
4719
4720   if (flags & EF_FRV_DOUBLE)
4721     fprintf (file, " -mdouble");
4722
4723   if (flags & EF_FRV_MEDIA)
4724     fprintf (file, " -mmedia");
4725
4726   if (flags & EF_FRV_MULADD)
4727     fprintf (file, " -mmuladd");
4728
4729   if (flags & EF_FRV_PIC)
4730     fprintf (file, " -fpic");
4731
4732   if (flags & EF_FRV_BIGPIC)
4733     fprintf (file, " -fPIC");
4734
4735   if (flags & EF_FRV_LIBPIC)
4736     fprintf (file, " -mlibrary-pic");
4737
4738   if (flags & EF_FRV_FDPIC)
4739     fprintf (file, " -mfdpic");
4740   
4741   if (flags & EF_FRV_NON_PIC_RELOCS)
4742     fprintf (file, " non-pic relocations");
4743
4744   if (flags & EF_FRV_G0)
4745     fprintf (file, " -G0");
4746
4747   fputc ('\n', file);
4748   return TRUE;
4749 }
4750
4751 \f
4752 #define ELF_ARCH                bfd_arch_frv
4753 #define ELF_MACHINE_CODE        EM_CYGNUS_FRV
4754 #define ELF_MAXPAGESIZE         0x1000
4755
4756 #define TARGET_BIG_SYM          bfd_elf32_frv_vec
4757 #define TARGET_BIG_NAME         "elf32-frv"
4758
4759 #define elf_info_to_howto                       frv_info_to_howto_rela
4760 #define elf_backend_relocate_section            elf32_frv_relocate_section
4761 #define elf_backend_gc_mark_hook                elf32_frv_gc_mark_hook
4762 #define elf_backend_gc_sweep_hook               elf32_frv_gc_sweep_hook
4763 #define elf_backend_check_relocs                elf32_frv_check_relocs
4764 #define elf_backend_object_p                    elf32_frv_object_p
4765 #define elf_backend_add_symbol_hook             elf32_frv_add_symbol_hook
4766
4767 #define elf_backend_can_gc_sections             1
4768 #define elf_backend_rela_normal                 1
4769
4770 #define bfd_elf32_bfd_reloc_type_lookup         frv_reloc_type_lookup
4771 #define bfd_elf32_bfd_set_private_flags         frv_elf_set_private_flags
4772 #define bfd_elf32_bfd_copy_private_bfd_data     frv_elf_copy_private_bfd_data
4773 #define bfd_elf32_bfd_merge_private_bfd_data    frv_elf_merge_private_bfd_data
4774 #define bfd_elf32_bfd_print_private_bfd_data    frv_elf_print_private_bfd_data
4775
4776 #define elf_backend_want_got_sym        1
4777 #define elf_backend_got_header_size     0
4778 #define elf_backend_want_got_plt        0
4779 #define elf_backend_plt_readonly        1
4780 #define elf_backend_want_plt_sym        0
4781 #define elf_backend_plt_header_size     0
4782
4783 #define elf_backend_finish_dynamic_sections \
4784                 elf32_frv_finish_dynamic_sections
4785
4786 #include "elf32-target.h"
4787
4788 #undef ELF_MAXPAGESIZE
4789 #define ELF_MAXPAGESIZE         0x4000
4790
4791 #undef TARGET_BIG_SYM
4792 #define TARGET_BIG_SYM          bfd_elf32_frvfdpic_vec
4793 #undef TARGET_BIG_NAME
4794 #define TARGET_BIG_NAME         "elf32-frvfdpic"
4795 #undef  elf32_bed
4796 #define elf32_bed               elf32_frvfdpic_bed
4797
4798 #undef elf_info_to_howto_rel
4799 #define elf_info_to_howto_rel   frvfdpic_info_to_howto_rel
4800
4801 #undef bfd_elf32_bfd_link_hash_table_create
4802 #define bfd_elf32_bfd_link_hash_table_create \
4803                 frvfdpic_elf_link_hash_table_create
4804 #undef elf_backend_always_size_sections
4805 #define elf_backend_always_size_sections \
4806                 elf32_frvfdpic_always_size_sections
4807 #undef elf_backend_modify_segment_map
4808 #define elf_backend_modify_segment_map \
4809                 elf32_frvfdpic_modify_segment_map
4810 #undef bfd_elf32_bfd_copy_private_bfd_data
4811 #define bfd_elf32_bfd_copy_private_bfd_data \
4812                 elf32_frvfdpic_copy_private_bfd_data
4813
4814 #undef elf_backend_create_dynamic_sections
4815 #define elf_backend_create_dynamic_sections \
4816                 elf32_frvfdpic_create_dynamic_sections
4817 #undef elf_backend_adjust_dynamic_symbol
4818 #define elf_backend_adjust_dynamic_symbol \
4819                 elf32_frvfdpic_adjust_dynamic_symbol
4820 #undef elf_backend_size_dynamic_sections
4821 #define elf_backend_size_dynamic_sections \
4822                 elf32_frvfdpic_size_dynamic_sections
4823 #undef elf_backend_finish_dynamic_symbol
4824 #define elf_backend_finish_dynamic_symbol \
4825                 elf32_frvfdpic_finish_dynamic_symbol
4826 #undef elf_backend_finish_dynamic_sections
4827 #define elf_backend_finish_dynamic_sections \
4828                 elf32_frvfdpic_finish_dynamic_sections
4829
4830 #undef elf_backend_can_make_relative_eh_frame
4831 #define elf_backend_can_make_relative_eh_frame \
4832                 frvfdpic_elf_use_relative_eh_frame
4833 #undef elf_backend_can_make_lsda_relative_eh_frame
4834 #define elf_backend_can_make_lsda_relative_eh_frame \
4835                 frvfdpic_elf_use_relative_eh_frame
4836 #undef elf_backend_encode_eh_address
4837 #define elf_backend_encode_eh_address \
4838                 frvfdpic_elf_encode_eh_address
4839
4840 #undef elf_backend_may_use_rel_p
4841 #define elf_backend_may_use_rel_p       1
4842 #undef elf_backend_may_use_rela_p
4843 #define elf_backend_may_use_rela_p      1
4844 /* We use REL for dynamic relocations only.  */
4845 #undef elf_backend_default_use_rela_p
4846 #define elf_backend_default_use_rela_p  1
4847
4848 #undef elf_backend_omit_section_dynsym
4849 #define elf_backend_omit_section_dynsym _frvfdpic_link_omit_section_dynsym
4850
4851 #include "elf32-target.h"