OBVIOUS: fix several occurrences of 'This options has' to 'This option has'
[external/binutils.git] / bfd / elf64-nfp.c
1 /* NFP-specific support for 64-bit ELF
2    Copyright (C) 2017-2019 Free Software Foundation, Inc.
3    Contributed by Francois H. Theron <francois.theron@netronome.com>
4
5    This file is part of BFD, the Binary File Descriptor library.
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 3 of the License, or
10    (at your option) any later version.
11
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software
19    Foundation, Inc., 51 Franklin Street - Fifth Floor,
20    Boston, MA 02110-1301, USA.  */
21
22 #include "sysdep.h"
23 #include "bfd.h"
24 #include "libbfd.h"
25 #include "elf-bfd.h"
26 #include "elf/nfp.h"
27
28
29 static bfd_reloc_status_type
30 elf64_nfp_reloc (bfd * abfd ATTRIBUTE_UNUSED,
31                  arelent * reloc_entry,
32                  asymbol * symbol,
33                  void *data ATTRIBUTE_UNUSED,
34                  asection * input_section,
35                  bfd * output_bfd,
36                  char **error_message ATTRIBUTE_UNUSED);
37
38 /* We don't actually apply any relocations in this toolset
39    so we make them all do nothing, but at least display useful
40    names.
41    Most of these are mainly used by the NFP toolchain to resolve things
42    before the final ELF file is created.  */
43 static reloc_howto_type elf_nfp_howto_table[] =
44 {
45   HOWTO (R_NFP_NOTYPE,          /* Type.  */
46          0,                     /* Rightshift.  */
47          3,                     /* Size.  */
48          0,                     /* Bitsize.  */
49          FALSE,                 /* PC_relative.  */
50          0,                     /* Bitpos.  */
51          complain_overflow_dont,/* Complain_on_overflow.  */
52          elf64_nfp_reloc,       /* Special_function.  */
53          "R_NFP_NOTYPE",        /* Name.  */
54          FALSE,                 /* Partial_inplace.  */
55          0,                     /* Src_mask.  */
56          0,                     /* Dst_mask.  */
57          FALSE),                /* PCrel_offset.  */
58   HOWTO (R_NFP_W32LE, 0, 3, 0, FALSE, 0,
59          complain_overflow_dont, elf64_nfp_reloc,
60          "R_NFP_W32LE",
61          FALSE, 0, 0, FALSE),
62   HOWTO (R_NFP_SRC8_A, 0, 3, 0, FALSE, 0,
63          complain_overflow_dont, elf64_nfp_reloc,
64          "R_NFP_SRC8_A",
65          FALSE, 0, 0, FALSE),
66   HOWTO (R_NFP_SRC8_B, 0, 3, 0, FALSE, 0,
67          complain_overflow_dont, elf64_nfp_reloc,
68          "R_NFP_SRC8_B",
69          FALSE, 0, 0, FALSE),
70   HOWTO (R_NFP_IMMED8_I, 0, 3, 0, FALSE, 0,
71          complain_overflow_dont, elf64_nfp_reloc,
72          "R_NFP_IMMED8_I",
73          FALSE, 0, 0, FALSE),
74   HOWTO (R_NFP_SC, 0, 3, 0, FALSE, 0,
75          complain_overflow_dont, elf64_nfp_reloc,
76          "R_NFP_SC",
77          FALSE, 0, 0, FALSE),
78   HOWTO (R_NFP_IMMED_LO16_I_A, 0, 3, 0, FALSE, 0,
79          complain_overflow_dont, elf64_nfp_reloc,
80          "R_NFP_IMMED_LO16_I_A",
81          FALSE, 0, 0, FALSE),
82   HOWTO (R_NFP_IMMED_LO16_I_B, 0, 3, 0, FALSE, 0,
83          complain_overflow_dont, elf64_nfp_reloc,
84          "R_NFP_IMMED_LO16_I_B",
85          TRUE, 0, 0, FALSE),
86   HOWTO (R_NFP_SRC7_B, 0, 3, 0, FALSE, 0,
87          complain_overflow_dont, elf64_nfp_reloc,
88          "R_NFP_SRC7_B",
89          FALSE, 0, 0, FALSE),
90   HOWTO (R_NFP_SRC7_A, 0, 3, 0, FALSE, 0,
91          complain_overflow_dont, elf64_nfp_reloc,
92          "R_NFP_SRC7_A",
93          FALSE, 0, 0, FALSE),
94   HOWTO (R_NFP_SRC8_I_B, 0, 3, 0, FALSE, 0,
95          complain_overflow_dont, elf64_nfp_reloc,
96          "R_NFP_SRC8_I_B",
97          FALSE, 0, 0, FALSE),
98   HOWTO (R_NFP_SRC8_I_A, 0, 3, 0, FALSE, 0,
99          complain_overflow_dont, elf64_nfp_reloc,
100          "R_NFP_SRC8_I_A",
101          FALSE, 0, 0, FALSE),
102   HOWTO (R_NFP_IMMED_HI16_I_A, 0, 3, 0, FALSE, 0,
103          complain_overflow_dont, elf64_nfp_reloc,
104          "R_NFP_IMMED_HI16_I_A",
105          FALSE, 0, 0, FALSE),
106   HOWTO (R_NFP_IMMED_HI16_I_B, 0, 3, 0, FALSE, 0,
107          complain_overflow_dont, elf64_nfp_reloc,
108          "R_NFP_IMMED_HI16_I_B",
109          FALSE, 0, 0, FALSE),
110   HOWTO (R_NFP_W64LE, 0, 3, 0, FALSE, 0,
111          complain_overflow_dont, elf64_nfp_reloc,
112          "R_NFP_W64LE",
113          FALSE, 0, 0, FALSE),
114   HOWTO (R_NFP_SH_INFO, 0, 3, 0, FALSE, 0,
115          complain_overflow_dont, elf64_nfp_reloc,
116          "R_NFP_SH_INFO",
117          FALSE, 0, 0, FALSE),
118   HOWTO (R_NFP_W32BE, 0, 3, 0, FALSE, 0,
119          complain_overflow_dont, elf64_nfp_reloc,
120          "R_NFP_W32BE",
121          FALSE, 0, 0, FALSE),
122   HOWTO (R_NFP_W64BE, 0, 3, 0, FALSE, 0,
123          complain_overflow_dont, elf64_nfp_reloc,
124          "R_NFP_W64BE",
125          FALSE, 0, 0, FALSE),
126   HOWTO (R_NFP_W32_29_24, 0, 3, 0, FALSE, 0,
127          complain_overflow_dont, elf64_nfp_reloc,
128          "R_NFP_W32_29_24",
129          FALSE, 0, 0, FALSE),
130   HOWTO (R_NFP_W32LE_AND, 0, 3, 0, FALSE, 0,
131          complain_overflow_dont, elf64_nfp_reloc,
132          "R_NFP_W32LE_AND",
133          FALSE, 0, 0, FALSE),
134   HOWTO (R_NFP_W32BE_AND, 0, 3, 0, FALSE, 0,
135          complain_overflow_dont, elf64_nfp_reloc,
136          "R_NFP_W32BE_AND",
137          FALSE, 0, 0, FALSE),
138   HOWTO (R_NFP_W32LE_OR, 0, 3, 0, FALSE, 0,
139          complain_overflow_dont, elf64_nfp_reloc,
140          "R_NFP_W32LE_OR",
141          FALSE, 0, 0, FALSE),
142   HOWTO (R_NFP_W32BE_OR, 0, 3, 0, FALSE, 0,
143          complain_overflow_dont, elf64_nfp_reloc,
144          "R_NFP_W32BE_OR",
145          FALSE, 0, 0, FALSE),
146   HOWTO (R_NFP_W64LE_AND, 0, 3, 0, FALSE, 0,
147          complain_overflow_dont, elf64_nfp_reloc,
148          "R_NFP_W64LE_AND",
149          FALSE, 0, 0, FALSE),
150   HOWTO (R_NFP_W64BE_AND, 0, 3, 0, FALSE, 0,
151          complain_overflow_dont, elf64_nfp_reloc,
152          "R_NFP_W64BE_AND",
153          FALSE, 0, 0, FALSE),
154   HOWTO (R_NFP_W64LE_OR, 0, 3, 0, FALSE, 0,
155          complain_overflow_dont, elf64_nfp_reloc,
156          "R_NFP_W64LE_OR",
157          FALSE, 0, 0, FALSE),
158   HOWTO (R_NFP_W64BE_OR, 0, 3, 0, FALSE, 0,
159          complain_overflow_dont, elf64_nfp_reloc,
160          "R_NFP_W64BE_OR",
161          FALSE, 0, 0, FALSE)
162 };
163
164 static bfd_boolean
165 elf64_nfp_object_p (bfd * abfd)
166 {
167   /* If the e_machine value is one of the unofficial ones, we convert
168      it first and set e_flags accordingly for later consistency.  */
169   if (elf_elfheader (abfd)->e_machine == E_NFP_MACH_3200)
170     {
171       elf_elfheader (abfd)->e_machine = EM_NFP;
172       elf_elfheader (abfd)->e_flags &= ~EF_NFP_SET_MACH (~0);
173       elf_elfheader (abfd)->e_flags |= EF_NFP_SET_MACH (E_NFP_MACH_3200);
174     }
175   else if (elf_elfheader (abfd)->e_machine == E_NFP_MACH_6000)
176     {
177       elf_elfheader (abfd)->e_machine = EM_NFP;
178       elf_elfheader (abfd)->e_flags &= ~EF_NFP_SET_MACH (~0);
179       elf_elfheader (abfd)->e_flags |= EF_NFP_SET_MACH (E_NFP_MACH_6000);
180     }
181
182   if (elf_elfheader (abfd)->e_machine == EM_NFP)
183     {
184       int e_mach = EF_NFP_MACH (elf_elfheader (abfd)->e_flags);
185
186       switch (e_mach)
187         {
188         case E_NFP_MACH_3200:
189         case E_NFP_MACH_6000:
190           if (!bfd_default_set_arch_mach (abfd, bfd_arch_nfp, e_mach))
191             return FALSE;
192         default:
193           break;
194         }
195     }
196
197   return TRUE;
198 }
199
200 static bfd_boolean
201 elf64_nfp_section_from_shdr (bfd * abfd,
202                              Elf_Internal_Shdr * hdr,
203                              const char *name, int shindex)
204 {
205   switch (hdr->sh_type)
206     {
207     case SHT_NFP_INITREG:
208     case SHT_NFP_MECONFIG:
209     case SHT_NFP_UDEBUG:
210       return _bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex);
211     default:
212       return FALSE;
213     }
214 }
215
216 bfd_reloc_status_type
217 elf64_nfp_reloc (bfd * abfd ATTRIBUTE_UNUSED,
218                  arelent * reloc_entry ATTRIBUTE_UNUSED,
219                  asymbol * symbol ATTRIBUTE_UNUSED,
220                  void *data ATTRIBUTE_UNUSED,
221                  asection * input_section ATTRIBUTE_UNUSED,
222                  bfd * output_bfd ATTRIBUTE_UNUSED,
223                  char **error_message ATTRIBUTE_UNUSED)
224 {
225   return bfd_reloc_ok;
226 }
227
228 static bfd_boolean
229 elf64_nfp_info_to_howto (bfd * abfd ATTRIBUTE_UNUSED,
230                          arelent * cache_ptr, Elf_Internal_Rela * dst)
231 {
232   unsigned int r_type;
233
234   r_type = ELF64_R_TYPE (dst->r_info);
235   if (r_type >= R_NFP_MAX)
236     {
237       /* xgettext:c-format */
238       _bfd_error_handler (_("%pB: unsupported relocation type %#x"),
239                           abfd, r_type);
240       bfd_set_error (bfd_error_bad_value);
241       return FALSE;
242     }
243   cache_ptr->howto = &elf_nfp_howto_table[r_type];
244   return TRUE;
245 }
246
247 static reloc_howto_type *
248 elf64_nfp_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
249                              bfd_reloc_code_real_type code ATTRIBUTE_UNUSED)
250 {
251   return NULL;
252 }
253
254 static reloc_howto_type *
255 elf64_nfp_reloc_name_lookup (bfd * abfd ATTRIBUTE_UNUSED,
256                              const char *r_name ATTRIBUTE_UNUSED)
257 {
258   return NULL;
259 }
260
261 #define ELF_ARCH                bfd_arch_nfp
262 #define ELF_MACHINE_CODE        EM_NFP
263 #define ELF_MACHINE_ALT1        E_NFP_MACH_6000
264 #define ELF_MACHINE_ALT2        E_NFP_MACH_3200
265 #define ELF_MAXPAGESIZE         1
266 #define TARGET_LITTLE_NAME      "elf64-nfp"
267 #define TARGET_LITTLE_SYM       nfp_elf64_vec
268
269 #define elf_backend_object_p            elf64_nfp_object_p
270 #define elf_backend_section_from_shdr   elf64_nfp_section_from_shdr
271 #define elf_info_to_howto               elf64_nfp_info_to_howto
272 #define bfd_elf64_bfd_reloc_type_lookup      elf64_nfp_reloc_type_lookup
273 #define bfd_elf64_bfd_reloc_name_lookup      elf64_nfp_reloc_name_lookup
274
275 #include "elf64-target.h"