Coverage Report

Created: 2025-06-24 06:45

/src/binutils-gdb/bfd/elf32-rl78.c
Line
Count
Source (jump to first uncovered line)
1
/* Renesas RL78 specific support for 32-bit ELF.
2
   Copyright (C) 2011-2025 Free Software Foundation, Inc.
3
4
   This file is part of BFD, the Binary File Descriptor library.
5
6
   This program is free software; you can redistribute it and/or modify
7
   it under the terms of the GNU General Public License as published by
8
   the Free Software Foundation; either version 3 of the License, or
9
   (at your option) any later version.
10
11
   This program is distributed in the hope that it will be useful,
12
   but WITHOUT ANY WARRANTY; without even the implied warranty of
13
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14
   GNU General Public License for more details.
15
16
   You should have received a copy of the GNU General Public License
17
   along with this program; if not, write to the Free Software
18
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
19
   MA 02110-1301, USA.  */
20
21
#include "sysdep.h"
22
#include "bfd.h"
23
#include "libbfd.h"
24
#include "elf-bfd.h"
25
#include "elf/rl78.h"
26
#include "libiberty.h"
27
28
0
#define valid_16bit_address(v) ((v) <= 0x0ffff || (v) >= 0xf0000)
29
30
#define RL78REL(n,sz,bit,mask,shift,complain,pcrel) \
31
  HOWTO (R_RL78_##n, shift, sz, bit, pcrel, 0, complain_overflow_ ## complain, \
32
   bfd_elf_generic_reloc, "R_RL78_" #n, false, 0, mask, false)
33
34
static bfd_reloc_status_type rl78_special_reloc (bfd *, arelent *, asymbol *, void *,
35
             asection *, bfd *, char **);
36
37
#define RL78_OP_REL(n,sz,bit,mask,shift,complain,pcrel)     \
38
  HOWTO (R_RL78_##n, shift, sz, bit, pcrel, 0, complain_overflow_ ## complain, \
39
   rl78_special_reloc, "R_RL78_" #n, false, 0, mask, false)
40
41
/* Note that the relocations around 0x7f are internal to this file;
42
   feel free to move them as needed to avoid conflicts with published
43
   relocation numbers.  */
44
45
static reloc_howto_type rl78_elf_howto_table [] =
46
{
47
  RL78REL (NONE,   0,  0, 0,          0, dont,     false),
48
  RL78REL (DIR32,  4, 32, 0xffffffff, 0, dont,     false),
49
  RL78REL (DIR24S,   4, 24, 0xffffff,   0, signed,   false),
50
  RL78REL (DIR16,  2, 16, 0xffff,     0, bitfield, false),
51
  RL78REL (DIR16U,   2, 16, 0xffff,     0, unsigned, false),
52
  RL78REL (DIR16S,   2, 16, 0xffff,     0, bitfield, false),
53
  RL78REL (DIR8,   1,  8, 0xff,       0, dont,     false),
54
  RL78REL (DIR8U,  1,  8, 0xff,       0, unsigned, false),
55
  RL78REL (DIR8S,  1,  8, 0xff,       0, bitfield, false),
56
  RL78REL (DIR24S_PCREL, 4, 24, 0xffffff,   0, signed,   true),
57
  RL78REL (DIR16S_PCREL, 2, 16, 0xffff,     0, signed,   true),
58
  RL78REL (DIR8S_PCREL,  1,  8, 0xff,       0, signed,   true),
59
  RL78REL (DIR16UL,  2, 16, 0xffff,     2, unsigned, false),
60
  RL78REL (DIR16UW,  2, 16, 0xffff,     1, unsigned, false),
61
  RL78REL (DIR8UL,   1,  8, 0xff,       2, unsigned, false),
62
  RL78REL (DIR8UW,   1,  8, 0xff,       1, unsigned, false),
63
  RL78REL (DIR32_REV,  4, 32, 0xffffffff, 0, dont,     false),
64
  RL78REL (DIR16_REV,  2, 16, 0xffff,     0, bitfield, false),
65
  RL78REL (DIR3U_PCREL,  1,  3, 0x7,        0, unsigned, true),
66
67
  EMPTY_HOWTO (0x13),
68
  EMPTY_HOWTO (0x14),
69
  EMPTY_HOWTO (0x15),
70
  EMPTY_HOWTO (0x16),
71
  EMPTY_HOWTO (0x17),
72
  EMPTY_HOWTO (0x18),
73
  EMPTY_HOWTO (0x19),
74
  EMPTY_HOWTO (0x1a),
75
  EMPTY_HOWTO (0x1b),
76
  EMPTY_HOWTO (0x1c),
77
  EMPTY_HOWTO (0x1d),
78
  EMPTY_HOWTO (0x1e),
79
  EMPTY_HOWTO (0x1f),
80
81
  EMPTY_HOWTO (0x20),
82
  EMPTY_HOWTO (0x21),
83
  EMPTY_HOWTO (0x22),
84
  EMPTY_HOWTO (0x23),
85
  EMPTY_HOWTO (0x24),
86
  EMPTY_HOWTO (0x25),
87
  EMPTY_HOWTO (0x26),
88
  EMPTY_HOWTO (0x27),
89
  EMPTY_HOWTO (0x28),
90
  EMPTY_HOWTO (0x29),
91
  EMPTY_HOWTO (0x2a),
92
  EMPTY_HOWTO (0x2b),
93
  EMPTY_HOWTO (0x2c),
94
95
  RL78REL (RH_RELAX,   0,  0, 0,          0, dont,   false),
96
  RL78REL (RH_SFR,   1,  8, 0xff,       0, unsigned, false),
97
  RL78REL (RH_SADDR,   1,  8, 0xff,       0, unsigned, false),
98
99
  EMPTY_HOWTO (0x30),
100
  EMPTY_HOWTO (0x31),
101
  EMPTY_HOWTO (0x32),
102
  EMPTY_HOWTO (0x33),
103
  EMPTY_HOWTO (0x34),
104
  EMPTY_HOWTO (0x35),
105
  EMPTY_HOWTO (0x36),
106
  EMPTY_HOWTO (0x37),
107
  EMPTY_HOWTO (0x38),
108
  EMPTY_HOWTO (0x39),
109
  EMPTY_HOWTO (0x3a),
110
  EMPTY_HOWTO (0x3b),
111
  EMPTY_HOWTO (0x3c),
112
  EMPTY_HOWTO (0x3d),
113
  EMPTY_HOWTO (0x3e),
114
  EMPTY_HOWTO (0x3f),
115
  EMPTY_HOWTO (0x40),
116
117
  RL78_OP_REL (ABS32,      4, 32, 0xffffffff, 0, dont,  false),
118
  RL78_OP_REL (ABS24S,       4, 24, 0xffffff,   0, signed,  false),
119
  RL78_OP_REL (ABS16,      2, 16, 0xffff,     0, bitfield,  false),
120
  RL78_OP_REL (ABS16U,       2, 16, 0xffff,     0, unsigned,  false),
121
  RL78_OP_REL (ABS16S,       2, 16, 0xffff,     0, signed,  false),
122
  RL78_OP_REL (ABS8,       1,  8, 0xff,       0, bitfield,  false),
123
  RL78_OP_REL (ABS8U,      1,  8, 0xff,       0, unsigned,  false),
124
  RL78_OP_REL (ABS8S,      1,  8, 0xff,       0, signed,  false),
125
  RL78_OP_REL (ABS24S_PCREL, 4, 24, 0xffffff,   0, signed,  true),
126
  RL78_OP_REL (ABS16S_PCREL, 2, 16, 0xffff,     0, signed,  true),
127
  RL78_OP_REL (ABS8S_PCREL,  1,  8, 0xff,       0, signed,  true),
128
  RL78_OP_REL (ABS16UL,      2, 16, 0xffff,     0, unsigned,  false),
129
  RL78_OP_REL (ABS16UW,      2, 16, 0xffff,     0, unsigned,  false),
130
  RL78_OP_REL (ABS8UL,       1,  8, 0xff,       0, unsigned,  false),
131
  RL78_OP_REL (ABS8UW,       1,  8, 0xff,       0, unsigned,  false),
132
  RL78_OP_REL (ABS32_REV,    4, 32, 0xffffffff, 0, dont,  false),
133
  RL78_OP_REL (ABS16_REV,    2, 16, 0xffff,     0, bitfield,  false),
134
135
0
#define STACK_REL_P(x) ((x) <= R_RL78_ABS16_REV && (x) >= R_RL78_ABS32)
136
137
  EMPTY_HOWTO (0x52),
138
  EMPTY_HOWTO (0x53),
139
  EMPTY_HOWTO (0x54),
140
  EMPTY_HOWTO (0x55),
141
  EMPTY_HOWTO (0x56),
142
  EMPTY_HOWTO (0x57),
143
  EMPTY_HOWTO (0x58),
144
  EMPTY_HOWTO (0x59),
145
  EMPTY_HOWTO (0x5a),
146
  EMPTY_HOWTO (0x5b),
147
  EMPTY_HOWTO (0x5c),
148
  EMPTY_HOWTO (0x5d),
149
  EMPTY_HOWTO (0x5e),
150
  EMPTY_HOWTO (0x5f),
151
  EMPTY_HOWTO (0x60),
152
  EMPTY_HOWTO (0x61),
153
  EMPTY_HOWTO (0x62),
154
  EMPTY_HOWTO (0x63),
155
  EMPTY_HOWTO (0x64),
156
  EMPTY_HOWTO (0x65),
157
  EMPTY_HOWTO (0x66),
158
  EMPTY_HOWTO (0x67),
159
  EMPTY_HOWTO (0x68),
160
  EMPTY_HOWTO (0x69),
161
  EMPTY_HOWTO (0x6a),
162
  EMPTY_HOWTO (0x6b),
163
  EMPTY_HOWTO (0x6c),
164
  EMPTY_HOWTO (0x6d),
165
  EMPTY_HOWTO (0x6e),
166
  EMPTY_HOWTO (0x6f),
167
  EMPTY_HOWTO (0x70),
168
  EMPTY_HOWTO (0x71),
169
  EMPTY_HOWTO (0x72),
170
  EMPTY_HOWTO (0x73),
171
  EMPTY_HOWTO (0x74),
172
  EMPTY_HOWTO (0x75),
173
  EMPTY_HOWTO (0x76),
174
  EMPTY_HOWTO (0x77),
175
176
  EMPTY_HOWTO (0x78),
177
  EMPTY_HOWTO (0x79),
178
  EMPTY_HOWTO (0x7a),
179
  EMPTY_HOWTO (0x7b),
180
  EMPTY_HOWTO (0x7c),
181
  EMPTY_HOWTO (0x7d),
182
  EMPTY_HOWTO (0x7e),
183
  EMPTY_HOWTO (0x7f),
184
185
  RL78_OP_REL (SYM,   0, 0, 0, 0, dont, false),
186
  RL78_OP_REL (OPneg,   0, 0, 0, 0, dont, false),
187
  RL78_OP_REL (OPadd,   0, 0, 0, 0, dont, false),
188
  RL78_OP_REL (OPsub,   0, 0, 0, 0, dont, false),
189
  RL78_OP_REL (OPmul,   0, 0, 0, 0, dont, false),
190
  RL78_OP_REL (OPdiv,   0, 0, 0, 0, dont, false),
191
  RL78_OP_REL (OPshla,    0, 0, 0, 0, dont, false),
192
  RL78_OP_REL (OPshra,    0, 0, 0, 0, dont, false),
193
  RL78_OP_REL (OPsctsize, 0, 0, 0, 0, dont, false),
194
  EMPTY_HOWTO (0x89),
195
  EMPTY_HOWTO (0x8a),
196
  EMPTY_HOWTO (0x8b),
197
  EMPTY_HOWTO (0x8c),
198
  RL78_OP_REL (OPscttop,  0, 0, 0, 0, dont, false),
199
  EMPTY_HOWTO (0x8e),
200
  EMPTY_HOWTO (0x8f),
201
  RL78_OP_REL (OPand,   0, 0, 0, 0, dont, false),
202
  RL78_OP_REL (OPor,    0, 0, 0, 0, dont, false),
203
  RL78_OP_REL (OPxor,   0, 0, 0, 0, dont, false),
204
  RL78_OP_REL (OPnot,   0, 0, 0, 0, dont, false),
205
  RL78_OP_REL (OPmod,   0, 0, 0, 0, dont, false),
206
  RL78_OP_REL (OPromtop,  0, 0, 0, 0, dont, false),
207
  RL78_OP_REL (OPramtop,  0, 0, 0, 0, dont, false)
208
};
209

210
/* Map BFD reloc types to RL78 ELF reloc types.  */
211
212
struct rl78_reloc_map
213
{
214
  bfd_reloc_code_real_type  bfd_reloc_val;
215
  unsigned int        rl78_reloc_val;
216
};
217
218
static const struct rl78_reloc_map rl78_reloc_map [] =
219
{
220
  { BFD_RELOC_NONE,   R_RL78_NONE },
221
  { BFD_RELOC_8,    R_RL78_DIR8S },
222
  { BFD_RELOC_16,   R_RL78_DIR16S },
223
  { BFD_RELOC_24,   R_RL78_DIR24S },
224
  { BFD_RELOC_32,   R_RL78_DIR32 },
225
  { BFD_RELOC_RL78_16_OP, R_RL78_DIR16 },
226
  { BFD_RELOC_RL78_DIR3U_PCREL, R_RL78_DIR3U_PCREL },
227
  { BFD_RELOC_8_PCREL,    R_RL78_DIR8S_PCREL },
228
  { BFD_RELOC_16_PCREL,   R_RL78_DIR16S_PCREL },
229
  { BFD_RELOC_24_PCREL,   R_RL78_DIR24S_PCREL },
230
  { BFD_RELOC_RL78_8U,    R_RL78_DIR8U },
231
  { BFD_RELOC_RL78_16U,   R_RL78_DIR16U },
232
  { BFD_RELOC_RL78_SYM,   R_RL78_SYM },
233
  { BFD_RELOC_RL78_OP_SUBTRACT, R_RL78_OPsub },
234
  { BFD_RELOC_RL78_OP_NEG,  R_RL78_OPneg },
235
  { BFD_RELOC_RL78_OP_AND,  R_RL78_OPand },
236
  { BFD_RELOC_RL78_OP_SHRA, R_RL78_OPshra },
237
  { BFD_RELOC_RL78_ABS8,  R_RL78_ABS8 },
238
  { BFD_RELOC_RL78_ABS16, R_RL78_ABS16 },
239
  { BFD_RELOC_RL78_ABS16_REV, R_RL78_ABS16_REV },
240
  { BFD_RELOC_RL78_ABS32, R_RL78_ABS32 },
241
  { BFD_RELOC_RL78_ABS32_REV, R_RL78_ABS32_REV },
242
  { BFD_RELOC_RL78_ABS16UL, R_RL78_ABS16UL },
243
  { BFD_RELOC_RL78_ABS16UW, R_RL78_ABS16UW },
244
  { BFD_RELOC_RL78_ABS16U,  R_RL78_ABS16U },
245
  { BFD_RELOC_RL78_SADDR, R_RL78_RH_SADDR },
246
  { BFD_RELOC_RL78_RELAX, R_RL78_RH_RELAX }
247
};
248
249
static reloc_howto_type *
250
rl78_reloc_type_lookup (bfd * abfd ATTRIBUTE_UNUSED,
251
      bfd_reloc_code_real_type code)
252
0
{
253
0
  unsigned int i;
254
255
0
  if (code == BFD_RELOC_RL78_32_OP)
256
0
    return rl78_elf_howto_table + R_RL78_DIR32;
257
258
0
  for (i = ARRAY_SIZE (rl78_reloc_map); i--;)
259
0
    if (rl78_reloc_map [i].bfd_reloc_val == code)
260
0
      return rl78_elf_howto_table + rl78_reloc_map[i].rl78_reloc_val;
261
262
0
  return NULL;
263
0
}
264
265
static reloc_howto_type *
266
rl78_reloc_name_lookup (bfd * abfd ATTRIBUTE_UNUSED, const char * r_name)
267
0
{
268
0
  unsigned int i;
269
270
0
  for (i = 0; i < ARRAY_SIZE (rl78_elf_howto_table); i++)
271
0
    if (rl78_elf_howto_table[i].name != NULL
272
0
  && strcasecmp (rl78_elf_howto_table[i].name, r_name) == 0)
273
0
      return rl78_elf_howto_table + i;
274
275
0
  return NULL;
276
0
}
277
278
/* Set the howto pointer for an RL78 ELF reloc.  */
279
280
static bool
281
rl78_info_to_howto_rela (bfd *         abfd,
282
       arelent *       cache_ptr,
283
       Elf_Internal_Rela * dst)
284
0
{
285
0
  unsigned int r_type;
286
287
0
  r_type = ELF32_R_TYPE (dst->r_info);
288
0
  if (r_type >= (unsigned int) R_RL78_max)
289
0
    {
290
      /* xgettext:c-format */
291
0
      _bfd_error_handler (_("%pB: unsupported relocation type %#x"),
292
0
        abfd, r_type);
293
0
      bfd_set_error (bfd_error_bad_value);
294
0
      return false;
295
0
    }
296
0
  cache_ptr->howto = rl78_elf_howto_table + r_type;
297
0
  return true;
298
0
}
299

300
static bfd_vma
301
get_symbol_value (const char *      name,
302
      struct bfd_link_info *  info,
303
      bfd *       input_bfd,
304
      asection *      input_section,
305
      int       offset)
306
0
{
307
0
  struct bfd_link_hash_entry * h;
308
309
0
  if (info == NULL)
310
0
    return 0;
311
312
0
  h = bfd_link_hash_lookup (info->hash, name, false, false, true);
313
314
0
  if (h == NULL
315
0
      || (h->type != bfd_link_hash_defined
316
0
    && h->type != bfd_link_hash_defweak))
317
0
    {
318
0
      (*info->callbacks->undefined_symbol)
319
0
  (info, name, input_bfd, input_section, offset, true);
320
0
      return 0;
321
0
    }
322
323
0
  return (h->u.def.value
324
0
    + h->u.def.section->output_section->vma
325
0
    + h->u.def.section->output_offset);
326
0
}
327
328
static bfd_vma
329
get_romstart (struct bfd_link_info *  info,
330
        bfd *         abfd,
331
        asection *        sec,
332
        int         offset)
333
0
{
334
0
  static bool cached = false;
335
0
  static bfd_vma cached_value = 0;
336
337
0
  if (!cached)
338
0
    {
339
0
      cached_value = get_symbol_value ("_start", info, abfd, sec, offset);
340
0
      cached = true;
341
0
    }
342
0
  return cached_value;
343
0
}
344
345
static bfd_vma
346
get_ramstart (struct bfd_link_info *  info,
347
        bfd *         abfd,
348
        asection *        sec,
349
        int         offset)
350
0
{
351
0
  static bool cached = false;
352
0
  static bfd_vma cached_value = 0;
353
354
0
  if (!cached)
355
0
    {
356
0
      cached_value = get_symbol_value ("__datastart", info, abfd, sec, offset);
357
0
      cached = true;
358
0
    }
359
0
  return cached_value;
360
0
}
361
362
0
#define NUM_STACK_ENTRIES 16
363
static int32_t rl78_stack [ NUM_STACK_ENTRIES ];
364
static unsigned int rl78_stack_top;
365
366
static inline void
367
rl78_stack_push (bfd_vma val, bfd_reloc_status_type *r)
368
0
{
369
0
  if (rl78_stack_top < NUM_STACK_ENTRIES)
370
0
    rl78_stack[rl78_stack_top++] = val;
371
0
  else
372
0
    *r = bfd_reloc_dangerous;
373
0
}
374
375
static inline bfd_vma
376
rl78_stack_pop (bfd_reloc_status_type *r)
377
0
{
378
0
  if (rl78_stack_top > 0)
379
0
    return rl78_stack[-- rl78_stack_top];
380
0
  else
381
0
    *r = bfd_reloc_dangerous;
382
0
  return 0;
383
0
}
384
385
/* Special handling for RL78 complex relocs.  Returns the
386
   value of the reloc, or 0 for relocs which do not generate
387
   a result.  SYMVAL is the value of the symbol for relocs
388
   which use a symbolic argument.  */
389
390
static bfd_vma
391
rl78_compute_complex_reloc (unsigned long  r_type,
392
          bfd_vma symval,
393
          asection *input_section,
394
          bfd_reloc_status_type *r,
395
          char **error_message)
396
0
{
397
0
  int32_t tmp1, tmp2;
398
0
  bfd_vma relocation = 0;
399
0
  bfd_reloc_status_type status = bfd_reloc_ok;
400
401
0
  switch (r_type)
402
0
    {
403
0
    default:
404
0
      status = bfd_reloc_notsupported;
405
0
      break;
406
407
0
    case R_RL78_ABS24S_PCREL:
408
0
    case R_RL78_ABS16S_PCREL:
409
0
    case R_RL78_ABS8S_PCREL:
410
0
      relocation = rl78_stack_pop (&status);
411
0
      relocation -= input_section->output_section->vma + input_section->output_offset;
412
0
      break;
413
414
0
    case R_RL78_ABS32:
415
0
    case R_RL78_ABS32_REV:
416
0
    case R_RL78_ABS16:
417
0
    case R_RL78_ABS16_REV:
418
0
    case R_RL78_ABS16S:
419
0
    case R_RL78_ABS16U:
420
0
    case R_RL78_ABS8:
421
0
    case R_RL78_ABS8U:
422
0
    case R_RL78_ABS8S:
423
0
      relocation = rl78_stack_pop (&status);
424
0
      break;
425
426
0
    case R_RL78_ABS16UL:
427
0
    case R_RL78_ABS8UL:
428
0
      relocation = rl78_stack_pop (&status) >> 2;
429
0
      break;;
430
431
0
    case R_RL78_ABS16UW:
432
0
    case R_RL78_ABS8UW:
433
0
      relocation = rl78_stack_pop (&status) >> 1;
434
0
      break;
435
436
      /* The rest of the relocs compute values and then push them onto the stack.  */
437
0
    case R_RL78_OPramtop:
438
0
    case R_RL78_OPromtop:
439
0
    case R_RL78_SYM:
440
0
      rl78_stack_push (symval, &status);
441
0
      break;
442
443
0
    case R_RL78_OPneg:
444
0
      tmp1 = rl78_stack_pop (&status);
445
0
      tmp1 = - tmp1;
446
0
      rl78_stack_push (tmp1, &status);
447
0
      break;
448
449
0
    case R_RL78_OPadd:
450
0
      tmp2 = rl78_stack_pop (&status);
451
0
      tmp1 = rl78_stack_pop (&status);
452
0
      tmp1 += tmp2;
453
0
      rl78_stack_push (tmp1, &status);
454
0
      break;
455
456
0
    case R_RL78_OPsub:
457
      /* For the expression "A - B", the assembler pushes A,
458
   then B, then OPSUB.  So the first op we pop is B, not A.  */
459
0
      tmp2 = rl78_stack_pop (&status);  /* B */
460
0
      tmp1 = rl78_stack_pop (&status);  /* A */
461
0
      tmp1 -= tmp2;   /* A - B */
462
0
      rl78_stack_push (tmp1, &status);
463
0
      break;
464
465
0
    case R_RL78_OPmul:
466
0
      tmp2 = rl78_stack_pop (&status);
467
0
      tmp1 = rl78_stack_pop (&status);
468
0
      tmp1 *= tmp2;
469
0
      rl78_stack_push (tmp1, &status);
470
0
      break;
471
472
0
    case R_RL78_OPdiv:
473
0
      tmp2 = rl78_stack_pop (&status);
474
0
      tmp1 = rl78_stack_pop (&status);
475
0
      if (tmp2 != 0)
476
0
  tmp1 /= tmp2;
477
0
      else
478
0
  {
479
0
    tmp1 = 0;
480
0
    status = bfd_reloc_overflow;
481
0
  }
482
0
      rl78_stack_push (tmp1, &status);
483
0
      break;
484
485
0
    case R_RL78_OPshla:
486
0
      tmp2 = rl78_stack_pop (&status);
487
0
      tmp1 = rl78_stack_pop (&status);
488
0
      tmp1 <<= tmp2;
489
0
      rl78_stack_push (tmp1, &status);
490
0
      break;
491
492
0
    case R_RL78_OPshra:
493
0
      tmp2 = rl78_stack_pop (&status);
494
0
      tmp1 = rl78_stack_pop (&status);
495
0
      tmp1 >>= tmp2;
496
0
      rl78_stack_push (tmp1, &status);
497
0
      break;
498
499
0
    case R_RL78_OPsctsize:
500
0
      rl78_stack_push (input_section->size, &status);
501
0
      break;
502
503
0
    case R_RL78_OPscttop:
504
0
      rl78_stack_push (input_section->output_section->vma, &status);
505
0
      break;
506
507
0
    case R_RL78_OPand:
508
0
      tmp2 = rl78_stack_pop (&status);
509
0
      tmp1 = rl78_stack_pop (&status);
510
0
      tmp1 &= tmp2;
511
0
      rl78_stack_push (tmp1, &status);
512
0
      break;
513
514
0
    case R_RL78_OPor:
515
0
      tmp2 = rl78_stack_pop (&status);
516
0
      tmp1 = rl78_stack_pop (&status);
517
0
      tmp1 |= tmp2;
518
0
      rl78_stack_push (tmp1, &status);
519
0
      break;
520
521
0
    case R_RL78_OPxor:
522
0
      tmp2 = rl78_stack_pop (&status);
523
0
      tmp1 = rl78_stack_pop (&status);
524
0
      tmp1 ^= tmp2;
525
0
      rl78_stack_push (tmp1, &status);
526
0
      break;
527
528
0
    case R_RL78_OPnot:
529
0
      tmp1 = rl78_stack_pop (&status);
530
0
      tmp1 = ~ tmp1;
531
0
      rl78_stack_push (tmp1, &status);
532
0
      break;
533
534
0
    case R_RL78_OPmod:
535
0
      tmp2 = rl78_stack_pop (&status);
536
0
      tmp1 = rl78_stack_pop (&status);
537
0
      if (tmp2 != 0)
538
0
  tmp1 %= tmp2;
539
0
      else
540
0
  {
541
0
    tmp1 = 0;
542
0
    status = bfd_reloc_overflow;
543
0
  }
544
0
      rl78_stack_push (tmp1, &status);
545
0
      break;
546
0
    }
547
548
0
  if (r)
549
0
    {
550
0
      if (status == bfd_reloc_dangerous)
551
0
  *error_message = (_("RL78 reloc stack overflow/underflow"));
552
0
      else if (status == bfd_reloc_overflow)
553
0
  {
554
0
    status = bfd_reloc_dangerous;
555
0
    *error_message = (_("RL78 reloc divide by zero"));
556
0
  }
557
0
      *r = status;
558
0
    }
559
0
  return relocation;
560
0
}
561
562
/* Check whether RELOCATION overflows a relocation field described by
563
   HOWTO.  */
564
565
static bfd_reloc_status_type
566
check_overflow (reloc_howto_type *howto, bfd_vma relocation)
567
0
{
568
0
  switch (howto->complain_on_overflow)
569
0
    {
570
0
    case complain_overflow_dont:
571
0
      break;
572
573
0
    case complain_overflow_bitfield:
574
0
      if ((bfd_signed_vma) relocation < -(1LL << (howto->bitsize - 1))
575
0
    || (bfd_signed_vma) relocation >= 1LL << howto->bitsize)
576
0
  return bfd_reloc_overflow;
577
0
      break;
578
579
0
    case complain_overflow_signed:
580
0
      if ((bfd_signed_vma) relocation < -(1LL << (howto->bitsize - 1))
581
0
    || (bfd_signed_vma) relocation >= 1LL << (howto->bitsize - 1))
582
0
  return bfd_reloc_overflow;
583
0
      break;
584
585
0
    case complain_overflow_unsigned:
586
0
      if (relocation >= 1ULL << howto->bitsize)
587
0
  return bfd_reloc_overflow;
588
0
      break;
589
0
    }
590
0
  return bfd_reloc_ok;
591
0
}
592
593
static bfd_reloc_status_type
594
rl78_special_reloc (bfd *      input_bfd,
595
        arelent *  reloc,
596
        asymbol *  symbol,
597
        void *     data,
598
        asection * input_section,
599
        bfd *      output_bfd ATTRIBUTE_UNUSED,
600
        char **    error_message)
601
0
{
602
0
  bfd_reloc_status_type  r = bfd_reloc_ok;
603
0
  bfd_vma    relocation = 0;
604
0
  unsigned long    r_type = reloc->howto->type;
605
0
  bfd_byte *     contents = data;
606
607
  /* If necessary, compute the symbolic value of the relocation.  */
608
0
  switch (r_type)
609
0
    {
610
0
    case R_RL78_SYM:
611
0
      relocation = (symbol->value
612
0
        + symbol->section->output_section->vma
613
0
        + symbol->section->output_offset
614
0
        + reloc->addend);
615
0
  break;
616
617
0
    case R_RL78_OPromtop:
618
0
      relocation = get_romstart (NULL, input_bfd, input_section,
619
0
         reloc->address);
620
0
      break;
621
622
0
    case R_RL78_OPramtop:
623
0
      relocation = get_ramstart (NULL, input_bfd, input_section,
624
0
         reloc->address);
625
0
      break;
626
0
    }
627
628
  /* Get the value of the relocation.  */
629
0
  relocation = rl78_compute_complex_reloc (r_type, relocation, input_section,
630
0
             &r, error_message);
631
632
0
  if (STACK_REL_P (r_type))
633
0
    {
634
0
      bfd_size_type limit;
635
0
      unsigned int nbytes;
636
637
0
      if (r == bfd_reloc_ok)
638
0
  r = check_overflow (reloc->howto, relocation);
639
640
0
      if (r_type == R_RL78_ABS16_REV)
641
0
  relocation = ((relocation & 0xff) << 8) | ((relocation >> 8) & 0xff);
642
0
      else if (r_type == R_RL78_ABS32_REV)
643
0
  relocation = (((relocation & 0xff) << 24)
644
0
          | ((relocation & 0xff00) << 8)
645
0
          | ((relocation >> 8) & 0xff00)
646
0
          | ((relocation >> 24) & 0xff));
647
648
0
      limit = bfd_get_section_limit_octets (input_bfd, input_section);
649
0
      nbytes = reloc->howto->bitsize / 8;
650
0
      if (reloc->address < limit
651
0
    && nbytes <= limit - reloc->address)
652
0
  {
653
0
    unsigned int i;
654
655
0
    for (i = 0; i < nbytes; i++)
656
0
      {
657
0
        contents[reloc->address + i] = relocation;
658
0
        relocation >>= 8;
659
0
      }
660
0
  }
661
0
      else
662
0
  r = bfd_reloc_outofrange;
663
0
    }
664
665
0
  return r;
666
0
}
667
668
0
#define OP(i)      (contents[rel->r_offset + (i)])
669
670
/* Relocate an RL78 ELF section.
671
   There is some attempt to make this function usable for many architectures,
672
   both USE_REL and USE_RELA ['twould be nice if such a critter existed],
673
   if only to serve as a learning tool.
674
675
   The RELOCATE_SECTION function is called by the new ELF backend linker
676
   to handle the relocations for a section.
677
678
   The relocs are always passed as Rela structures; if the section
679
   actually uses Rel structures, the r_addend field will always be
680
   zero.
681
682
   This function is responsible for adjusting the section contents as
683
   necessary, and (if using Rela relocs and generating a relocatable
684
   output file) adjusting the reloc addend as necessary.
685
686
   This function does not have to worry about setting the reloc
687
   address or the reloc symbol index.
688
689
   LOCAL_SYMS is a pointer to the swapped in local symbols.
690
691
   LOCAL_SECTIONS is an array giving the section in the input file
692
   corresponding to the st_shndx field of each local symbol.
693
694
   The global hash table entry for the global symbols can be found
695
   via elf_sym_hashes (input_bfd).
696
697
   When generating relocatable output, this function must handle
698
   STB_LOCAL/STT_SECTION symbols specially.  The output symbol is
699
   going to be the section symbol corresponding to the output
700
   section, which means that the addend must be adjusted
701
   accordingly.  */
702
703
static int
704
rl78_elf_relocate_section
705
    (bfd *         output_bfd,
706
     struct bfd_link_info *  info,
707
     bfd *         input_bfd,
708
     asection *        input_section,
709
     bfd_byte *        contents,
710
     Elf_Internal_Rela *     relocs,
711
     Elf_Internal_Sym *      local_syms,
712
     asection **       local_sections)
713
0
{
714
0
  Elf_Internal_Shdr *   symtab_hdr;
715
0
  struct elf_link_hash_entry ** sym_hashes;
716
0
  Elf_Internal_Rela *   rel;
717
0
  Elf_Internal_Rela *   relend;
718
0
  asection *splt;
719
0
  bool ret;
720
721
0
  symtab_hdr = & elf_tdata (input_bfd)->symtab_hdr;
722
0
  sym_hashes = elf_sym_hashes (input_bfd);
723
0
  relend     = relocs + input_section->reloc_count;
724
725
0
  splt = elf_hash_table (info)->splt;
726
0
  ret = true;
727
0
  for (rel = relocs; rel < relend; rel ++)
728
0
    {
729
0
      reloc_howto_type *howto;
730
0
      unsigned long r_symndx;
731
0
      Elf_Internal_Sym *sym;
732
0
      asection *sec;
733
0
      struct elf_link_hash_entry *h;
734
0
      bfd_vma relocation;
735
0
      bfd_reloc_status_type r;
736
0
      const char *name = NULL;
737
0
      bool unresolved_reloc = true;
738
0
      int r_type;
739
0
      char *error_message;
740
741
0
      r_type = ELF32_R_TYPE (rel->r_info);
742
0
      r_symndx = ELF32_R_SYM (rel->r_info);
743
744
0
      howto  = rl78_elf_howto_table + ELF32_R_TYPE (rel->r_info);
745
0
      h      = NULL;
746
0
      sym    = NULL;
747
0
      sec    = NULL;
748
0
      relocation = 0;
749
750
0
      if (r_symndx < symtab_hdr->sh_info)
751
0
  {
752
0
    sym = local_syms + r_symndx;
753
0
    sec = local_sections [r_symndx];
754
0
    relocation = _bfd_elf_rela_local_sym (output_bfd, sym, & sec, rel);
755
756
0
    name = bfd_elf_string_from_elf_section
757
0
      (input_bfd, symtab_hdr->sh_link, sym->st_name);
758
0
    name = sym->st_name == 0 ? bfd_section_name (sec) : name;
759
0
  }
760
0
      else
761
0
  {
762
0
    bool warned ATTRIBUTE_UNUSED;
763
0
    bool ignored ATTRIBUTE_UNUSED;
764
765
0
    RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
766
0
           r_symndx, symtab_hdr, sym_hashes, h,
767
0
           sec, relocation, unresolved_reloc,
768
0
           warned, ignored);
769
770
0
    name = h->root.root.string;
771
0
  }
772
773
0
      if (sec != NULL && discarded_section (sec))
774
0
  RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
775
0
           rel, 1, relend, howto, 0, contents);
776
777
0
      if (bfd_link_relocatable (info))
778
0
  {
779
    /* This is a relocatable link.  We don't have to change
780
       anything, unless the reloc is against a section symbol,
781
       in which case we have to adjust according to where the
782
       section symbol winds up in the output section.  */
783
0
    if (sym != NULL && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
784
0
      rel->r_addend += sec->output_offset;
785
0
    continue;
786
0
  }
787
788
0
      switch (ELF32_R_TYPE (rel->r_info))
789
0
  {
790
0
  case R_RL78_DIR16S:
791
0
    {
792
0
      bfd_vma *plt_offset;
793
794
0
      if (h != NULL)
795
0
        plt_offset = &h->plt.offset;
796
0
      else
797
0
        plt_offset = elf_local_got_offsets (input_bfd) + r_symndx;
798
799
0
      if (! valid_16bit_address (relocation))
800
0
        {
801
    /* If this is the first time we've processed this symbol,
802
       fill in the plt entry with the correct symbol address.  */
803
0
    if ((*plt_offset & 1) == 0)
804
0
      {
805
0
        unsigned int x;
806
807
0
        x = 0x000000ec;  /* br !!abs24 */
808
0
        x |= (relocation << 8) & 0xffffff00;
809
0
        bfd_put_32 (input_bfd, x, splt->contents + *plt_offset);
810
0
        *plt_offset |= 1;
811
0
      }
812
813
0
    relocation = (splt->output_section->vma
814
0
            + splt->output_offset
815
0
            + (*plt_offset & -2));
816
0
    if (name)
817
0
    {
818
0
      char *newname = bfd_malloc (strlen(name)+5);
819
0
      strcpy (newname, name);
820
0
      strcat(newname, ".plt");
821
0
      _bfd_generic_link_add_one_symbol (info,
822
0
                input_bfd,
823
0
                newname,
824
0
                BSF_FUNCTION | BSF_WEAK,
825
0
                splt,
826
0
                (*plt_offset & -2),
827
0
                0,
828
0
                1,
829
0
                0,
830
0
                0);
831
0
    }
832
0
        }
833
0
    }
834
0
    break;
835
0
  }
836
837
0
      if (h != NULL && h->root.type == bfd_link_hash_undefweak)
838
  /* If the symbol is undefined and weak
839
     then the relocation resolves to zero.  */
840
0
  relocation = 0;
841
0
      else
842
0
  {
843
0
    if (howto->pc_relative)
844
0
      {
845
0
        relocation -= (input_section->output_section->vma
846
0
           + input_section->output_offset
847
0
           + rel->r_offset);
848
0
        relocation -= bfd_get_reloc_size (howto);
849
0
      }
850
851
0
    relocation += rel->r_addend;
852
0
  }
853
854
0
      r = bfd_reloc_ok;
855
0
      if (howto->bitsize != 0
856
0
    && (rel->r_offset >= input_section->size
857
0
        || ((howto->bitsize + 7u) / 8
858
0
      > input_section->size - rel->r_offset)))
859
0
  r = bfd_reloc_outofrange;
860
0
      else
861
0
  switch (r_type)
862
0
    {
863
0
    case R_RL78_NONE:
864
0
      break;
865
866
0
    case R_RL78_RH_RELAX:
867
0
      break;
868
869
0
    case R_RL78_DIR8S_PCREL:
870
0
      OP (0) = relocation;
871
0
      break;
872
873
0
    case R_RL78_DIR8S:
874
0
      OP (0) = relocation;
875
0
      break;
876
877
0
    case R_RL78_DIR8U:
878
0
      OP (0) = relocation;
879
0
      break;
880
881
0
    case R_RL78_DIR16S_PCREL:
882
0
      OP (0) = relocation;
883
0
      OP (1) = relocation >> 8;
884
0
      break;
885
886
0
    case R_RL78_DIR16S:
887
0
      if ((relocation & 0xf0000) == 0xf0000)
888
0
        relocation &= 0xffff;
889
0
      OP (0) = relocation;
890
0
      OP (1) = relocation >> 8;
891
0
      break;
892
893
0
    case R_RL78_DIR16U:
894
0
      OP (0) = relocation;
895
0
      OP (1) = relocation >> 8;
896
0
      break;
897
898
0
    case R_RL78_DIR16:
899
0
      OP (0) = relocation;
900
0
      OP (1) = relocation >> 8;
901
0
      break;
902
903
0
    case R_RL78_DIR16_REV:
904
0
      OP (1) = relocation;
905
0
      OP (0) = relocation >> 8;
906
0
      break;
907
908
0
    case R_RL78_DIR3U_PCREL:
909
0
      OP (0) &= 0xf8;
910
0
      OP (0) |= relocation & 0x07;
911
      /* Map [3, 10] to [0, 7].  The code below using howto
912
         bitsize will check for unsigned overflow.  */
913
0
      relocation -= 3;
914
0
      break;
915
916
0
    case R_RL78_DIR24S_PCREL:
917
0
      OP (0) = relocation;
918
0
      OP (1) = relocation >> 8;
919
0
      OP (2) = relocation >> 16;
920
0
      break;
921
922
0
    case R_RL78_DIR24S:
923
0
      OP (0) = relocation;
924
0
      OP (1) = relocation >> 8;
925
0
      OP (2) = relocation >> 16;
926
0
      break;
927
928
0
    case R_RL78_DIR32:
929
0
      OP (0) = relocation;
930
0
      OP (1) = relocation >> 8;
931
0
      OP (2) = relocation >> 16;
932
0
      OP (3) = relocation >> 24;
933
0
      break;
934
935
0
    case R_RL78_DIR32_REV:
936
0
      OP (3) = relocation;
937
0
      OP (2) = relocation >> 8;
938
0
      OP (1) = relocation >> 16;
939
0
      OP (0) = relocation >> 24;
940
0
      break;
941
942
0
    case R_RL78_RH_SFR:
943
0
      relocation -= 0xfff00;
944
0
      OP (0) = relocation;
945
0
      break;
946
947
0
    case R_RL78_RH_SADDR:
948
0
      relocation -= 0xffe20;
949
0
      OP (0) = relocation;
950
0
      break;
951
952
      /* Complex reloc handling:  */
953
0
    case R_RL78_ABS32:
954
0
    case R_RL78_ABS32_REV:
955
0
    case R_RL78_ABS24S_PCREL:
956
0
    case R_RL78_ABS24S:
957
0
    case R_RL78_ABS16:
958
0
    case R_RL78_ABS16_REV:
959
0
    case R_RL78_ABS16S_PCREL:
960
0
    case R_RL78_ABS16S:
961
0
    case R_RL78_ABS16U:
962
0
    case R_RL78_ABS16UL:
963
0
    case R_RL78_ABS16UW:
964
0
    case R_RL78_ABS8:
965
0
    case R_RL78_ABS8U:
966
0
    case R_RL78_ABS8UL:
967
0
    case R_RL78_ABS8UW:
968
0
    case R_RL78_ABS8S_PCREL:
969
0
    case R_RL78_ABS8S:
970
0
    case R_RL78_OPneg:
971
0
    case R_RL78_OPadd:
972
0
    case R_RL78_OPsub:
973
0
    case R_RL78_OPmul:
974
0
    case R_RL78_OPdiv:
975
0
    case R_RL78_OPshla:
976
0
    case R_RL78_OPshra:
977
0
    case R_RL78_OPsctsize:
978
0
    case R_RL78_OPscttop:
979
0
    case R_RL78_OPand:
980
0
    case R_RL78_OPor:
981
0
    case R_RL78_OPxor:
982
0
    case R_RL78_OPnot:
983
0
    case R_RL78_OPmod:
984
0
      relocation = rl78_compute_complex_reloc (r_type, 0, input_section,
985
0
                 &r, &error_message);
986
987
0
      switch (r_type)
988
0
        {
989
0
        case R_RL78_ABS32:
990
0
    OP (0) = relocation;
991
0
    OP (1) = relocation >> 8;
992
0
    OP (2) = relocation >> 16;
993
0
    OP (3) = relocation >> 24;
994
0
    break;
995
996
0
        case R_RL78_ABS32_REV:
997
0
    OP (3) = relocation;
998
0
    OP (2) = relocation >> 8;
999
0
    OP (1) = relocation >> 16;
1000
0
    OP (0) = relocation >> 24;
1001
0
    break;
1002
1003
0
        case R_RL78_ABS24S_PCREL:
1004
0
        case R_RL78_ABS24S:
1005
0
    OP (0) = relocation;
1006
0
    OP (1) = relocation >> 8;
1007
0
    OP (2) = relocation >> 16;
1008
0
    break;
1009
1010
0
        case R_RL78_ABS16:
1011
0
    OP (0) = relocation;
1012
0
    OP (1) = relocation >> 8;
1013
0
    break;
1014
1015
0
        case R_RL78_ABS16_REV:
1016
0
    OP (1) = relocation;
1017
0
    OP (0) = relocation >> 8;
1018
0
    break;
1019
1020
0
        case R_RL78_ABS16S_PCREL:
1021
0
        case R_RL78_ABS16S:
1022
0
    OP (0) = relocation;
1023
0
    OP (1) = relocation >> 8;
1024
0
    break;
1025
1026
0
        case R_RL78_ABS16U:
1027
0
        case R_RL78_ABS16UL:
1028
0
        case R_RL78_ABS16UW:
1029
0
    OP (0) = relocation;
1030
0
    OP (1) = relocation >> 8;
1031
0
    break;
1032
1033
0
        case R_RL78_ABS8:
1034
0
    OP (0) = relocation;
1035
0
    break;
1036
1037
0
        case R_RL78_ABS8U:
1038
0
        case R_RL78_ABS8UL:
1039
0
        case R_RL78_ABS8UW:
1040
0
    OP (0) = relocation;
1041
0
    break;
1042
1043
0
        case R_RL78_ABS8S_PCREL:
1044
0
        case R_RL78_ABS8S:
1045
0
    OP (0) = relocation;
1046
0
    break;
1047
1048
0
        default:
1049
0
    break;
1050
0
        }
1051
0
      break;
1052
1053
0
    case R_RL78_SYM:
1054
0
      if (r_symndx < symtab_hdr->sh_info)
1055
0
        relocation = sec->output_section->vma + sec->output_offset
1056
0
    + sym->st_value + rel->r_addend;
1057
0
      else if (h != NULL
1058
0
         && (h->root.type == bfd_link_hash_defined
1059
0
       || h->root.type == bfd_link_hash_defweak))
1060
0
        relocation = h->root.u.def.value
1061
0
    + sec->output_section->vma
1062
0
    + sec->output_offset
1063
0
    + rel->r_addend;
1064
0
      else
1065
0
        {
1066
0
    relocation = 0;
1067
0
    if (h->root.type != bfd_link_hash_undefweak)
1068
0
      _bfd_error_handler
1069
0
        (_("warning: RL78_SYM reloc with an unknown symbol"));
1070
0
        }
1071
0
      (void) rl78_compute_complex_reloc (r_type, relocation, input_section,
1072
0
                 &r, &error_message);
1073
0
      break;
1074
1075
0
    case R_RL78_OPromtop:
1076
0
      relocation = get_romstart (info, input_bfd, input_section,
1077
0
               rel->r_offset);
1078
0
      (void) rl78_compute_complex_reloc (r_type, relocation, input_section,
1079
0
                 &r, &error_message);
1080
0
      break;
1081
1082
0
    case R_RL78_OPramtop:
1083
0
      relocation = get_ramstart (info, input_bfd, input_section,
1084
0
               rel->r_offset);
1085
0
      (void) rl78_compute_complex_reloc (r_type, relocation, input_section,
1086
0
                 &r, &error_message);
1087
0
      break;
1088
1089
0
    default:
1090
0
      r = bfd_reloc_notsupported;
1091
0
      break;
1092
0
    }
1093
1094
0
      if (r == bfd_reloc_ok)
1095
0
  r = check_overflow (howto, relocation);
1096
1097
0
      if (r != bfd_reloc_ok)
1098
0
  {
1099
0
    switch (r)
1100
0
      {
1101
0
      case bfd_reloc_overflow:
1102
0
        (*info->callbacks->reloc_overflow)
1103
0
    (info, (h ? &h->root : NULL), name, howto->name, (bfd_vma) 0,
1104
0
     input_bfd, input_section, rel->r_offset);
1105
0
        break;
1106
1107
0
      case bfd_reloc_undefined:
1108
0
        (*info->callbacks->undefined_symbol)
1109
0
    (info, name, input_bfd, input_section, rel->r_offset, true);
1110
0
        break;
1111
1112
0
      case bfd_reloc_outofrange:
1113
         /* xgettext:c-format */
1114
0
        (*info->callbacks->einfo)
1115
0
    (_("%H: %s out of range\n"),
1116
0
     input_bfd, input_section, rel->r_offset, howto->name);
1117
0
        break;
1118
1119
0
      case bfd_reloc_notsupported:
1120
        /* xgettext:c-format */
1121
0
        (*info->callbacks->einfo)
1122
0
    (_("%H: relocation type %u is not supported\n"),
1123
0
     input_bfd, input_section, rel->r_offset, r_type);
1124
0
        break;
1125
1126
0
      case bfd_reloc_dangerous:
1127
0
        (*info->callbacks->reloc_dangerous)
1128
0
    (info, error_message, input_bfd, input_section, rel->r_offset);
1129
0
        break;
1130
1131
0
      default:
1132
        /* xgettext:c-format */
1133
0
        (*info->callbacks->einfo)
1134
0
    (_("%H: relocation %s returns an unrecognized value %x\n"),
1135
0
     input_bfd, input_section, rel->r_offset, howto->name, r);
1136
0
        break;
1137
0
      }
1138
0
    ret = false;
1139
0
  }
1140
0
    }
1141
1142
0
  return ret;
1143
0
}
1144

1145
/* Function to set the ELF flag bits.  */
1146
1147
static bool
1148
rl78_elf_set_private_flags (bfd * abfd, flagword flags)
1149
0
{
1150
0
  elf_elfheader (abfd)->e_flags = flags;
1151
0
  elf_flags_init (abfd) = true;
1152
0
  return true;
1153
0
}
1154
1155
static bool no_warn_mismatch = false;
1156
1157
void bfd_elf32_rl78_set_target_flags (bool);
1158
1159
void
1160
bfd_elf32_rl78_set_target_flags (bool user_no_warn_mismatch)
1161
0
{
1162
0
  no_warn_mismatch = user_no_warn_mismatch;
1163
0
}
1164
1165
static const char *
1166
rl78_cpu_name (flagword flags)
1167
0
{
1168
0
  switch (flags & E_FLAG_RL78_CPU_MASK)
1169
0
    {
1170
0
    default: return "";
1171
0
    case E_FLAG_RL78_G10:     return "G10";
1172
0
    case E_FLAG_RL78_G13:     return "G13";
1173
0
    case E_FLAG_RL78_G14:     return "G14";
1174
0
    }
1175
0
}
1176
1177
/* Merge backend specific data from an object file to the output
1178
   object file when linking.  */
1179
1180
static bool
1181
rl78_elf_merge_private_bfd_data (bfd *ibfd, struct bfd_link_info *info)
1182
0
{
1183
0
  bfd *obfd = info->output_bfd;
1184
0
  flagword new_flags;
1185
0
  flagword old_flags;
1186
0
  bool error = false;
1187
1188
0
  new_flags = elf_elfheader (ibfd)->e_flags;
1189
0
  old_flags = elf_elfheader (obfd)->e_flags;
1190
1191
0
  if (!elf_flags_init (obfd))
1192
0
    {
1193
      /* First call, no flags set.  */
1194
0
      elf_flags_init (obfd) = true;
1195
0
      elf_elfheader (obfd)->e_flags = new_flags;
1196
0
    }
1197
0
  else if (old_flags != new_flags)
1198
0
    {
1199
0
      flagword changed_flags = old_flags ^ new_flags;
1200
1201
0
      if (changed_flags & E_FLAG_RL78_CPU_MASK)
1202
0
  {
1203
0
    flagword out_cpu = old_flags & E_FLAG_RL78_CPU_MASK;
1204
0
    flagword in_cpu = new_flags & E_FLAG_RL78_CPU_MASK;
1205
1206
0
    if (in_cpu == E_FLAG_RL78_ANY_CPU || in_cpu == out_cpu)
1207
0
      /* It does not matter what new_cpu may have.  */;
1208
0
    else if (out_cpu == E_FLAG_RL78_ANY_CPU)
1209
0
      {
1210
0
        if (in_cpu == E_FLAG_RL78_G10)
1211
0
    {
1212
      /* G10 files can only be linked with other G10 files.
1213
         If the output is set to "any" this means that it is
1214
         a G14 file that does not use hardware multiply/divide,
1215
         but that is still incompatible with the G10 ABI.  */
1216
0
      error = true;
1217
1218
0
      _bfd_error_handler
1219
        /* xgettext:c-format */
1220
0
        (_("RL78 ABI conflict: G10 file %pB cannot be linked"
1221
0
           " with %s file %pB"),
1222
0
         ibfd, rl78_cpu_name (out_cpu), obfd);
1223
0
    }
1224
0
        else
1225
0
    {
1226
0
      old_flags &= ~ E_FLAG_RL78_CPU_MASK;
1227
0
      old_flags |= in_cpu;
1228
0
      elf_elfheader (obfd)->e_flags = old_flags;
1229
0
    }
1230
0
      }
1231
0
    else
1232
0
      {
1233
0
        error = true;
1234
1235
0
        _bfd_error_handler
1236
    /* xgettext:c-format */
1237
0
    (_("RL78 ABI conflict: cannot link %s file %pB with %s file %pB"),
1238
0
     rl78_cpu_name (in_cpu),  ibfd,
1239
0
     rl78_cpu_name (out_cpu), obfd);
1240
0
      }
1241
0
  }
1242
1243
0
      if (changed_flags & E_FLAG_RL78_64BIT_DOUBLES)
1244
0
  {
1245
0
    _bfd_error_handler
1246
0
      (_("RL78 merge conflict: cannot link 32-bit and 64-bit objects together"));
1247
1248
0
    if (old_flags & E_FLAG_RL78_64BIT_DOUBLES)
1249
      /* xgettext:c-format */
1250
0
      _bfd_error_handler (_("- %pB is 64-bit, %pB is not"),
1251
0
        obfd, ibfd);
1252
0
    else
1253
      /* xgettext:c-format */
1254
0
      _bfd_error_handler (_("- %pB is 64-bit, %pB is not"),
1255
0
        ibfd, obfd);
1256
0
    error = true;
1257
0
  }
1258
0
    }
1259
1260
0
  return !error;
1261
0
}
1262

1263
static bool
1264
rl78_elf_print_private_bfd_data (bfd * abfd, void * ptr)
1265
2
{
1266
2
  FILE * file = (FILE *) ptr;
1267
2
  flagword flags;
1268
1269
2
  BFD_ASSERT (abfd != NULL && ptr != NULL);
1270
1271
  /* Print normal ELF private data.  */
1272
2
  _bfd_elf_print_private_bfd_data (abfd, ptr);
1273
1274
2
  flags = elf_elfheader (abfd)->e_flags;
1275
2
  fprintf (file, _("private flags = 0x%lx:"), (long) flags);
1276
1277
2
  if (flags & E_FLAG_RL78_CPU_MASK)
1278
0
    fprintf (file, " [%s]", rl78_cpu_name (flags));
1279
1280
2
  if (flags & E_FLAG_RL78_64BIT_DOUBLES)
1281
1
    fprintf (file, _(" [64-bit doubles]"));
1282
1283
2
  fputc ('\n', file);
1284
2
  return true;
1285
2
}
1286
1287
/* Return the MACH for an e_flags value.  */
1288
1289
static int
1290
elf32_rl78_machine (bfd * abfd ATTRIBUTE_UNUSED)
1291
1.61k
{
1292
1.61k
  return bfd_mach_rl78;
1293
1.61k
}
1294
1295
static bool
1296
rl78_elf_object_p (bfd * abfd)
1297
1.61k
{
1298
1.61k
  bfd_default_set_arch_mach (abfd, bfd_arch_rl78,
1299
1.61k
           elf32_rl78_machine (abfd));
1300
1.61k
  return true;
1301
1.61k
}
1302

1303
/* support PLT for 16-bit references to 24-bit functions.  */
1304
1305
/* We support 16-bit pointers to code above 64k by generating a thunk
1306
   below 64k containing a JMP instruction to the final address.  */
1307
1308
static bool
1309
rl78_elf_check_relocs
1310
    (bfd *           abfd,
1311
     struct bfd_link_info *    info,
1312
     asection *          sec,
1313
     const Elf_Internal_Rela * relocs)
1314
0
{
1315
0
  Elf_Internal_Shdr *   symtab_hdr;
1316
0
  struct elf_link_hash_entry ** sym_hashes;
1317
0
  const Elf_Internal_Rela * rel;
1318
0
  const Elf_Internal_Rela * rel_end;
1319
0
  bfd_vma *local_plt_offsets;
1320
0
  asection *splt;
1321
0
  bfd *dynobj;
1322
1323
0
  if (bfd_link_relocatable (info))
1324
0
    return true;
1325
1326
0
  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
1327
0
  sym_hashes = elf_sym_hashes (abfd);
1328
0
  local_plt_offsets = elf_local_got_offsets (abfd);
1329
0
  dynobj = elf_hash_table(info)->dynobj;
1330
1331
0
  rel_end = relocs + sec->reloc_count;
1332
0
  for (rel = relocs; rel < rel_end; rel++)
1333
0
    {
1334
0
      struct elf_link_hash_entry *h;
1335
0
      unsigned long r_symndx;
1336
0
      bfd_vma *offset;
1337
1338
0
      r_symndx = ELF32_R_SYM (rel->r_info);
1339
0
      if (r_symndx < symtab_hdr->sh_info)
1340
0
  h = NULL;
1341
0
      else
1342
0
  {
1343
0
    h = sym_hashes[r_symndx - symtab_hdr->sh_info];
1344
0
    while (h->root.type == bfd_link_hash_indirect
1345
0
     || h->root.type == bfd_link_hash_warning)
1346
0
      h = (struct elf_link_hash_entry *) h->root.u.i.link;
1347
0
  }
1348
1349
0
      switch (ELF32_R_TYPE (rel->r_info))
1350
0
  {
1351
    /* This relocation describes a 16-bit pointer to a function.
1352
       We may need to allocate a thunk in low memory; reserve memory
1353
       for it now.  */
1354
0
  case R_RL78_DIR16S:
1355
0
    if (dynobj == NULL)
1356
0
      elf_hash_table (info)->dynobj = dynobj = abfd;
1357
0
    splt = elf_hash_table (info)->splt;
1358
0
    if (splt == NULL)
1359
0
      {
1360
0
        flagword flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
1361
0
        | SEC_IN_MEMORY | SEC_LINKER_CREATED
1362
0
        | SEC_READONLY | SEC_CODE);
1363
0
        splt = bfd_make_section_anyway_with_flags (dynobj, ".plt",
1364
0
               flags);
1365
0
        elf_hash_table (info)->splt = splt;
1366
0
        if (splt == NULL
1367
0
      || !bfd_set_section_alignment (splt, 1))
1368
0
    return false;
1369
0
      }
1370
1371
0
    if (h != NULL)
1372
0
      offset = &h->plt.offset;
1373
0
    else
1374
0
      {
1375
0
        if (local_plt_offsets == NULL)
1376
0
    {
1377
0
      size_t size;
1378
0
      unsigned int i;
1379
1380
0
      size = symtab_hdr->sh_info * sizeof (bfd_vma);
1381
0
      local_plt_offsets = (bfd_vma *) bfd_alloc (abfd, size);
1382
0
      if (local_plt_offsets == NULL)
1383
0
        return false;
1384
0
      elf_local_got_offsets (abfd) = local_plt_offsets;
1385
1386
0
      for (i = 0; i < symtab_hdr->sh_info; i++)
1387
0
        local_plt_offsets[i] = (bfd_vma) -1;
1388
0
    }
1389
0
        offset = &local_plt_offsets[r_symndx];
1390
0
      }
1391
1392
0
    if (*offset == (bfd_vma) -1)
1393
0
      {
1394
0
        *offset = splt->size;
1395
0
        splt->size += 4;
1396
0
      }
1397
0
    break;
1398
0
  }
1399
0
    }
1400
1401
0
  return true;
1402
0
}
1403
1404
/* This must exist if dynobj is ever set.  */
1405
1406
static bool
1407
rl78_elf_finish_dynamic_sections (bfd *abfd ATTRIBUTE_UNUSED,
1408
          struct bfd_link_info *info)
1409
0
{
1410
0
  bfd *dynobj;
1411
0
  asection *splt;
1412
1413
0
  if (!elf_hash_table (info)->dynamic_sections_created)
1414
0
    return true;
1415
1416
  /* As an extra sanity check, verify that all plt entries have been
1417
     filled in.  However, relaxing might have changed the relocs so
1418
     that some plt entries don't get filled in, so we have to skip
1419
     this check if we're relaxing.  Unfortunately, check_relocs is
1420
     called before relaxation.  */
1421
1422
0
  if (info->relax_trip > 0)
1423
0
    return true;
1424
1425
0
  dynobj = elf_hash_table (info)->dynobj;
1426
0
  splt = elf_hash_table (info)->splt;
1427
0
  if (dynobj != NULL && splt != NULL)
1428
0
    {
1429
0
      bfd_byte *contents = splt->contents;
1430
0
      unsigned int i, size = splt->size;
1431
1432
0
      for (i = 0; i < size; i += 4)
1433
0
  {
1434
0
    unsigned int x = bfd_get_32 (dynobj, contents + i);
1435
0
    BFD_ASSERT (x != 0);
1436
0
  }
1437
0
    }
1438
1439
0
  return true;
1440
0
}
1441
1442
static bool
1443
rl78_elf_early_size_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
1444
            struct bfd_link_info *info)
1445
0
{
1446
0
  bfd *dynobj;
1447
0
  asection *splt;
1448
1449
0
  if (bfd_link_relocatable (info))
1450
0
    return true;
1451
1452
0
  dynobj = elf_hash_table (info)->dynobj;
1453
0
  if (dynobj == NULL)
1454
0
    return true;
1455
1456
0
  splt = elf_hash_table (info)->splt;
1457
0
  BFD_ASSERT (splt != NULL);
1458
1459
0
  splt->contents = (bfd_byte *) bfd_zalloc (dynobj, splt->size);
1460
0
  if (splt->contents == NULL)
1461
0
    return false;
1462
0
  splt->alloced = 1;
1463
1464
0
  return true;
1465
0
}
1466
1467

1468
1469
/* Handle relaxing.  */
1470
1471
/* A subroutine of rl78_elf_relax_section.  If the global symbol H
1472
   is within the low 64k, remove any entry for it in the plt.  */
1473
1474
struct relax_plt_data
1475
{
1476
  asection *splt;
1477
  bool *again;
1478
};
1479
1480
static bool
1481
rl78_relax_plt_check (struct elf_link_hash_entry *h, void * xdata)
1482
0
{
1483
0
  struct relax_plt_data *data = (struct relax_plt_data *) xdata;
1484
1485
0
  if (h->plt.offset != (bfd_vma) -1)
1486
0
    {
1487
0
      bfd_vma address;
1488
1489
0
      if (h->root.type == bfd_link_hash_undefined
1490
0
    || h->root.type == bfd_link_hash_undefweak)
1491
0
  address = 0;
1492
0
      else
1493
0
  address = (h->root.u.def.section->output_section->vma
1494
0
       + h->root.u.def.section->output_offset
1495
0
       + h->root.u.def.value);
1496
1497
0
      if (valid_16bit_address (address))
1498
0
  {
1499
0
    h->plt.offset = -1;
1500
0
    data->splt->size -= 4;
1501
0
    *data->again = true;
1502
0
  }
1503
0
    }
1504
1505
0
  return true;
1506
0
}
1507
1508
/* A subroutine of rl78_elf_relax_section.  If the global symbol H
1509
   previously had a plt entry, give it a new entry offset.  */
1510
1511
static bool
1512
rl78_relax_plt_realloc (struct elf_link_hash_entry *h, void * xdata)
1513
0
{
1514
0
  bfd_vma *entry = (bfd_vma *) xdata;
1515
1516
0
  if (h->plt.offset != (bfd_vma) -1)
1517
0
    {
1518
0
      h->plt.offset = *entry;
1519
0
      *entry += 4;
1520
0
    }
1521
1522
0
  return true;
1523
0
}
1524
1525
static bool
1526
rl78_elf_relax_plt_section (bfd *dynobj,
1527
          asection *splt,
1528
          struct bfd_link_info *info,
1529
          bool *again)
1530
0
{
1531
0
  struct relax_plt_data relax_plt_data;
1532
0
  bfd *ibfd;
1533
1534
  /* Assume nothing changes.  */
1535
0
  *again = false;
1536
1537
0
  if (bfd_link_relocatable (info))
1538
0
    return true;
1539
1540
  /* We only relax the .plt section at the moment.  */
1541
0
  if (dynobj != elf_hash_table (info)->dynobj
1542
0
      || strcmp (splt->name, ".plt") != 0)
1543
0
    return true;
1544
1545
  /* Quick check for an empty plt.  */
1546
0
  if (splt->size == 0)
1547
0
    return true;
1548
1549
  /* Map across all global symbols; see which ones happen to
1550
     fall in the low 64k.  */
1551
0
  relax_plt_data.splt = splt;
1552
0
  relax_plt_data.again = again;
1553
0
  elf_link_hash_traverse (elf_hash_table (info), rl78_relax_plt_check,
1554
0
        &relax_plt_data);
1555
1556
  /* Likewise for local symbols, though that's somewhat less convenient
1557
     as we have to walk the list of input bfds and swap in symbol data.  */
1558
0
  for (ibfd = info->input_bfds; ibfd ; ibfd = ibfd->link.next)
1559
0
    {
1560
0
      bfd_vma *local_plt_offsets = elf_local_got_offsets (ibfd);
1561
0
      Elf_Internal_Shdr *symtab_hdr;
1562
0
      Elf_Internal_Sym *isymbuf = NULL;
1563
0
      unsigned int idx;
1564
1565
0
      if (! local_plt_offsets)
1566
0
  continue;
1567
1568
0
      symtab_hdr = &elf_tdata (ibfd)->symtab_hdr;
1569
0
      if (symtab_hdr->sh_info != 0)
1570
0
  {
1571
0
    isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
1572
0
    if (isymbuf == NULL)
1573
0
      isymbuf = bfd_elf_get_elf_syms (ibfd, symtab_hdr,
1574
0
              symtab_hdr->sh_info, 0,
1575
0
              NULL, NULL, NULL);
1576
0
    if (isymbuf == NULL)
1577
0
      return false;
1578
0
  }
1579
1580
0
      for (idx = 0; idx < symtab_hdr->sh_info; ++idx)
1581
0
  {
1582
0
    Elf_Internal_Sym *isym;
1583
0
    asection *tsec;
1584
0
    bfd_vma address;
1585
1586
0
    if (local_plt_offsets[idx] == (bfd_vma) -1)
1587
0
      continue;
1588
1589
0
    isym = &isymbuf[idx];
1590
0
    if (isym->st_shndx == SHN_UNDEF)
1591
0
      continue;
1592
0
    else if (isym->st_shndx == SHN_ABS)
1593
0
      tsec = bfd_abs_section_ptr;
1594
0
    else if (isym->st_shndx == SHN_COMMON)
1595
0
      tsec = bfd_com_section_ptr;
1596
0
    else
1597
0
      tsec = bfd_section_from_elf_index (ibfd, isym->st_shndx);
1598
1599
0
    address = (tsec->output_section->vma
1600
0
         + tsec->output_offset
1601
0
         + isym->st_value);
1602
0
    if (valid_16bit_address (address))
1603
0
      {
1604
0
        local_plt_offsets[idx] = -1;
1605
0
        splt->size -= 4;
1606
0
        *again = true;
1607
0
      }
1608
0
  }
1609
1610
0
      if (isymbuf != NULL
1611
0
    && symtab_hdr->contents != (unsigned char *) isymbuf)
1612
0
  {
1613
0
    if (! info->keep_memory)
1614
0
      free (isymbuf);
1615
0
    else
1616
0
      {
1617
        /* Cache the symbols for elf_link_input_bfd.  */
1618
0
        symtab_hdr->contents = (unsigned char *) isymbuf;
1619
0
      }
1620
0
  }
1621
0
    }
1622
1623
  /* If we changed anything, walk the symbols again to reallocate
1624
     .plt entry addresses.  */
1625
0
  if (*again && splt->size > 0)
1626
0
    {
1627
0
      bfd_vma entry = 0;
1628
1629
0
      elf_link_hash_traverse (elf_hash_table (info),
1630
0
            rl78_relax_plt_realloc, &entry);
1631
1632
0
      for (ibfd = info->input_bfds; ibfd ; ibfd = ibfd->link.next)
1633
0
  {
1634
0
    bfd_vma *local_plt_offsets = elf_local_got_offsets (ibfd);
1635
0
    unsigned int nlocals = elf_tdata (ibfd)->symtab_hdr.sh_info;
1636
0
    unsigned int idx;
1637
1638
0
    if (! local_plt_offsets)
1639
0
      continue;
1640
1641
0
    for (idx = 0; idx < nlocals; ++idx)
1642
0
      if (local_plt_offsets[idx] != (bfd_vma) -1)
1643
0
        {
1644
0
    local_plt_offsets[idx] = entry;
1645
0
    entry += 4;
1646
0
        }
1647
0
  }
1648
0
    }
1649
1650
0
  return true;
1651
0
}
1652
1653
/* Delete some bytes from a section while relaxing.  */
1654
1655
static bool
1656
elf32_rl78_relax_delete_bytes (bfd *abfd, asection *sec, bfd_vma addr, int count,
1657
             Elf_Internal_Rela *alignment_rel, int force_snip)
1658
0
{
1659
0
  Elf_Internal_Shdr * symtab_hdr;
1660
0
  unsigned int        sec_shndx;
1661
0
  bfd_byte *        contents;
1662
0
  Elf_Internal_Rela * irel;
1663
0
  Elf_Internal_Rela * irelend;
1664
0
  Elf_Internal_Sym *  isym;
1665
0
  Elf_Internal_Sym *  isymend;
1666
0
  bfd_vma       toaddr;
1667
0
  unsigned int        symcount;
1668
0
  struct elf_link_hash_entry ** sym_hashes;
1669
0
  struct elf_link_hash_entry ** end_hashes;
1670
1671
0
  if (!alignment_rel)
1672
0
    force_snip = 1;
1673
1674
0
  sec_shndx = _bfd_elf_section_from_bfd_section (abfd, sec);
1675
1676
0
  contents = elf_section_data (sec)->this_hdr.contents;
1677
1678
  /* The deletion must stop at the next alignment boundary, if
1679
     ALIGNMENT_REL is non-NULL.  */
1680
0
  toaddr = sec->size;
1681
0
  if (alignment_rel)
1682
0
    toaddr = alignment_rel->r_offset;
1683
1684
0
  irel = elf_section_data (sec)->relocs;
1685
0
  if (irel == NULL)
1686
0
    {
1687
0
      _bfd_elf_link_read_relocs (sec->owner, sec, NULL, NULL, true);
1688
0
      irel = elf_section_data (sec)->relocs;
1689
0
    }
1690
1691
0
  irelend = irel + sec->reloc_count;
1692
1693
  /* Actually delete the bytes.  */
1694
0
  memmove (contents + addr, contents + addr + count,
1695
0
     (size_t) (toaddr - addr - count));
1696
1697
  /* If we don't have an alignment marker to worry about, we can just
1698
     shrink the section.  Otherwise, we have to fill in the newly
1699
     created gap with NOP insns (0x03).  */
1700
0
  if (force_snip)
1701
0
    sec->size -= count;
1702
0
  else
1703
0
    memset (contents + toaddr - count, 0x03, count);
1704
1705
  /* Adjust all the relocs.  */
1706
0
  for (; irel && irel < irelend; irel++)
1707
0
    {
1708
      /* Get the new reloc address.  */
1709
0
      if (irel->r_offset > addr
1710
0
    && (irel->r_offset < toaddr
1711
0
        || (force_snip && irel->r_offset == toaddr)))
1712
0
  irel->r_offset -= count;
1713
1714
      /* If we see an ALIGN marker at the end of the gap, we move it
1715
   to the beginning of the gap, since marking these gaps is what
1716
   they're for.  */
1717
0
      if (irel->r_offset == toaddr
1718
0
    && ELF32_R_TYPE (irel->r_info) == R_RL78_RH_RELAX
1719
0
    && irel->r_addend & RL78_RELAXA_ALIGN)
1720
0
  irel->r_offset -= count;
1721
0
    }
1722
1723
  /* Adjust the local symbols defined in this section.  */
1724
0
  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
1725
0
  isym = (Elf_Internal_Sym *) symtab_hdr->contents;
1726
0
  isymend = isym + symtab_hdr->sh_info;
1727
1728
0
  for (; isym < isymend; isym++)
1729
0
    {
1730
      /* If the symbol is in the range of memory we just moved, we
1731
   have to adjust its value.  */
1732
0
      if (isym->st_shndx == sec_shndx
1733
0
    && isym->st_value > addr
1734
0
    && isym->st_value < toaddr)
1735
0
  isym->st_value -= count;
1736
1737
      /* If the symbol *spans* the bytes we just deleted (i.e. it's
1738
   *end* is in the moved bytes but it's *start* isn't), then we
1739
   must adjust its size.  */
1740
0
      if (isym->st_shndx == sec_shndx
1741
0
    && isym->st_value < addr
1742
0
    && isym->st_value + isym->st_size > addr
1743
0
    && isym->st_value + isym->st_size < toaddr)
1744
0
  isym->st_size -= count;
1745
0
    }
1746
1747
  /* Now adjust the global symbols defined in this section.  */
1748
0
  symcount = (symtab_hdr->sh_size / sizeof (Elf32_External_Sym)
1749
0
        - symtab_hdr->sh_info);
1750
0
  sym_hashes = elf_sym_hashes (abfd);
1751
0
  end_hashes = sym_hashes + symcount;
1752
1753
0
  for (; sym_hashes < end_hashes; sym_hashes++)
1754
0
    {
1755
0
      struct elf_link_hash_entry *sym_hash = *sym_hashes;
1756
1757
0
      if ((sym_hash->root.type == bfd_link_hash_defined
1758
0
     || sym_hash->root.type == bfd_link_hash_defweak)
1759
0
    && sym_hash->root.u.def.section == sec)
1760
0
  {
1761
    /* As above, adjust the value if needed.  */
1762
0
    if (sym_hash->root.u.def.value > addr
1763
0
        && sym_hash->root.u.def.value < toaddr)
1764
0
      sym_hash->root.u.def.value -= count;
1765
1766
    /* As above, adjust the size if needed.  */
1767
0
    if (sym_hash->root.u.def.value < addr
1768
0
        && sym_hash->root.u.def.value + sym_hash->size > addr
1769
0
        && sym_hash->root.u.def.value + sym_hash->size < toaddr)
1770
0
      sym_hash->size -= count;
1771
0
  }
1772
0
    }
1773
1774
0
  return true;
1775
0
}
1776
1777
/* Used to sort relocs by address.  If relocs have the same address,
1778
   we maintain their relative order, except that R_RL78_RH_RELAX
1779
   alignment relocs must be the first reloc for any given address.  */
1780
1781
static void
1782
reloc_bubblesort (Elf_Internal_Rela * r, int count)
1783
0
{
1784
0
  int i;
1785
0
  bool again;
1786
0
  bool swappit;
1787
1788
  /* This is almost a classic bubblesort.  It's the slowest sort, but
1789
     we're taking advantage of the fact that the relocations are
1790
     mostly in order already (the assembler emits them that way) and
1791
     we need relocs with the same address to remain in the same
1792
     relative order.  */
1793
0
  again = true;
1794
0
  while (again)
1795
0
    {
1796
0
      again = false;
1797
0
      for (i = 0; i < count - 1; i ++)
1798
0
  {
1799
0
    if (r[i].r_offset > r[i + 1].r_offset)
1800
0
      swappit = true;
1801
0
    else if (r[i].r_offset < r[i + 1].r_offset)
1802
0
      swappit = false;
1803
0
    else if (ELF32_R_TYPE (r[i + 1].r_info) == R_RL78_RH_RELAX
1804
0
       && (r[i + 1].r_addend & RL78_RELAXA_ALIGN))
1805
0
      swappit = true;
1806
0
    else if (ELF32_R_TYPE (r[i + 1].r_info) == R_RL78_RH_RELAX
1807
0
       && (r[i + 1].r_addend & RL78_RELAXA_ELIGN)
1808
0
       && !(ELF32_R_TYPE (r[i].r_info) == R_RL78_RH_RELAX
1809
0
      && (r[i].r_addend & RL78_RELAXA_ALIGN)))
1810
0
      swappit = true;
1811
0
    else
1812
0
      swappit = false;
1813
1814
0
    if (swappit)
1815
0
      {
1816
0
        Elf_Internal_Rela tmp;
1817
1818
0
        tmp = r[i];
1819
0
        r[i] = r[i + 1];
1820
0
        r[i + 1] = tmp;
1821
        /* If we do move a reloc back, re-scan to see if it
1822
     needs to be moved even further back.  This avoids
1823
     most of the O(n^2) behavior for our cases.  */
1824
0
        if (i > 0)
1825
0
    i -= 2;
1826
0
        again = true;
1827
0
      }
1828
0
  }
1829
0
    }
1830
0
}
1831
1832
1833
#define OFFSET_FOR_RELOC(rel, lrel, scale) \
1834
0
  rl78_offset_for_reloc (abfd, rel + 1, symtab_hdr, shndx_buf, intsyms, \
1835
0
       lrel, abfd, sec, link_info, scale)
1836
1837
static bfd_vma
1838
rl78_offset_for_reloc (bfd *      abfd,
1839
           Elf_Internal_Rela *  rel,
1840
           Elf_Internal_Shdr *  symtab_hdr,
1841
           bfd_byte *   shndx_buf ATTRIBUTE_UNUSED,
1842
           Elf_Internal_Sym * intsyms,
1843
           Elf_Internal_Rela ** lrel,
1844
           bfd *      input_bfd,
1845
           asection *   input_section,
1846
           struct bfd_link_info * info,
1847
           int *      scale)
1848
0
{
1849
0
  bfd_vma symval;
1850
1851
0
  *scale = 1;
1852
1853
  /* REL is the first of 1..N relocations.  We compute the symbol
1854
     value for each relocation, then combine them if needed.  LREL
1855
     gets a pointer to the last relocation used.  */
1856
0
  while (1)
1857
0
    {
1858
0
      unsigned long r_type;
1859
1860
      /* Get the value of the symbol referred to by the reloc.  */
1861
0
      if (ELF32_R_SYM (rel->r_info) < symtab_hdr->sh_info)
1862
0
  {
1863
    /* A local symbol.  */
1864
0
    Elf_Internal_Sym *isym;
1865
0
    asection *ssec;
1866
1867
0
    isym = intsyms + ELF32_R_SYM (rel->r_info);
1868
1869
0
    if (isym->st_shndx == SHN_UNDEF)
1870
0
      ssec = bfd_und_section_ptr;
1871
0
    else if (isym->st_shndx == SHN_ABS)
1872
0
      ssec = bfd_abs_section_ptr;
1873
0
    else if (isym->st_shndx == SHN_COMMON)
1874
0
      ssec = bfd_com_section_ptr;
1875
0
    else
1876
0
      ssec = bfd_section_from_elf_index (abfd,
1877
0
                 isym->st_shndx);
1878
1879
    /* Initial symbol value.  */
1880
0
    symval = isym->st_value;
1881
1882
    /* GAS may have made this symbol relative to a section, in
1883
       which case, we have to add the addend to find the
1884
       symbol.  */
1885
0
    if (ELF_ST_TYPE (isym->st_info) == STT_SECTION)
1886
0
      symval += rel->r_addend;
1887
1888
0
    if (ssec)
1889
0
      {
1890
0
        if ((ssec->flags & SEC_MERGE)
1891
0
      && ssec->sec_info_type == SEC_INFO_TYPE_MERGE)
1892
0
    symval = _bfd_merged_section_offset (abfd, & ssec,
1893
0
                 elf_section_data (ssec)->sec_info,
1894
0
                 symval);
1895
0
      }
1896
1897
    /* Now make the offset relative to where the linker is putting it.  */
1898
0
    if (ssec)
1899
0
      symval +=
1900
0
        ssec->output_section->vma + ssec->output_offset;
1901
1902
0
    symval += rel->r_addend;
1903
0
  }
1904
0
      else
1905
0
  {
1906
0
    unsigned long indx;
1907
0
    struct elf_link_hash_entry * h;
1908
1909
    /* An external symbol.  */
1910
0
    indx = ELF32_R_SYM (rel->r_info) - symtab_hdr->sh_info;
1911
0
    h = elf_sym_hashes (abfd)[indx];
1912
0
    BFD_ASSERT (h != NULL);
1913
1914
0
    if (h->root.type != bfd_link_hash_defined
1915
0
        && h->root.type != bfd_link_hash_defweak)
1916
0
      {
1917
        /* This appears to be a reference to an undefined
1918
     symbol.  Just ignore it--it will be caught by the
1919
     regular reloc processing.  */
1920
0
        if (lrel)
1921
0
    *lrel = rel;
1922
0
        return 0;
1923
0
      }
1924
1925
0
    symval = (h->root.u.def.value
1926
0
        + h->root.u.def.section->output_section->vma
1927
0
        + h->root.u.def.section->output_offset);
1928
1929
0
    symval += rel->r_addend;
1930
0
  }
1931
1932
0
      r_type = ELF32_R_TYPE (rel->r_info);
1933
0
      switch (r_type)
1934
0
  {
1935
0
  case R_RL78_SYM:
1936
0
    (void) rl78_compute_complex_reloc (r_type, symval, input_section,
1937
0
               NULL, NULL);
1938
0
    break;
1939
1940
0
  case R_RL78_OPromtop:
1941
0
    symval = get_romstart (info, input_bfd, input_section, rel->r_offset);
1942
0
    (void) rl78_compute_complex_reloc (r_type, symval, input_section,
1943
0
               NULL, NULL);
1944
0
    break;
1945
1946
0
  case R_RL78_OPramtop:
1947
0
    symval = get_ramstart (info, input_bfd, input_section, rel->r_offset);
1948
0
    (void) rl78_compute_complex_reloc (r_type, symval, input_section,
1949
0
               NULL, NULL);
1950
0
    break;
1951
1952
0
  case R_RL78_OPneg:
1953
0
  case R_RL78_OPadd:
1954
0
  case R_RL78_OPsub:
1955
0
  case R_RL78_OPmul:
1956
0
  case R_RL78_OPdiv:
1957
0
  case R_RL78_OPshla:
1958
0
  case R_RL78_OPshra:
1959
0
  case R_RL78_OPsctsize:
1960
0
  case R_RL78_OPscttop:
1961
0
  case R_RL78_OPand:
1962
0
  case R_RL78_OPor:
1963
0
  case R_RL78_OPxor:
1964
0
  case R_RL78_OPnot:
1965
0
  case R_RL78_OPmod:
1966
0
    (void) rl78_compute_complex_reloc (r_type, 0, input_section,
1967
0
               NULL, NULL);
1968
0
    break;
1969
1970
0
  case R_RL78_DIR16UL:
1971
0
  case R_RL78_DIR8UL:
1972
0
  case R_RL78_ABS16UL:
1973
0
  case R_RL78_ABS8UL:
1974
0
    *scale = 4;
1975
0
    goto reloc_computes_value;
1976
1977
0
  case R_RL78_DIR16UW:
1978
0
  case R_RL78_DIR8UW:
1979
0
  case R_RL78_ABS16UW:
1980
0
  case R_RL78_ABS8UW:
1981
0
    *scale = 2;
1982
0
    goto reloc_computes_value;
1983
1984
0
  default:
1985
0
  reloc_computes_value:
1986
0
    symval = rl78_compute_complex_reloc (r_type, symval, input_section,
1987
0
                 NULL, NULL);
1988
    /* Fall through.  */
1989
0
  case R_RL78_DIR32:
1990
0
  case R_RL78_DIR24S:
1991
0
  case R_RL78_DIR16:
1992
0
  case R_RL78_DIR16U:
1993
0
  case R_RL78_DIR16S:
1994
0
  case R_RL78_DIR24S_PCREL:
1995
0
  case R_RL78_DIR16S_PCREL:
1996
0
  case R_RL78_DIR8S_PCREL:
1997
0
    if (lrel)
1998
0
      *lrel = rel;
1999
0
    return symval;
2000
0
  }
2001
2002
0
      rel ++;
2003
0
    }
2004
0
}
2005
2006
const struct {
2007
  int prefix;   /* or -1 for "no prefix" */
2008
  int insn;   /* or -1 for "end of list" */
2009
  int insn_for_saddr; /* or -1 for "no alternative" */
2010
  int insn_for_sfr; /* or -1 for "no alternative" */
2011
} relax_addr16[] = {
2012
  { -1, 0x02, 0x06, -1 }, /* ADDW AX, !addr16 */
2013
  { -1, 0x22, 0x26, -1 }, /* SUBW AX, !addr16 */
2014
  { -1, 0x42, 0x46, -1 }, /* CMPW AX, !addr16 */
2015
  { -1, 0x40, 0x4a, -1 }, /* CMP  !addr16, #byte */
2016
2017
  { -1, 0x0f, 0x0b, -1 }, /* ADD  A, !addr16 */
2018
  { -1, 0x1f, 0x1b, -1 }, /* ADDC A, !addr16 */
2019
  { -1, 0x2f, 0x2b, -1 }, /* SUB  A, !addr16 */
2020
  { -1, 0x3f, 0x3b, -1 }, /* SUBC A, !addr16 */
2021
  { -1, 0x4f, 0x4b, -1 }, /* CMP  A, !addr16 */
2022
  { -1, 0x5f, 0x5b, -1 }, /* AND  A, !addr16 */
2023
  { -1, 0x6f, 0x6b, -1 }, /* OR A, !addr16 */
2024
  { -1, 0x7f, 0x7b, -1 }, /* XOR  A, !addr16 */
2025
2026
  { -1, 0x8f, 0x8d, 0x8e }, /* MOV  A, !addr16 */
2027
  { -1, 0x9f, 0x9d, 0x9e }, /* MOV  !addr16, A */
2028
  { -1, 0xaf, 0xad, 0xae }, /* MOVW AX, !addr16 */
2029
  { -1, 0xbf, 0xbd, 0xbe }, /* MOVW !addr16, AX */
2030
  { -1, 0xcf, 0xcd, 0xce }, /* MOVW !addr16, #word */
2031
2032
  { -1, 0xa0, 0xa4, -1 }, /* INC  !addr16 */
2033
  { -1, 0xa2, 0xa6, -1 }, /* INCW !addr16 */
2034
  { -1, 0xb0, 0xb4, -1 }, /* DEC  !addr16 */
2035
  { -1, 0xb2, 0xb6, -1 }, /* DECW !addr16 */
2036
2037
  { -1, 0xd5, 0xd4, -1 }, /* CMP0 !addr16 */
2038
  { -1, 0xe5, 0xe4, -1 }, /* ONEB !addr16 */
2039
  { -1, 0xf5, 0xf4, -1 }, /* CLRB !addr16 */
2040
2041
  { -1, 0xd9, 0xd8, -1 }, /* MOV  X, !addr16 */
2042
  { -1, 0xe9, 0xe8, -1 }, /* MOV  B, !addr16 */
2043
  { -1, 0xf9, 0xf8, -1 }, /* MOV  C, !addr16 */
2044
  { -1, 0xdb, 0xda, -1 }, /* MOVW BC, !addr16 */
2045
  { -1, 0xeb, 0xea, -1 }, /* MOVW DE, !addr16 */
2046
  { -1, 0xfb, 0xfa, -1 }, /* MOVW HL, !addr16 */
2047
2048
  { 0x61, 0xaa, 0xa8, -1 }, /* XCH  A, !addr16 */
2049
2050
  { 0x71, 0x00, 0x02, 0x0a }, /* SET1 !addr16.0 */
2051
  { 0x71, 0x10, 0x12, 0x1a }, /* SET1 !addr16.0 */
2052
  { 0x71, 0x20, 0x22, 0x2a }, /* SET1 !addr16.0 */
2053
  { 0x71, 0x30, 0x32, 0x3a }, /* SET1 !addr16.0 */
2054
  { 0x71, 0x40, 0x42, 0x4a }, /* SET1 !addr16.0 */
2055
  { 0x71, 0x50, 0x52, 0x5a }, /* SET1 !addr16.0 */
2056
  { 0x71, 0x60, 0x62, 0x6a }, /* SET1 !addr16.0 */
2057
  { 0x71, 0x70, 0x72, 0x7a }, /* SET1 !addr16.0 */
2058
2059
  { 0x71, 0x08, 0x03, 0x0b }, /* CLR1 !addr16.0 */
2060
  { 0x71, 0x18, 0x13, 0x1b }, /* CLR1 !addr16.0 */
2061
  { 0x71, 0x28, 0x23, 0x2b }, /* CLR1 !addr16.0 */
2062
  { 0x71, 0x38, 0x33, 0x3b }, /* CLR1 !addr16.0 */
2063
  { 0x71, 0x48, 0x43, 0x4b }, /* CLR1 !addr16.0 */
2064
  { 0x71, 0x58, 0x53, 0x5b }, /* CLR1 !addr16.0 */
2065
  { 0x71, 0x68, 0x63, 0x6b }, /* CLR1 !addr16.0 */
2066
  { 0x71, 0x78, 0x73, 0x7b }, /* CLR1 !addr16.0 */
2067
2068
  { -1, -1, -1, -1 }
2069
};
2070
2071
/* Relax one section.  */
2072
2073
static bool
2074
rl78_elf_relax_section (bfd *abfd,
2075
      asection *sec,
2076
      struct bfd_link_info *link_info,
2077
      bool *again)
2078
0
{
2079
0
  Elf_Internal_Shdr * symtab_hdr;
2080
0
  Elf_Internal_Shdr * shndx_hdr;
2081
0
  Elf_Internal_Rela * internal_relocs;
2082
0
  Elf_Internal_Rela * free_relocs = NULL;
2083
0
  Elf_Internal_Rela * irel;
2084
0
  Elf_Internal_Rela * srel;
2085
0
  Elf_Internal_Rela * irelend;
2086
0
  Elf_Internal_Rela * next_alignment;
2087
0
  bfd_byte *        contents = NULL;
2088
0
  bfd_byte *        free_contents = NULL;
2089
0
  Elf_Internal_Sym *  intsyms = NULL;
2090
0
  Elf_Internal_Sym *  free_intsyms = NULL;
2091
0
  bfd_byte *        shndx_buf = NULL;
2092
0
  bfd_vma pc;
2093
0
  bfd_vma symval ATTRIBUTE_UNUSED = 0;
2094
0
  int pcrel ATTRIBUTE_UNUSED = 0;
2095
0
  int code ATTRIBUTE_UNUSED = 0;
2096
0
  int section_alignment_glue;
2097
0
  int scale;
2098
2099
0
  if (abfd == elf_hash_table (link_info)->dynobj
2100
0
      && strcmp (sec->name, ".plt") == 0)
2101
0
    return rl78_elf_relax_plt_section (abfd, sec, link_info, again);
2102
2103
  /* Assume nothing changes.  */
2104
0
  *again = false;
2105
2106
  /* We don't have to do anything for a relocatable link, if
2107
     this section does not have relocs, or if this is not a
2108
     code section.  */
2109
0
  if (bfd_link_relocatable (link_info)
2110
0
      || sec->reloc_count == 0
2111
0
      || (sec->flags & SEC_RELOC) == 0
2112
0
      || (sec->flags & SEC_HAS_CONTENTS) == 0
2113
0
      || (sec->flags & SEC_CODE) == 0)
2114
0
    return true;
2115
2116
0
  symtab_hdr = & elf_symtab_hdr (abfd);
2117
0
  if (elf_symtab_shndx_list (abfd))
2118
0
    shndx_hdr = & elf_symtab_shndx_list (abfd)->hdr;
2119
0
  else
2120
0
    shndx_hdr = NULL;
2121
2122
  /* Get the section contents.  */
2123
0
  if (elf_section_data (sec)->this_hdr.contents != NULL)
2124
0
    contents = elf_section_data (sec)->this_hdr.contents;
2125
  /* Go get them off disk.  */
2126
0
  else
2127
0
    {
2128
0
      if (! bfd_malloc_and_get_section (abfd, sec, &contents))
2129
0
  goto error_return;
2130
0
      elf_section_data (sec)->this_hdr.contents = contents;
2131
0
    }
2132
2133
  /* Read this BFD's symbols.  */
2134
  /* Get cached copy if it exists.  */
2135
0
  if (symtab_hdr->contents != NULL)
2136
0
    intsyms = (Elf_Internal_Sym *) symtab_hdr->contents;
2137
0
  else
2138
0
    {
2139
0
      intsyms = bfd_elf_get_elf_syms (abfd, symtab_hdr, symtab_hdr->sh_info, 0, NULL, NULL, NULL);
2140
0
      symtab_hdr->contents = (bfd_byte *) intsyms;
2141
0
    }
2142
2143
0
  if (shndx_hdr && shndx_hdr->sh_size != 0)
2144
0
    {
2145
0
      size_t amt;
2146
2147
0
      if (_bfd_mul_overflow (symtab_hdr->sh_info,
2148
0
           sizeof (Elf_External_Sym_Shndx), &amt))
2149
0
  {
2150
0
    bfd_set_error (bfd_error_no_memory);
2151
0
    goto error_return;
2152
0
  }
2153
0
      if (bfd_seek (abfd, shndx_hdr->sh_offset, SEEK_SET) != 0)
2154
0
  goto error_return;
2155
0
      shndx_buf = _bfd_malloc_and_read (abfd, amt, amt);
2156
0
      if (shndx_buf == NULL)
2157
0
  goto error_return;
2158
0
      shndx_hdr->contents = shndx_buf;
2159
0
    }
2160
2161
  /* Get a copy of the native relocations.  */
2162
0
  internal_relocs = (_bfd_elf_link_read_relocs
2163
0
         (abfd, sec, NULL, (Elf_Internal_Rela *) NULL,
2164
0
          link_info->keep_memory));
2165
0
  if (internal_relocs == NULL)
2166
0
    goto error_return;
2167
0
  if (! link_info->keep_memory)
2168
0
    free_relocs = internal_relocs;
2169
2170
  /* The RL_ relocs must be just before the operand relocs they go
2171
     with, so we must sort them to guarantee this.  We use bubblesort
2172
     instead of qsort so we can guarantee that relocs with the same
2173
     address remain in the same relative order.  */
2174
0
  reloc_bubblesort (internal_relocs, sec->reloc_count);
2175
2176
  /* Walk through them looking for relaxing opportunities.  */
2177
0
  irelend = internal_relocs + sec->reloc_count;
2178
2179
2180
  /* This will either be NULL or a pointer to the next alignment
2181
     relocation.  */
2182
0
  next_alignment = internal_relocs;
2183
2184
  /* We calculate worst case shrinkage caused by alignment directives.
2185
     No fool-proof, but better than either ignoring the problem or
2186
     doing heavy duty analysis of all the alignment markers in all
2187
     input sections.  */
2188
0
  section_alignment_glue = 0;
2189
0
  for (irel = internal_relocs; irel < irelend; irel++)
2190
0
      if (ELF32_R_TYPE (irel->r_info) == R_RL78_RH_RELAX
2191
0
    && irel->r_addend & RL78_RELAXA_ALIGN)
2192
0
  {
2193
0
    int this_glue = 1 << (irel->r_addend & RL78_RELAXA_ANUM);
2194
2195
0
    if (section_alignment_glue < this_glue)
2196
0
      section_alignment_glue = this_glue;
2197
0
  }
2198
  /* Worst case is all 0..N alignments, in order, causing 2*N-1 byte
2199
     shrinkage.  */
2200
0
  section_alignment_glue *= 2;
2201
2202
0
  for (irel = internal_relocs; irel < irelend; irel++)
2203
0
    {
2204
0
      unsigned char *insn;
2205
0
      int nrelocs;
2206
2207
      /* The insns we care about are all marked with one of these.  */
2208
0
      if (ELF32_R_TYPE (irel->r_info) != R_RL78_RH_RELAX)
2209
0
  continue;
2210
2211
0
      if (irel->r_addend & RL78_RELAXA_ALIGN
2212
0
    || next_alignment == internal_relocs)
2213
0
  {
2214
    /* When we delete bytes, we need to maintain all the alignments
2215
       indicated.  In addition, we need to be careful about relaxing
2216
       jumps across alignment boundaries - these displacements
2217
       *grow* when we delete bytes.  For now, don't shrink
2218
       displacements across an alignment boundary, just in case.
2219
       Note that this only affects relocations to the same
2220
       section.  */
2221
0
    next_alignment += 2;
2222
0
    while (next_alignment < irelend
2223
0
     && (ELF32_R_TYPE (next_alignment->r_info) != R_RL78_RH_RELAX
2224
0
         || !(next_alignment->r_addend & RL78_RELAXA_ELIGN)))
2225
0
      next_alignment ++;
2226
0
    if (next_alignment >= irelend || next_alignment->r_offset == 0)
2227
0
      next_alignment = NULL;
2228
0
  }
2229
2230
      /* When we hit alignment markers, see if we've shrunk enough
2231
   before them to reduce the gap without violating the alignment
2232
   requirements.  */
2233
0
      if (irel->r_addend & RL78_RELAXA_ALIGN)
2234
0
  {
2235
    /* At this point, the next relocation *should* be the ELIGN
2236
       end marker.  */
2237
0
    Elf_Internal_Rela *erel = irel + 1;
2238
0
    unsigned int alignment, nbytes;
2239
2240
0
    if (ELF32_R_TYPE (erel->r_info) != R_RL78_RH_RELAX)
2241
0
      continue;
2242
0
    if (!(erel->r_addend & RL78_RELAXA_ELIGN))
2243
0
      continue;
2244
2245
0
    alignment = 1 << (irel->r_addend & RL78_RELAXA_ANUM);
2246
2247
0
    if (erel->r_offset - irel->r_offset < alignment)
2248
0
      continue;
2249
2250
0
    nbytes = erel->r_offset - irel->r_offset;
2251
0
    nbytes /= alignment;
2252
0
    nbytes *= alignment;
2253
2254
0
    elf32_rl78_relax_delete_bytes (abfd, sec, erel->r_offset - nbytes, nbytes,
2255
0
           next_alignment, erel->r_offset == sec->size);
2256
0
    *again = true;
2257
2258
0
    continue;
2259
0
  }
2260
2261
0
      if (irel->r_addend & RL78_RELAXA_ELIGN)
2262
0
    continue;
2263
2264
0
      insn = contents + irel->r_offset;
2265
2266
0
      nrelocs = irel->r_addend & RL78_RELAXA_RNUM;
2267
2268
      /* At this point, we have an insn that is a candidate for linker
2269
   relaxation.  There are NRELOCS relocs following that may be
2270
   relaxed, although each reloc may be made of more than one
2271
   reloc entry (such as gp-rel symbols).  */
2272
2273
      /* Get the value of the symbol referred to by the reloc.  Just
2274
   in case this is the last reloc in the list, use the RL's
2275
   addend to choose between this reloc (no addend) or the next
2276
   (yes addend, which means at least one following reloc).  */
2277
2278
      /* srel points to the "current" reloction for this insn -
2279
   actually the last reloc for a given operand, which is the one
2280
   we need to update.  We check the relaxations in the same
2281
   order that the relocations happen, so we'll just push it
2282
   along as we go.  */
2283
0
      srel = irel;
2284
2285
0
      pc = sec->output_section->vma + sec->output_offset
2286
0
  + srel->r_offset;
2287
2288
0
#define GET_RELOC         \
2289
0
      BFD_ASSERT (nrelocs > 0);       \
2290
0
      symval = OFFSET_FOR_RELOC (srel, &srel, &scale); \
2291
0
      pcrel = symval - pc + srel->r_addend;   \
2292
0
      nrelocs --;
2293
2294
0
#define SNIPNR(offset, nbytes) \
2295
0
  elf32_rl78_relax_delete_bytes (abfd, sec, (insn - contents) + offset, nbytes, next_alignment, 0);
2296
2297
0
#define SNIP(offset, nbytes, newtype)         \
2298
0
  SNIPNR (offset, nbytes);          \
2299
0
  srel->r_info = ELF32_R_INFO (ELF32_R_SYM (srel->r_info), newtype)
2300
2301
      /* The order of these bit tests must match the order that the
2302
   relocs appear in.  Since we sorted those by offset, we can
2303
   predict them.  */
2304
2305
      /*----------------------------------------------------------------------*/
2306
      /* EF ad    BR $rel8  pcrel
2307
   ED al ah BR !abs16 abs
2308
   EE al ah BR $!rel16  pcrel
2309
   EC al ah as  BR !!abs20  abs
2310
2311
   FD al ah CALL !abs16 abs
2312
   FE al ah CALL $!rel16  pcrel
2313
   FC al ah as  CALL !!abs20  abs
2314
2315
   DC ad    BC  $rel8
2316
   DE ad    BNC $rel8
2317
   DD ad    BZ  $rel8
2318
   DF ad    BNZ $rel8
2319
   61 C3 ad BH  $rel8
2320
   61 D3 ad BNH $rel8
2321
   61 C8 EF ad  SKC  ; BR $rel8
2322
   61 D8 EF ad  SKNC ; BR $rel8
2323
   61 E8 EF ad  SKZ  ; BR $rel8
2324
   61 F8 EF ad  SKNZ ; BR $rel8
2325
   61 E3 EF ad  SKH  ; BR $rel8
2326
   61 F3 EF ad  SKNH ; BR $rel8
2327
       */
2328
2329
0
      if ((irel->r_addend & RL78_RELAXA_MASK) == RL78_RELAXA_BRA)
2330
0
  {
2331
    /* SKIP opcodes that skip non-branches will have a relax tag
2332
       but no corresponding symbol to relax against; we just
2333
       skip those.  */
2334
0
    if (irel->r_addend & RL78_RELAXA_RNUM)
2335
0
      {
2336
0
        GET_RELOC;
2337
0
      }
2338
2339
0
    switch (insn[0])
2340
0
      {
2341
0
      case 0xdc: /* BC */
2342
0
      case 0xdd: /* BZ */
2343
0
      case 0xde: /* BNC */
2344
0
      case 0xdf: /* BNZ */
2345
0
        if (insn[1] == 0x03 && insn[2] == 0xee /* BR */
2346
0
      && (srel->r_offset - irel->r_offset) > 1) /* a B<c> without its own reloc */
2347
0
    {
2348
      /* This is a "long" conditional as generated by gas:
2349
         DC 03 EE ad.dr  */
2350
0
      if (pcrel < 127
2351
0
          && pcrel > -127)
2352
0
        {
2353
0
          insn[0] ^= 0x02; /* invert conditional */
2354
0
          SNIPNR (4, 1);
2355
0
          SNIP (1, 2, R_RL78_DIR8S_PCREL);
2356
0
          insn[1] = pcrel;
2357
0
          *again = true;
2358
0
        }
2359
0
    }
2360
0
        break;
2361
2362
0
      case 0xec: /* BR !!abs20 */
2363
2364
0
        if (pcrel < 127
2365
0
      && pcrel > -127)
2366
0
    {
2367
0
      insn[0] = 0xef;
2368
0
      insn[1] = pcrel;
2369
0
      SNIP (2, 2, R_RL78_DIR8S_PCREL);
2370
0
      *again = true;
2371
0
    }
2372
0
        else if (symval < 65536)
2373
0
    {
2374
0
      insn[0] = 0xed;
2375
0
      insn[1] = symval & 0xff;
2376
0
      insn[2] = symval >> 8;
2377
0
      SNIP (2, 1, R_RL78_DIR16U);
2378
0
      *again = true;
2379
0
    }
2380
0
        else if (pcrel < 32767
2381
0
           && pcrel > -32767)
2382
0
    {
2383
0
      insn[0] = 0xee;
2384
0
      insn[1] = pcrel & 0xff;
2385
0
      insn[2] = pcrel >> 8;
2386
0
      SNIP (2, 1, R_RL78_DIR16S_PCREL);
2387
0
      *again = true;
2388
0
    }
2389
0
        break;
2390
2391
0
      case 0xee: /* BR $!pcrel16 */
2392
0
      case 0xed: /* BR $!abs16 */
2393
0
        if (pcrel < 127
2394
0
      && pcrel > -127)
2395
0
    {
2396
0
      insn[0] = 0xef;
2397
0
      insn[1] = pcrel;
2398
0
      SNIP (2, 1, R_RL78_DIR8S_PCREL);
2399
0
      *again = true;
2400
0
    }
2401
0
        break;
2402
2403
0
      case 0xfc: /* CALL !!abs20 */
2404
0
        if (symval < 65536)
2405
0
    {
2406
0
      insn[0] = 0xfd;
2407
0
      insn[1] = symval & 0xff;
2408
0
      insn[2] = symval >> 8;
2409
0
      SNIP (2, 1, R_RL78_DIR16U);
2410
0
      *again = true;
2411
0
    }
2412
0
        else if (pcrel < 32767
2413
0
           && pcrel > -32767)
2414
0
    {
2415
0
      insn[0] = 0xfe;
2416
0
      insn[1] = pcrel & 0xff;
2417
0
      insn[2] = pcrel >> 8;
2418
0
      SNIP (2, 1, R_RL78_DIR16S_PCREL);
2419
0
      *again = true;
2420
0
    }
2421
0
        break;
2422
2423
0
      case 0x61: /* PREFIX */
2424
        /* For SKIP/BR, we change the BR opcode and delete the
2425
     SKIP.  That way, we don't have to find and change the
2426
     relocation for the BR.  */
2427
        /* Note that, for the case where we're skipping some
2428
     other insn, we have no "other" reloc but that's safe
2429
     here anyway. */
2430
0
        switch (insn[1])
2431
0
    {
2432
0
    case 0xd3: /* BNH */
2433
0
    case 0xc3: /* BH */
2434
0
      if (insn[2] == 0x03 && insn[3] == 0xee
2435
0
          && (srel->r_offset - irel->r_offset) > 2) /* a B<c> without its own reloc */
2436
0
        {
2437
          /* Another long branch by gas:
2438
       61 D3 03 EE ad.dr  */
2439
0
          if (pcrel < 127
2440
0
        && pcrel > -127)
2441
0
      {
2442
0
        insn[1] ^= 0x10; /* invert conditional */
2443
0
        SNIPNR (5, 1);
2444
0
        SNIP (2, 2, R_RL78_DIR8S_PCREL);
2445
0
        insn[2] = pcrel;
2446
0
        *again = true;
2447
0
      }
2448
0
        }
2449
0
      break;
2450
2451
0
    case 0xc8: /* SKC */
2452
0
      if (insn[2] == 0xef)
2453
0
        {
2454
0
          insn[2] = 0xde; /* BNC */
2455
0
          SNIPNR (0, 2);
2456
0
        }
2457
0
      break;
2458
2459
0
    case 0xd8: /* SKNC */
2460
0
      if (insn[2] == 0xef)
2461
0
        {
2462
0
          insn[2] = 0xdc; /* BC */
2463
0
          SNIPNR (0, 2);
2464
0
        }
2465
0
      break;
2466
2467
0
    case 0xe8: /* SKZ */
2468
0
      if (insn[2] == 0xef)
2469
0
        {
2470
0
          insn[2] = 0xdf; /* BNZ */
2471
0
          SNIPNR (0, 2);
2472
0
        }
2473
0
      break;
2474
2475
0
    case 0xf8: /* SKNZ */
2476
0
      if (insn[2] == 0xef)
2477
0
        {
2478
0
          insn[2] = 0xdd; /* BZ */
2479
0
          SNIPNR (0, 2);
2480
0
        }
2481
0
      break;
2482
2483
0
    case 0xe3: /* SKH */
2484
0
      if (insn[2] == 0xef)
2485
0
        {
2486
0
          insn[2] = 0xd3; /* BNH */
2487
0
          SNIPNR (1, 1); /* we reuse the 0x61 prefix from the SKH */
2488
0
        }
2489
0
      break;
2490
2491
0
    case 0xf3: /* SKNH */
2492
0
      if (insn[2] == 0xef)
2493
0
        {
2494
0
          insn[2] = 0xc3; /* BH */
2495
0
          SNIPNR (1, 1); /* we reuse the 0x61 prefix from the SKH */
2496
0
        }
2497
0
      break;
2498
0
    }
2499
0
        break;
2500
0
      }
2501
0
  }
2502
2503
0
      if ((irel->r_addend &  RL78_RELAXA_MASK) == RL78_RELAXA_ADDR16
2504
0
    && nrelocs > 0)
2505
0
  {
2506
    /*----------------------------------------------------------------------*/
2507
    /* Some insns have both a 16-bit address operand and an 8-bit
2508
       variant if the address is within a special range:
2509
2510
       Address    16-bit operand  SADDR range SFR range
2511
       FFF00-FFFFF  0xff00-0xffff 0x00-0xff
2512
       FFE20-FFF1F  0xfe20-0xff1f     0x00-0xff
2513
2514
       The RELAX_ADDR16[] array has the insn encodings for the
2515
       16-bit operand version, as well as the SFR and SADDR
2516
       variants.  We only need to replace the encodings and
2517
       adjust the operand.
2518
2519
       Note: we intentionally do not attempt to decode and skip
2520
       any ES: prefix, as adding ES: means the addr16 (likely)
2521
       no longer points to saddr/sfr space.
2522
    */
2523
2524
0
    int is_sfr;
2525
0
    int is_saddr;
2526
0
    int idx;
2527
0
    int poff;
2528
2529
0
    GET_RELOC;
2530
2531
0
    if (0xffe20 <= symval && symval <= 0xfffff)
2532
0
      {
2533
2534
0
        is_saddr = (0xffe20 <= symval && symval <= 0xfff1f);
2535
0
        is_sfr   = (0xfff00 <= symval && symval <= 0xfffff);
2536
2537
0
        for (idx = 0; relax_addr16[idx].insn != -1; idx ++)
2538
0
    {
2539
0
      if (relax_addr16[idx].prefix != -1
2540
0
          && insn[0] == relax_addr16[idx].prefix
2541
0
          && insn[1] == relax_addr16[idx].insn)
2542
0
        {
2543
0
          poff = 1;
2544
0
        }
2545
0
      else if (relax_addr16[idx].prefix == -1
2546
0
         && insn[0] == relax_addr16[idx].insn)
2547
0
        {
2548
0
          poff = 0;
2549
0
        }
2550
0
      else
2551
0
        continue;
2552
2553
      /* We have a matched insn, and poff is 0 or 1 depending
2554
         on the base pattern size.  */
2555
2556
0
      if (is_sfr && relax_addr16[idx].insn_for_sfr != -1)
2557
0
        {
2558
0
          insn[poff] = relax_addr16[idx].insn_for_sfr;
2559
0
          SNIP (poff+2, 1, R_RL78_RH_SFR);
2560
0
        }
2561
2562
0
      else if  (is_saddr && relax_addr16[idx].insn_for_saddr != -1)
2563
0
        {
2564
0
          insn[poff] = relax_addr16[idx].insn_for_saddr;
2565
0
          SNIP (poff+2, 1, R_RL78_RH_SADDR);
2566
0
        }
2567
0
    }
2568
0
      }
2569
0
  }
2570
      /*----------------------------------------------------------------------*/
2571
0
    }
2572
2573
0
  return true;
2574
2575
0
 error_return:
2576
0
  free (free_relocs);
2577
0
  free (free_contents);
2578
2579
0
  if (shndx_buf != NULL)
2580
0
    {
2581
0
      shndx_hdr->contents = NULL;
2582
0
      free (shndx_buf);
2583
0
    }
2584
2585
0
  free (free_intsyms);
2586
2587
0
  return true;
2588
0
}
2589
2590

2591
2592
#define ELF_ARCH    bfd_arch_rl78
2593
#define ELF_MACHINE_CODE  EM_RL78
2594
#define ELF_MAXPAGESIZE   0x1000
2595
2596
#define TARGET_LITTLE_SYM rl78_elf32_vec
2597
#define TARGET_LITTLE_NAME  "elf32-rl78"
2598
2599
#define elf_info_to_howto_rel     NULL
2600
#define elf_info_to_howto     rl78_info_to_howto_rela
2601
#define elf_backend_object_p      rl78_elf_object_p
2602
#define elf_backend_relocate_section    rl78_elf_relocate_section
2603
#define elf_symbol_leading_char     ('_')
2604
#define elf_backend_can_gc_sections   1
2605
2606
#define bfd_elf32_bfd_reloc_type_lookup   rl78_reloc_type_lookup
2607
#define bfd_elf32_bfd_reloc_name_lookup   rl78_reloc_name_lookup
2608
#define bfd_elf32_bfd_set_private_flags   rl78_elf_set_private_flags
2609
#define bfd_elf32_bfd_merge_private_bfd_data  rl78_elf_merge_private_bfd_data
2610
#define bfd_elf32_bfd_print_private_bfd_data  rl78_elf_print_private_bfd_data
2611
2612
#define bfd_elf32_bfd_relax_section   rl78_elf_relax_section
2613
#define elf_backend_check_relocs    rl78_elf_check_relocs
2614
#define elf_backend_early_size_sections \
2615
  rl78_elf_early_size_sections
2616
#define elf_backend_finish_dynamic_sections \
2617
  rl78_elf_finish_dynamic_sections
2618
2619
#include "elf32-target.h"