PR 1004
[deliverable/binutils-gdb.git] / bfd / elf32-v850.c
CommitLineData
252b5132 1/* V850-specific support for 32-bit ELF
9553c638 2 Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005
7898deda 3 Free Software Foundation, Inc.
252b5132 4
86aba9db 5 This file is part of BFD, the Binary File Descriptor library.
252b5132 6
86aba9db
NC
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 2 of the License, or
10 (at your option) any later version.
252b5132 11
86aba9db
NC
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.
252b5132 16
86aba9db
NC
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
47b0e7ad
NC
19 Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
20 MA 02110-1301, USA. */
252b5132 21
252b5132 22/* XXX FIXME: This code is littered with 32bit int, 16bit short, 8bit char
86aba9db 23 dependencies. As is the gas & simulator code for the v850. */
252b5132 24
252b5132
RH
25#include "bfd.h"
26#include "sysdep.h"
27#include "bfdlink.h"
28#include "libbfd.h"
29#include "elf-bfd.h"
30#include "elf/v850.h"
e12dd2ea 31#include "libiberty.h"
252b5132 32
e12dd2ea 33/* Sign-extend a 24-bit number. */
dc810e39 34#define SEXT24(x) ((((x) & 0xffffff) ^ 0x800000) - 0x800000)
435b1e90 35
252b5132
RH
36/* Look through the relocs for a section during the first phase, and
37 allocate space in the global offset table or procedure linkage
38 table. */
39
b34976b6 40static bfd_boolean
47b0e7ad
NC
41v850_elf_check_relocs (bfd *abfd,
42 struct bfd_link_info *info,
43 asection *sec,
44 const Elf_Internal_Rela *relocs)
252b5132 45{
b34976b6 46 bfd_boolean ret = TRUE;
252b5132
RH
47 bfd *dynobj;
48 Elf_Internal_Shdr *symtab_hdr;
49 struct elf_link_hash_entry **sym_hashes;
50 const Elf_Internal_Rela *rel;
51 const Elf_Internal_Rela *rel_end;
52 asection *sreloc;
53 enum v850_reloc_type r_type;
54 int other = 0;
47b0e7ad 55 const char *common = NULL;
252b5132 56
1049f94e 57 if (info->relocatable)
b34976b6 58 return TRUE;
252b5132
RH
59
60#ifdef DEBUG
d003868e
AM
61 _bfd_error_handler ("v850_elf_check_relocs called for section %A in %B",
62 sec, abfd);
252b5132
RH
63#endif
64
65 dynobj = elf_hash_table (info)->dynobj;
66 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
67 sym_hashes = elf_sym_hashes (abfd);
68 sreloc = NULL;
69
70 rel_end = relocs + sec->reloc_count;
71 for (rel = relocs; rel < rel_end; rel++)
72 {
73 unsigned long r_symndx;
74 struct elf_link_hash_entry *h;
75
76 r_symndx = ELF32_R_SYM (rel->r_info);
77 if (r_symndx < symtab_hdr->sh_info)
78 h = NULL;
79 else
973a3492
L
80 {
81 h = sym_hashes[r_symndx - symtab_hdr->sh_info];
82 while (h->root.type == bfd_link_hash_indirect
83 || h->root.type == bfd_link_hash_warning)
84 h = (struct elf_link_hash_entry *) h->root.u.i.link;
85 }
252b5132
RH
86
87 r_type = (enum v850_reloc_type) ELF32_R_TYPE (rel->r_info);
88 switch (r_type)
89 {
90 default:
91 case R_V850_NONE:
92 case R_V850_9_PCREL:
93 case R_V850_22_PCREL:
94 case R_V850_HI16_S:
95 case R_V850_HI16:
96 case R_V850_LO16:
1e50d24d 97 case R_V850_LO16_SPLIT_OFFSET:
e30ddb24
NC
98 case R_V850_ABS32:
99 case R_V850_REL32:
252b5132
RH
100 case R_V850_16:
101 case R_V850_8:
102 case R_V850_CALLT_6_7_OFFSET:
103 case R_V850_CALLT_16_16_OFFSET:
104 break;
105
106 /* This relocation describes the C++ object vtable hierarchy.
107 Reconstruct it for later use during GC. */
108 case R_V850_GNU_VTINHERIT:
c152c796 109 if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
b34976b6 110 return FALSE;
252b5132
RH
111 break;
112
e12dd2ea
NC
113 /* This relocation describes which C++ vtable entries
114 are actually used. Record for later use during GC. */
252b5132 115 case R_V850_GNU_VTENTRY:
c152c796 116 if (!bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
b34976b6 117 return FALSE;
252b5132
RH
118 break;
119
120 case R_V850_SDA_16_16_SPLIT_OFFSET:
121 case R_V850_SDA_16_16_OFFSET:
122 case R_V850_SDA_15_16_OFFSET:
123 other = V850_OTHER_SDA;
124 common = ".scommon";
125 goto small_data_common;
435b1e90 126
252b5132
RH
127 case R_V850_ZDA_16_16_SPLIT_OFFSET:
128 case R_V850_ZDA_16_16_OFFSET:
129 case R_V850_ZDA_15_16_OFFSET:
130 other = V850_OTHER_ZDA;
131 common = ".zcommon";
132 goto small_data_common;
435b1e90 133
252b5132
RH
134 case R_V850_TDA_4_5_OFFSET:
135 case R_V850_TDA_4_4_OFFSET:
136 case R_V850_TDA_6_8_OFFSET:
137 case R_V850_TDA_7_8_OFFSET:
138 case R_V850_TDA_7_7_OFFSET:
139 case R_V850_TDA_16_16_OFFSET:
140 other = V850_OTHER_TDA;
141 common = ".tcommon";
142 /* fall through */
143
144#define V850_OTHER_MASK (V850_OTHER_TDA | V850_OTHER_SDA | V850_OTHER_ZDA)
145
146 small_data_common:
147 if (h)
148 {
e12dd2ea
NC
149 /* Flag which type of relocation was used. */
150 h->other |= other;
252b5132
RH
151 if ((h->other & V850_OTHER_MASK) != (other & V850_OTHER_MASK)
152 && (h->other & V850_OTHER_ERROR) == 0)
153 {
154 const char * msg;
155 static char buff[200]; /* XXX */
156
157 switch (h->other & V850_OTHER_MASK)
158 {
159 default:
160 msg = _("Variable `%s' cannot occupy in multiple small data regions");
161 break;
162 case V850_OTHER_SDA | V850_OTHER_ZDA | V850_OTHER_TDA:
163 msg = _("Variable `%s' can only be in one of the small, zero, and tiny data regions");
164 break;
165 case V850_OTHER_SDA | V850_OTHER_ZDA:
166 msg = _("Variable `%s' cannot be in both small and zero data regions simultaneously");
167 break;
168 case V850_OTHER_SDA | V850_OTHER_TDA:
169 msg = _("Variable `%s' cannot be in both small and tiny data regions simultaneously");
170 break;
171 case V850_OTHER_ZDA | V850_OTHER_TDA:
172 msg = _("Variable `%s' cannot be in both zero and tiny data regions simultaneously");
173 break;
174 }
175
176 sprintf (buff, msg, h->root.root.string);
177 info->callbacks->warning (info, buff, h->root.root.string,
dc810e39
AM
178 abfd, h->root.u.def.section,
179 (bfd_vma) 0);
252b5132
RH
180
181 bfd_set_error (bfd_error_bad_value);
182 h->other |= V850_OTHER_ERROR;
b34976b6 183 ret = FALSE;
252b5132
RH
184 }
185 }
186
187 if (h && h->root.type == bfd_link_hash_common
188 && h->root.u.c.p
189 && !strcmp (bfd_get_section_name (abfd, h->root.u.c.p->section), "COMMON"))
190 {
e12dd2ea
NC
191 asection * section;
192
193 section = h->root.u.c.p->section = bfd_make_section_old_way (abfd, common);
252b5132
RH
194 section->flags |= SEC_IS_COMMON;
195 }
196
197#ifdef DEBUG
198 fprintf (stderr, "v850_elf_check_relocs, found %s relocation for %s%s\n",
199 v850_elf_howto_table[ (int)r_type ].name,
200 (h && h->root.root.string) ? h->root.root.string : "<unknown>",
201 (h->root.type == bfd_link_hash_common) ? ", symbol is common" : "");
202#endif
203 break;
204 }
205 }
206
207 return ret;
208}
209
e12dd2ea
NC
210/* In the old version, when an entry was checked out from the table,
211 it was deleted. This produced an error if the entry was needed
212 more than once, as the second attempted retry failed.
213
214 In the current version, the entry is not deleted, instead we set
b34976b6 215 the field 'found' to TRUE. If a second lookup matches the same
e12dd2ea
NC
216 entry, then we know that the hi16s reloc has already been updated
217 and does not need to be updated a second time.
218
219 TODO - TOFIX: If it is possible that we need to restore 2 different
220 addresses from the same table entry, where the first generates an
221 overflow, whilst the second do not, then this code will fail. */
252b5132
RH
222
223typedef struct hi16s_location
224{
47b0e7ad
NC
225 bfd_vma addend;
226 bfd_byte * address;
227 unsigned long counter;
228 bfd_boolean found;
229 struct hi16s_location * next;
252b5132
RH
230}
231hi16s_location;
232
47b0e7ad
NC
233static hi16s_location * previous_hi16s;
234static hi16s_location * free_hi16s;
235static unsigned long hi16s_counter;
252b5132
RH
236
237static void
47b0e7ad 238remember_hi16s_reloc (bfd *abfd, bfd_vma addend, bfd_byte *address)
252b5132
RH
239{
240 hi16s_location * entry = NULL;
dc810e39 241 bfd_size_type amt = sizeof (* free_hi16s);
435b1e90 242
252b5132
RH
243 /* Find a free structure. */
244 if (free_hi16s == NULL)
47b0e7ad 245 free_hi16s = bfd_zalloc (abfd, amt);
252b5132
RH
246
247 entry = free_hi16s;
248 free_hi16s = free_hi16s->next;
435b1e90 249
252b5132
RH
250 entry->addend = addend;
251 entry->address = address;
252 entry->counter = hi16s_counter ++;
b34976b6 253 entry->found = FALSE;
252b5132
RH
254 entry->next = previous_hi16s;
255 previous_hi16s = entry;
435b1e90 256
252b5132
RH
257 /* Cope with wrap around of our counter. */
258 if (hi16s_counter == 0)
259 {
47b0e7ad 260 /* XXX: Assume that all counter entries differ only in their low 16 bits. */
252b5132
RH
261 for (entry = previous_hi16s; entry != NULL; entry = entry->next)
262 entry->counter &= 0xffff;
263
264 hi16s_counter = 0x10000;
265 }
252b5132
RH
266}
267
268static bfd_byte *
47b0e7ad 269find_remembered_hi16s_reloc (bfd_vma addend, bfd_boolean *already_found)
252b5132 270{
b34976b6
AM
271 hi16s_location *match = NULL;
272 hi16s_location *entry;
273 hi16s_location *previous = NULL;
274 hi16s_location *prev;
275 bfd_byte *addr;
435b1e90 276
252b5132
RH
277 /* Search the table. Record the most recent entry that matches. */
278 for (entry = previous_hi16s; entry; entry = entry->next)
279 {
280 if (entry->addend == addend
281 && (match == NULL || match->counter < entry->counter))
282 {
283 previous = prev;
284 match = entry;
285 }
435b1e90 286
252b5132
RH
287 prev = entry;
288 }
289
290 if (match == NULL)
291 return NULL;
292
293 /* Extract the address. */
294 addr = match->address;
295
4cc11e76 296 /* Remember if this entry has already been used before. */
252b5132
RH
297 if (already_found)
298 * already_found = match->found;
299
300 /* Note that this entry has now been used. */
b34976b6 301 match->found = TRUE;
435b1e90 302
252b5132 303 return addr;
435b1e90 304}
252b5132 305
1e50d24d
RS
306/* Calculate the final operand value for a R_V850_LO16 or
307 R_V850_LO16_SPLIT_OFFSET. *INSN is the current operand value and
308 ADDEND is the sum of the relocation symbol and offset. Store the
309 operand value in *INSN and return true on success.
310
311 The assembler has already done some of this: If the value stored in
312 the instruction has its 15th bit set, (counting from zero) then the
313 assembler will have added 1 to the value stored in the associated
314 HI16S reloc. So for example, these relocations:
315
316 movhi hi( fred ), r0, r1
317 movea lo( fred ), r1, r1
318
319 will store 0 in the value fields for the MOVHI and MOVEA instructions
320 and addend will be the address of fred, but for these instructions:
321
322 movhi hi( fred + 0x123456), r0, r1
323 movea lo( fred + 0x123456), r1, r1
324
325 the value stored in the MOVHI instruction will be 0x12 and the value
326 stored in the MOVEA instruction will be 0x3456. If however the
327 instructions were:
328
329 movhi hi( fred + 0x10ffff), r0, r1
330 movea lo( fred + 0x10ffff), r1, r1
331
332 then the value stored in the MOVHI instruction would be 0x11 (not
333 0x10) and the value stored in the MOVEA instruction would be 0xffff.
334 Thus (assuming for the moment that the addend is 0), at run time the
335 MOVHI instruction loads 0x110000 into r1, then the MOVEA instruction
336 adds 0xffffffff (sign extension!) producing 0x10ffff. Similarly if
337 the instructions were:
338
339 movhi hi( fred - 1), r0, r1
340 movea lo( fred - 1), r1, r1
341
342 then 0 is stored in the MOVHI instruction and -1 is stored in the
343 MOVEA instruction.
344
345 Overflow can occur if the addition of the value stored in the
346 instruction plus the addend sets the 15th bit when before it was clear.
347 This is because the 15th bit will be sign extended into the high part,
348 thus reducing its value by one, but since the 15th bit was originally
349 clear, the assembler will not have added 1 to the previous HI16S reloc
350 to compensate for this effect. For example:
351
352 movhi hi( fred + 0x123456), r0, r1
353 movea lo( fred + 0x123456), r1, r1
354
355 The value stored in HI16S reloc is 0x12, the value stored in the LO16
356 reloc is 0x3456. If we assume that the address of fred is 0x00007000
357 then the relocations become:
358
359 HI16S: 0x0012 + (0x00007000 >> 16) = 0x12
360 LO16: 0x3456 + (0x00007000 & 0xffff) = 0xa456
361
362 but when the instructions are executed, the MOVEA instruction's value
363 is signed extended, so the sum becomes:
364
365 0x00120000
366 + 0xffffa456
367 ------------
368 0x0011a456 but 'fred + 0x123456' = 0x0012a456
369
370 Note that if the 15th bit was set in the value stored in the LO16
371 reloc, then we do not have to do anything:
372
373 movhi hi( fred + 0x10ffff), r0, r1
374 movea lo( fred + 0x10ffff), r1, r1
375
376 HI16S: 0x0011 + (0x00007000 >> 16) = 0x11
377 LO16: 0xffff + (0x00007000 & 0xffff) = 0x6fff
378
379 0x00110000
380 + 0x00006fff
381 ------------
382 0x00116fff = fred + 0x10ffff = 0x7000 + 0x10ffff
383
384 Overflow can also occur if the computation carries into the 16th bit
385 and it also results in the 15th bit having the same value as the 15th
386 bit of the original value. What happens is that the HI16S reloc
387 will have already examined the 15th bit of the original value and
388 added 1 to the high part if the bit is set. This compensates for the
389 sign extension of 15th bit of the result of the computation. But now
390 there is a carry into the 16th bit, and this has not been allowed for.
391
392 So, for example if fred is at address 0xf000:
393
394 movhi hi( fred + 0xffff), r0, r1 [bit 15 of the offset is set]
395 movea lo( fred + 0xffff), r1, r1
396
397 HI16S: 0x0001 + (0x0000f000 >> 16) = 0x0001
398 LO16: 0xffff + (0x0000f000 & 0xffff) = 0xefff (carry into bit 16 is lost)
399
400 0x00010000
401 + 0xffffefff
402 ------------
403 0x0000efff but 'fred + 0xffff' = 0x0001efff
404
405 Similarly, if the 15th bit remains clear, but overflow occurs into
406 the 16th bit then (assuming the address of fred is 0xf000):
407
408 movhi hi( fred + 0x7000), r0, r1 [bit 15 of the offset is clear]
409 movea lo( fred + 0x7000), r1, r1
410
411 HI16S: 0x0000 + (0x0000f000 >> 16) = 0x0000
412 LO16: 0x7000 + (0x0000f000 & 0xffff) = 0x6fff (carry into bit 16 is lost)
413
414 0x00000000
415 + 0x00006fff
416 ------------
417 0x00006fff but 'fred + 0x7000' = 0x00016fff
418
419 Note - there is no need to change anything if a carry occurs, and the
420 15th bit changes its value from being set to being clear, as the HI16S
421 reloc will have already added in 1 to the high part for us:
422
423 movhi hi( fred + 0xffff), r0, r1 [bit 15 of the offset is set]
424 movea lo( fred + 0xffff), r1, r1
425
426 HI16S: 0x0001 + (0x00007000 >> 16)
427 LO16: 0xffff + (0x00007000 & 0xffff) = 0x6fff (carry into bit 16 is lost)
428
429 0x00010000
430 + 0x00006fff (bit 15 not set, so the top half is zero)
431 ------------
432 0x00016fff which is right (assuming that fred is at 0x7000)
433
434 but if the 15th bit goes from being clear to being set, then we must
435 once again handle overflow:
436
437 movhi hi( fred + 0x7000), r0, r1 [bit 15 of the offset is clear]
438 movea lo( fred + 0x7000), r1, r1
439
440 HI16S: 0x0000 + (0x0000ffff >> 16)
441 LO16: 0x7000 + (0x0000ffff & 0xffff) = 0x6fff (carry into bit 16)
442
443 0x00000000
444 + 0x00006fff (bit 15 not set, so the top half is zero)
445 ------------
446 0x00006fff which is wrong (assuming that fred is at 0xffff). */
447
448static bfd_boolean
449v850_elf_perform_lo16_relocation (bfd *abfd, unsigned long *insn,
450 unsigned long addend)
451{
452#define BIT15_SET(x) ((x) & 0x8000)
453#define OVERFLOWS(a,i) ((((a) & 0xffff) + (i)) > 0xffff)
47b0e7ad 454
1e50d24d
RS
455 if ((BIT15_SET (*insn + addend) && ! BIT15_SET (addend))
456 || (OVERFLOWS (addend, *insn)
457 && ((! BIT15_SET (*insn)) || (BIT15_SET (addend)))))
458 {
459 bfd_boolean already_updated;
460 bfd_byte *hi16s_address = find_remembered_hi16s_reloc
461 (addend, & already_updated);
462
463 /* Amend the matching HI16_S relocation. */
464 if (hi16s_address != NULL)
465 {
466 if (! already_updated)
467 {
468 unsigned long hi_insn = bfd_get_16 (abfd, hi16s_address);
469 hi_insn += 1;
470 bfd_put_16 (abfd, hi_insn, hi16s_address);
471 }
472 }
473 else
474 {
475 fprintf (stderr, _("FAILED to find previous HI16 reloc\n"));
476 return FALSE;
477 }
478 }
479#undef OVERFLOWS
480#undef BIT15_SET
481
482 /* Do not complain if value has top bit set, as this has been
483 anticipated. */
484 *insn = (*insn + addend) & 0xffff;
485 return TRUE;
486}
487
252b5132 488/* FIXME: The code here probably ought to be removed and the code in reloc.c
4cc11e76 489 allowed to do its stuff instead. At least for most of the relocs, anyway. */
e12dd2ea 490
252b5132 491static bfd_reloc_status_type
47b0e7ad
NC
492v850_elf_perform_relocation (bfd *abfd,
493 unsigned int r_type,
494 bfd_vma addend,
495 bfd_byte *address)
252b5132
RH
496{
497 unsigned long insn;
1e50d24d 498 unsigned long result;
252b5132 499 bfd_signed_vma saddend = (bfd_signed_vma) addend;
435b1e90 500
252b5132
RH
501 switch (r_type)
502 {
503 default:
252b5132 504 return bfd_reloc_notsupported;
435b1e90 505
e30ddb24
NC
506 case R_V850_REL32:
507 case R_V850_ABS32:
252b5132
RH
508 bfd_put_32 (abfd, addend, address);
509 return bfd_reloc_ok;
435b1e90 510
252b5132
RH
511 case R_V850_22_PCREL:
512 if (saddend > 0x1fffff || saddend < -0x200000)
513 return bfd_reloc_overflow;
435b1e90 514
252b5132
RH
515 if ((addend % 2) != 0)
516 return bfd_reloc_dangerous;
435b1e90 517
252b5132
RH
518 insn = bfd_get_32 (abfd, address);
519 insn &= ~0xfffe003f;
520 insn |= (((addend & 0xfffe) << 16) | ((addend & 0x3f0000) >> 16));
dc810e39 521 bfd_put_32 (abfd, (bfd_vma) insn, address);
252b5132 522 return bfd_reloc_ok;
435b1e90 523
252b5132
RH
524 case R_V850_9_PCREL:
525 if (saddend > 0xff || saddend < -0x100)
526 return bfd_reloc_overflow;
435b1e90 527
252b5132
RH
528 if ((addend % 2) != 0)
529 return bfd_reloc_dangerous;
435b1e90 530
252b5132
RH
531 insn = bfd_get_16 (abfd, address);
532 insn &= ~ 0xf870;
533 insn |= ((addend & 0x1f0) << 7) | ((addend & 0x0e) << 3);
534 break;
435b1e90 535
252b5132
RH
536 case R_V850_HI16:
537 addend += (bfd_get_16 (abfd, address) << 16);
538 addend = (addend >> 16);
539 insn = addend;
540 break;
435b1e90 541
252b5132
RH
542 case R_V850_HI16_S:
543 /* Remember where this relocation took place. */
544 remember_hi16s_reloc (abfd, addend, address);
545
546 addend += (bfd_get_16 (abfd, address) << 16);
547 addend = (addend >> 16) + ((addend & 0x8000) != 0);
435b1e90
KH
548
549 /* This relocation cannot overflow. */
252b5132
RH
550 if (addend > 0x7fff)
551 addend = 0;
435b1e90 552
252b5132
RH
553 insn = addend;
554 break;
435b1e90 555
252b5132 556 case R_V850_LO16:
1e50d24d
RS
557 insn = bfd_get_16 (abfd, address);
558 if (! v850_elf_perform_lo16_relocation (abfd, &insn, addend))
559 return bfd_reloc_overflow;
560 break;
252b5132
RH
561
562 case R_V850_8:
563 addend += (char) bfd_get_8 (abfd, address);
564
565 saddend = (bfd_signed_vma) addend;
435b1e90 566
252b5132
RH
567 if (saddend > 0x7f || saddend < -0x80)
568 return bfd_reloc_overflow;
569
570 bfd_put_8 (abfd, addend, address);
571 return bfd_reloc_ok;
572
573 case R_V850_CALLT_16_16_OFFSET:
574 addend += bfd_get_16 (abfd, address);
435b1e90 575
252b5132 576 saddend = (bfd_signed_vma) addend;
435b1e90 577
252b5132
RH
578 if (saddend > 0xffff || saddend < 0)
579 return bfd_reloc_overflow;
580
581 insn = addend;
582 break;
435b1e90 583
252b5132 584 case R_V850_16:
252b5132
RH
585 case R_V850_SDA_16_16_OFFSET:
586 case R_V850_ZDA_16_16_OFFSET:
587 case R_V850_TDA_16_16_OFFSET:
588 addend += bfd_get_16 (abfd, address);
435b1e90 589
252b5132 590 saddend = (bfd_signed_vma) addend;
435b1e90 591
252b5132
RH
592 if (saddend > 0x7fff || saddend < -0x8000)
593 return bfd_reloc_overflow;
594
595 insn = addend;
596 break;
435b1e90 597
252b5132
RH
598 case R_V850_SDA_15_16_OFFSET:
599 case R_V850_ZDA_15_16_OFFSET:
600 insn = bfd_get_16 (abfd, address);
601 addend += (insn & 0xfffe);
435b1e90 602
252b5132 603 saddend = (bfd_signed_vma) addend;
435b1e90 604
252b5132
RH
605 if (saddend > 0x7ffe || saddend < -0x8000)
606 return bfd_reloc_overflow;
435b1e90 607
252b5132
RH
608 if (addend & 1)
609 return bfd_reloc_dangerous;
435b1e90 610
dc810e39 611 insn = (addend &~ (bfd_vma) 1) | (insn & 1);
252b5132 612 break;
435b1e90 613
252b5132
RH
614 case R_V850_TDA_6_8_OFFSET:
615 insn = bfd_get_16 (abfd, address);
616 addend += ((insn & 0x7e) << 1);
435b1e90 617
252b5132 618 saddend = (bfd_signed_vma) addend;
435b1e90 619
252b5132
RH
620 if (saddend > 0xfc || saddend < 0)
621 return bfd_reloc_overflow;
435b1e90 622
252b5132
RH
623 if (addend & 3)
624 return bfd_reloc_dangerous;
435b1e90 625
252b5132
RH
626 insn &= 0xff81;
627 insn |= (addend >> 1);
628 break;
435b1e90 629
252b5132
RH
630 case R_V850_TDA_7_8_OFFSET:
631 insn = bfd_get_16 (abfd, address);
632 addend += ((insn & 0x7f) << 1);
435b1e90 633
252b5132 634 saddend = (bfd_signed_vma) addend;
435b1e90 635
252b5132
RH
636 if (saddend > 0xfe || saddend < 0)
637 return bfd_reloc_overflow;
435b1e90 638
252b5132
RH
639 if (addend & 1)
640 return bfd_reloc_dangerous;
435b1e90 641
252b5132
RH
642 insn &= 0xff80;
643 insn |= (addend >> 1);
644 break;
435b1e90 645
252b5132
RH
646 case R_V850_TDA_7_7_OFFSET:
647 insn = bfd_get_16 (abfd, address);
648 addend += insn & 0x7f;
435b1e90 649
252b5132 650 saddend = (bfd_signed_vma) addend;
435b1e90 651
252b5132
RH
652 if (saddend > 0x7f || saddend < 0)
653 return bfd_reloc_overflow;
435b1e90 654
252b5132
RH
655 insn &= 0xff80;
656 insn |= addend;
657 break;
435b1e90 658
252b5132
RH
659 case R_V850_TDA_4_5_OFFSET:
660 insn = bfd_get_16 (abfd, address);
661 addend += ((insn & 0xf) << 1);
435b1e90 662
252b5132 663 saddend = (bfd_signed_vma) addend;
435b1e90 664
252b5132
RH
665 if (saddend > 0x1e || saddend < 0)
666 return bfd_reloc_overflow;
435b1e90 667
252b5132
RH
668 if (addend & 1)
669 return bfd_reloc_dangerous;
435b1e90 670
252b5132
RH
671 insn &= 0xfff0;
672 insn |= (addend >> 1);
673 break;
435b1e90 674
252b5132
RH
675 case R_V850_TDA_4_4_OFFSET:
676 insn = bfd_get_16 (abfd, address);
677 addend += insn & 0xf;
435b1e90 678
252b5132 679 saddend = (bfd_signed_vma) addend;
435b1e90 680
252b5132
RH
681 if (saddend > 0xf || saddend < 0)
682 return bfd_reloc_overflow;
435b1e90 683
252b5132
RH
684 insn &= 0xfff0;
685 insn |= addend;
686 break;
435b1e90 687
1e50d24d
RS
688 case R_V850_LO16_SPLIT_OFFSET:
689 insn = bfd_get_32 (abfd, address);
690 result = ((insn & 0xfffe0000) >> 16) | ((insn & 0x20) >> 5);
691 if (! v850_elf_perform_lo16_relocation (abfd, &result, addend))
692 return bfd_reloc_overflow;
693 insn = (((result << 16) & 0xfffe0000)
694 | ((result << 5) & 0x20)
695 | (insn & ~0xfffe0020));
696 bfd_put_32 (abfd, insn, address);
697 return bfd_reloc_ok;
698
252b5132
RH
699 case R_V850_ZDA_16_16_SPLIT_OFFSET:
700 case R_V850_SDA_16_16_SPLIT_OFFSET:
701 insn = bfd_get_32 (abfd, address);
702 addend += ((insn & 0xfffe0000) >> 16) + ((insn & 0x20) >> 5);
435b1e90 703
252b5132 704 saddend = (bfd_signed_vma) addend;
435b1e90 705
252b5132
RH
706 if (saddend > 0x7fff || saddend < -0x8000)
707 return bfd_reloc_overflow;
435b1e90 708
252b5132
RH
709 insn &= 0x0001ffdf;
710 insn |= (addend & 1) << 5;
dc810e39 711 insn |= (addend &~ (bfd_vma) 1) << 16;
435b1e90 712
dc810e39 713 bfd_put_32 (abfd, (bfd_vma) insn, address);
252b5132 714 return bfd_reloc_ok;
435b1e90 715
252b5132
RH
716 case R_V850_CALLT_6_7_OFFSET:
717 insn = bfd_get_16 (abfd, address);
718 addend += ((insn & 0x3f) << 1);
435b1e90 719
252b5132 720 saddend = (bfd_signed_vma) addend;
435b1e90 721
252b5132
RH
722 if (saddend > 0x7e || saddend < 0)
723 return bfd_reloc_overflow;
435b1e90 724
252b5132
RH
725 if (addend & 1)
726 return bfd_reloc_dangerous;
435b1e90 727
252b5132
RH
728 insn &= 0xff80;
729 insn |= (addend >> 1);
730 break;
731
732 case R_V850_GNU_VTINHERIT:
733 case R_V850_GNU_VTENTRY:
734 return bfd_reloc_ok;
735
736 }
737
dc810e39 738 bfd_put_16 (abfd, (bfd_vma) insn, address);
252b5132
RH
739 return bfd_reloc_ok;
740}
252b5132
RH
741\f
742/* Insert the addend into the instruction. */
e12dd2ea 743
252b5132 744static bfd_reloc_status_type
47b0e7ad
NC
745v850_elf_reloc (bfd *abfd ATTRIBUTE_UNUSED,
746 arelent *reloc,
747 asymbol *symbol,
748 void * data ATTRIBUTE_UNUSED,
749 asection *isection,
750 bfd *obfd,
751 char **err ATTRIBUTE_UNUSED)
252b5132
RH
752{
753 long relocation;
435b1e90 754
252b5132
RH
755 /* If there is an output BFD,
756 and the symbol is not a section name (which is only defined at final link time),
757 and either we are not putting the addend into the instruction
e12dd2ea 758 or the addend is zero, so there is nothing to add into the instruction
252b5132 759 then just fixup the address and return. */
47b0e7ad 760 if (obfd != NULL
252b5132
RH
761 && (symbol->flags & BSF_SECTION_SYM) == 0
762 && (! reloc->howto->partial_inplace
763 || reloc->addend == 0))
764 {
765 reloc->address += isection->output_offset;
766 return bfd_reloc_ok;
767 }
435b1e90 768
252b5132
RH
769 /* Catch relocs involving undefined symbols. */
770 if (bfd_is_und_section (symbol->section)
771 && (symbol->flags & BSF_WEAK) == 0
772 && obfd == NULL)
773 return bfd_reloc_undefined;
774
775 /* We handle final linking of some relocs ourselves. */
776
777 /* Is the address of the relocation really within the section? */
07515404 778 if (reloc->address > bfd_get_section_limit (abfd, isection))
252b5132 779 return bfd_reloc_outofrange;
435b1e90 780
4cc11e76 781 /* Work out which section the relocation is targeted at and the
252b5132 782 initial relocation command value. */
435b1e90 783
b34976b6 784 if (reloc->howto->pc_relative)
86aba9db
NC
785 return bfd_reloc_ok;
786
252b5132
RH
787 /* Get symbol value. (Common symbols are special.) */
788 if (bfd_is_com_section (symbol->section))
789 relocation = 0;
790 else
791 relocation = symbol->value;
435b1e90 792
252b5132
RH
793 /* Convert input-section-relative symbol value to absolute + addend. */
794 relocation += symbol->section->output_section->vma;
795 relocation += symbol->section->output_offset;
796 relocation += reloc->addend;
435b1e90 797
435b1e90 798 reloc->addend = relocation;
252b5132
RH
799 return bfd_reloc_ok;
800}
86aba9db
NC
801
802/* This function is used for relocs which are only used
803 for relaxing, which the linker should otherwise ignore. */
804
805static bfd_reloc_status_type
47b0e7ad
NC
806v850_elf_ignore_reloc (bfd *abfd ATTRIBUTE_UNUSED,
807 arelent *reloc_entry,
808 asymbol *symbol ATTRIBUTE_UNUSED,
809 void * data ATTRIBUTE_UNUSED,
810 asection *input_section,
811 bfd *output_bfd,
812 char **error_message ATTRIBUTE_UNUSED)
86aba9db
NC
813{
814 if (output_bfd != NULL)
815 reloc_entry->address += input_section->output_offset;
816
817 return bfd_reloc_ok;
818}
47b0e7ad
NC
819/* Note: It is REQUIRED that the 'type' value of each entry
820 in this array match the index of the entry in the array. */
821static reloc_howto_type v850_elf_howto_table[] =
822{
823 /* This reloc does nothing. */
824 HOWTO (R_V850_NONE, /* Type. */
825 0, /* Rightshift. */
826 2, /* Size (0 = byte, 1 = short, 2 = long). */
827 32, /* Bitsize. */
828 FALSE, /* PC_relative. */
829 0, /* Bitpos. */
830 complain_overflow_bitfield, /* Complain_on_overflow. */
831 bfd_elf_generic_reloc, /* Special_function. */
832 "R_V850_NONE", /* Name. */
833 FALSE, /* Partial_inplace. */
834 0, /* Src_mask. */
835 0, /* Dst_mask. */
836 FALSE), /* PCrel_offset. */
837
838 /* A PC relative 9 bit branch. */
839 HOWTO (R_V850_9_PCREL, /* Type. */
840 2, /* Rightshift. */
841 2, /* Size (0 = byte, 1 = short, 2 = long). */
842 26, /* Bitsize. */
843 TRUE, /* PC_relative. */
844 0, /* Bitpos. */
845 complain_overflow_bitfield, /* Complain_on_overflow. */
846 v850_elf_reloc, /* Special_function. */
847 "R_V850_9_PCREL", /* Name. */
848 FALSE, /* Partial_inplace. */
849 0x00ffffff, /* Src_mask. */
850 0x00ffffff, /* Dst_mask. */
851 TRUE), /* PCrel_offset. */
852
853 /* A PC relative 22 bit branch. */
854 HOWTO (R_V850_22_PCREL, /* Type. */
855 2, /* Rightshift. */
856 2, /* Size (0 = byte, 1 = short, 2 = long). */
857 22, /* Bitsize. */
858 TRUE, /* PC_relative. */
859 7, /* Bitpos. */
860 complain_overflow_signed, /* Complain_on_overflow. */
861 v850_elf_reloc, /* Special_function. */
862 "R_V850_22_PCREL", /* Name. */
863 FALSE, /* Partial_inplace. */
864 0x07ffff80, /* Src_mask. */
865 0x07ffff80, /* Dst_mask. */
866 TRUE), /* PCrel_offset. */
867
868 /* High 16 bits of symbol value. */
869 HOWTO (R_V850_HI16_S, /* Type. */
870 0, /* Rightshift. */
871 1, /* Size (0 = byte, 1 = short, 2 = long). */
872 16, /* Bitsize. */
873 FALSE, /* PC_relative. */
874 0, /* Bitpos. */
875 complain_overflow_dont, /* Complain_on_overflow. */
876 v850_elf_reloc, /* Special_function. */
877 "R_V850_HI16_S", /* Name. */
878 FALSE, /* Partial_inplace. */
879 0xffff, /* Src_mask. */
880 0xffff, /* Dst_mask. */
881 FALSE), /* PCrel_offset. */
882
883 /* High 16 bits of symbol value. */
884 HOWTO (R_V850_HI16, /* Type. */
885 0, /* Rightshift. */
886 1, /* Size (0 = byte, 1 = short, 2 = long). */
887 16, /* Bitsize. */
888 FALSE, /* PC_relative. */
889 0, /* Bitpos. */
890 complain_overflow_dont, /* Complain_on_overflow. */
891 v850_elf_reloc, /* Special_function. */
892 "R_V850_HI16", /* Name. */
893 FALSE, /* Partial_inplace. */
894 0xffff, /* Src_mask. */
895 0xffff, /* Dst_mask. */
896 FALSE), /* PCrel_offset. */
897
898 /* Low 16 bits of symbol value. */
899 HOWTO (R_V850_LO16, /* Type. */
900 0, /* Rightshift. */
901 1, /* Size (0 = byte, 1 = short, 2 = long). */
902 16, /* Bitsize. */
903 FALSE, /* PC_relative. */
904 0, /* Bitpos. */
905 complain_overflow_dont, /* Complain_on_overflow. */
906 v850_elf_reloc, /* Special_function. */
907 "R_V850_LO16", /* Name. */
908 FALSE, /* Partial_inplace. */
909 0xffff, /* Src_mask. */
910 0xffff, /* Dst_mask. */
911 FALSE), /* PCrel_offset. */
912
913 /* Simple 32bit reloc. */
914 HOWTO (R_V850_ABS32, /* Type. */
915 0, /* Rightshift. */
916 2, /* Size (0 = byte, 1 = short, 2 = long). */
917 32, /* Bitsize. */
918 FALSE, /* PC_relative. */
919 0, /* Bitpos. */
920 complain_overflow_dont, /* Complain_on_overflow. */
921 v850_elf_reloc, /* Special_function. */
922 "R_V850_ABS32", /* Name. */
923 FALSE, /* Partial_inplace. */
924 0xffffffff, /* Src_mask. */
925 0xffffffff, /* Dst_mask. */
926 FALSE), /* PCrel_offset. */
927
928 /* Simple 16bit reloc. */
929 HOWTO (R_V850_16, /* Type. */
930 0, /* Rightshift. */
931 1, /* Size (0 = byte, 1 = short, 2 = long). */
932 16, /* Bitsize. */
933 FALSE, /* PC_relative. */
934 0, /* Bitpos. */
935 complain_overflow_dont, /* Complain_on_overflow. */
936 bfd_elf_generic_reloc, /* Special_function. */
937 "R_V850_16", /* Name. */
938 FALSE, /* Partial_inplace. */
939 0xffff, /* Src_mask. */
940 0xffff, /* Dst_mask. */
941 FALSE), /* PCrel_offset. */
942
943 /* Simple 8bit reloc. */
944 HOWTO (R_V850_8, /* Type. */
945 0, /* Rightshift. */
946 0, /* Size (0 = byte, 1 = short, 2 = long). */
947 8, /* Bitsize. */
948 FALSE, /* PC_relative. */
949 0, /* Bitpos. */
950 complain_overflow_dont, /* Complain_on_overflow. */
951 bfd_elf_generic_reloc, /* Special_function. */
952 "R_V850_8", /* Name. */
953 FALSE, /* Partial_inplace. */
954 0xff, /* Src_mask. */
955 0xff, /* Dst_mask. */
956 FALSE), /* PCrel_offset. */
957
958 /* 16 bit offset from the short data area pointer. */
959 HOWTO (R_V850_SDA_16_16_OFFSET, /* Type. */
960 0, /* Rightshift. */
961 1, /* Size (0 = byte, 1 = short, 2 = long). */
962 16, /* Bitsize. */
963 FALSE, /* PC_relative. */
964 0, /* Bitpos. */
965 complain_overflow_dont, /* Complain_on_overflow. */
966 v850_elf_reloc, /* Special_function. */
967 "R_V850_SDA_16_16_OFFSET", /* Name. */
968 FALSE, /* Partial_inplace. */
969 0xffff, /* Src_mask. */
970 0xffff, /* Dst_mask. */
971 FALSE), /* PCrel_offset. */
972
973 /* 15 bit offset from the short data area pointer. */
974 HOWTO (R_V850_SDA_15_16_OFFSET, /* Type. */
975 1, /* Rightshift. */
976 1, /* Size (0 = byte, 1 = short, 2 = long). */
977 16, /* Bitsize. */
978 FALSE, /* PC_relative. */
979 1, /* Bitpos. */
980 complain_overflow_dont, /* Complain_on_overflow. */
981 v850_elf_reloc, /* Special_function. */
982 "R_V850_SDA_15_16_OFFSET", /* Name. */
983 FALSE, /* Partial_inplace. */
984 0xfffe, /* Src_mask. */
985 0xfffe, /* Dst_mask. */
986 FALSE), /* PCrel_offset. */
987
988 /* 16 bit offset from the zero data area pointer. */
989 HOWTO (R_V850_ZDA_16_16_OFFSET, /* Type. */
990 0, /* Rightshift. */
991 1, /* Size (0 = byte, 1 = short, 2 = long). */
992 16, /* Bitsize. */
993 FALSE, /* PC_relative. */
994 0, /* Bitpos. */
995 complain_overflow_dont, /* Complain_on_overflow. */
996 v850_elf_reloc, /* Special_function. */
997 "R_V850_ZDA_16_16_OFFSET", /* Name. */
998 FALSE, /* Partial_inplace. */
999 0xffff, /* Src_mask. */
1000 0xffff, /* Dst_mask. */
1001 FALSE), /* PCrel_offset. */
1002
1003 /* 15 bit offset from the zero data area pointer. */
1004 HOWTO (R_V850_ZDA_15_16_OFFSET, /* Type. */
1005 1, /* Rightshift. */
1006 1, /* Size (0 = byte, 1 = short, 2 = long). */
1007 16, /* Bitsize. */
1008 FALSE, /* PC_relative. */
1009 1, /* Bitpos. */
1010 complain_overflow_dont, /* Complain_on_overflow. */
1011 v850_elf_reloc, /* Special_function. */
1012 "R_V850_ZDA_15_16_OFFSET", /* Name. */
1013 FALSE, /* Partial_inplace. */
1014 0xfffe, /* Src_mask. */
1015 0xfffe, /* Dst_mask. */
1016 FALSE), /* PCrel_offset. */
1017
1018 /* 6 bit offset from the tiny data area pointer. */
1019 HOWTO (R_V850_TDA_6_8_OFFSET, /* Type. */
1020 2, /* Rightshift. */
1021 1, /* Size (0 = byte, 1 = short, 2 = long). */
1022 8, /* Bitsize. */
1023 FALSE, /* PC_relative. */
1024 1, /* Bitpos. */
1025 complain_overflow_dont, /* Complain_on_overflow. */
1026 v850_elf_reloc, /* Special_function. */
1027 "R_V850_TDA_6_8_OFFSET", /* Name. */
1028 FALSE, /* Partial_inplace. */
1029 0x7e, /* Src_mask. */
1030 0x7e, /* Dst_mask. */
1031 FALSE), /* PCrel_offset. */
1032
1033 /* 8 bit offset from the tiny data area pointer. */
1034 HOWTO (R_V850_TDA_7_8_OFFSET, /* Type. */
1035 1, /* Rightshift. */
1036 1, /* Size (0 = byte, 1 = short, 2 = long). */
1037 8, /* Bitsize. */
1038 FALSE, /* PC_relative. */
1039 0, /* Bitpos. */
1040 complain_overflow_dont, /* Complain_on_overflow. */
1041 v850_elf_reloc, /* Special_function. */
1042 "R_V850_TDA_7_8_OFFSET", /* Name. */
1043 FALSE, /* Partial_inplace. */
1044 0x7f, /* Src_mask. */
1045 0x7f, /* Dst_mask. */
1046 FALSE), /* PCrel_offset. */
1047
1048 /* 7 bit offset from the tiny data area pointer. */
1049 HOWTO (R_V850_TDA_7_7_OFFSET, /* Type. */
1050 0, /* Rightshift. */
1051 1, /* Size (0 = byte, 1 = short, 2 = long). */
1052 7, /* Bitsize. */
1053 FALSE, /* PC_relative. */
1054 0, /* Bitpos. */
1055 complain_overflow_dont, /* Complain_on_overflow. */
1056 v850_elf_reloc, /* Special_function. */
1057 "R_V850_TDA_7_7_OFFSET", /* Name. */
1058 FALSE, /* Partial_inplace. */
1059 0x7f, /* Src_mask. */
1060 0x7f, /* Dst_mask. */
1061 FALSE), /* PCrel_offset. */
1062
1063 /* 16 bit offset from the tiny data area pointer! */
1064 HOWTO (R_V850_TDA_16_16_OFFSET, /* Type. */
1065 0, /* Rightshift. */
1066 1, /* Size (0 = byte, 1 = short, 2 = long). */
1067 16, /* Bitsize. */
1068 FALSE, /* PC_relative. */
1069 0, /* Bitpos. */
1070 complain_overflow_dont, /* Complain_on_overflow. */
1071 v850_elf_reloc, /* Special_function. */
1072 "R_V850_TDA_16_16_OFFSET", /* Name. */
1073 FALSE, /* Partial_inplace. */
1074 0xffff, /* Src_mask. */
1075 0xfff, /* Dst_mask. */
1076 FALSE), /* PCrel_offset. */
1077
1078 /* 5 bit offset from the tiny data area pointer. */
1079 HOWTO (R_V850_TDA_4_5_OFFSET, /* Type. */
1080 1, /* Rightshift. */
1081 1, /* Size (0 = byte, 1 = short, 2 = long). */
1082 5, /* Bitsize. */
1083 FALSE, /* PC_relative. */
1084 0, /* Bitpos. */
1085 complain_overflow_dont, /* Complain_on_overflow. */
1086 v850_elf_reloc, /* Special_function. */
1087 "R_V850_TDA_4_5_OFFSET", /* Name. */
1088 FALSE, /* Partial_inplace. */
1089 0x0f, /* Src_mask. */
1090 0x0f, /* Dst_mask. */
1091 FALSE), /* PCrel_offset. */
1092
1093 /* 4 bit offset from the tiny data area pointer. */
1094 HOWTO (R_V850_TDA_4_4_OFFSET, /* Type. */
1095 0, /* Rightshift. */
1096 1, /* Size (0 = byte, 1 = short, 2 = long). */
1097 4, /* Bitsize. */
1098 FALSE, /* PC_relative. */
1099 0, /* Bitpos. */
1100 complain_overflow_dont, /* Complain_on_overflow. */
1101 v850_elf_reloc, /* Special_function. */
1102 "R_V850_TDA_4_4_OFFSET", /* Name. */
1103 FALSE, /* Partial_inplace. */
1104 0x0f, /* Src_mask. */
1105 0x0f, /* Dst_mask. */
1106 FALSE), /* PCrel_offset. */
1107
1108 /* 16 bit offset from the short data area pointer. */
1109 HOWTO (R_V850_SDA_16_16_SPLIT_OFFSET, /* Type. */
1110 0, /* Rightshift. */
1111 2, /* Size (0 = byte, 1 = short, 2 = long). */
1112 16, /* Bitsize. */
1113 FALSE, /* PC_relative. */
1114 0, /* Bitpos. */
1115 complain_overflow_dont, /* Complain_on_overflow. */
1116 v850_elf_reloc, /* Special_function. */
1117 "R_V850_SDA_16_16_SPLIT_OFFSET",/* Name. */
1118 FALSE, /* Partial_inplace. */
1119 0xfffe0020, /* Src_mask. */
1120 0xfffe0020, /* Dst_mask. */
1121 FALSE), /* PCrel_offset. */
1122
1123 /* 16 bit offset from the zero data area pointer. */
1124 HOWTO (R_V850_ZDA_16_16_SPLIT_OFFSET, /* Type. */
1125 0, /* Rightshift. */
1126 2, /* Size (0 = byte, 1 = short, 2 = long). */
1127 16, /* Bitsize. */
1128 FALSE, /* PC_relative. */
1129 0, /* Bitpos. */
1130 complain_overflow_dont, /* Complain_on_overflow. */
1131 v850_elf_reloc, /* Special_function. */
1132 "R_V850_ZDA_16_16_SPLIT_OFFSET",/* Name. */
1133 FALSE, /* Partial_inplace. */
1134 0xfffe0020, /* Src_mask. */
1135 0xfffe0020, /* Dst_mask. */
1136 FALSE), /* PCrel_offset. */
1137
1138 /* 6 bit offset from the call table base pointer. */
1139 HOWTO (R_V850_CALLT_6_7_OFFSET, /* Type. */
1140 0, /* Rightshift. */
1141 1, /* Size (0 = byte, 1 = short, 2 = long). */
1142 7, /* Bitsize. */
1143 FALSE, /* PC_relative. */
1144 0, /* Bitpos. */
1145 complain_overflow_dont, /* Complain_on_overflow. */
1146 v850_elf_reloc, /* Special_function. */
1147 "R_V850_CALLT_6_7_OFFSET", /* Name. */
1148 FALSE, /* Partial_inplace. */
1149 0x3f, /* Src_mask. */
1150 0x3f, /* Dst_mask. */
1151 FALSE), /* PCrel_offset. */
1152
1153 /* 16 bit offset from the call table base pointer. */
1154 HOWTO (R_V850_CALLT_16_16_OFFSET, /* Type. */
1155 0, /* Rightshift. */
1156 1, /* Size (0 = byte, 1 = short, 2 = long). */
1157 16, /* Bitsize. */
1158 FALSE, /* PC_relative. */
1159 0, /* Bitpos. */
1160 complain_overflow_dont, /* Complain_on_overflow. */
1161 v850_elf_reloc, /* Special_function. */
1162 "R_V850_CALLT_16_16_OFFSET", /* Name. */
1163 FALSE, /* Partial_inplace. */
1164 0xffff, /* Src_mask. */
1165 0xffff, /* Dst_mask. */
1166 FALSE), /* PCrel_offset. */
1167
1168 /* GNU extension to record C++ vtable hierarchy */
1169 HOWTO (R_V850_GNU_VTINHERIT, /* Type. */
1170 0, /* Rightshift. */
1171 2, /* Size (0 = byte, 1 = short, 2 = long). */
1172 0, /* Bitsize. */
1173 FALSE, /* PC_relative. */
1174 0, /* Bitpos. */
1175 complain_overflow_dont, /* Complain_on_overflow. */
1176 NULL, /* Special_function. */
1177 "R_V850_GNU_VTINHERIT", /* Name. */
1178 FALSE, /* Partial_inplace. */
1179 0, /* Src_mask. */
1180 0, /* Dst_mask. */
1181 FALSE), /* PCrel_offset. */
1182
1183 /* GNU extension to record C++ vtable member usage */
1184 HOWTO (R_V850_GNU_VTENTRY, /* Type. */
1185 0, /* Rightshift. */
1186 2, /* Size (0 = byte, 1 = short, 2 = long). */
1187 0, /* Bitsize. */
1188 FALSE, /* PC_relative. */
1189 0, /* Bitpos. */
1190 complain_overflow_dont, /* Complain_on_overflow. */
1191 _bfd_elf_rel_vtable_reloc_fn, /* Special_function. */
1192 "R_V850_GNU_VTENTRY", /* Name. */
1193 FALSE, /* Partial_inplace. */
1194 0, /* Src_mask. */
1195 0, /* Dst_mask. */
1196 FALSE), /* PCrel_offset. */
1197
1198 /* Indicates a .longcall pseudo-op. The compiler will generate a .longcall
1199 pseudo-op when it finds a function call which can be relaxed. */
1200 HOWTO (R_V850_LONGCALL, /* Type. */
1201 0, /* Rightshift. */
1202 2, /* Size (0 = byte, 1 = short, 2 = long). */
1203 32, /* Bitsize. */
1204 TRUE, /* PC_relative. */
1205 0, /* Bitpos. */
1206 complain_overflow_signed, /* Complain_on_overflow. */
1207 v850_elf_ignore_reloc, /* Special_function. */
1208 "R_V850_LONGCALL", /* Name. */
1209 FALSE, /* Partial_inplace. */
1210 0, /* Src_mask. */
1211 0, /* Dst_mask. */
1212 TRUE), /* PCrel_offset. */
1213
1214 /* Indicates a .longjump pseudo-op. The compiler will generate a
1215 .longjump pseudo-op when it finds a branch which can be relaxed. */
1216 HOWTO (R_V850_LONGJUMP, /* Type. */
1217 0, /* Rightshift. */
1218 2, /* Size (0 = byte, 1 = short, 2 = long). */
1219 32, /* Bitsize. */
1220 TRUE, /* PC_relative. */
1221 0, /* Bitpos. */
1222 complain_overflow_signed, /* Complain_on_overflow. */
1223 v850_elf_ignore_reloc, /* Special_function. */
1224 "R_V850_LONGJUMP", /* Name. */
1225 FALSE, /* Partial_inplace. */
1226 0, /* Src_mask. */
1227 0, /* Dst_mask. */
1228 TRUE), /* PCrel_offset. */
1229
1230 HOWTO (R_V850_ALIGN, /* Type. */
1231 0, /* Rightshift. */
1232 1, /* Size (0 = byte, 1 = short, 2 = long). */
1233 0, /* Bitsize. */
1234 FALSE, /* PC_relative. */
1235 0, /* Bitpos. */
1236 complain_overflow_unsigned, /* Complain_on_overflow. */
1237 v850_elf_ignore_reloc, /* Special_function. */
1238 "R_V850_ALIGN", /* Name. */
1239 FALSE, /* Partial_inplace. */
1240 0, /* Src_mask. */
1241 0, /* Dst_mask. */
1242 TRUE), /* PCrel_offset. */
1243
1244 /* Simple pc-relative 32bit reloc. */
1245 HOWTO (R_V850_REL32, /* Type. */
1246 0, /* Rightshift. */
1247 2, /* Size (0 = byte, 1 = short, 2 = long). */
1248 32, /* Bitsize. */
1249 TRUE, /* PC_relative. */
1250 0, /* Bitpos. */
1251 complain_overflow_dont, /* Complain_on_overflow. */
1252 v850_elf_reloc, /* Special_function. */
1253 "R_V850_REL32", /* Name. */
1254 FALSE, /* Partial_inplace. */
1255 0xffffffff, /* Src_mask. */
1256 0xffffffff, /* Dst_mask. */
1257 FALSE), /* PCrel_offset. */
1258
1259 /* An ld.bu version of R_V850_LO16. */
1260 HOWTO (R_V850_LO16_SPLIT_OFFSET, /* Type. */
1261 0, /* Rightshift. */
1262 2, /* Size (0 = byte, 1 = short, 2 = long). */
1263 16, /* Bitsize. */
1264 FALSE, /* PC_relative. */
1265 0, /* Bitpos. */
1266 complain_overflow_dont, /* Complain_on_overflow. */
1267 v850_elf_reloc, /* Special_function. */
1268 "R_V850_LO16_SPLIT_OFFSET", /* Name. */
1269 FALSE, /* Partial_inplace. */
1270 0xfffe0020, /* Src_mask. */
1271 0xfffe0020, /* Dst_mask. */
1272 FALSE), /* PCrel_offset. */
1273};
1274
1275/* Map BFD reloc types to V850 ELF reloc types. */
1276
1277struct v850_elf_reloc_map
1278{
1279 /* BFD_RELOC_V850_CALLT_16_16_OFFSET is 258, which will not fix in an
1280 unsigned char. */
1281 bfd_reloc_code_real_type bfd_reloc_val;
1282 unsigned int elf_reloc_val;
1283};
1284
1285static const struct v850_elf_reloc_map v850_elf_reloc_map[] =
1286{
1287 { BFD_RELOC_NONE, R_V850_NONE },
1288 { BFD_RELOC_V850_9_PCREL, R_V850_9_PCREL },
1289 { BFD_RELOC_V850_22_PCREL, R_V850_22_PCREL },
1290 { BFD_RELOC_HI16_S, R_V850_HI16_S },
1291 { BFD_RELOC_HI16, R_V850_HI16 },
1292 { BFD_RELOC_LO16, R_V850_LO16 },
1293 { BFD_RELOC_32, R_V850_ABS32 },
1294 { BFD_RELOC_32_PCREL, R_V850_REL32 },
1295 { BFD_RELOC_16, R_V850_16 },
1296 { BFD_RELOC_8, R_V850_8 },
1297 { BFD_RELOC_V850_SDA_16_16_OFFSET, R_V850_SDA_16_16_OFFSET },
1298 { BFD_RELOC_V850_SDA_15_16_OFFSET, R_V850_SDA_15_16_OFFSET },
1299 { BFD_RELOC_V850_ZDA_16_16_OFFSET, R_V850_ZDA_16_16_OFFSET },
1300 { BFD_RELOC_V850_ZDA_15_16_OFFSET, R_V850_ZDA_15_16_OFFSET },
1301 { BFD_RELOC_V850_TDA_6_8_OFFSET, R_V850_TDA_6_8_OFFSET },
1302 { BFD_RELOC_V850_TDA_7_8_OFFSET, R_V850_TDA_7_8_OFFSET },
1303 { BFD_RELOC_V850_TDA_7_7_OFFSET, R_V850_TDA_7_7_OFFSET },
1304 { BFD_RELOC_V850_TDA_16_16_OFFSET, R_V850_TDA_16_16_OFFSET },
1305 { BFD_RELOC_V850_TDA_4_5_OFFSET, R_V850_TDA_4_5_OFFSET },
1306 { BFD_RELOC_V850_TDA_4_4_OFFSET, R_V850_TDA_4_4_OFFSET },
1307 { BFD_RELOC_V850_LO16_SPLIT_OFFSET, R_V850_LO16_SPLIT_OFFSET },
1308 { BFD_RELOC_V850_SDA_16_16_SPLIT_OFFSET, R_V850_SDA_16_16_SPLIT_OFFSET },
1309 { BFD_RELOC_V850_ZDA_16_16_SPLIT_OFFSET, R_V850_ZDA_16_16_SPLIT_OFFSET },
1310 { BFD_RELOC_V850_CALLT_6_7_OFFSET, R_V850_CALLT_6_7_OFFSET },
1311 { BFD_RELOC_V850_CALLT_16_16_OFFSET, R_V850_CALLT_16_16_OFFSET },
1312 { BFD_RELOC_VTABLE_INHERIT, R_V850_GNU_VTINHERIT },
1313 { BFD_RELOC_VTABLE_ENTRY, R_V850_GNU_VTENTRY },
1314 { BFD_RELOC_V850_LONGCALL, R_V850_LONGCALL },
1315 { BFD_RELOC_V850_LONGJUMP, R_V850_LONGJUMP },
1316 { BFD_RELOC_V850_ALIGN, R_V850_ALIGN },
1317
1318};
1319\f
1320/* Map a bfd relocation into the appropriate howto structure. */
1321
1322static reloc_howto_type *
1323v850_elf_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
1324 bfd_reloc_code_real_type code)
1325{
1326 unsigned int i;
1327
1328 for (i = ARRAY_SIZE (v850_elf_reloc_map); i --;)
1329 if (v850_elf_reloc_map[i].bfd_reloc_val == code)
1330 {
1331 unsigned int elf_reloc_val = v850_elf_reloc_map[i].elf_reloc_val;
1332
1333 BFD_ASSERT (v850_elf_howto_table[elf_reloc_val].type == elf_reloc_val);
1334
1335 return v850_elf_howto_table + elf_reloc_val;
1336 }
1337
1338 return NULL;
1339}
1340\f
1341/* Set the howto pointer for an V850 ELF reloc. */
1342
1343static void
1344v850_elf_info_to_howto_rel (bfd *abfd ATTRIBUTE_UNUSED,
1345 arelent *cache_ptr,
1346 Elf_Internal_Rela *dst)
1347{
1348 unsigned int r_type;
1349
1350 r_type = ELF32_R_TYPE (dst->r_info);
1351 BFD_ASSERT (r_type < (unsigned int) R_V850_max);
1352 cache_ptr->howto = &v850_elf_howto_table[r_type];
1353}
1354
1355/* Set the howto pointer for a V850 ELF reloc (type RELA). */
1356
1357static void
1358v850_elf_info_to_howto_rela (bfd *abfd ATTRIBUTE_UNUSED,
1359 arelent * cache_ptr,
1360 Elf_Internal_Rela *dst)
1361{
1362 unsigned int r_type;
1363
1364 r_type = ELF32_R_TYPE (dst->r_info);
1365 BFD_ASSERT (r_type < (unsigned int) R_V850_max);
1366 cache_ptr->howto = &v850_elf_howto_table[r_type];
1367}
252b5132 1368\f
b34976b6 1369static bfd_boolean
47b0e7ad 1370v850_elf_is_local_label_name (bfd *abfd ATTRIBUTE_UNUSED, const char *name)
252b5132
RH
1371{
1372 return ( (name[0] == '.' && (name[1] == 'L' || name[1] == '.'))
1373 || (name[0] == '_' && name[1] == '.' && name[2] == 'L' && name[3] == '_'));
1374}
252b5132 1375\f
5cec6941
NC
1376/* We overload some of the bfd_reloc error codes for own purposes. */
1377#define bfd_reloc_gp_not_found bfd_reloc_other
1378#define bfd_reloc_ep_not_found bfd_reloc_continue
1379#define bfd_reloc_ctbp_not_found (bfd_reloc_dangerous + 1)
1380
252b5132 1381/* Perform a relocation as part of a final link. */
e12dd2ea 1382
252b5132 1383static bfd_reloc_status_type
47b0e7ad
NC
1384v850_elf_final_link_relocate (reloc_howto_type *howto,
1385 bfd *input_bfd,
1386 bfd *output_bfd ATTRIBUTE_UNUSED,
1387 asection *input_section,
1388 bfd_byte *contents,
1389 bfd_vma offset,
1390 bfd_vma value,
1391 bfd_vma addend,
1392 struct bfd_link_info *info,
1393 asection *sym_sec,
1394 int is_local ATTRIBUTE_UNUSED)
252b5132 1395{
b34976b6
AM
1396 unsigned int r_type = howto->type;
1397 bfd_byte *hit_data = contents + offset;
252b5132
RH
1398
1399 /* Adjust the value according to the relocation. */
1400 switch (r_type)
1401 {
1402 case R_V850_9_PCREL:
1403 value -= (input_section->output_section->vma
1404 + input_section->output_offset);
1405 value -= offset;
1406 break;
435b1e90 1407
252b5132
RH
1408 case R_V850_22_PCREL:
1409 value -= (input_section->output_section->vma
1410 + input_section->output_offset
1411 + offset);
1412
232fb1a3
NC
1413 /* If the sign extension will corrupt the value then we have overflowed. */
1414 if (((value & 0xff000000) != 0x0) && ((value & 0xff000000) != 0xff000000))
1415 return bfd_reloc_overflow;
435b1e90 1416
47b0e7ad 1417 /* Only the bottom 24 bits of the PC are valid. */
e12dd2ea 1418 value = SEXT24 (value);
252b5132 1419 break;
435b1e90 1420
e30ddb24
NC
1421 case R_V850_REL32:
1422 value -= (input_section->output_section->vma
1423 + input_section->output_offset
1424 + offset);
1425 break;
1426
252b5132
RH
1427 case R_V850_HI16_S:
1428 case R_V850_HI16:
1429 case R_V850_LO16:
1e50d24d 1430 case R_V850_LO16_SPLIT_OFFSET:
252b5132 1431 case R_V850_16:
e30ddb24 1432 case R_V850_ABS32:
252b5132
RH
1433 case R_V850_8:
1434 break;
1435
435b1e90 1436 case R_V850_ZDA_15_16_OFFSET:
252b5132
RH
1437 case R_V850_ZDA_16_16_OFFSET:
1438 case R_V850_ZDA_16_16_SPLIT_OFFSET:
1439 if (sym_sec == NULL)
1440 return bfd_reloc_undefined;
435b1e90 1441
252b5132
RH
1442 value -= sym_sec->output_section->vma;
1443 break;
1444
1445 case R_V850_SDA_15_16_OFFSET:
1446 case R_V850_SDA_16_16_OFFSET:
1447 case R_V850_SDA_16_16_SPLIT_OFFSET:
1448 {
1449 unsigned long gp;
1450 struct bfd_link_hash_entry * h;
1451
1452 if (sym_sec == NULL)
1453 return bfd_reloc_undefined;
435b1e90 1454
252b5132 1455 /* Get the value of __gp. */
b34976b6 1456 h = bfd_link_hash_lookup (info->hash, "__gp", FALSE, FALSE, TRUE);
47b0e7ad 1457 if (h == NULL
252b5132 1458 || h->type != bfd_link_hash_defined)
5cec6941 1459 return bfd_reloc_gp_not_found;
252b5132
RH
1460
1461 gp = (h->u.def.value
1462 + h->u.def.section->output_section->vma
1463 + h->u.def.section->output_offset);
1464
1465 value -= sym_sec->output_section->vma;
1466 value -= (gp - sym_sec->output_section->vma);
1467 }
1468 break;
1469
1470 case R_V850_TDA_4_4_OFFSET:
1471 case R_V850_TDA_4_5_OFFSET:
1472 case R_V850_TDA_16_16_OFFSET:
1473 case R_V850_TDA_7_7_OFFSET:
1474 case R_V850_TDA_7_8_OFFSET:
1475 case R_V850_TDA_6_8_OFFSET:
1476 {
1477 unsigned long ep;
1478 struct bfd_link_hash_entry * h;
435b1e90 1479
252b5132 1480 /* Get the value of __ep. */
b34976b6 1481 h = bfd_link_hash_lookup (info->hash, "__ep", FALSE, FALSE, TRUE);
47b0e7ad 1482 if (h == NULL
252b5132 1483 || h->type != bfd_link_hash_defined)
5cec6941 1484 return bfd_reloc_ep_not_found;
252b5132
RH
1485
1486 ep = (h->u.def.value
1487 + h->u.def.section->output_section->vma
1488 + h->u.def.section->output_offset);
1489
1490 value -= ep;
1491 }
1492 break;
435b1e90 1493
252b5132
RH
1494 case R_V850_CALLT_6_7_OFFSET:
1495 {
1496 unsigned long ctbp;
1497 struct bfd_link_hash_entry * h;
435b1e90 1498
252b5132 1499 /* Get the value of __ctbp. */
b34976b6 1500 h = bfd_link_hash_lookup (info->hash, "__ctbp", FALSE, FALSE, TRUE);
47b0e7ad 1501 if (h == NULL
252b5132 1502 || h->type != bfd_link_hash_defined)
5cec6941 1503 return bfd_reloc_ctbp_not_found;
252b5132
RH
1504
1505 ctbp = (h->u.def.value
1506 + h->u.def.section->output_section->vma
1507 + h->u.def.section->output_offset);
1508 value -= ctbp;
1509 }
1510 break;
435b1e90 1511
252b5132
RH
1512 case R_V850_CALLT_16_16_OFFSET:
1513 {
1514 unsigned long ctbp;
1515 struct bfd_link_hash_entry * h;
1516
1517 if (sym_sec == NULL)
1518 return bfd_reloc_undefined;
435b1e90 1519
252b5132 1520 /* Get the value of __ctbp. */
b34976b6 1521 h = bfd_link_hash_lookup (info->hash, "__ctbp", FALSE, FALSE, TRUE);
47b0e7ad 1522 if (h == NULL
252b5132 1523 || h->type != bfd_link_hash_defined)
5cec6941 1524 return bfd_reloc_ctbp_not_found;
252b5132
RH
1525
1526 ctbp = (h->u.def.value
1527 + h->u.def.section->output_section->vma
1528 + h->u.def.section->output_offset);
1529
1530 value -= sym_sec->output_section->vma;
1531 value -= (ctbp - sym_sec->output_section->vma);
1532 }
1533 break;
435b1e90 1534
252b5132
RH
1535 case R_V850_NONE:
1536 case R_V850_GNU_VTINHERIT:
1537 case R_V850_GNU_VTENTRY:
86aba9db
NC
1538 case R_V850_LONGCALL:
1539 case R_V850_LONGJUMP:
1540 case R_V850_ALIGN:
252b5132
RH
1541 return bfd_reloc_ok;
1542
1543 default:
1544 return bfd_reloc_notsupported;
1545 }
1546
1547 /* Perform the relocation. */
435b1e90 1548 return v850_elf_perform_relocation (input_bfd, r_type, value + addend, hit_data);
252b5132 1549}
252b5132
RH
1550\f
1551/* Relocate an V850 ELF section. */
e12dd2ea 1552
b34976b6 1553static bfd_boolean
47b0e7ad
NC
1554v850_elf_relocate_section (bfd *output_bfd,
1555 struct bfd_link_info *info,
1556 bfd *input_bfd,
1557 asection *input_section,
1558 bfd_byte *contents,
1559 Elf_Internal_Rela *relocs,
1560 Elf_Internal_Sym *local_syms,
1561 asection **local_sections)
252b5132 1562{
b34976b6
AM
1563 Elf_Internal_Shdr *symtab_hdr;
1564 struct elf_link_hash_entry **sym_hashes;
1565 Elf_Internal_Rela *rel;
1566 Elf_Internal_Rela *relend;
252b5132 1567
1049f94e 1568 if (info->relocatable)
b34976b6 1569 return TRUE;
f0fe0e16 1570
252b5132
RH
1571 symtab_hdr = & elf_tdata (input_bfd)->symtab_hdr;
1572 sym_hashes = elf_sym_hashes (input_bfd);
1573
252b5132
RH
1574 /* Reset the list of remembered HI16S relocs to empty. */
1575 free_hi16s = previous_hi16s;
1576 previous_hi16s = NULL;
1577 hi16s_counter = 0;
435b1e90 1578
252b5132
RH
1579 rel = relocs;
1580 relend = relocs + input_section->reloc_count;
1581 for (; rel < relend; rel++)
1582 {
b34976b6
AM
1583 int r_type;
1584 reloc_howto_type *howto;
1585 unsigned long r_symndx;
1586 Elf_Internal_Sym *sym;
1587 asection *sec;
1588 struct elf_link_hash_entry *h;
1589 bfd_vma relocation;
1590 bfd_reloc_status_type r;
252b5132
RH
1591
1592 r_symndx = ELF32_R_SYM (rel->r_info);
1593 r_type = ELF32_R_TYPE (rel->r_info);
1594
1595 if (r_type == R_V850_GNU_VTENTRY
1596 || r_type == R_V850_GNU_VTINHERIT)
1597 continue;
1598
252b5132 1599 /* This is a final link. */
f0fe0e16 1600 howto = v850_elf_howto_table + r_type;
252b5132
RH
1601 h = NULL;
1602 sym = NULL;
1603 sec = NULL;
1604 if (r_symndx < symtab_hdr->sh_info)
1605 {
1606 sym = local_syms + r_symndx;
1607 sec = local_sections[r_symndx];
8517fae7 1608 relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
252b5132
RH
1609 }
1610 else
1611 {
59c2e50f 1612 bfd_boolean unresolved_reloc, warned;
435b1e90 1613
47b0e7ad
NC
1614 /* Note - this check is delayed until now as it is possible and
1615 valid to have a file without any symbols but with relocs that
1616 can be processed. */
641bd093
NC
1617 if (sym_hashes == NULL)
1618 {
1619 info->callbacks->warning
1620 (info, "no hash table available",
1621 NULL, input_bfd, input_section, (bfd_vma) 0);
1622
1623 return FALSE;
1624 }
1625
b2a8e766
AM
1626 RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
1627 r_symndx, symtab_hdr, sym_hashes,
1628 h, sec, relocation,
1629 unresolved_reloc, warned);
252b5132
RH
1630 }
1631
e12dd2ea 1632 /* FIXME: We should use the addend, but the COFF relocations don't. */
252b5132
RH
1633 r = v850_elf_final_link_relocate (howto, input_bfd, output_bfd,
1634 input_section,
1635 contents, rel->r_offset,
1636 relocation, rel->r_addend,
1637 info, sec, h == NULL);
1638
1639 if (r != bfd_reloc_ok)
1640 {
1641 const char * name;
47b0e7ad 1642 const char * msg = NULL;
252b5132
RH
1643
1644 if (h != NULL)
1645 name = h->root.root.string;
1646 else
1647 {
1648 name = (bfd_elf_string_from_elf_section
1649 (input_bfd, symtab_hdr->sh_link, sym->st_name));
1650 if (name == NULL || *name == '\0')
1651 name = bfd_section_name (input_bfd, sec);
1652 }
1653
1654 switch (r)
1655 {
1656 case bfd_reloc_overflow:
1657 if (! ((*info->callbacks->reloc_overflow)
dfeffb9f
L
1658 (info, (h ? &h->root : NULL), name, howto->name,
1659 (bfd_vma) 0, input_bfd, input_section,
1660 rel->r_offset)))
b34976b6 1661 return FALSE;
252b5132
RH
1662 break;
1663
1664 case bfd_reloc_undefined:
1665 if (! ((*info->callbacks->undefined_symbol)
1666 (info, name, input_bfd, input_section,
b34976b6
AM
1667 rel->r_offset, TRUE)))
1668 return FALSE;
252b5132
RH
1669 break;
1670
1671 case bfd_reloc_outofrange:
1672 msg = _("internal error: out of range error");
1673 goto common_error;
1674
1675 case bfd_reloc_notsupported:
1676 msg = _("internal error: unsupported relocation error");
1677 goto common_error;
1678
1679 case bfd_reloc_dangerous:
1680 msg = _("internal error: dangerous relocation");
1681 goto common_error;
1682
5cec6941 1683 case bfd_reloc_gp_not_found:
252b5132
RH
1684 msg = _("could not locate special linker symbol __gp");
1685 goto common_error;
1686
5cec6941 1687 case bfd_reloc_ep_not_found:
252b5132
RH
1688 msg = _("could not locate special linker symbol __ep");
1689 goto common_error;
1690
5cec6941 1691 case bfd_reloc_ctbp_not_found:
252b5132
RH
1692 msg = _("could not locate special linker symbol __ctbp");
1693 goto common_error;
435b1e90 1694
252b5132
RH
1695 default:
1696 msg = _("internal error: unknown error");
1697 /* fall through */
1698
1699 common_error:
1700 if (!((*info->callbacks->warning)
1701 (info, msg, name, input_bfd, input_section,
1702 rel->r_offset)))
b34976b6 1703 return FALSE;
252b5132
RH
1704 break;
1705 }
1706 }
1707 }
1708
b34976b6 1709 return TRUE;
252b5132
RH
1710}
1711
b34976b6 1712static bfd_boolean
47b0e7ad
NC
1713v850_elf_gc_sweep_hook (bfd *abfd ATTRIBUTE_UNUSED,
1714 struct bfd_link_info *info ATTRIBUTE_UNUSED,
1715 asection *sec ATTRIBUTE_UNUSED,
1716 const Elf_Internal_Rela *relocs ATTRIBUTE_UNUSED)
252b5132 1717{
e12dd2ea 1718 /* No got and plt entries for v850-elf. */
b34976b6 1719 return TRUE;
252b5132
RH
1720}
1721
1722static asection *
47b0e7ad
NC
1723v850_elf_gc_mark_hook (asection *sec,
1724 struct bfd_link_info *info ATTRIBUTE_UNUSED,
1725 Elf_Internal_Rela *rel,
1726 struct elf_link_hash_entry *h,
1727 Elf_Internal_Sym *sym)
252b5132
RH
1728{
1729 if (h != NULL)
1730 {
1731 switch (ELF32_R_TYPE (rel->r_info))
1732 {
1733 case R_V850_GNU_VTINHERIT:
1734 case R_V850_GNU_VTENTRY:
1735 break;
1736
1737 default:
1738 switch (h->root.type)
1739 {
1740 case bfd_link_hash_defined:
1741 case bfd_link_hash_defweak:
1742 return h->root.u.def.section;
1743
1744 case bfd_link_hash_common:
1745 return h->root.u.c.p->section;
e049a0de
ILT
1746
1747 default:
1748 break;
252b5132
RH
1749 }
1750 }
1751 }
1752 else
1e2f5b6e 1753 return bfd_section_from_elf_index (sec->owner, sym->st_shndx);
9ad5cbcf 1754
252b5132
RH
1755 return NULL;
1756}
e12dd2ea 1757
252b5132 1758/* Set the right machine number. */
e12dd2ea 1759
b34976b6 1760static bfd_boolean
47b0e7ad 1761v850_elf_object_p (bfd *abfd)
252b5132
RH
1762{
1763 switch (elf_elfheader (abfd)->e_flags & EF_V850_ARCH)
1764 {
1765 default:
250d94fd
AM
1766 case E_V850_ARCH:
1767 bfd_default_set_arch_mach (abfd, bfd_arch_v850, bfd_mach_v850);
1768 break;
1769 case E_V850E_ARCH:
1770 bfd_default_set_arch_mach (abfd, bfd_arch_v850, bfd_mach_v850e);
1771 break;
8ad30312
NC
1772 case E_V850E1_ARCH:
1773 bfd_default_set_arch_mach (abfd, bfd_arch_v850, bfd_mach_v850e1);
1774 break;
252b5132 1775 }
b34976b6 1776 return TRUE;
252b5132
RH
1777}
1778
1779/* Store the machine number in the flags field. */
e12dd2ea 1780
252b5132 1781static void
47b0e7ad
NC
1782v850_elf_final_write_processing (bfd *abfd,
1783 bfd_boolean linker ATTRIBUTE_UNUSED)
252b5132
RH
1784{
1785 unsigned long val;
1786
1787 switch (bfd_get_mach (abfd))
1788 {
b34976b6 1789 default:
47b0e7ad
NC
1790 case bfd_mach_v850: val = E_V850_ARCH; break;
1791 case bfd_mach_v850e: val = E_V850E_ARCH; break;
1792 case bfd_mach_v850e1: val = E_V850E1_ARCH; break;
252b5132
RH
1793 }
1794
1795 elf_elfheader (abfd)->e_flags &=~ EF_V850_ARCH;
1796 elf_elfheader (abfd)->e_flags |= val;
1797}
1798
435b1e90 1799/* Function to keep V850 specific file flags. */
e12dd2ea 1800
b34976b6 1801static bfd_boolean
47b0e7ad 1802v850_elf_set_private_flags (bfd *abfd, flagword flags)
252b5132
RH
1803{
1804 BFD_ASSERT (!elf_flags_init (abfd)
1805 || elf_elfheader (abfd)->e_flags == flags);
1806
1807 elf_elfheader (abfd)->e_flags = flags;
b34976b6
AM
1808 elf_flags_init (abfd) = TRUE;
1809 return TRUE;
252b5132
RH
1810}
1811
e12dd2ea
NC
1812/* Merge backend specific data from an object file
1813 to the output object file when linking. */
47b0e7ad 1814
b34976b6 1815static bfd_boolean
47b0e7ad 1816v850_elf_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
252b5132
RH
1817{
1818 flagword out_flags;
1819 flagword in_flags;
1820
1821 if ( bfd_get_flavour (ibfd) != bfd_target_elf_flavour
1822 || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
b34976b6 1823 return TRUE;
252b5132
RH
1824
1825 in_flags = elf_elfheader (ibfd)->e_flags;
1826 out_flags = elf_elfheader (obfd)->e_flags;
1827
1828 if (! elf_flags_init (obfd))
1829 {
1830 /* If the input is the default architecture then do not
1831 bother setting the flags for the output architecture,
1832 instead allow future merges to do this. If no future
1833 merges ever set these flags then they will retain their
1834 unitialised values, which surprise surprise, correspond
1835 to the default values. */
1836 if (bfd_get_arch_info (ibfd)->the_default)
b34976b6 1837 return TRUE;
435b1e90 1838
b34976b6 1839 elf_flags_init (obfd) = TRUE;
252b5132
RH
1840 elf_elfheader (obfd)->e_flags = in_flags;
1841
1842 if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
1843 && bfd_get_arch_info (obfd)->the_default)
e12dd2ea 1844 return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd), bfd_get_mach (ibfd));
252b5132 1845
b34976b6 1846 return TRUE;
252b5132
RH
1847 }
1848
1849 /* Check flag compatibility. */
1850 if (in_flags == out_flags)
b34976b6 1851 return TRUE;
252b5132
RH
1852
1853 if ((in_flags & EF_V850_ARCH) != (out_flags & EF_V850_ARCH)
1854 && (in_flags & EF_V850_ARCH) != E_V850_ARCH)
8ad30312
NC
1855 {
1856 /* Allow v850e1 binaries to be linked with v850e binaries.
1857 Set the output binary to v850e. */
1858 if ((in_flags & EF_V850_ARCH) == E_V850E1_ARCH
1859 && (out_flags & EF_V850_ARCH) == E_V850E_ARCH)
1860 return TRUE;
1861
1862 if ((in_flags & EF_V850_ARCH) == E_V850E_ARCH
1863 && (out_flags & EF_V850_ARCH) == E_V850E1_ARCH)
1864 {
1865 elf_elfheader (obfd)->e_flags =
1866 ((out_flags & ~ EF_V850_ARCH) | E_V850E_ARCH);
1867 return TRUE;
1868 }
1869
d003868e
AM
1870 _bfd_error_handler (_("%B: Architecture mismatch with previous modules"),
1871 ibfd);
8ad30312 1872 }
252b5132 1873
b34976b6 1874 return TRUE;
252b5132 1875}
e12dd2ea
NC
1876
1877/* Display the flags field. */
252b5132 1878
b34976b6 1879static bfd_boolean
47b0e7ad 1880v850_elf_print_private_bfd_data (bfd *abfd, void * ptr)
252b5132
RH
1881{
1882 FILE * file = (FILE *) ptr;
435b1e90 1883
252b5132 1884 BFD_ASSERT (abfd != NULL && ptr != NULL);
435b1e90 1885
252b5132 1886 _bfd_elf_print_private_bfd_data (abfd, ptr);
435b1e90 1887
252b5132
RH
1888 /* xgettext:c-format */
1889 fprintf (file, _("private flags = %lx: "), elf_elfheader (abfd)->e_flags);
435b1e90 1890
252b5132
RH
1891 switch (elf_elfheader (abfd)->e_flags & EF_V850_ARCH)
1892 {
1893 default:
1894 case E_V850_ARCH: fprintf (file, _("v850 architecture")); break;
47b0e7ad 1895 case E_V850E_ARCH: fprintf (file, _("v850e architecture")); break;
8ad30312 1896 case E_V850E1_ARCH: fprintf (file, _("v850e1 architecture")); break;
252b5132 1897 }
435b1e90 1898
252b5132 1899 fputc ('\n', file);
435b1e90 1900
b34976b6 1901 return TRUE;
252b5132
RH
1902}
1903
1904/* V850 ELF uses four common sections. One is the usual one, and the
1905 others are for (small) objects in one of the special data areas:
1906 small, tiny and zero. All the objects are kept together, and then
1907 referenced via the gp register, the ep register or the r0 register
1908 respectively, which yields smaller, faster assembler code. This
1909 approach is copied from elf32-mips.c. */
1910
1911static asection v850_elf_scom_section;
1912static asymbol v850_elf_scom_symbol;
1913static asymbol * v850_elf_scom_symbol_ptr;
1914static asection v850_elf_tcom_section;
1915static asymbol v850_elf_tcom_symbol;
1916static asymbol * v850_elf_tcom_symbol_ptr;
1917static asection v850_elf_zcom_section;
1918static asymbol v850_elf_zcom_symbol;
1919static asymbol * v850_elf_zcom_symbol_ptr;
1920
e12dd2ea
NC
1921/* Given a BFD section, try to locate the
1922 corresponding ELF section index. */
252b5132 1923
b34976b6 1924static bfd_boolean
47b0e7ad
NC
1925v850_elf_section_from_bfd_section (bfd *abfd ATTRIBUTE_UNUSED,
1926 asection *sec,
1927 int *retval)
252b5132
RH
1928{
1929 if (strcmp (bfd_get_section_name (abfd, sec), ".scommon") == 0)
1930 *retval = SHN_V850_SCOMMON;
1931 else if (strcmp (bfd_get_section_name (abfd, sec), ".tcommon") == 0)
1932 *retval = SHN_V850_TCOMMON;
1933 else if (strcmp (bfd_get_section_name (abfd, sec), ".zcommon") == 0)
1934 *retval = SHN_V850_ZCOMMON;
1935 else
b34976b6 1936 return FALSE;
435b1e90 1937
b34976b6 1938 return TRUE;
252b5132
RH
1939}
1940
1941/* Handle the special V850 section numbers that a symbol may use. */
1942
1943static void
47b0e7ad 1944v850_elf_symbol_processing (bfd *abfd, asymbol *asym)
252b5132
RH
1945{
1946 elf_symbol_type * elfsym = (elf_symbol_type *) asym;
9ad5cbcf 1947 unsigned int indx;
435b1e90 1948
9ad5cbcf 1949 indx = elfsym->internal_elf_sym.st_shndx;
252b5132
RH
1950
1951 /* If the section index is an "ordinary" index, then it may
1952 refer to a v850 specific section created by the assembler.
1953 Check the section's type and change the index it matches.
435b1e90 1954
252b5132 1955 FIXME: Should we alter the st_shndx field as well ? */
435b1e90 1956
9ad5cbcf
AM
1957 if (indx < elf_numsections (abfd))
1958 switch (elf_elfsections(abfd)[indx]->sh_type)
252b5132
RH
1959 {
1960 case SHT_V850_SCOMMON:
9ad5cbcf 1961 indx = SHN_V850_SCOMMON;
252b5132 1962 break;
435b1e90 1963
252b5132 1964 case SHT_V850_TCOMMON:
9ad5cbcf 1965 indx = SHN_V850_TCOMMON;
252b5132 1966 break;
435b1e90 1967
252b5132 1968 case SHT_V850_ZCOMMON:
9ad5cbcf 1969 indx = SHN_V850_ZCOMMON;
252b5132 1970 break;
435b1e90 1971
252b5132
RH
1972 default:
1973 break;
1974 }
435b1e90 1975
9ad5cbcf 1976 switch (indx)
252b5132
RH
1977 {
1978 case SHN_V850_SCOMMON:
1979 if (v850_elf_scom_section.name == NULL)
1980 {
1981 /* Initialize the small common section. */
1982 v850_elf_scom_section.name = ".scommon";
1983 v850_elf_scom_section.flags = SEC_IS_COMMON | SEC_ALLOC | SEC_DATA;
1984 v850_elf_scom_section.output_section = & v850_elf_scom_section;
1985 v850_elf_scom_section.symbol = & v850_elf_scom_symbol;
1986 v850_elf_scom_section.symbol_ptr_ptr = & v850_elf_scom_symbol_ptr;
1987 v850_elf_scom_symbol.name = ".scommon";
1988 v850_elf_scom_symbol.flags = BSF_SECTION_SYM;
1989 v850_elf_scom_symbol.section = & v850_elf_scom_section;
1990 v850_elf_scom_symbol_ptr = & v850_elf_scom_symbol;
1991 }
1992 asym->section = & v850_elf_scom_section;
1993 asym->value = elfsym->internal_elf_sym.st_size;
1994 break;
435b1e90 1995
252b5132
RH
1996 case SHN_V850_TCOMMON:
1997 if (v850_elf_tcom_section.name == NULL)
1998 {
1999 /* Initialize the tcommon section. */
2000 v850_elf_tcom_section.name = ".tcommon";
2001 v850_elf_tcom_section.flags = SEC_IS_COMMON;
2002 v850_elf_tcom_section.output_section = & v850_elf_tcom_section;
2003 v850_elf_tcom_section.symbol = & v850_elf_tcom_symbol;
2004 v850_elf_tcom_section.symbol_ptr_ptr = & v850_elf_tcom_symbol_ptr;
2005 v850_elf_tcom_symbol.name = ".tcommon";
2006 v850_elf_tcom_symbol.flags = BSF_SECTION_SYM;
2007 v850_elf_tcom_symbol.section = & v850_elf_tcom_section;
2008 v850_elf_tcom_symbol_ptr = & v850_elf_tcom_symbol;
2009 }
2010 asym->section = & v850_elf_tcom_section;
2011 asym->value = elfsym->internal_elf_sym.st_size;
2012 break;
2013
2014 case SHN_V850_ZCOMMON:
2015 if (v850_elf_zcom_section.name == NULL)
2016 {
2017 /* Initialize the zcommon section. */
2018 v850_elf_zcom_section.name = ".zcommon";
2019 v850_elf_zcom_section.flags = SEC_IS_COMMON;
2020 v850_elf_zcom_section.output_section = & v850_elf_zcom_section;
2021 v850_elf_zcom_section.symbol = & v850_elf_zcom_symbol;
2022 v850_elf_zcom_section.symbol_ptr_ptr = & v850_elf_zcom_symbol_ptr;
2023 v850_elf_zcom_symbol.name = ".zcommon";
2024 v850_elf_zcom_symbol.flags = BSF_SECTION_SYM;
2025 v850_elf_zcom_symbol.section = & v850_elf_zcom_section;
2026 v850_elf_zcom_symbol_ptr = & v850_elf_zcom_symbol;
2027 }
2028 asym->section = & v850_elf_zcom_section;
2029 asym->value = elfsym->internal_elf_sym.st_size;
2030 break;
2031 }
2032}
2033
2034/* Hook called by the linker routine which adds symbols from an object
2035 file. We must handle the special v850 section numbers here. */
2036
b34976b6 2037static bfd_boolean
47b0e7ad
NC
2038v850_elf_add_symbol_hook (bfd *abfd,
2039 struct bfd_link_info *info ATTRIBUTE_UNUSED,
2040 Elf_Internal_Sym *sym,
2041 const char **namep ATTRIBUTE_UNUSED,
2042 flagword *flagsp ATTRIBUTE_UNUSED,
2043 asection **secp,
2044 bfd_vma *valp)
252b5132 2045{
9ad5cbcf 2046 unsigned int indx = sym->st_shndx;
435b1e90 2047
252b5132
RH
2048 /* If the section index is an "ordinary" index, then it may
2049 refer to a v850 specific section created by the assembler.
2050 Check the section's type and change the index it matches.
435b1e90 2051
252b5132 2052 FIXME: Should we alter the st_shndx field as well ? */
435b1e90 2053
9ad5cbcf
AM
2054 if (indx < elf_numsections (abfd))
2055 switch (elf_elfsections(abfd)[indx]->sh_type)
252b5132
RH
2056 {
2057 case SHT_V850_SCOMMON:
9ad5cbcf 2058 indx = SHN_V850_SCOMMON;
252b5132 2059 break;
435b1e90 2060
252b5132 2061 case SHT_V850_TCOMMON:
9ad5cbcf 2062 indx = SHN_V850_TCOMMON;
252b5132 2063 break;
435b1e90 2064
252b5132 2065 case SHT_V850_ZCOMMON:
9ad5cbcf 2066 indx = SHN_V850_ZCOMMON;
252b5132 2067 break;
435b1e90 2068
252b5132
RH
2069 default:
2070 break;
2071 }
435b1e90 2072
9ad5cbcf 2073 switch (indx)
252b5132
RH
2074 {
2075 case SHN_V850_SCOMMON:
2076 *secp = bfd_make_section_old_way (abfd, ".scommon");
2077 (*secp)->flags |= SEC_IS_COMMON;
2078 *valp = sym->st_size;
2079 break;
435b1e90 2080
252b5132
RH
2081 case SHN_V850_TCOMMON:
2082 *secp = bfd_make_section_old_way (abfd, ".tcommon");
2083 (*secp)->flags |= SEC_IS_COMMON;
2084 *valp = sym->st_size;
2085 break;
435b1e90 2086
252b5132
RH
2087 case SHN_V850_ZCOMMON:
2088 *secp = bfd_make_section_old_way (abfd, ".zcommon");
2089 (*secp)->flags |= SEC_IS_COMMON;
2090 *valp = sym->st_size;
2091 break;
2092 }
2093
b34976b6 2094 return TRUE;
252b5132
RH
2095}
2096
b34976b6 2097static bfd_boolean
47b0e7ad
NC
2098v850_elf_link_output_symbol_hook (struct bfd_link_info *info ATTRIBUTE_UNUSED,
2099 const char *name ATTRIBUTE_UNUSED,
2100 Elf_Internal_Sym *sym,
2101 asection *input_sec,
2102 struct elf_link_hash_entry *h ATTRIBUTE_UNUSED)
252b5132
RH
2103{
2104 /* If we see a common symbol, which implies a relocatable link, then
2105 if a symbol was in a special common section in an input file, mark
2106 it as a special common in the output file. */
435b1e90 2107
252b5132
RH
2108 if (sym->st_shndx == SHN_COMMON)
2109 {
2110 if (strcmp (input_sec->name, ".scommon") == 0)
2111 sym->st_shndx = SHN_V850_SCOMMON;
2112 else if (strcmp (input_sec->name, ".tcommon") == 0)
2113 sym->st_shndx = SHN_V850_TCOMMON;
2114 else if (strcmp (input_sec->name, ".zcommon") == 0)
2115 sym->st_shndx = SHN_V850_ZCOMMON;
2116 }
2117
b34976b6 2118 return TRUE;
252b5132
RH
2119}
2120
b34976b6 2121static bfd_boolean
6dc132d9
L
2122v850_elf_section_from_shdr (bfd *abfd,
2123 Elf_Internal_Shdr *hdr,
2124 const char *name,
2125 int shindex)
252b5132
RH
2126{
2127 /* There ought to be a place to keep ELF backend specific flags, but
2128 at the moment there isn't one. We just keep track of the
2129 sections by their name, instead. */
2130
6dc132d9 2131 if (! _bfd_elf_make_section_from_shdr (abfd, hdr, name, shindex))
b34976b6 2132 return FALSE;
252b5132
RH
2133
2134 switch (hdr->sh_type)
2135 {
2136 case SHT_V850_SCOMMON:
2137 case SHT_V850_TCOMMON:
2138 case SHT_V850_ZCOMMON:
2139 if (! bfd_set_section_flags (abfd, hdr->bfd_section,
2140 (bfd_get_section_flags (abfd,
2141 hdr->bfd_section)
2142 | SEC_IS_COMMON)))
b34976b6 2143 return FALSE;
252b5132
RH
2144 }
2145
b34976b6 2146 return TRUE;
252b5132
RH
2147}
2148
e12dd2ea
NC
2149/* Set the correct type for a V850 ELF section. We do this
2150 by the section name, which is a hack, but ought to work. */
2151
b34976b6 2152static bfd_boolean
47b0e7ad
NC
2153v850_elf_fake_sections (bfd *abfd ATTRIBUTE_UNUSED,
2154 Elf_Internal_Shdr *hdr,
2155 asection *sec)
252b5132 2156{
47b0e7ad 2157 const char * name;
252b5132
RH
2158
2159 name = bfd_get_section_name (abfd, sec);
2160
2161 if (strcmp (name, ".scommon") == 0)
47b0e7ad 2162 hdr->sh_type = SHT_V850_SCOMMON;
252b5132 2163 else if (strcmp (name, ".tcommon") == 0)
47b0e7ad 2164 hdr->sh_type = SHT_V850_TCOMMON;
252b5132
RH
2165 else if (strcmp (name, ".zcommon") == 0)
2166 hdr->sh_type = SHT_V850_ZCOMMON;
435b1e90 2167
b34976b6 2168 return TRUE;
252b5132 2169}
86aba9db
NC
2170
2171/* Delete some bytes from a section while relaxing. */
2172
b34976b6 2173static bfd_boolean
47b0e7ad
NC
2174v850_elf_relax_delete_bytes (bfd *abfd,
2175 asection *sec,
2176 bfd_vma addr,
2177 bfd_vma toaddr,
2178 int count)
86aba9db 2179{
b34976b6
AM
2180 Elf_Internal_Shdr *symtab_hdr;
2181 Elf32_External_Sym *extsyms;
2182 Elf32_External_Sym *esym;
2183 Elf32_External_Sym *esymend;
2184 int index;
2185 unsigned int sec_shndx;
2186 bfd_byte *contents;
2187 Elf_Internal_Rela *irel;
2188 Elf_Internal_Rela *irelend;
2189 struct elf_link_hash_entry *sym_hash;
2190 Elf_Internal_Shdr *shndx_hdr;
2191 Elf_External_Sym_Shndx *shndx;
86aba9db
NC
2192
2193 symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
2194 extsyms = (Elf32_External_Sym *) symtab_hdr->contents;
2195
2196 sec_shndx = _bfd_elf_section_from_bfd_section (abfd, sec);
2197
2198 contents = elf_section_data (sec)->this_hdr.contents;
2199
2200 /* The deletion must stop at the next ALIGN reloc for an alignment
2201 power larger than the number of bytes we are deleting. */
2202
2203 /* Actually delete the bytes. */
2204#if (DEBUG_RELAX & 2)
2205 fprintf (stderr, "relax_delete: contents: sec: %s %p .. %p %x\n",
2206 sec->name, addr, toaddr, count );
2207#endif
2208 memmove (contents + addr, contents + addr + count,
2209 toaddr - addr - count);
2210 memset (contents + toaddr-count, 0, count);
2211
2212 /* Adjust all the relocs. */
2213 irel = elf_section_data (sec)->relocs;
2214 irelend = irel + sec->reloc_count;
2215 shndx_hdr = &elf_tdata (abfd)->symtab_shndx_hdr;
2216 shndx = (Elf_External_Sym_Shndx *) shndx_hdr->contents;
2217
2218 for (; irel < irelend; irel++)
2219 {
2220 bfd_vma raddr, paddr, symval;
2221 Elf_Internal_Sym isym;
2222
2223 /* Get the new reloc address. */
2224 raddr = irel->r_offset;
2225 if ((raddr >= (addr + count) && raddr < toaddr))
b34976b6 2226 irel->r_offset -= count;
86aba9db
NC
2227
2228 if (raddr >= addr && raddr < addr + count)
2229 {
2230 irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irel->r_info),
2231 (int) R_V850_NONE);
2232 continue;
2233 }
b34976b6 2234
86aba9db
NC
2235 if (ELF32_R_TYPE (irel->r_info) == (int) R_V850_ALIGN)
2236 continue;
2237
2238 bfd_elf32_swap_symbol_in (abfd,
2239 extsyms + ELF32_R_SYM (irel->r_info),
2240 shndx ? shndx + ELF32_R_SYM (irel->r_info) : NULL,
2241 & isym);
b34976b6 2242
86aba9db
NC
2243 if (isym.st_shndx != sec_shndx)
2244 continue;
2245
2246 /* Get the value of the symbol referred to by the reloc. */
2247 if (ELF32_R_SYM (irel->r_info) < symtab_hdr->sh_info)
2248 {
2249 symval = isym.st_value;
2250#if (DEBUG_RELAX & 2)
2251 {
2252 char * name = bfd_elf_string_from_elf_section
2253 (abfd, symtab_hdr->sh_link, isym.st_name);
2254 fprintf (stderr,
2255 "relax_delete: local: sec: %s, sym: %s (%d), value: %x + %x + %x addend %x\n",
2256 sec->name, name, isym.st_name,
2257 sec->output_section->vma, sec->output_offset,
2258 isym.st_value, irel->r_addend);
2259 }
2260#endif
2261 }
2262 else
2263 {
2264 unsigned long indx;
2265 struct elf_link_hash_entry * h;
2266
2267 /* An external symbol. */
2268 indx = ELF32_R_SYM (irel->r_info) - symtab_hdr->sh_info;
2269
2270 h = elf_sym_hashes (abfd) [indx];
2271 BFD_ASSERT (h != NULL);
2272
2273 symval = h->root.u.def.value;
2274#if (DEBUG_RELAX & 2)
2275 fprintf (stderr,
2276 "relax_delete: defined: sec: %s, name: %s, value: %x + %x + %x addend %x\n",
2277 sec->name, h->root.root.string, h->root.u.def.value,
2278 sec->output_section->vma, sec->output_offset, irel->r_addend);
2279#endif
2280 }
b34976b6 2281
86aba9db 2282 paddr = symval + irel->r_addend;
b34976b6 2283
86aba9db
NC
2284 if ( (symval >= addr + count && symval < toaddr)
2285 && (paddr < addr + count || paddr >= toaddr))
2286 irel->r_addend += count;
2287 else if ( (symval < addr + count || symval >= toaddr)
2288 && (paddr >= addr + count && paddr < toaddr))
2289 irel->r_addend -= count;
2290 }
2291
2292 /* Adjust the local symbols defined in this section. */
2293 esym = extsyms;
2294 esymend = esym + symtab_hdr->sh_info;
2295
2296 for (; esym < esymend; esym++, shndx = (shndx ? shndx + 1 : NULL))
2297 {
2298 Elf_Internal_Sym isym;
2299
2300 bfd_elf32_swap_symbol_in (abfd, esym, shndx, & isym);
2301
2302 if (isym.st_shndx == sec_shndx
2303 && isym.st_value >= addr + count
2304 && isym.st_value < toaddr)
2305 {
2306 isym.st_value -= count;
2307
2308 if (isym.st_value + isym.st_size >= toaddr)
b34976b6
AM
2309 isym.st_size += count;
2310
63a23799 2311 bfd_elf32_swap_symbol_out (abfd, & isym, esym, shndx);
86aba9db
NC
2312 }
2313 else if (isym.st_shndx == sec_shndx
2314 && isym.st_value < addr + count)
2315 {
2316 if (isym.st_value+isym.st_size >= addr + count
2317 && isym.st_value+isym.st_size < toaddr)
2318 isym.st_size -= count;
2319
2320 if (isym.st_value >= addr
2321 && isym.st_value < addr + count)
2322 isym.st_value = addr;
2323
63a23799 2324 bfd_elf32_swap_symbol_out (abfd, & isym, esym, shndx);
86aba9db
NC
2325 }
2326 }
2327
2328 /* Now adjust the global symbols defined in this section. */
2329 esym = extsyms + symtab_hdr->sh_info;
2330 esymend = extsyms + (symtab_hdr->sh_size / sizeof (Elf32_External_Sym));
2331
2332 for (index = 0; esym < esymend; esym ++, index ++)
2333 {
2334 Elf_Internal_Sym isym;
2335
2336 bfd_elf32_swap_symbol_in (abfd, esym, shndx, & isym);
2337 sym_hash = elf_sym_hashes (abfd) [index];
2338
2339 if (isym.st_shndx == sec_shndx
2340 && ((sym_hash)->root.type == bfd_link_hash_defined
2341 || (sym_hash)->root.type == bfd_link_hash_defweak)
2342 && (sym_hash)->root.u.def.section == sec
2343 && (sym_hash)->root.u.def.value >= addr + count
2344 && (sym_hash)->root.u.def.value < toaddr)
2345 {
2346 if ((sym_hash)->root.u.def.value + isym.st_size >= toaddr)
2347 {
2348 isym.st_size += count;
63a23799 2349 bfd_elf32_swap_symbol_out (abfd, & isym, esym, shndx);
86aba9db
NC
2350 }
2351
2352 (sym_hash)->root.u.def.value -= count;
2353 }
2354 else if (isym.st_shndx == sec_shndx
2355 && ((sym_hash)->root.type == bfd_link_hash_defined
2356 || (sym_hash)->root.type == bfd_link_hash_defweak)
2357 && (sym_hash)->root.u.def.section == sec
2358 && (sym_hash)->root.u.def.value < addr + count)
2359 {
2360 if ((sym_hash)->root.u.def.value+isym.st_size >= addr + count
2361 && (sym_hash)->root.u.def.value+isym.st_size < toaddr)
2362 isym.st_size -= count;
2363
2364 if ((sym_hash)->root.u.def.value >= addr
2365 && (sym_hash)->root.u.def.value < addr + count)
2366 (sym_hash)->root.u.def.value = addr;
2367
63a23799 2368 bfd_elf32_swap_symbol_out (abfd, & isym, esym, shndx);
86aba9db
NC
2369 }
2370
2371 if (shndx)
2372 ++ shndx;
2373 }
2374
b34976b6 2375 return TRUE;
86aba9db
NC
2376}
2377
2378#define NOP_OPCODE (0x0000)
b34976b6 2379#define MOVHI 0x0640 /* 4byte */
86aba9db 2380#define MOVHI_MASK 0x07e0
b34976b6 2381#define MOVHI_R1(insn) ((insn) & 0x1f) /* 4byte */
86aba9db
NC
2382#define MOVHI_R2(insn) ((insn) >> 11)
2383#define MOVEA 0x0620 /* 2byte */
2384#define MOVEA_MASK 0x07e0
2385#define MOVEA_R1(insn) ((insn) & 0x1f)
2386#define MOVEA_R2(insn) ((insn) >> 11)
2387#define JARL_4 0x00040780 /* 4byte */
2388#define JARL_4_MASK 0xFFFF07FF
2389#define JARL_R2(insn) (int)(((insn) & (~JARL_4_MASK)) >> 11)
2390#define ADD_I 0x0240 /* 2byte */
2391#define ADD_I_MASK 0x07e0
2392#define ADD_I5(insn) ((((insn) & 0x001f) << 11) >> 11) /* 2byte */
2393#define ADD_R2(insn) ((insn) >> 11)
2394#define JMP_R 0x0060 /* 2byte */
2395#define JMP_R_MASK 0xFFE0
2396#define JMP_R1(insn) ((insn) & 0x1f)
2397
b34976b6 2398static bfd_boolean
47b0e7ad
NC
2399v850_elf_relax_section (bfd *abfd,
2400 asection *sec,
2401 struct bfd_link_info *link_info,
2402 bfd_boolean *again)
86aba9db 2403{
b34976b6
AM
2404 Elf_Internal_Shdr *symtab_hdr;
2405 Elf_Internal_Rela *internal_relocs;
2406 Elf_Internal_Rela *irel;
2407 Elf_Internal_Rela *irelend;
2408 Elf_Internal_Rela *irelalign = NULL;
2409 Elf_Internal_Sym *isymbuf = NULL;
2410 bfd_byte *contents = NULL;
2411 bfd_vma addr = 0;
2412 bfd_vma toaddr;
2413 int align_pad_size = 0;
2414 bfd_boolean result = TRUE;
2415
2416 *again = FALSE;
86aba9db 2417
1049f94e 2418 if (link_info->relocatable
86aba9db
NC
2419 || (sec->flags & SEC_RELOC) == 0
2420 || sec->reloc_count == 0)
b34976b6 2421 return TRUE;
86aba9db 2422
86aba9db
NC
2423 symtab_hdr = & elf_tdata (abfd)->symtab_hdr;
2424
45d6a902 2425 internal_relocs = (_bfd_elf_link_read_relocs
47b0e7ad 2426 (abfd, sec, NULL, NULL, link_info->keep_memory));
86aba9db
NC
2427 if (internal_relocs == NULL)
2428 goto error_return;
86aba9db
NC
2429
2430 irelend = internal_relocs + sec->reloc_count;
b34976b6 2431
eea6121a 2432 while (addr < sec->size)
86aba9db 2433 {
eea6121a 2434 toaddr = sec->size;
86aba9db
NC
2435
2436 for (irel = internal_relocs; irel < irelend; irel ++)
2437 if (ELF32_R_TYPE (irel->r_info) == (int) R_V850_ALIGN
2438 && irel->r_offset > addr
2439 && irel->r_offset < toaddr)
2440 toaddr = irel->r_offset;
b34976b6 2441
86aba9db
NC
2442#ifdef DEBUG_RELAX
2443 fprintf (stderr, "relax region 0x%x to 0x%x align pad %d\n",
2444 addr, toaddr, align_pad_size);
2445#endif
2446 if (irelalign)
2447 {
2448 bfd_vma alignto;
2449 bfd_vma alignmoveto;
2450
2451 alignmoveto = BFD_ALIGN (addr - align_pad_size, 1 << irelalign->r_addend);
2452 alignto = BFD_ALIGN (addr, 1 << irelalign->r_addend);
2453
2454 if (alignmoveto < alignto)
2455 {
2456 unsigned int i;
2457
2458 align_pad_size = alignto - alignmoveto;
2459#ifdef DEBUG_RELAX
2460 fprintf (stderr, "relax move region 0x%x to 0x%x delete size 0x%x\n",
2461 alignmoveto, toaddr, align_pad_size);
2462#endif
2463 if (!v850_elf_relax_delete_bytes (abfd, sec, alignmoveto,
2464 toaddr, align_pad_size))
b34976b6 2465 goto error_return;
86aba9db
NC
2466
2467 for (i = BFD_ALIGN (toaddr - align_pad_size, 1);
2468 (i + 1) < toaddr; i += 2)
2469 bfd_put_16 (abfd, NOP_OPCODE, contents + i);
2470
2471 addr = alignmoveto;
2472 }
2473 else
2474 align_pad_size = 0;
2475 }
2476
2477 for (irel = internal_relocs; irel < irelend; irel++)
2478 {
b34976b6
AM
2479 bfd_vma laddr;
2480 bfd_vma addend;
2481 bfd_vma symval;
2482 int insn[5];
2483 int no_match = -1;
2484 Elf_Internal_Rela *hi_irelfn;
2485 Elf_Internal_Rela *lo_irelfn;
2486 Elf_Internal_Rela *irelcall;
2487 bfd_signed_vma foff;
86aba9db
NC
2488
2489 if (! (irel->r_offset >= addr && irel->r_offset < toaddr
2490 && (ELF32_R_TYPE (irel->r_info) == (int) R_V850_LONGCALL
2491 || ELF32_R_TYPE (irel->r_info) == (int) R_V850_LONGJUMP)))
2492 continue;
2493
2494#ifdef DEBUG_RELAX
2495 fprintf (stderr, "relax check r_info 0x%x r_offset 0x%x r_addend 0x%x\n",
2496 irel->r_info,
2497 irel->r_offset,
2498 irel->r_addend );
2499#endif
2500
2501 /* Get the section contents. */
2502 if (contents == NULL)
2503 {
2504 if (elf_section_data (sec)->this_hdr.contents != NULL)
2505 contents = elf_section_data (sec)->this_hdr.contents;
2506 else
2507 {
47b0e7ad 2508 if (! bfd_malloc_and_get_section (abfd, sec, &contents))
86aba9db
NC
2509 goto error_return;
2510 }
2511 }
2512
5cec6941
NC
2513 /* Read this BFD's local symbols if we haven't done so already. */
2514 if (isymbuf == NULL && symtab_hdr->sh_info != 0)
86aba9db 2515 {
5cec6941
NC
2516 isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
2517 if (isymbuf == NULL)
2518 isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
2519 symtab_hdr->sh_info, 0,
2520 NULL, NULL, NULL);
2521 if (isymbuf == NULL)
2522 goto error_return;
86aba9db
NC
2523 }
2524
2525 laddr = irel->r_offset;
2526
2527 if (ELF32_R_TYPE (irel->r_info) == (int) R_V850_LONGCALL)
2528 {
2529 /* Check code for -mlong-calls output. */
eea6121a 2530 if (laddr + 16 <= (bfd_vma) sec->size)
86aba9db
NC
2531 {
2532 insn[0] = bfd_get_16 (abfd, contents + laddr);
2533 insn[1] = bfd_get_16 (abfd, contents + laddr + 4);
2534 insn[2] = bfd_get_32 (abfd, contents + laddr + 8);
2535 insn[3] = bfd_get_16 (abfd, contents + laddr + 12);
2536 insn[4] = bfd_get_16 (abfd, contents + laddr + 14);
b34976b6 2537
86aba9db
NC
2538 if ((insn[0] & MOVHI_MASK) != MOVHI
2539 || MOVHI_R1 (insn[0]) != 0)
2540 no_match = 0;
2541
2542 if (no_match < 0
2543 && ((insn[1] & MOVEA_MASK) != MOVEA
2544 || MOVHI_R2 (insn[0]) != MOVEA_R1 (insn[1])))
2545 no_match = 1;
2546
2547 if (no_match < 0
2548 && (insn[2] & JARL_4_MASK) != JARL_4)
2549 no_match = 2;
2550
2551 if (no_match < 0
2552 && ((insn[3] & ADD_I_MASK) != ADD_I
2553 || ADD_I5 (insn[3]) != 4
2554 || JARL_R2 (insn[2]) != ADD_R2 (insn[3])))
2555 no_match = 3;
2556
2557 if (no_match < 0
2558 && ((insn[4] & JMP_R_MASK) != JMP_R
2559 || MOVEA_R2 (insn[1]) != JMP_R1 (insn[4])))
2560 no_match = 4;
2561 }
2562 else
2563 {
2564 ((*_bfd_error_handler)
2565 ("%s: 0x%lx: warning: R_V850_LONGCALL points to unrecognized insns",
2566 bfd_get_filename (abfd), (unsigned long) irel->r_offset));
2567
2568 continue;
2569 }
2570
2571 if (no_match >= 0)
2572 {
2573 ((*_bfd_error_handler)
2574 ("%s: 0x%lx: warning: R_V850_LONGCALL points to unrecognized insn 0x%x",
2575 bfd_get_filename (abfd), (unsigned long) irel->r_offset+no_match, insn[no_match]));
2576
2577 continue;
b34976b6 2578 }
86aba9db
NC
2579
2580 /* Get the reloc for the address from which the register is
2581 being loaded. This reloc will tell us which function is
2582 actually being called. */
2583 for (hi_irelfn = internal_relocs; hi_irelfn < irelend; hi_irelfn ++)
2584 if (hi_irelfn->r_offset == laddr + 2
b34976b6 2585 && ELF32_R_TYPE (hi_irelfn->r_info)
86aba9db
NC
2586 == (int) R_V850_HI16_S)
2587 break;
2588
2589 for (lo_irelfn = internal_relocs; lo_irelfn < irelend; lo_irelfn ++)
2590 if (lo_irelfn->r_offset == laddr + 6
2591 && ELF32_R_TYPE (lo_irelfn->r_info)
2592 == (int) R_V850_LO16)
2593 break;
2594
2595 for (irelcall = internal_relocs; irelcall < irelend; irelcall ++)
2596 if (irelcall->r_offset == laddr + 8
2597 && ELF32_R_TYPE (irelcall->r_info)
2598 == (int) R_V850_22_PCREL)
2599 break;
2600
2601 if ( hi_irelfn == irelend
2602 || lo_irelfn == irelend
2603 || irelcall == irelend)
2604 {
2605 ((*_bfd_error_handler)
2606 ("%s: 0x%lx: warning: R_V850_LONGCALL points to unrecognized reloc",
2607 bfd_get_filename (abfd), (unsigned long) irel->r_offset ));
2608
2609 continue;
2610 }
b34976b6 2611
86aba9db
NC
2612 if (ELF32_R_SYM (irelcall->r_info) < symtab_hdr->sh_info)
2613 {
5cec6941 2614 Elf_Internal_Sym * isym;
86aba9db
NC
2615
2616 /* A local symbol. */
5cec6941 2617 isym = isymbuf + ELF32_R_SYM (irelcall->r_info);
86aba9db 2618
5cec6941 2619 symval = isym->st_value;
86aba9db
NC
2620 }
2621 else
2622 {
2623 unsigned long indx;
2624 struct elf_link_hash_entry * h;
2625
2626 /* An external symbol. */
2627 indx = ELF32_R_SYM (irelcall->r_info) - symtab_hdr->sh_info;
2628 h = elf_sym_hashes (abfd)[indx];
2629 BFD_ASSERT (h != NULL);
2630
2631 if ( h->root.type != bfd_link_hash_defined
2632 && h->root.type != bfd_link_hash_defweak)
2633 /* This appears to be a reference to an undefined
2634 symbol. Just ignore it--it will be caught by the
2635 regular reloc processing. */
2636 continue;
2637
2638 symval = h->root.u.def.value;
2639 }
2640
2641 if (symval + irelcall->r_addend != irelcall->r_offset + 4)
2642 {
2643 ((*_bfd_error_handler)
2644 ("%s: 0x%lx: warning: R_V850_LONGCALL points to unrecognized reloc 0x%lx",
2645 bfd_get_filename (abfd), (unsigned long) irel->r_offset, irelcall->r_offset ));
2646
2647 continue;
2648 }
2649
2650 /* Get the value of the symbol referred to by the reloc. */
2651 if (ELF32_R_SYM (hi_irelfn->r_info) < symtab_hdr->sh_info)
2652 {
b34976b6
AM
2653 Elf_Internal_Sym *isym;
2654 asection *sym_sec;
86aba9db
NC
2655
2656 /* A local symbol. */
5cec6941 2657 isym = isymbuf + ELF32_R_SYM (hi_irelfn->r_info);
b34976b6 2658
5cec6941 2659 if (isym->st_shndx == SHN_UNDEF)
86aba9db 2660 sym_sec = bfd_und_section_ptr;
5cec6941 2661 else if (isym->st_shndx == SHN_ABS)
86aba9db 2662 sym_sec = bfd_abs_section_ptr;
5cec6941 2663 else if (isym->st_shndx == SHN_COMMON)
86aba9db
NC
2664 sym_sec = bfd_com_section_ptr;
2665 else
5cec6941
NC
2666 sym_sec = bfd_section_from_elf_index (abfd, isym->st_shndx);
2667 symval = (isym->st_value
86aba9db
NC
2668 + sym_sec->output_section->vma
2669 + sym_sec->output_offset);
2670 }
2671 else
2672 {
2673 unsigned long indx;
b34976b6 2674 struct elf_link_hash_entry *h;
86aba9db
NC
2675
2676 /* An external symbol. */
5cec6941 2677 indx = ELF32_R_SYM (hi_irelfn->r_info) - symtab_hdr->sh_info;
86aba9db
NC
2678 h = elf_sym_hashes (abfd)[indx];
2679 BFD_ASSERT (h != NULL);
2680
2681 if ( h->root.type != bfd_link_hash_defined
2682 && h->root.type != bfd_link_hash_defweak)
2683 /* This appears to be a reference to an undefined
2684 symbol. Just ignore it--it will be caught by the
2685 regular reloc processing. */
2686 continue;
2687
2688 symval = (h->root.u.def.value
2689 + h->root.u.def.section->output_section->vma
2690 + h->root.u.def.section->output_offset);
2691 }
2692
2693 addend = irel->r_addend;
2694
2695 foff = (symval + addend
2696 - (irel->r_offset
2697 + sec->output_section->vma
2698 + sec->output_offset
2699 + 4));
2700#ifdef DEBUG_RELAX
2701 fprintf (stderr, "relax longcall r_offset 0x%x ptr 0x%x symbol 0x%x addend 0x%x distance 0x%x\n",
2702 irel->r_offset,
2703 (irel->r_offset
2704 + sec->output_section->vma
2705 + sec->output_offset),
2706 symval, addend, foff);
2707#endif
2708
2709 if (foff < -0x100000 || foff >= 0x100000)
2710 /* After all that work, we can't shorten this function call. */
2711 continue;
2712
2713 /* For simplicity of coding, we are going to modify the section
2714 contents, the section relocs, and the BFD symbol table. We
2715 must tell the rest of the code not to free up this
2716 information. It would be possible to instead create a table
2717 of changes which have to be made, as is done in coff-mips.c;
2718 that would be more work, but would require less memory when
2719 the linker is run. */
2720 elf_section_data (sec)->relocs = internal_relocs;
86aba9db 2721 elf_section_data (sec)->this_hdr.contents = contents;
5cec6941 2722 symtab_hdr->contents = (bfd_byte *) isymbuf;
b34976b6 2723
86aba9db
NC
2724 /* Replace the long call with a jarl. */
2725 irel->r_info = ELF32_R_INFO (ELF32_R_SYM (hi_irelfn->r_info), R_V850_22_PCREL);
2726
2727 addend = 0;
2728
2729 if (ELF32_R_SYM (hi_irelfn->r_info) < symtab_hdr->sh_info)
2730 /* If this needs to be changed because of future relaxing,
2731 it will be handled here like other internal IND12W
2732 relocs. */
2733 bfd_put_32 (abfd,
2734 0x00000780 | (JARL_R2 (insn[2])<<11) | ((addend << 16) & 0xffff) | ((addend >> 16) & 0xf),
2735 contents + irel->r_offset);
2736 else
2737 /* We can't fully resolve this yet, because the external
2738 symbol value may be changed by future relaxing.
2739 We let the final link phase handle it. */
2740 bfd_put_32 (abfd, 0x00000780 | (JARL_R2 (insn[2])<<11),
2741 contents + irel->r_offset);
2742
b34976b6 2743 hi_irelfn->r_info =
86aba9db
NC
2744 ELF32_R_INFO (ELF32_R_SYM (hi_irelfn->r_info), R_V850_NONE);
2745 lo_irelfn->r_info =
2746 ELF32_R_INFO (ELF32_R_SYM (lo_irelfn->r_info), R_V850_NONE);
2747 irelcall->r_info =
2748 ELF32_R_INFO (ELF32_R_SYM (irelcall->r_info), R_V850_NONE);
2749
2750 if (! v850_elf_relax_delete_bytes (abfd, sec,
2751 irel->r_offset + 4, toaddr, 12))
2752 goto error_return;
2753
2754 align_pad_size += 12;
2755 }
2756 else if (ELF32_R_TYPE (irel->r_info) == (int) R_V850_LONGJUMP)
2757 {
2758 /* Check code for -mlong-jumps output. */
eea6121a 2759 if (laddr + 10 <= (bfd_vma) sec->size)
86aba9db
NC
2760 {
2761 insn[0] = bfd_get_16 (abfd, contents + laddr);
2762 insn[1] = bfd_get_16 (abfd, contents + laddr + 4);
2763 insn[2] = bfd_get_16 (abfd, contents + laddr + 8);
2764
2765 if ((insn[0] & MOVHI_MASK) != MOVHI
2766 || MOVHI_R1 (insn[0]) != 0)
2767 no_match = 0;
2768
2769 if (no_match < 0
2770 && ((insn[1] & MOVEA_MASK) != MOVEA
2771 || MOVHI_R2 (insn[0]) != MOVEA_R1 (insn[1])))
2772 no_match = 1;
2773
2774 if (no_match < 0
2775 && ((insn[2] & JMP_R_MASK) != JMP_R
2776 || MOVEA_R2 (insn[1]) != JMP_R1 (insn[2])))
2777 no_match = 4;
2778 }
2779 else
2780 {
2781 ((*_bfd_error_handler)
2782 ("%s: 0x%lx: warning: R_V850_LONGJUMP points to unrecognized insns",
2783 bfd_get_filename (abfd), (unsigned long) irel->r_offset));
2784
2785 continue;
2786 }
2787
2788 if (no_match >= 0)
2789 {
2790 ((*_bfd_error_handler)
2791 ("%s: 0x%lx: warning: R_V850_LONGJUMP points to unrecognized insn 0x%x",
2792 bfd_get_filename (abfd), (unsigned long) irel->r_offset+no_match, insn[no_match]));
2793
2794 continue;
2795 }
2796
2797 /* Get the reloc for the address from which the register is
2798 being loaded. This reloc will tell us which function is
2799 actually being called. */
2800 for (hi_irelfn = internal_relocs; hi_irelfn < irelend; hi_irelfn ++)
2801 if (hi_irelfn->r_offset == laddr + 2
b34976b6 2802 && ELF32_R_TYPE (hi_irelfn->r_info) == (int) R_V850_HI16_S)
86aba9db
NC
2803 break;
2804
2805 for (lo_irelfn = internal_relocs; lo_irelfn < irelend; lo_irelfn ++)
2806 if (lo_irelfn->r_offset == laddr + 6
2807 && ELF32_R_TYPE (lo_irelfn->r_info) == (int) R_V850_LO16)
2808 break;
2809
2810 if ( hi_irelfn == irelend
2811 || lo_irelfn == irelend)
2812 {
2813 ((*_bfd_error_handler)
2814 ("%s: 0x%lx: warning: R_V850_LONGJUMP points to unrecognized reloc",
2815 bfd_get_filename (abfd), (unsigned long) irel->r_offset ));
2816
2817 continue;
2818 }
b34976b6 2819
86aba9db
NC
2820 /* Get the value of the symbol referred to by the reloc. */
2821 if (ELF32_R_SYM (hi_irelfn->r_info) < symtab_hdr->sh_info)
2822 {
5cec6941
NC
2823 Elf_Internal_Sym * isym;
2824 asection * sym_sec;
86aba9db
NC
2825
2826 /* A local symbol. */
5cec6941
NC
2827 isym = isymbuf + ELF32_R_SYM (hi_irelfn->r_info);
2828
2829 if (isym->st_shndx == SHN_UNDEF)
86aba9db 2830 sym_sec = bfd_und_section_ptr;
5cec6941 2831 else if (isym->st_shndx == SHN_ABS)
86aba9db 2832 sym_sec = bfd_abs_section_ptr;
5cec6941 2833 else if (isym->st_shndx == SHN_COMMON)
86aba9db
NC
2834 sym_sec = bfd_com_section_ptr;
2835 else
5cec6941
NC
2836 sym_sec = bfd_section_from_elf_index (abfd, isym->st_shndx);
2837 symval = (isym->st_value
86aba9db
NC
2838 + sym_sec->output_section->vma
2839 + sym_sec->output_offset);
2840#ifdef DEBUG_RELAX
2841 {
2842 char * name = bfd_elf_string_from_elf_section
5cec6941 2843 (abfd, symtab_hdr->sh_link, isym->st_name);
86aba9db
NC
2844
2845 fprintf (stderr, "relax long jump local: sec: %s, sym: %s (%d), value: %x + %x + %x addend %x\n",
5cec6941
NC
2846 sym_sec->name, name, isym->st_name,
2847 sym_sec->output_section->vma,
2848 sym_sec->output_offset,
2849 isym->st_value, irel->r_addend);
86aba9db
NC
2850 }
2851#endif
2852 }
2853 else
2854 {
2855 unsigned long indx;
2856 struct elf_link_hash_entry * h;
2857
2858 /* An external symbol. */
2859 indx = ELF32_R_SYM (irel->r_info) - symtab_hdr->sh_info;
2860 h = elf_sym_hashes (abfd)[indx];
2861 BFD_ASSERT (h != NULL);
2862
2863 if ( h->root.type != bfd_link_hash_defined
2864 && h->root.type != bfd_link_hash_defweak)
2865 /* This appears to be a reference to an undefined
2866 symbol. Just ignore it--it will be caught by the
2867 regular reloc processing. */
2868 continue;
2869
2870 symval = (h->root.u.def.value
2871 + h->root.u.def.section->output_section->vma
2872 + h->root.u.def.section->output_offset);
2873#ifdef DEBUG_RELAX
2874 fprintf (stderr,
2875 "relax longjump defined: sec: %s, name: %s, value: %x + %x + %x addend %x\n",
2876 sec->name, h->root.root.string, h->root.u.def.value,
2877 sec->output_section->vma, sec->output_offset, irel->r_addend);
2878#endif
2879 }
2880
2881 addend = irel->r_addend;
2882
2883 foff = (symval + addend
2884 - (irel->r_offset
2885 + sec->output_section->vma
2886 + sec->output_offset
2887 + 4));
2888#ifdef DEBUG_RELAX
2889 fprintf (stderr, "relax longjump r_offset 0x%x ptr 0x%x symbol 0x%x addend 0x%x distance 0x%x\n",
2890 irel->r_offset,
2891 (irel->r_offset
2892 + sec->output_section->vma
2893 + sec->output_offset),
2894 symval, addend, foff);
2895#endif
2896 if (foff < -0x100000 || foff >= 0x100000)
2897 /* After all that work, we can't shorten this function call. */
2898 continue;
2899
2900 /* For simplicity of coding, we are going to modify the section
2901 contents, the section relocs, and the BFD symbol table. We
2902 must tell the rest of the code not to free up this
2903 information. It would be possible to instead create a table
2904 of changes which have to be made, as is done in coff-mips.c;
2905 that would be more work, but would require less memory when
2906 the linker is run. */
2907 elf_section_data (sec)->relocs = internal_relocs;
86aba9db 2908 elf_section_data (sec)->this_hdr.contents = contents;
5cec6941 2909 symtab_hdr->contents = (bfd_byte *) isymbuf;
86aba9db
NC
2910
2911 if (foff < -0x100 || foff >= 0x100)
2912 {
2913 /* Replace the long jump with a jr. */
2914
2915 irel->r_info =
b34976b6
AM
2916 ELF32_R_INFO (ELF32_R_SYM (irel->r_info), R_V850_22_PCREL);
2917
86aba9db
NC
2918 irel->r_addend = addend;
2919 addend = 0;
2920
2921 if (ELF32_R_SYM (hi_irelfn->r_info) < symtab_hdr->sh_info)
2922 /* If this needs to be changed because of future relaxing,
2923 it will be handled here like other internal IND12W
2924 relocs. */
2925 bfd_put_32 (abfd,
2926 0x00000780 | ((addend << 15) & 0xffff0000) | ((addend >> 17) & 0xf),
2927 contents + irel->r_offset);
2928 else
2929 /* We can't fully resolve this yet, because the external
2930 symbol value may be changed by future relaxing.
2931 We let the final link phase handle it. */
2932 bfd_put_32 (abfd, 0x00000780, contents + irel->r_offset);
2933
2934 hi_irelfn->r_info =
2935 ELF32_R_INFO (ELF32_R_SYM (hi_irelfn->r_info), R_V850_NONE);
2936 lo_irelfn->r_info =
2937 ELF32_R_INFO (ELF32_R_SYM (lo_irelfn->r_info), R_V850_NONE);
2938 if (!v850_elf_relax_delete_bytes (abfd, sec,
2939 irel->r_offset + 4, toaddr, 6))
2940 goto error_return;
2941
2942 align_pad_size += 6;
2943 }
2944 else
2945 {
2946 /* Replace the long jump with a br. */
2947
2948 irel->r_info =
2949 ELF32_R_INFO (ELF32_R_SYM (irel->r_info), R_V850_9_PCREL);
2950
2951 irel->r_addend = addend;
2952 addend = 0;
2953
2954 if (ELF32_R_SYM (hi_irelfn->r_info) < symtab_hdr->sh_info)
2955 /* If this needs to be changed because of future relaxing,
2956 it will be handled here like other internal IND12W
2957 relocs. */
2958 bfd_put_16 (abfd,
2959 0x0585 | ((addend << 10) & 0xf800) | ((addend << 3) & 0x0070),
2960 contents + irel->r_offset);
2961 else
2962 /* We can't fully resolve this yet, because the external
2963 symbol value may be changed by future relaxing.
2964 We let the final link phase handle it. */
2965 bfd_put_16 (abfd, 0x0585, contents + irel->r_offset);
2966
2967 hi_irelfn->r_info =
2968 ELF32_R_INFO (ELF32_R_SYM (hi_irelfn->r_info), R_V850_NONE);
2969 lo_irelfn->r_info =
2970 ELF32_R_INFO (ELF32_R_SYM (lo_irelfn->r_info), R_V850_NONE);
2971 if (!v850_elf_relax_delete_bytes (abfd, sec,
2972 irel->r_offset + 2, toaddr, 8))
2973 goto error_return;
2974
2975 align_pad_size += 8;
2976 }
2977 }
2978 }
2979
2980 irelalign = NULL;
2981 for (irel = internal_relocs; irel < irelend; irel++)
2982 {
2983 if (ELF32_R_TYPE (irel->r_info) == (int) R_V850_ALIGN
2984 && irel->r_offset == toaddr)
2985 {
2986 irel->r_offset -= align_pad_size;
2987
2988 if (irelalign == NULL || irelalign->r_addend > irel->r_addend)
2989 irelalign = irel;
2990 }
2991 }
2992
2993 addr = toaddr;
2994 }
2995
2996 if (!irelalign)
2997 {
2998#ifdef DEBUG_RELAX
2999 fprintf (stderr, "relax pad %d shorten %d -> %d\n",
3000 align_pad_size,
eea6121a
AM
3001 sec->size,
3002 sec->size - align_pad_size);
86aba9db 3003#endif
eea6121a 3004 sec->size -= align_pad_size;
86aba9db
NC
3005 }
3006
5cec6941
NC
3007 finish:
3008 if (internal_relocs != NULL
3009 && elf_section_data (sec)->relocs != internal_relocs)
3010 free (internal_relocs);
86aba9db 3011
5cec6941
NC
3012 if (contents != NULL
3013 && elf_section_data (sec)->this_hdr.contents != (unsigned char *) contents)
3014 free (contents);
86aba9db 3015
5cec6941
NC
3016 if (isymbuf != NULL
3017 && symtab_hdr->contents != (bfd_byte *) isymbuf)
3018 free (isymbuf);
86aba9db 3019
5cec6941 3020 return result;
86aba9db 3021
5cec6941 3022 error_return:
b34976b6 3023 result = FALSE;
5cec6941 3024 goto finish;
86aba9db 3025}
2f89ff8d 3026
551b43fd 3027static struct bfd_elf_special_section const v850_elf_special_sections[] =
7f4d3958
L
3028{
3029 { ".call_table_data", 16, 0, SHT_PROGBITS, (SHF_ALLOC
3030 + SHF_WRITE) },
3031 { ".call_table_text", 16, 0, SHT_PROGBITS, (SHF_ALLOC + SHF_WRITE
3032 + SHF_EXECINSTR) },
7dcb9820
AM
3033 { ".rosdata", 8, -2, SHT_PROGBITS, (SHF_ALLOC
3034 + SHF_V850_GPREL) },
7f4d3958
L
3035 { ".rozdata", 8, -2, SHT_PROGBITS, (SHF_ALLOC
3036 + SHF_V850_R0REL) },
7dcb9820
AM
3037 { ".sbss", 5, -2, SHT_NOBITS, (SHF_ALLOC + SHF_WRITE
3038 + SHF_V850_GPREL) },
3039 { ".scommon", 8, -2, SHT_V850_SCOMMON, (SHF_ALLOC + SHF_WRITE
3040 + SHF_V850_GPREL) },
551b43fd
AM
3041 { ".sdata", 6, -2, SHT_PROGBITS, (SHF_ALLOC + SHF_WRITE
3042 + SHF_V850_GPREL) },
7dcb9820
AM
3043 { ".tbss", 5, -2, SHT_NOBITS, (SHF_ALLOC + SHF_WRITE
3044 + SHF_V850_EPREL) },
3045 { ".tcommon", 8, -2, SHT_V850_TCOMMON, (SHF_ALLOC + SHF_WRITE
3046 + SHF_V850_R0REL) },
551b43fd
AM
3047 { ".tdata", 6, -2, SHT_PROGBITS, (SHF_ALLOC + SHF_WRITE
3048 + SHF_V850_EPREL) },
7dcb9820
AM
3049 { ".zbss", 5, -2, SHT_NOBITS, (SHF_ALLOC + SHF_WRITE
3050 + SHF_V850_R0REL) },
3051 { ".zcommon", 8, -2, SHT_V850_ZCOMMON, (SHF_ALLOC + SHF_WRITE
3052 + SHF_V850_R0REL) },
551b43fd
AM
3053 { ".zdata", 6, -2, SHT_PROGBITS, (SHF_ALLOC + SHF_WRITE
3054 + SHF_V850_R0REL) },
7f4d3958
L
3055 { NULL, 0, 0, 0, 0 }
3056};
3057
551b43fd
AM
3058static const struct bfd_elf_special_section *
3059v850_elf_get_sec_type_attr (bfd *abfd, asection *sec)
7f4d3958 3060{
551b43fd
AM
3061 const struct bfd_elf_special_section const *ssect;
3062
3063 /* See if this is one of the special sections. */
3064 if (sec->name == NULL)
3065 return NULL;
3066
3067 ssect = _bfd_elf_get_special_section (sec->name,
3068 v850_elf_special_sections,
3069 sec->use_rela_p);
3070 if (ssect != NULL)
3071 return ssect;
3072
3073 return _bfd_elf_get_sec_type_attr (abfd, sec);
3074}
252b5132
RH
3075\f
3076#define TARGET_LITTLE_SYM bfd_elf32_v850_vec
3077#define TARGET_LITTLE_NAME "elf32-v850"
3078#define ELF_ARCH bfd_arch_v850
aa4f99bb
AO
3079#define ELF_MACHINE_CODE EM_V850
3080#define ELF_MACHINE_ALT1 EM_CYGNUS_V850
46767561 3081#define ELF_MACHINE_ALT2 EM_V800 /* This is the value used by the GreenHills toolchain. */
252b5132 3082#define ELF_MAXPAGESIZE 0x1000
435b1e90 3083
252b5132
RH
3084#define elf_info_to_howto v850_elf_info_to_howto_rela
3085#define elf_info_to_howto_rel v850_elf_info_to_howto_rel
3086
3087#define elf_backend_check_relocs v850_elf_check_relocs
3088#define elf_backend_relocate_section v850_elf_relocate_section
3089#define elf_backend_object_p v850_elf_object_p
3090#define elf_backend_final_write_processing v850_elf_final_write_processing
3091#define elf_backend_section_from_bfd_section v850_elf_section_from_bfd_section
3092#define elf_backend_symbol_processing v850_elf_symbol_processing
3093#define elf_backend_add_symbol_hook v850_elf_add_symbol_hook
3094#define elf_backend_link_output_symbol_hook v850_elf_link_output_symbol_hook
3095#define elf_backend_section_from_shdr v850_elf_section_from_shdr
3096#define elf_backend_fake_sections v850_elf_fake_sections
3097#define elf_backend_gc_mark_hook v850_elf_gc_mark_hook
3098#define elf_backend_gc_sweep_hook v850_elf_gc_sweep_hook
551b43fd 3099#define elf_backend_get_sec_type_attr v850_elf_get_sec_type_attr
252b5132
RH
3100
3101#define elf_backend_can_gc_sections 1
f0fe0e16 3102#define elf_backend_rela_normal 1
252b5132 3103
252b5132
RH
3104#define bfd_elf32_bfd_is_local_label_name v850_elf_is_local_label_name
3105#define bfd_elf32_bfd_reloc_type_lookup v850_elf_reloc_type_lookup
252b5132
RH
3106#define bfd_elf32_bfd_merge_private_bfd_data v850_elf_merge_private_bfd_data
3107#define bfd_elf32_bfd_set_private_flags v850_elf_set_private_flags
3108#define bfd_elf32_bfd_print_private_bfd_data v850_elf_print_private_bfd_data
86aba9db 3109#define bfd_elf32_bfd_relax_section v850_elf_relax_section
252b5132
RH
3110
3111#define elf_symbol_leading_char '_'
3112
3113#include "elf32-target.h"
This page took 0.567907 seconds and 4 git commands to generate.