This fixes the processing of BFD_RELOC_RL78_DIFF fixups when the size is less
[external/binutils.git] / gas / config / tc-rl78.c
1 /* tc-rl78.c -- Assembler for the Renesas RL78
2    Copyright (C) 2011-2014 Free Software Foundation, Inc.
3
4    This file is part of GAS, the GNU Assembler.
5
6    GAS 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, or (at your option)
9    any later version.
10
11    GAS 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 GAS; see the file COPYING.  If not, write to the Free
18    Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
19    02110-1301, USA.  */
20
21 #include "as.h"
22 #include "struc-symbol.h"
23 #include "safe-ctype.h"
24 #include "dwarf2dbg.h"
25 #include "libbfd.h"
26 #include "elf/common.h"
27 #include "elf/rl78.h"
28 #include "rl78-defs.h"
29 #include "filenames.h"
30 #include "listing.h"
31 #include "sb.h"
32 #include "macro.h"
33
34 const char comment_chars[]        = ";";
35 /* Note that input_file.c hand checks for '#' at the beginning of the
36    first line of the input file.  This is because the compiler outputs
37    #NO_APP at the beginning of its output.  */
38 const char line_comment_chars[]   = "#";
39 /* Use something that isn't going to be needed by any expressions or
40    other syntax.  */
41 const char line_separator_chars[] = "@";
42
43 const char EXP_CHARS[]            = "eE";
44 const char FLT_CHARS[]            = "dD";
45
46 /* ELF flags to set in the output file header.  */
47 static int elf_flags = 0;
48
49 /*------------------------------------------------------------------*/
50
51 char * rl78_lex_start;
52 char * rl78_lex_end;
53
54 typedef struct rl78_bytesT
55 {
56   char prefix[1];
57   int n_prefix;
58   char base[4];
59   int n_base;
60   char ops[8];
61   int n_ops;
62   struct
63   {
64     expressionS  exp;
65     char         offset;
66     char         nbits;
67     char         type; /* RL78REL_*.  */
68     int          reloc;
69     fixS *       fixP;
70   } fixups[2];
71   int n_fixups;
72   struct
73   {
74     char type;
75     char field_pos;
76     char val_ofs;
77   } relax[2];
78   int n_relax;
79   int link_relax;
80   fixS *link_relax_fixP;
81   char times_grown;
82   char times_shrank;
83 } rl78_bytesT;
84
85 static rl78_bytesT rl78_bytes;
86
87 void
88 rl78_relax (int type, int pos)
89 {
90   rl78_bytes.relax[rl78_bytes.n_relax].type = type;
91   rl78_bytes.relax[rl78_bytes.n_relax].field_pos = pos;
92   rl78_bytes.relax[rl78_bytes.n_relax].val_ofs = rl78_bytes.n_base + rl78_bytes.n_ops;
93   rl78_bytes.n_relax ++;
94 }
95
96 void
97 rl78_linkrelax_addr16 (void)
98 {
99   rl78_bytes.link_relax |= RL78_RELAXA_ADDR16;
100 }
101
102 void
103 rl78_linkrelax_branch (void)
104 {
105   rl78_bytes.link_relax |= RL78_RELAXA_BRA;
106 }
107
108 static void
109 rl78_fixup (expressionS exp, int offsetbits, int nbits, int type)
110 {
111   rl78_bytes.fixups[rl78_bytes.n_fixups].exp = exp;
112   rl78_bytes.fixups[rl78_bytes.n_fixups].offset = offsetbits;
113   rl78_bytes.fixups[rl78_bytes.n_fixups].nbits = nbits;
114   rl78_bytes.fixups[rl78_bytes.n_fixups].type = type;
115   rl78_bytes.fixups[rl78_bytes.n_fixups].reloc = exp.X_md;
116   rl78_bytes.n_fixups ++;
117 }
118
119 #define rl78_field_fixup(exp, offset, nbits, type)      \
120   rl78_fixup (exp, offset + 8 * rl78_bytes.n_prefix), nbits, type)
121
122 #define rl78_op_fixup(exp, offset, nbits, type)         \
123   rl78_fixup (exp, offset + 8 * (rl78_bytes.n_prefix + rl78_bytes.n_base), nbits, type)
124
125 void
126 rl78_prefix (int p)
127 {
128   rl78_bytes.prefix[0] = p;
129   rl78_bytes.n_prefix = 1;
130 }
131
132 int
133 rl78_has_prefix ()
134 {
135   return rl78_bytes.n_prefix;
136 }
137
138 void
139 rl78_base1 (int b1)
140 {
141   rl78_bytes.base[0] = b1;
142   rl78_bytes.n_base = 1;
143 }
144
145 void
146 rl78_base2 (int b1, int b2)
147 {
148   rl78_bytes.base[0] = b1;
149   rl78_bytes.base[1] = b2;
150   rl78_bytes.n_base = 2;
151 }
152
153 void
154 rl78_base3 (int b1, int b2, int b3)
155 {
156   rl78_bytes.base[0] = b1;
157   rl78_bytes.base[1] = b2;
158   rl78_bytes.base[2] = b3;
159   rl78_bytes.n_base = 3;
160 }
161
162 void
163 rl78_base4 (int b1, int b2, int b3, int b4)
164 {
165   rl78_bytes.base[0] = b1;
166   rl78_bytes.base[1] = b2;
167   rl78_bytes.base[2] = b3;
168   rl78_bytes.base[3] = b4;
169   rl78_bytes.n_base = 4;
170 }
171
172 #define F_PRECISION 2
173
174 void
175 rl78_op (expressionS exp, int nbytes, int type)
176 {
177   int v = 0;
178
179   if ((exp.X_op == O_constant || exp.X_op == O_big)
180       && type != RL78REL_PCREL)
181     {
182       if (exp.X_op == O_big && exp.X_add_number <= 0)
183         {
184           LITTLENUM_TYPE w[2];
185           char * ip = rl78_bytes.ops + rl78_bytes.n_ops;
186
187           gen_to_words (w, F_PRECISION, 8);
188           ip[3] = w[0] >> 8;
189           ip[2] = w[0];
190           ip[1] = w[1] >> 8;
191           ip[0] = w[1];
192           rl78_bytes.n_ops += 4;
193         }
194       else
195         {
196           v = exp.X_add_number;
197           while (nbytes)
198             {
199               rl78_bytes.ops[rl78_bytes.n_ops++] =v & 0xff;
200               v >>= 8;
201               nbytes --;
202             }
203         }
204     }
205   else
206     {
207       if (nbytes > 2
208           && exp.X_md == BFD_RELOC_RL78_CODE)
209         exp.X_md = 0;
210
211       if (nbytes == 1
212           && (exp.X_md == BFD_RELOC_RL78_LO16
213               || exp.X_md == BFD_RELOC_RL78_HI16))
214         as_bad (_("16-bit relocation used in 8-bit operand"));
215
216       if (nbytes == 2
217           && exp.X_md == BFD_RELOC_RL78_HI8)
218         as_bad (_("8-bit relocation used in 16-bit operand"));
219
220       rl78_op_fixup (exp, rl78_bytes.n_ops * 8, nbytes * 8, type);
221       memset (rl78_bytes.ops + rl78_bytes.n_ops, 0, nbytes);
222       rl78_bytes.n_ops += nbytes;
223     }
224 }
225
226 /* This gets complicated when the field spans bytes, because fields
227    are numbered from the MSB of the first byte as zero, and bits are
228    stored LSB towards the LSB of the byte.  Thus, a simple four-bit
229    insertion of 12 at position 4 of 0x00 yields: 0x0b.  A three-bit
230    insertion of b'MXL at position 7 is like this:
231
232      - - - -  - - - -   - - - -  - - - -
233                     M   X L               */
234
235 void
236 rl78_field (int val, int pos, int sz)
237 {
238   int valm;
239   int bytep, bitp;
240
241   if (sz > 0)
242     {
243       if (val < 0 || val >= (1 << sz))
244         as_bad (_("Value %d doesn't fit in unsigned %d-bit field"), val, sz);
245     }
246   else
247     {
248       sz = - sz;
249       if (val < -(1 << (sz - 1)) || val >= (1 << (sz - 1)))
250         as_bad (_("Value %d doesn't fit in signed %d-bit field"), val, sz);
251     }
252
253   /* This code points at 'M' in the above example.  */
254   bytep = pos / 8;
255   bitp = pos % 8;
256
257   while (bitp + sz > 8)
258     {
259       int ssz = 8 - bitp;
260       int svalm;
261
262       svalm = val >> (sz - ssz);
263       svalm = svalm & ((1 << ssz) - 1);
264       svalm = svalm << (8 - bitp - ssz);
265       gas_assert (bytep < rl78_bytes.n_base);
266       rl78_bytes.base[bytep] |= svalm;
267
268       bitp = 0;
269       sz -= ssz;
270       bytep ++;
271     }
272   valm = val & ((1 << sz) - 1);
273   valm = valm << (8 - bitp - sz);
274   gas_assert (bytep < rl78_bytes.n_base);
275   rl78_bytes.base[bytep] |= valm;
276 }
277
278 /*------------------------------------------------------------------*/
279
280 enum options
281 {
282   OPTION_RELAX = OPTION_MD_BASE,
283   OPTION_G10,
284   OPTION_32BIT_DOUBLES,
285   OPTION_64BIT_DOUBLES,
286 };
287
288 #define RL78_SHORTOPTS ""
289 const char * md_shortopts = RL78_SHORTOPTS;
290
291 /* Assembler options.  */
292 struct option md_longopts[] =
293 {
294   {"relax", no_argument, NULL, OPTION_RELAX},
295   {"mg10", no_argument, NULL, OPTION_G10},
296   {"m32bit-doubles", no_argument, NULL, OPTION_32BIT_DOUBLES},
297   {"m64bit-doubles", no_argument, NULL, OPTION_64BIT_DOUBLES},
298   {NULL, no_argument, NULL, 0}
299 };
300 size_t md_longopts_size = sizeof (md_longopts);
301
302 int
303 md_parse_option (int c, char * arg ATTRIBUTE_UNUSED)
304 {
305   switch (c)
306     {
307     case OPTION_RELAX:
308       linkrelax = 1;
309       return 1;
310
311     case OPTION_G10:
312       elf_flags |= E_FLAG_RL78_G10;
313       return 1;
314
315     case OPTION_32BIT_DOUBLES:
316       elf_flags &= ~ E_FLAG_RL78_64BIT_DOUBLES;
317       return 1;
318
319     case OPTION_64BIT_DOUBLES:
320       elf_flags |= E_FLAG_RL78_64BIT_DOUBLES;
321       return 1;
322     }
323   return 0;
324 }
325
326 void
327 md_show_usage (FILE * stream ATTRIBUTE_UNUSED)
328 {
329   fprintf (stream, _(" RL78 specific command line options:\n"));
330   fprintf (stream, _("  --mg10            Enable support for G10 variant\n"));
331   fprintf (stream, _("  --m32bit-doubles  [default]\n"));
332   fprintf (stream, _("  --m64bit-doubles\n"));
333 }
334
335 static void
336 s_bss (int ignore ATTRIBUTE_UNUSED)
337 {
338   int temp;
339
340   temp = get_absolute_expression ();
341   subseg_set (bss_section, (subsegT) temp);
342   demand_empty_rest_of_line ();
343 }
344
345 static void
346 rl78_float_cons (int ignore ATTRIBUTE_UNUSED)
347 {
348   if (elf_flags & E_FLAG_RL78_64BIT_DOUBLES)
349     return float_cons ('d');
350   return float_cons ('f');
351 }
352
353 /* The target specific pseudo-ops which we support.  */
354 const pseudo_typeS md_pseudo_table[] =
355 {
356   /* Our "standard" pseudos.  */
357   { "double", rl78_float_cons,  'd' },
358   { "bss",    s_bss,            0 },
359   { "3byte",  cons,             3 },
360   { "int",    cons,             4 },
361   { "word",   cons,             4 },
362
363   /* End of list marker.  */
364   { NULL,       NULL,           0 }
365 };
366
367 void
368 md_begin (void)
369 {
370 }
371
372 void
373 rl78_md_end (void)
374 {
375 }
376
377 /* Set the ELF specific flags.  */
378 void
379 rl78_elf_final_processing (void)
380 {
381   elf_elfheader (stdoutput)->e_flags |= elf_flags;
382 }
383
384 /* Write a value out to the object file, using the appropriate endianness.  */
385 void
386 md_number_to_chars (char * buf, valueT val, int n)
387 {
388   number_to_chars_littleendian (buf, val, n);
389 }
390
391 static void
392 require_end_of_expr (char *fname)
393 {
394   while (* input_line_pointer == ' '
395          || * input_line_pointer == '\t')
396     input_line_pointer ++;
397
398   if (! * input_line_pointer
399       || strchr ("\n\r,", * input_line_pointer)
400       || strchr (comment_chars, * input_line_pointer)
401       || strchr (line_comment_chars, * input_line_pointer)
402       || strchr (line_separator_chars, * input_line_pointer))
403     return;
404
405   as_bad (_("%%%s() must be outermost term in expression"), fname);
406 }
407
408 static struct
409 {
410   char * fname;
411   int    reloc;
412 }
413 reloc_functions[] =
414 {
415   { "code", BFD_RELOC_RL78_CODE },
416   { "lo16", BFD_RELOC_RL78_LO16 },
417   { "hi16", BFD_RELOC_RL78_HI16 },
418   { "hi8",  BFD_RELOC_RL78_HI8 },
419   { 0, 0 }
420 };
421
422 void
423 md_operand (expressionS * exp ATTRIBUTE_UNUSED)
424 {
425   int reloc = 0;
426   int i;
427
428   for (i = 0; reloc_functions[i].fname; i++)
429     {
430       int flen = strlen (reloc_functions[i].fname);
431
432       if (input_line_pointer[0] == '%'
433           && strncasecmp (input_line_pointer + 1, reloc_functions[i].fname, flen) == 0
434           && input_line_pointer[flen + 1] == '(')
435         {
436           reloc = reloc_functions[i].reloc;
437           input_line_pointer += flen + 2;
438           break;
439         }
440     }
441   if (reloc == 0)
442     return;
443
444   expression (exp);
445   if (* input_line_pointer == ')')
446     input_line_pointer ++;
447
448   exp->X_md = reloc;
449
450   require_end_of_expr (reloc_functions[i].fname);
451 }
452
453 void
454 rl78_frag_init (fragS * fragP)
455 {
456   if (rl78_bytes.n_relax || rl78_bytes.link_relax)
457     {
458       fragP->tc_frag_data = malloc (sizeof (rl78_bytesT));
459       memcpy (fragP->tc_frag_data, & rl78_bytes, sizeof (rl78_bytesT));
460     }
461   else
462     fragP->tc_frag_data = 0;
463 }
464
465 /* When relaxing, we need to output a reloc for any .align directive
466    so that we can retain this alignment as we adjust opcode sizes.  */
467 void
468 rl78_handle_align (fragS * frag)
469 {
470   if (linkrelax
471       && (frag->fr_type == rs_align
472           || frag->fr_type == rs_align_code)
473       && frag->fr_address + frag->fr_fix > 0
474       && frag->fr_offset > 0
475       && now_seg != bss_section)
476     {
477       fix_new (frag, frag->fr_fix, 0,
478                &abs_symbol, RL78_RELAXA_ALIGN + frag->fr_offset,
479                0, BFD_RELOC_RL78_RELAX);
480       /* For the purposes of relaxation, this relocation is attached
481          to the byte *after* the alignment - i.e. the byte that must
482          remain aligned.  */
483       fix_new (frag->fr_next, 0, 0,
484                &abs_symbol, RL78_RELAXA_ELIGN + frag->fr_offset,
485                0, BFD_RELOC_RL78_RELAX);
486     }
487 }
488
489 char *
490 md_atof (int type, char * litP, int * sizeP)
491 {
492   return ieee_md_atof (type, litP, sizeP, target_big_endian);
493 }
494
495 symbolS *
496 md_undefined_symbol (char * name ATTRIBUTE_UNUSED)
497 {
498   return NULL;
499 }
500
501 #define APPEND(B, N_B)                                 \
502   if (rl78_bytes.N_B)                                  \
503     {                                                  \
504       memcpy (bytes + idx, rl78_bytes.B, rl78_bytes.N_B);  \
505       idx += rl78_bytes.N_B;                           \
506     }
507
508
509 void
510 md_assemble (char * str)
511 {
512   char * bytes;
513   fragS * frag_then = frag_now;
514   int idx = 0;
515   int i;
516   int rel;
517   expressionS  *exp;
518
519   /*printf("\033[32mASM: %s\033[0m\n", str);*/
520
521   dwarf2_emit_insn (0);
522
523   memset (& rl78_bytes, 0, sizeof (rl78_bytes));
524
525   rl78_lex_init (str, str + strlen (str));
526
527   rl78_parse ();
528
529   /* This simplifies the relaxation code.  */
530   if (rl78_bytes.n_relax || rl78_bytes.link_relax)
531     {
532       int olen = rl78_bytes.n_prefix + rl78_bytes.n_base + rl78_bytes.n_ops;
533       /* We do it this way because we want the frag to have the
534          rl78_bytes in it, which we initialize above.  The extra bytes
535          are for relaxing.  */
536       bytes = frag_more (olen + 3);
537       frag_then = frag_now;
538       frag_variant (rs_machine_dependent,
539                     olen /* max_chars */,
540                     0 /* var */,
541                     olen /* subtype */,
542                     0 /* symbol */,
543                     0 /* offset */,
544                     0 /* opcode */);
545       frag_then->fr_opcode = bytes;
546       frag_then->fr_fix = olen + (bytes - frag_then->fr_literal);
547       frag_then->fr_subtype = olen;
548       frag_then->fr_var = 0;
549     }
550   else
551     {
552       bytes = frag_more (rl78_bytes.n_prefix + rl78_bytes.n_base + rl78_bytes.n_ops);
553       frag_then = frag_now;
554     }
555
556   APPEND (prefix, n_prefix);
557   APPEND (base, n_base);
558   APPEND (ops, n_ops);
559
560   if (rl78_bytes.link_relax)
561     {
562       fixS * f;
563
564       f = fix_new (frag_then,
565                    (char *) bytes - frag_then->fr_literal,
566                    0,
567                    abs_section_sym,
568                    rl78_bytes.link_relax | rl78_bytes.n_fixups,
569                    0,
570                    BFD_RELOC_RL78_RELAX);
571       frag_then->tc_frag_data->link_relax_fixP = f;
572     }
573
574   for (i = 0; i < rl78_bytes.n_fixups; i ++)
575     {
576       /* index: [nbytes][type] */
577       static int reloc_map[5][4] =
578         {
579           { 0,            0 },
580           { BFD_RELOC_8,  BFD_RELOC_8_PCREL },
581           { BFD_RELOC_16, BFD_RELOC_16_PCREL },
582           { BFD_RELOC_24, BFD_RELOC_24_PCREL },
583           { BFD_RELOC_32, BFD_RELOC_32_PCREL },
584         };
585       fixS * f;
586
587       idx = rl78_bytes.fixups[i].offset / 8;
588       rel = reloc_map [rl78_bytes.fixups[i].nbits / 8][(int) rl78_bytes.fixups[i].type];
589
590       if (rl78_bytes.fixups[i].reloc)
591         rel = rl78_bytes.fixups[i].reloc;
592
593       if (frag_then->tc_frag_data)
594         exp = & frag_then->tc_frag_data->fixups[i].exp;
595       else
596         exp = & rl78_bytes.fixups[i].exp;
597
598       f = fix_new_exp (frag_then,
599                        (char *) bytes + idx - frag_then->fr_literal,
600                        rl78_bytes.fixups[i].nbits / 8,
601                        exp,
602                        rl78_bytes.fixups[i].type == RL78REL_PCREL ? 1 : 0,
603                        rel);
604       if (frag_then->tc_frag_data)
605         frag_then->tc_frag_data->fixups[i].fixP = f;
606     }
607 }
608
609 void
610 rl78_cons_fix_new (fragS *      frag,
611                  int            where,
612                  int            size,
613                  expressionS *  exp)
614 {
615   bfd_reloc_code_real_type type;
616   fixS *fixP;
617
618   switch (size)
619     {
620     case 1:
621       type = BFD_RELOC_8;
622       break;
623     case 2:
624       type = BFD_RELOC_16;
625       break;
626     case 3:
627       type = BFD_RELOC_24;
628       break;
629     case 4:
630       type = BFD_RELOC_32;
631       break;
632     default:
633       as_bad (_("unsupported constant size %d\n"), size);
634       return;
635     }
636
637   switch (exp->X_md)
638     {
639     case BFD_RELOC_RL78_CODE:
640       if (size == 2)
641         type = exp->X_md;
642       break;
643     case BFD_RELOC_RL78_LO16:
644     case BFD_RELOC_RL78_HI16:
645       if (size != 2)
646         as_bad (_("%%hi16/%%lo16 only applies to .short or .hword"));
647       type = exp->X_md;
648       break;
649     case BFD_RELOC_RL78_HI8:
650       if (size != 1)
651         as_bad (_("%%hi8 only applies to .byte"));
652       type = exp->X_md;
653       break;
654     default:
655       break;
656     }
657
658   if (exp->X_op == O_subtract && exp->X_op_symbol)
659     {
660       if (size != 4 && size != 2 && size != 1)
661         as_bad (_("difference of two symbols only supported with .long, .short, or .byte"));
662       else
663         type = BFD_RELOC_RL78_DIFF;
664     }
665
666   fixP = fix_new_exp (frag, where, (int) size, exp, 0, type);
667   switch (exp->X_md)
668     {
669       /* These are intended to have values larger than the container,
670          since the backend puts only the portion we need in it.
671          However, we don't have a backend-specific reloc for them as
672          they're handled with complex relocations.  */
673     case BFD_RELOC_RL78_LO16:
674     case BFD_RELOC_RL78_HI16:
675     case BFD_RELOC_RL78_HI8:
676       fixP->fx_no_overflow = 1;
677       break;
678     default:
679       break;
680     }
681 }
682
683 \f
684 /*----------------------------------------------------------------------*/
685 /* To recap: we estimate everything based on md_estimate_size, then
686    adjust based on rl78_relax_frag.  When it all settles, we call
687    md_convert frag to update the bytes.  The relaxation types and
688    relocations are in fragP->tc_frag_data, which is a copy of that
689    rl78_bytes.
690
691    Our scheme is as follows: fr_fix has the size of the smallest
692    opcode (like BRA.S).  We store the number of total bytes we need in
693    fr_subtype.  When we're done relaxing, we use fr_subtype and the
694    existing opcode bytes to figure out what actual opcode we need to
695    put in there.  If the fixup isn't resolvable now, we use the
696    maximal size.  */
697
698 #define TRACE_RELAX 0
699 #define tprintf if (TRACE_RELAX) printf
700
701
702 typedef enum
703 {
704   OT_other,
705   OT_bt,
706   OT_bt_sfr,
707   OT_bt_es,
708   OT_bc,
709   OT_bh
710 } op_type_T;
711
712 /* We're looking for these types of relaxations:
713
714    BT           00110001 sbit0cc1 addr----      (cc is 10 (BF) or 01 (BT))
715    B~T          00110001 sbit0cc1 00000011 11101110 pcrel16- -------- (BR $!pcrel20)
716
717    BT sfr       00110001 sbit0cc0 sfr----- addr----
718    BT ES:       00010001 00101110 sbit0cc1 addr----
719
720    BC           110111cc addr----
721    B~C          110111cc 00000011 11101110 pcrel16- -------- (BR $!pcrel20)
722
723    BH           01100001 110c0011 00000011 11101110 pcrel16- -------- (BR $!pcrel20)
724    B~H          01100001 110c0011 00000011 11101110 pcrel16- -------- (BR $!pcrel20)
725 */
726
727 /* Given the opcode bytes at OP, figure out which opcode it is and
728    return the type of opcode.  We use this to re-encode the opcode as
729    a different size later.  */
730
731 static op_type_T
732 rl78_opcode_type (char * op)
733 {
734   if (op[0] == 0x31
735       && ((op[1] & 0x0f) == 0x05
736           || (op[1] & 0x0f) == 0x03))
737     return OT_bt;
738
739   if (op[0] == 0x31
740       && ((op[1] & 0x0f) == 0x04
741           || (op[1] & 0x0f) == 0x02))
742     return OT_bt_sfr;
743
744   if (op[0] == 0x11
745       && op[1] == 0x31
746       && ((op[2] & 0x0f) == 0x05
747           || (op[2] & 0x0f) == 0x03))
748     return OT_bt_es;
749
750   if ((op[0] & 0xfc) == 0xdc)
751     return OT_bc;
752
753   if (op[0] == 0x61
754       && (op[1] & 0xef) == 0xc3)
755     return OT_bh;
756
757   return OT_other;
758 }
759
760 /* Returns zero if *addrP has the target address.  Else returns nonzero
761    if we cannot compute the target address yet.  */
762
763 static int
764 rl78_frag_fix_value (fragS *    fragP,
765                      segT       segment,
766                      int        which,
767                      addressT * addrP,
768                      int        need_diff,
769                      addressT * sym_addr)
770 {
771   addressT addr = 0;
772   rl78_bytesT * b = fragP->tc_frag_data;
773   expressionS * exp = & b->fixups[which].exp;
774
775   if (need_diff && exp->X_op != O_subtract)
776     return 1;
777
778   if (exp->X_add_symbol)
779     {
780       if (S_FORCE_RELOC (exp->X_add_symbol, 1))
781         return 1;
782       if (S_GET_SEGMENT (exp->X_add_symbol) != segment)
783         return 1;
784       addr += S_GET_VALUE (exp->X_add_symbol);
785     }
786
787   if (exp->X_op_symbol)
788     {
789       if (exp->X_op != O_subtract)
790         return 1;
791       if (S_FORCE_RELOC (exp->X_op_symbol, 1))
792         return 1;
793       if (S_GET_SEGMENT (exp->X_op_symbol) != segment)
794         return 1;
795       addr -= S_GET_VALUE (exp->X_op_symbol);
796     }
797   if (sym_addr)
798     * sym_addr = addr;
799   addr += exp->X_add_number;
800   * addrP = addr;
801   return 0;
802 }
803
804 /* Estimate how big the opcode is after this relax pass.  The return
805    value is the difference between fr_fix and the actual size.  We
806    compute the total size in rl78_relax_frag and store it in fr_subtype,
807    sowe only need to subtract fx_fix and return it.  */
808
809 int
810 md_estimate_size_before_relax (fragS * fragP ATTRIBUTE_UNUSED, segT segment ATTRIBUTE_UNUSED)
811 {
812   int opfixsize;
813   int delta;
814
815   /* This is the size of the opcode that's accounted for in fr_fix.  */
816   opfixsize = fragP->fr_fix - (fragP->fr_opcode - fragP->fr_literal);
817   /* This is the size of the opcode that isn't.  */
818   delta = (fragP->fr_subtype - opfixsize);
819
820   tprintf (" -> opfixsize %d delta %d\n", opfixsize, delta);
821   return delta;
822 }
823
824 /* Given the new addresses for this relax pass, figure out how big
825    each opcode must be.  We store the total number of bytes needed in
826    fr_subtype.  The return value is the difference between the size
827    after the last pass and the size after this pass, so we use the old
828    fr_subtype to calculate the difference.  */
829
830 int
831 rl78_relax_frag (segT segment ATTRIBUTE_UNUSED, fragS * fragP, long stretch)
832 {
833   addressT addr0, sym_addr;
834   addressT mypc;
835   int disp;
836   int oldsize = fragP->fr_subtype;
837   int newsize = oldsize;
838   op_type_T optype;
839   int ri;
840
841   mypc = fragP->fr_address + (fragP->fr_opcode - fragP->fr_literal);
842
843   /* If we ever get more than one reloc per opcode, this is the one
844      we're relaxing.  */
845   ri = 0;
846
847   optype = rl78_opcode_type (fragP->fr_opcode);
848   /* Try to get the target address.  */
849   if (rl78_frag_fix_value (fragP, segment, ri, & addr0,
850                            fragP->tc_frag_data->relax[ri].type != RL78_RELAX_BRANCH,
851                            & sym_addr))
852     {
853       /* If we don't, we must use the maximum size for the linker.  */
854       switch (fragP->tc_frag_data->relax[ri].type)
855         {
856         case RL78_RELAX_BRANCH:
857           switch (optype)
858             {
859             case OT_bt:
860               newsize = 6;
861               break;
862             case OT_bt_sfr:
863             case OT_bt_es:
864               newsize = 7;
865               break;
866             case OT_bc:
867               newsize = 5;
868               break;
869             case OT_bh:
870               newsize = 6;
871               break;
872             case OT_other:
873               newsize = oldsize;
874               break;
875             }
876           break;
877
878         }
879       fragP->fr_subtype = newsize;
880       tprintf (" -> new %d old %d delta %d (external)\n", newsize, oldsize, newsize-oldsize);
881       return newsize - oldsize;
882     }
883
884   if (sym_addr > mypc)
885     addr0 += stretch;
886
887   switch (fragP->tc_frag_data->relax[ri].type)
888     {
889     case  RL78_RELAX_BRANCH:
890       disp = (int) addr0 - (int) mypc;
891
892       switch (optype)
893         {
894         case OT_bt:
895           if (disp >= -128 && (disp - (oldsize-2)) <= 127)
896             newsize = 3;
897           else
898             newsize = 6;
899           break;
900         case OT_bt_sfr:
901         case OT_bt_es:
902           if (disp >= -128 && (disp - (oldsize-3)) <= 127)
903             newsize = 4;
904           else
905             newsize = 7;
906           break;
907         case OT_bc:
908           if (disp >= -128 && (disp - (oldsize-1)) <= 127)
909             newsize = 2;
910           else
911             newsize = 5;
912           break;
913         case OT_bh:
914           if (disp >= -128 && (disp - (oldsize-2)) <= 127)
915             newsize = 3;
916           else
917             newsize = 6;
918           break;
919         case OT_other:
920           newsize = oldsize;
921           break;
922         }
923       break;
924     }
925
926   /* This prevents infinite loops in align-heavy sources.  */
927   if (newsize < oldsize)
928     {
929       if (fragP->tc_frag_data->times_shrank > 10
930          && fragP->tc_frag_data->times_grown > 10)
931        newsize = oldsize;
932       if (fragP->tc_frag_data->times_shrank < 20)
933        fragP->tc_frag_data->times_shrank ++;
934     }
935   else if (newsize > oldsize)
936     {
937       if (fragP->tc_frag_data->times_grown < 20)
938        fragP->tc_frag_data->times_grown ++;
939     }
940
941   fragP->fr_subtype = newsize;
942   tprintf (" -> new %d old %d delta %d\n", newsize, oldsize, newsize-oldsize);
943   return newsize - oldsize;
944  }
945  
946 /* This lets us test for the opcode type and the desired size in a
947    switch statement.  */
948 #define OPCODE(type,size) ((type) * 16 + (size))
949
950 /* Given the opcode stored in fr_opcode and the number of bytes we
951    think we need, encode a new opcode.  We stored a pointer to the
952    fixup for this opcode in the tc_frag_data structure.  If we can do
953    the fixup here, we change the relocation type to "none" (we test
954    for that in tc_gen_reloc) else we change it to the right type for
955    the new (biggest) opcode.  */
956
957 void
958 md_convert_frag (bfd *   abfd ATTRIBUTE_UNUSED,
959                  segT    segment ATTRIBUTE_UNUSED,
960                  fragS * fragP ATTRIBUTE_UNUSED)
961 {
962   rl78_bytesT * rl78b = fragP->tc_frag_data;
963   addressT addr0, mypc;
964   int disp;
965   int reloc_type, reloc_adjust;
966   char * op = fragP->fr_opcode;
967   int keep_reloc = 0;
968   int ri;
969   int fi = (rl78b->n_fixups > 1) ? 1 : 0;
970   fixS * fix = rl78b->fixups[fi].fixP;
971
972   /* If we ever get more than one reloc per opcode, this is the one
973      we're relaxing.  */
974   ri = 0;
975
976   /* We used a new frag for this opcode, so the opcode address should
977      be the frag address.  */
978   mypc = fragP->fr_address + (fragP->fr_opcode - fragP->fr_literal);
979   tprintf("\033[32mmypc: 0x%x\033[0m\n", (int)mypc);
980
981   /* Try to get the target address.  If we fail here, we just use the
982      largest format.  */
983   if (rl78_frag_fix_value (fragP, segment, 0, & addr0,
984                          fragP->tc_frag_data->relax[ri].type != RL78_RELAX_BRANCH, 0))
985     {
986       /* We don't know the target address.  */
987       keep_reloc = 1;
988       addr0 = 0;
989       disp = 0;
990       tprintf ("unknown addr ? - %x = ?\n", (int)mypc);
991     }
992   else
993     {
994       /* We know the target address, and it's in addr0.  */
995       disp = (int) addr0 - (int) mypc;
996       tprintf ("known addr %x - %x = %d\n", (int)addr0, (int)mypc, disp);
997     }
998
999   if (linkrelax)
1000     keep_reloc = 1;
1001
1002   reloc_type = BFD_RELOC_NONE;
1003   reloc_adjust = 0;
1004
1005   switch (fragP->tc_frag_data->relax[ri].type)
1006     {
1007     case RL78_RELAX_BRANCH:
1008       switch (OPCODE (rl78_opcode_type (fragP->fr_opcode), fragP->fr_subtype))
1009         {
1010
1011         case OPCODE (OT_bt, 3): /* BT A,$ - no change.  */
1012           disp -= 3;
1013           op[2] = disp;
1014           break;
1015
1016         case OPCODE (OT_bt, 6): /* BT A,$ - long version.  */
1017           disp -= 3;
1018           op[1] ^= 0x06; /* toggle conditional.  */
1019           op[2] = 3; /* displacement over long branch.  */
1020           disp -= 3;
1021           op[3] = 0xEE; /* BR $!addr20 */
1022           op[4] = disp & 0xff;
1023           op[5] = disp >> 8;
1024           reloc_type = keep_reloc ? BFD_RELOC_16_PCREL : BFD_RELOC_NONE;
1025           reloc_adjust = 2;
1026           break;
1027
1028         case OPCODE (OT_bt_sfr, 4): /* BT PSW,$ - no change.  */
1029           disp -= 4;
1030           op[3] = disp;
1031           break;
1032
1033         case OPCODE (OT_bt_sfr, 7): /* BT PSW,$ - long version.  */
1034           disp -= 4;
1035           op[1] ^= 0x06; /* toggle conditional.  */
1036           op[3] = 3; /* displacement over long branch.  */
1037           disp -= 3;
1038           op[4] = 0xEE; /* BR $!addr20 */
1039           op[5] = disp & 0xff;
1040           op[6] = disp >> 8;
1041           reloc_type = keep_reloc ? BFD_RELOC_16_PCREL : BFD_RELOC_NONE;
1042           reloc_adjust = 2;
1043           break;
1044
1045         case OPCODE (OT_bt_es, 4): /* BT ES:[HL],$ - no change.  */
1046           disp -= 4;
1047           op[3] = disp;
1048           break;
1049
1050         case OPCODE (OT_bt_es, 7): /* BT PSW,$ - long version.  */
1051           disp -= 4;
1052           op[2] ^= 0x06; /* toggle conditional.  */
1053           op[3] = 3; /* displacement over long branch.  */
1054           disp -= 3;
1055           op[4] = 0xEE; /* BR $!addr20 */
1056           op[5] = disp & 0xff;
1057           op[6] = disp >> 8;
1058           reloc_type = keep_reloc ? BFD_RELOC_16_PCREL : BFD_RELOC_NONE;
1059           reloc_adjust = 2;
1060           break;
1061
1062         case OPCODE (OT_bc, 2): /* BC $ - no change.  */
1063           disp -= 2;
1064           op[1] = disp;
1065           break;
1066
1067         case OPCODE (OT_bc, 5): /* BC $ - long version.  */
1068           disp -= 2;
1069           op[0] ^= 0x02; /* toggle conditional.  */
1070           op[1] = 3;
1071           disp -= 3;
1072           op[2] = 0xEE; /* BR $!addr20 */
1073           op[3] = disp & 0xff;
1074           op[4] = disp >> 8;
1075           reloc_type = keep_reloc ? BFD_RELOC_16_PCREL : BFD_RELOC_NONE;
1076           reloc_adjust = 2;
1077           break;
1078
1079         case OPCODE (OT_bh, 3): /* BH $ - no change.  */
1080           disp -= 3;
1081           op[2] = disp;
1082           break;
1083
1084         case OPCODE (OT_bh, 6): /* BC $ - long version.  */
1085           disp -= 3;
1086           op[1] ^= 0x10; /* toggle conditional.  */
1087           op[2] = 3;
1088           disp -= 3;
1089           op[3] = 0xEE; /* BR $!addr20 */
1090           op[4] = disp & 0xff;
1091           op[5] = disp >> 8;
1092           reloc_type = keep_reloc ? BFD_RELOC_16_PCREL : BFD_RELOC_NONE;
1093           reloc_adjust = 2;
1094           break;
1095
1096         default:
1097           fprintf(stderr, "Missed case %d %d at 0x%lx\n",
1098                   rl78_opcode_type (fragP->fr_opcode), fragP->fr_subtype, mypc);
1099           abort ();
1100           
1101         }
1102       break;
1103
1104     default:
1105       if (rl78b->n_fixups)
1106         {
1107           reloc_type = fix->fx_r_type;
1108           reloc_adjust = 0;
1109         }
1110       break;
1111     }
1112
1113   if (rl78b->n_fixups)
1114     {
1115
1116       fix->fx_r_type = reloc_type;
1117       fix->fx_where += reloc_adjust;
1118       switch (reloc_type)
1119         {
1120         case BFD_RELOC_NONE:
1121           fix->fx_size = 0;
1122           break;
1123         case BFD_RELOC_8:
1124           fix->fx_size = 1;
1125           break;
1126         case BFD_RELOC_16_PCREL:
1127           fix->fx_size = 2;
1128           break;
1129         }
1130     }
1131
1132   fragP->fr_fix = fragP->fr_subtype + (fragP->fr_opcode - fragP->fr_literal);
1133   tprintf ("fragP->fr_fix now %ld (%d + (%p - %p)\n", (long) fragP->fr_fix,
1134           fragP->fr_subtype, fragP->fr_opcode, fragP->fr_literal);
1135   fragP->fr_var = 0;
1136
1137   tprintf ("compare 0x%lx vs 0x%lx - 0x%lx = 0x%lx (%p)\n",
1138            (long)fragP->fr_fix,
1139            (long)fragP->fr_next->fr_address, (long)fragP->fr_address,
1140            (long)(fragP->fr_next->fr_address - fragP->fr_address),
1141            fragP->fr_next);
1142
1143   if (fragP->fr_next != NULL
1144           && ((offsetT) (fragP->fr_next->fr_address - fragP->fr_address)
1145               != fragP->fr_fix))
1146     as_bad (_("bad frag at %p : fix %ld addr %ld %ld \n"), fragP,
1147             (long) fragP->fr_fix,
1148             (long) fragP->fr_address, (long) fragP->fr_next->fr_address);
1149 }
1150
1151 /* End of relaxation code.
1152   ----------------------------------------------------------------------*/
1153 \f
1154
1155 arelent **
1156 tc_gen_reloc (asection * seg ATTRIBUTE_UNUSED, fixS * fixp)
1157 {
1158   static arelent * reloc[8];
1159   int rp;
1160
1161   if (fixp->fx_r_type == BFD_RELOC_NONE)
1162     {
1163       reloc[0] = NULL;
1164       return reloc;
1165     }
1166
1167   if (fixp->fx_subsy
1168       && S_GET_SEGMENT (fixp->fx_subsy) == absolute_section)
1169     {
1170       fixp->fx_offset -= S_GET_VALUE (fixp->fx_subsy);
1171       fixp->fx_subsy = NULL;
1172     }
1173
1174   reloc[0]                = (arelent *) xmalloc (sizeof (arelent));
1175   reloc[0]->sym_ptr_ptr   = (asymbol **) xmalloc (sizeof (asymbol *));
1176   * reloc[0]->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
1177   reloc[0]->address       = fixp->fx_frag->fr_address + fixp->fx_where;
1178   reloc[0]->addend        = fixp->fx_offset;
1179
1180   if (fixp->fx_r_type == BFD_RELOC_RL78_32_OP
1181       && fixp->fx_subsy)
1182     {
1183       fixp->fx_r_type = BFD_RELOC_RL78_DIFF;
1184     }
1185
1186 #define OPX(REL,SYM,ADD)                                                        \
1187   reloc[rp]                = (arelent *) xmalloc (sizeof (arelent));            \
1188   reloc[rp]->sym_ptr_ptr   = (asymbol **) xmalloc (sizeof (asymbol *));         \
1189   reloc[rp]->howto         = bfd_reloc_type_lookup (stdoutput, REL);            \
1190   reloc[rp]->addend        = ADD;                                               \
1191   * reloc[rp]->sym_ptr_ptr = SYM;                                               \
1192   reloc[rp]->address       = fixp->fx_frag->fr_address + fixp->fx_where;        \
1193   reloc[++rp] = NULL
1194 #define OPSYM(SYM) OPX(BFD_RELOC_RL78_SYM, SYM, 0)
1195 #define OPIMM(IMM) OPX(BFD_RELOC_RL78_SYM, abs_symbol.bsym, IMM)
1196 #define OP(OP) OPX(BFD_RELOC_RL78_##OP, *reloc[0]->sym_ptr_ptr, 0)
1197 #define SYM0() reloc[0]->howto = bfd_reloc_type_lookup (stdoutput, BFD_RELOC_RL78_SYM)
1198
1199   rp = 1;
1200
1201   /* Certain BFD relocations cannot be translated directly into
1202      a single (non-Red Hat) RL78 relocation, but instead need
1203      multiple RL78 relocations - handle them here.  */
1204   switch (fixp->fx_r_type)
1205     {
1206     case BFD_RELOC_RL78_DIFF:
1207       SYM0 ();
1208       OPSYM (symbol_get_bfdsym (fixp->fx_subsy));
1209       OP(OP_SUBTRACT);
1210
1211       switch (fixp->fx_size)
1212         {
1213         case 1:
1214           OP(ABS8);
1215           break;
1216         case 2:
1217           OP (ABS16);
1218           break;
1219         case 4:
1220           OP (ABS32);
1221           break;
1222         }
1223       break;
1224
1225     case BFD_RELOC_RL78_NEG32:
1226       SYM0 ();
1227       OP (OP_NEG);
1228       OP (ABS32);
1229       break;
1230
1231     case BFD_RELOC_RL78_CODE:
1232       reloc[0]->howto = bfd_reloc_type_lookup (stdoutput, BFD_RELOC_RL78_16U);
1233       reloc[1] = NULL;
1234       break;
1235
1236     case BFD_RELOC_RL78_LO16:
1237       SYM0 ();
1238       OPIMM (0xffff);
1239       OP (OP_AND);
1240       OP (ABS16);
1241       break;
1242
1243     case BFD_RELOC_RL78_HI16:
1244       SYM0 ();
1245       OPIMM (16);
1246       OP (OP_SHRA);
1247       OP (ABS16);
1248       break;
1249
1250     case BFD_RELOC_RL78_HI8:
1251       SYM0 ();
1252       OPIMM (16);
1253       OP (OP_SHRA);
1254       OPIMM (0xff);
1255       OP (OP_AND);
1256       OP (ABS8);
1257       break;
1258
1259     default:
1260       reloc[0]->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
1261       reloc[1] = NULL;
1262       break;
1263     }
1264
1265   return reloc;
1266 }
1267
1268 int
1269 rl78_validate_fix_sub (struct fix * f)
1270 {
1271   /* We permit the subtraction of two symbols in a few cases.  */
1272   /* mov #sym1-sym2, R3 */
1273   if (f->fx_r_type == BFD_RELOC_RL78_32_OP)
1274     return 1;
1275   /* .long sym1-sym2 */
1276   if (f->fx_r_type == BFD_RELOC_RL78_DIFF
1277       && ! f->fx_pcrel
1278       && (f->fx_size == 4 || f->fx_size == 2 || f->fx_size == 1))
1279     return 1;
1280   return 0;
1281 }
1282
1283 long
1284 md_pcrel_from_section (fixS * fixP, segT sec)
1285 {
1286   long rv;
1287
1288   if (fixP->fx_addsy != NULL
1289       && (! S_IS_DEFINED (fixP->fx_addsy)
1290           || S_GET_SEGMENT (fixP->fx_addsy) != sec))
1291     /* The symbol is undefined (or is defined but not in this section).
1292        Let the linker figure it out.  */
1293     return 0;
1294
1295   rv = fixP->fx_frag->fr_address + fixP->fx_where;
1296   switch (fixP->fx_r_type)
1297     {
1298     case BFD_RELOC_8_PCREL:
1299       rv += 1;
1300       break;
1301     case BFD_RELOC_16_PCREL:
1302       rv += 2;
1303       break;
1304     default:
1305       break;
1306     }
1307   return rv;
1308 }
1309
1310 void
1311 md_apply_fix (struct fix * f ATTRIBUTE_UNUSED,
1312               valueT *     t ATTRIBUTE_UNUSED,
1313               segT         s ATTRIBUTE_UNUSED)
1314 {
1315   char * op;
1316   unsigned long val;
1317
1318   if (f->fx_addsy && S_FORCE_RELOC (f->fx_addsy, 1))
1319     return;
1320   if (f->fx_subsy && S_FORCE_RELOC (f->fx_subsy, 1))
1321     return;
1322
1323   op = f->fx_frag->fr_literal + f->fx_where;
1324   val = (unsigned long) * t;
1325
1326   switch (f->fx_r_type)
1327     {
1328     case BFD_RELOC_NONE:
1329       break;
1330
1331     case BFD_RELOC_RL78_RELAX:
1332       f->fx_done = 1;
1333       break;
1334
1335     case BFD_RELOC_8_PCREL:
1336       if ((long)val < -128 || (long)val > 127)
1337         as_bad_where (f->fx_file, f->fx_line,
1338                       _("value of %ld too large for 8-bit branch"),
1339                       val);
1340       /* Fall through.  */
1341     case BFD_RELOC_8:
1342       op[0] = val;
1343       break;
1344
1345     case BFD_RELOC_16_PCREL:
1346       if ((long)val < -32768 || (long)val > 32767)
1347         as_bad_where (f->fx_file, f->fx_line,
1348                       _("value of %ld too large for 16-bit branch"),
1349                       val);
1350       /* Fall through.  */
1351     case BFD_RELOC_16:
1352     case BFD_RELOC_RL78_CODE:
1353       op[0] = val;
1354       op[1] = val >> 8;
1355       break;
1356
1357     case BFD_RELOC_24:
1358       op[0] = val;
1359       op[1] = val >> 8;
1360       op[2] = val >> 16;
1361       break;
1362
1363     case BFD_RELOC_32:
1364       op[0] = val;
1365       op[1] = val >> 8;
1366       op[2] = val >> 16;
1367       op[3] = val >> 24;
1368       break;
1369
1370     case BFD_RELOC_RL78_DIFF:
1371       op[0] = val;
1372       if (f->fx_size > 1)
1373         op[1] = val >> 8;
1374       if (f->fx_size > 2)
1375         op[2] = val >> 16;
1376       if (f->fx_size > 3)
1377         op[3] = val >> 24;
1378       break;
1379
1380     case BFD_RELOC_RL78_HI8:
1381       val = val >> 16;
1382       op[0] = val;
1383       break;
1384
1385     case BFD_RELOC_RL78_HI16:
1386       val = val >> 16;
1387       op[0] = val;
1388       op[1] = val >> 8;
1389       break;
1390
1391     case BFD_RELOC_RL78_LO16:
1392       op[0] = val;
1393       op[1] = val >> 8;
1394       break;
1395
1396     default:
1397       as_bad (_("Unknown reloc in md_apply_fix: %s"),
1398               bfd_get_reloc_code_name (f->fx_r_type));
1399       break;
1400     }
1401
1402   if (f->fx_addsy == NULL)
1403     f->fx_done = 1;
1404 }
1405
1406 valueT
1407 md_section_align (segT segment, valueT size)
1408 {
1409   int align = bfd_get_section_alignment (stdoutput, segment);
1410   return ((size + (1 << align) - 1) & (-1 << align));
1411 }