OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [binutils-2.20.1/] [gas/] [config/] [tc-cr16.c] - Blame information for rev 438

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 205 julius
/* tc-cr16.c -- Assembler code for the CR16 CPU core.
2
   Copyright 2007, 2008, 2009 Free Software Foundation, Inc.
3
 
4
   Contributed by M R Swami Reddy <MR.Swami.Reddy@nsc.com>
5
 
6
   This file is part of GAS, the GNU Assembler.
7
 
8
   GAS is free software; you can redistribute it and/or modify
9
   it under the terms of the GNU General Public License as published by
10
   the Free Software Foundation; either version 3, or (at your option)
11
   any later version.
12
 
13
   GAS is distributed in the hope that it will be useful,
14
   but WITHOUT ANY WARRANTY; without even the implied warranty of
15
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
   GNU General Public License for more details.
17
 
18
   You should have received a copy of the GNU General Public License
19
   along with GAS; see the file COPYING.  If not, write to the
20
   Free Software Foundation, 51 Franklin Street - Fifth Floor, Boston,
21
   MA 02110-1301, USA.  */
22
 
23
#include "as.h"
24
#include "safe-ctype.h"
25
#include "dwarf2dbg.h"
26
#include "opcode/cr16.h"
27
#include "elf/cr16.h"
28
 
29
 
30
/* Word is considered here as a 16-bit unsigned short int.  */
31
#define WORD_SHIFT  16
32
 
33
/* Register is 2-byte size.  */
34
#define REG_SIZE   2
35
 
36
/* Maximum size of a single instruction (in words).  */
37
#define INSN_MAX_SIZE   3
38
 
39
/* Maximum bits which may be set in a `mask16' operand.  */
40
#define MAX_REGS_IN_MASK16  8
41
 
42
/* Assign a number NUM, shifted by SHIFT bytes, into a location
43
   pointed by index BYTE of array 'output_opcode'.  */
44
#define CR16_PRINT(BYTE, NUM, SHIFT)   output_opcode[BYTE] |= (NUM << SHIFT)
45
 
46
/* Operand errors.  */
47
typedef enum
48
  {
49
    OP_LEGAL = 0,       /* Legal operand.  */
50
    OP_OUT_OF_RANGE,    /* Operand not within permitted range.  */
51
    OP_NOT_EVEN         /* Operand is Odd number, should be even.  */
52
  }
53
op_err;
54
 
55
/* Opcode mnemonics hash table.  */
56
static struct hash_control *cr16_inst_hash;
57
/* CR16 registers hash table.  */
58
static struct hash_control *reg_hash;
59
/* CR16 register pair hash table.  */
60
static struct hash_control *regp_hash;
61
/* CR16 processor registers hash table.  */
62
static struct hash_control *preg_hash;
63
/* CR16 processor registers 32 bit hash table.  */
64
static struct hash_control *pregp_hash;
65
/* Current instruction we're assembling.  */
66
const inst *instruction;
67
 
68
 
69
static int code_label = 0;
70
 
71
/* Global variables.  */
72
 
73
/* Array to hold an instruction encoding.  */
74
long output_opcode[2];
75
 
76
/* Nonzero means a relocatable symbol.  */
77
int relocatable;
78
 
79
/* A copy of the original instruction (used in error messages).  */
80
char ins_parse[MAX_INST_LEN];
81
 
82
/* The current processed argument number.  */
83
int cur_arg_num;
84
 
85
/* Generic assembler global variables which must be defined by all targets.  */
86
 
87
/* Characters which always start a comment.  */
88
const char comment_chars[] = "#";
89
 
90
/* Characters which start a comment at the beginning of a line.  */
91
const char line_comment_chars[] = "#";
92
 
93
/* This array holds machine specific line separator characters.  */
94
const char line_separator_chars[] = ";";
95
 
96
/* Chars that can be used to separate mant from exp in floating point nums.  */
97
const char EXP_CHARS[] = "eE";
98
 
99
/* Chars that mean this number is a floating point constant as in 0f12.456  */
100
const char FLT_CHARS[] = "f'";
101
 
102
#ifdef OBJ_ELF
103
/* Pre-defined "_GLOBAL_OFFSET_TABLE_"  */
104
symbolS * GOT_symbol;
105
#endif
106
 
107
/* Target-specific multicharacter options, not const-declared at usage.  */
108
const char *md_shortopts = "";
109
struct option md_longopts[] =
110
{
111
  {NULL, no_argument, NULL, 0}
112
};
113
size_t md_longopts_size = sizeof (md_longopts);
114
 
115
static void
116
l_cons (int nbytes)
117
{
118
  int c;
119
  expressionS exp;
120
 
121
#ifdef md_flush_pending_output
122
    md_flush_pending_output ();
123
#endif
124
 
125
  if (is_it_end_of_statement ())
126
    {
127
      demand_empty_rest_of_line ();
128
      return;
129
    }
130
 
131
#ifdef TC_ADDRESS_BYTES
132
  if (nbytes == 0)
133
    nbytes = TC_ADDRESS_BYTES ();
134
#endif
135
 
136
#ifdef md_cons_align
137
  md_cons_align (nbytes);
138
#endif
139
 
140
  c = 0;
141
  do
142
    {
143
      unsigned int bits_available = BITS_PER_CHAR * nbytes;
144
      char *hold = input_line_pointer;
145
 
146
      expression (&exp);
147
 
148
      if (*input_line_pointer == ':')
149
        {
150
          /* Bitfields.  */
151
          long value = 0;
152
 
153
          for (;;)
154
            {
155
              unsigned long width;
156
 
157
              if (*input_line_pointer != ':')
158
                {
159
                  input_line_pointer = hold;
160
                  break;
161
                }
162
              if (exp.X_op == O_absent)
163
                {
164
                  as_warn (_("using a bit field width of zero"));
165
                  exp.X_add_number = 0;
166
                  exp.X_op = O_constant;
167
                }
168
 
169
              if (exp.X_op != O_constant)
170
                {
171
                  *input_line_pointer = '\0';
172
                  as_bad (_("field width \"%s\" too complex for a bitfield"), hold);
173
                  *input_line_pointer = ':';
174
                  demand_empty_rest_of_line ();
175
                  return;
176
                }
177
 
178
              if ((width = exp.X_add_number) >
179
                  (unsigned int)(BITS_PER_CHAR * nbytes))
180
                {
181
                  as_warn (_("field width %lu too big to fit in %d bytes: truncated to %d bits"), width, nbytes, (BITS_PER_CHAR * nbytes));
182
                  width = BITS_PER_CHAR * nbytes;
183
                }                   /* Too big.  */
184
 
185
 
186
              if (width > bits_available)
187
                {
188
                  /* FIXME-SOMEDAY: backing up and reparsing is wasteful.  */
189
                  input_line_pointer = hold;
190
                  exp.X_add_number = value;
191
                  break;
192
                }
193
 
194
              /* Skip ':'.  */
195
              hold = ++input_line_pointer;
196
 
197
              expression (&exp);
198
              if (exp.X_op != O_constant)
199
                {
200
                  char cache = *input_line_pointer;
201
 
202
                  *input_line_pointer = '\0';
203
                  as_bad (_("field value \"%s\" too complex for a bitfield"), hold);
204
                  *input_line_pointer = cache;
205
                  demand_empty_rest_of_line ();
206
                  return;
207
                }
208
 
209
              value |= ((~(-1 << width) & exp.X_add_number)
210
                        << ((BITS_PER_CHAR * nbytes) - bits_available));
211
 
212
              if ((bits_available -= width) == 0
213
                  || is_it_end_of_statement ()
214
                  || *input_line_pointer != ',')
215
                break;
216
 
217
              hold = ++input_line_pointer;
218
              expression (&exp);
219
            }
220
 
221
          exp.X_add_number = value;
222
          exp.X_op = O_constant;
223
          exp.X_unsigned = 1;
224
        }
225
 
226
      if ((*(input_line_pointer) == '@') && (*(input_line_pointer +1) == 'c'))
227
        code_label = 1;
228
      emit_expr (&exp, (unsigned int) nbytes);
229
      ++c;
230
      if ((*(input_line_pointer) == '@') && (*(input_line_pointer +1) == 'c'))
231
        {
232
          input_line_pointer +=3;
233
          break;
234
        }
235
    }
236
  while ((*input_line_pointer++ == ','));
237
 
238
  /* Put terminator back into stream.  */
239
  input_line_pointer--;
240
 
241
  demand_empty_rest_of_line ();
242
}
243
 
244
/* This table describes all the machine specific pseudo-ops
245
   the assembler has to support.  The fields are:
246
   *** Pseudo-op name without dot.
247
   *** Function to call to execute this pseudo-op.
248
   *** Integer arg to pass to the function.  */
249
 
250
const pseudo_typeS md_pseudo_table[] =
251
{
252
  /* In CR16 machine, align is in bytes (not a ptwo boundary).  */
253
  {"align", s_align_bytes, 0},
254
  {"long", l_cons,  4 },
255
  {"4byte", l_cons, 4 },
256
  {0, 0, 0}
257
};
258
 
259
/* CR16 relaxation table.  */
260
const relax_typeS md_relax_table[] =
261
{
262
  /* bCC  */
263
  {0x7f, -0x80, 2, 1},                  /*  8 */
264
  {0xfffe, -0x10000, 4, 2},             /* 16 */
265
  {0xfffffe, -0x1000000, 6, 0},         /* 24 */
266
};
267
 
268
/* Return the bit size for a given operand.  */
269
 
270
static int
271
get_opbits (operand_type op)
272
{
273
  if (op < MAX_OPRD)
274
    return cr16_optab[op].bit_size;
275
 
276
  return 0;
277
}
278
 
279
/* Return the argument type of a given operand.  */
280
 
281
static argtype
282
get_optype (operand_type op)
283
{
284
  if (op < MAX_OPRD)
285
    return cr16_optab[op].arg_type;
286
  else
287
    return nullargs;
288
}
289
 
290
/* Return the flags of a given operand.  */
291
 
292
static int
293
get_opflags (operand_type op)
294
{
295
  if (op < MAX_OPRD)
296
    return cr16_optab[op].flags;
297
 
298
  return 0;
299
}
300
 
301
/* Get the cc code.  */
302
 
303
static int
304
get_cc (char *cc_name)
305
{
306
   unsigned int i;
307
 
308
   for (i = 0; i < cr16_num_cc; i++)
309
     if (strcmp (cc_name, cr16_b_cond_tab[i]) == 0)
310
       return i;
311
 
312
   return -1;
313
}
314
 
315
/* Get the core processor register 'reg_name'.  */
316
 
317
static reg
318
get_register (char *reg_name)
319
{
320
  const reg_entry *reg;
321
 
322
  reg = (const reg_entry *) hash_find (reg_hash, reg_name);
323
 
324
  if (reg != NULL)
325
    return reg->value.reg_val;
326
 
327
  return nullregister;
328
}
329
/* Get the core processor register-pair 'reg_name'.  */
330
 
331
static reg
332
get_register_pair (char *reg_name)
333
{
334
  const reg_entry *reg;
335
  char tmp_rp[16]="\0";
336
 
337
  /* Add '(' and ')' to the reg pair, if its not present.  */
338
  if (reg_name[0] != '(')
339
    {
340
      tmp_rp[0] = '(';
341
      strcat (tmp_rp, reg_name);
342
      strcat (tmp_rp,")");
343
      reg = (const reg_entry *) hash_find (regp_hash, tmp_rp);
344
    }
345
  else
346
    reg = (const reg_entry *) hash_find (regp_hash, reg_name);
347
 
348
  if (reg != NULL)
349
    return reg->value.reg_val;
350
 
351
  return nullregister;
352
}
353
 
354
/* Get the index register 'reg_name'.  */
355
 
356
static reg
357
get_index_register (char *reg_name)
358
{
359
  const reg_entry *reg;
360
 
361
  reg = (const reg_entry *) hash_find (reg_hash, reg_name);
362
 
363
  if ((reg != NULL)
364
      && ((reg->value.reg_val == 12) || (reg->value.reg_val == 13)))
365
    return reg->value.reg_val;
366
 
367
  return nullregister;
368
}
369
/* Get the core processor index register-pair 'reg_name'.  */
370
 
371
static reg
372
get_index_register_pair (char *reg_name)
373
{
374
  const reg_entry *reg;
375
 
376
  reg = (const reg_entry *) hash_find (regp_hash, reg_name);
377
 
378
  if (reg != NULL)
379
    {
380
      if ((reg->value.reg_val != 1) || (reg->value.reg_val != 7)
381
          || (reg->value.reg_val != 9) || (reg->value.reg_val > 10))
382
        return reg->value.reg_val;
383
 
384
      as_bad (_("Unknown register pair - index relative mode: `%d'"), reg->value.reg_val);
385
    }
386
 
387
  return nullregister;
388
}
389
 
390
/* Get the processor register 'preg_name'.  */
391
 
392
static preg
393
get_pregister (char *preg_name)
394
{
395
  const reg_entry *preg;
396
 
397
  preg = (const reg_entry *) hash_find (preg_hash, preg_name);
398
 
399
  if (preg != NULL)
400
    return preg->value.preg_val;
401
 
402
  return nullpregister;
403
}
404
 
405
/* Get the processor register 'preg_name 32 bit'.  */
406
 
407
static preg
408
get_pregisterp (char *preg_name)
409
{
410
  const reg_entry *preg;
411
 
412
  preg = (const reg_entry *) hash_find (pregp_hash, preg_name);
413
 
414
  if (preg != NULL)
415
    return preg->value.preg_val;
416
 
417
  return nullpregister;
418
}
419
 
420
 
421
/* Round up a section size to the appropriate boundary.  */
422
 
423
valueT
424
md_section_align (segT seg, valueT val)
425
{
426
  /* Round .text section to a multiple of 2.  */
427
  if (seg == text_section)
428
    return (val + 1) & ~1;
429
  return val;
430
}
431
 
432
/* Parse an operand that is machine-specific (remove '*').  */
433
 
434
void
435
md_operand (expressionS * exp)
436
{
437
  char c = *input_line_pointer;
438
 
439
  switch (c)
440
    {
441
    case '*':
442
      input_line_pointer++;
443
      expression (exp);
444
      break;
445
    default:
446
      break;
447
    }
448
}
449
 
450
/* Reset global variables before parsing a new instruction.  */
451
 
452
static void
453
reset_vars (char *op)
454
{
455
  cur_arg_num = relocatable = 0;
456
  memset (& output_opcode, '\0', sizeof (output_opcode));
457
 
458
  /* Save a copy of the original OP (used in error messages).  */
459
  strncpy (ins_parse, op, sizeof ins_parse - 1);
460
  ins_parse [sizeof ins_parse - 1] = 0;
461
}
462
 
463
/* This macro decides whether a particular reloc is an entry in a
464
   switch table.  It is used when relaxing, because the linker needs
465
   to know about all such entries so that it can adjust them if
466
   necessary.  */
467
 
468
#define SWITCH_TABLE(fix)                                  \
469
  (   (fix)->fx_addsy != NULL                              \
470
   && (fix)->fx_subsy != NULL                              \
471
   && S_GET_SEGMENT ((fix)->fx_addsy) ==                   \
472
      S_GET_SEGMENT ((fix)->fx_subsy)                      \
473
   && S_GET_SEGMENT (fix->fx_addsy) != undefined_section   \
474
   && (   (fix)->fx_r_type == BFD_RELOC_CR16_NUM8          \
475
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM16         \
476
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM32         \
477
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM32a))
478
 
479
/* See whether we need to force a relocation into the output file.
480
   This is used to force out switch and PC relative relocations when
481
   relaxing.  */
482
 
483
int
484
cr16_force_relocation (fixS *fix)
485
{
486
  if (generic_force_reloc (fix) || SWITCH_TABLE (fix))
487
    return 1;
488
 
489
  return 0;
490
}
491
 
492
/* Record a fixup for a cons expression.  */
493
 
494
void
495
cr16_cons_fix_new (fragS *frag, int offset, int len, expressionS *exp)
496
{
497
  int rtype = BFD_RELOC_UNUSED;
498
 
499
  switch (len)
500
    {
501
    default: rtype = BFD_RELOC_NONE; break;
502
    case 1: rtype = BFD_RELOC_CR16_NUM8 ; break;
503
    case 2: rtype = BFD_RELOC_CR16_NUM16; break;
504
    case 4:
505
      if (code_label)
506
        {
507
          rtype = BFD_RELOC_CR16_NUM32a;
508
          code_label = 0;
509
        }
510
      else
511
        rtype = BFD_RELOC_CR16_NUM32;
512
      break;
513
    }
514
 
515
  fix_new_exp (frag, offset, len, exp, 0, rtype);
516
}
517
 
518
/* Generate a relocation entry for a fixup.  */
519
 
520
arelent *
521
tc_gen_reloc (asection *section ATTRIBUTE_UNUSED, fixS * fixP)
522
{
523
  arelent * reloc;
524
  bfd_reloc_code_real_type code;
525
 
526
  /* If symbols are local and resolved, then no relocation needed.  */
527
  if ( ((fixP->fx_addsy)
528
        && (S_GET_SEGMENT (fixP->fx_addsy) == absolute_section))
529
       || ((fixP->fx_subsy)
530
           && (S_GET_SEGMENT (fixP->fx_subsy) == absolute_section)))
531
     return NULL;
532
 
533
  reloc = xmalloc (sizeof (arelent));
534
  reloc->sym_ptr_ptr  = xmalloc (sizeof (asymbol *));
535
  *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixP->fx_addsy);
536
  reloc->address = fixP->fx_frag->fr_address + fixP->fx_where;
537
  reloc->addend = fixP->fx_offset;
538
 
539
  if (fixP->fx_subsy != NULL)
540
    {
541
      if (SWITCH_TABLE (fixP))
542
        {
543
          /* Keep the current difference in the addend.  */
544
          reloc->addend = (S_GET_VALUE (fixP->fx_addsy)
545
                           - S_GET_VALUE (fixP->fx_subsy) + fixP->fx_offset);
546
 
547
          switch (fixP->fx_r_type)
548
            {
549
            case BFD_RELOC_CR16_NUM8:
550
              fixP->fx_r_type = BFD_RELOC_CR16_SWITCH8;
551
              break;
552
            case BFD_RELOC_CR16_NUM16:
553
              fixP->fx_r_type = BFD_RELOC_CR16_SWITCH16;
554
              break;
555
            case BFD_RELOC_CR16_NUM32:
556
              fixP->fx_r_type = BFD_RELOC_CR16_SWITCH32;
557
              break;
558
            case BFD_RELOC_CR16_NUM32a:
559
              fixP->fx_r_type = BFD_RELOC_CR16_NUM32a;
560
              break;
561
            default:
562
              abort ();
563
              break;
564
            }
565
        }
566
      else
567
        {
568
          /* We only resolve difference expressions in the same section.  */
569
          as_bad_where (fixP->fx_file, fixP->fx_line,
570
                        _("can't resolve `%s' {%s section} - `%s' {%s section}"),
571
                        fixP->fx_addsy ? S_GET_NAME (fixP->fx_addsy) : "0",
572
                        segment_name (fixP->fx_addsy
573
                                      ? S_GET_SEGMENT (fixP->fx_addsy)
574
                                      : absolute_section),
575
                        S_GET_NAME (fixP->fx_subsy),
576
                        segment_name (S_GET_SEGMENT (fixP->fx_addsy)));
577
        }
578
    }
579
#ifdef OBJ_ELF
580
      if ((fixP->fx_r_type == BFD_RELOC_CR16_GOT_REGREL20)
581
           && GOT_symbol
582
           && fixP->fx_addsy == GOT_symbol)
583
        {
584
            code = BFD_RELOC_CR16_GOT_REGREL20;
585
            reloc->addend = fixP->fx_offset = reloc->address;
586
        }
587
      else if ((fixP->fx_r_type == BFD_RELOC_CR16_GOTC_REGREL20)
588
           && GOT_symbol
589
           && fixP->fx_addsy == GOT_symbol)
590
        {
591
            code = BFD_RELOC_CR16_GOTC_REGREL20;
592
            reloc->addend = fixP->fx_offset = reloc->address;
593
        }
594
#endif
595
 
596
  gas_assert ((int) fixP->fx_r_type > 0);
597
  reloc->howto = bfd_reloc_type_lookup (stdoutput, fixP->fx_r_type);
598
 
599
  if (reloc->howto == NULL)
600
    {
601
      as_bad_where (fixP->fx_file, fixP->fx_line,
602
                    _("internal error: reloc %d (`%s') not supported by object file format"),
603
                    fixP->fx_r_type,
604
                    bfd_get_reloc_code_name (fixP->fx_r_type));
605
      return NULL;
606
    }
607
  gas_assert (!fixP->fx_pcrel == !reloc->howto->pc_relative);
608
 
609
  return reloc;
610
}
611
 
612
/* Prepare machine-dependent frags for relaxation.  */
613
 
614
int
615
md_estimate_size_before_relax (fragS *fragp, asection *seg)
616
{
617
  /* If symbol is undefined or located in a different section,
618
     select the largest supported relocation.  */
619
  relax_substateT subtype;
620
  relax_substateT rlx_state[] = {0, 2};
621
 
622
  for (subtype = 0; subtype < ARRAY_SIZE (rlx_state); subtype += 2)
623
    {
624
      if (fragp->fr_subtype == rlx_state[subtype]
625
          && (!S_IS_DEFINED (fragp->fr_symbol)
626
              || seg != S_GET_SEGMENT (fragp->fr_symbol)))
627
        {
628
          fragp->fr_subtype = rlx_state[subtype + 1];
629
          break;
630
        }
631
    }
632
 
633
  if (fragp->fr_subtype >= ARRAY_SIZE (md_relax_table))
634
    abort ();
635
 
636
  return md_relax_table[fragp->fr_subtype].rlx_length;
637
}
638
 
639
void
640
md_convert_frag (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, fragS *fragP)
641
{
642
  /* 'opcode' points to the start of the instruction, whether
643
     we need to change the instruction's fixed encoding.  */
644
  char *opcode = fragP->fr_literal + fragP->fr_fix;
645
  bfd_reloc_code_real_type reloc;
646
 
647
  subseg_change (sec, 0);
648
 
649
  switch (fragP->fr_subtype)
650
    {
651
    case 0:
652
      reloc = BFD_RELOC_CR16_DISP8;
653
      break;
654
    case 1:
655
      /* If the subtype is not changed due to :m operand qualifier,
656
         then no need to update the opcode value.  */
657
      if ((int)opcode[1] != 0x18)
658
        {
659
          opcode[0] = (opcode[0] & 0xf0);
660
          opcode[1] = 0x18;
661
        }
662
      reloc = BFD_RELOC_CR16_DISP16;
663
      break;
664
    case 2:
665
      /* If the subtype is not changed due to :l operand qualifier,
666
         then no need to update the opcode value.  */
667
      if ((int)opcode[1] != 0)
668
        {
669
          opcode[2] = opcode[0];
670
          opcode[0] = opcode[1];
671
          opcode[1] = 0x0;
672
        }
673
      reloc = BFD_RELOC_CR16_DISP24;
674
      break;
675
    default:
676
      abort();
677
    }
678
 
679
  fix_new (fragP, fragP->fr_fix,
680
           bfd_get_reloc_size (bfd_reloc_type_lookup (stdoutput, reloc)),
681
           fragP->fr_symbol, fragP->fr_offset, 1, reloc);
682
  fragP->fr_var = 0;
683
  fragP->fr_fix += md_relax_table[fragP->fr_subtype].rlx_length;
684
}
685
 
686
symbolS *
687
md_undefined_symbol (char *name)
688
{
689
  if (*name == '_' && *(name + 1) == 'G'
690
      && strcmp (name, "_GLOBAL_OFFSET_TABLE_") == 0)
691
   {
692
     if (!GOT_symbol)
693
       {
694
         if (symbol_find (name))
695
             as_bad (_("GOT already in symbol table"));
696
          GOT_symbol = symbol_new (name, undefined_section,
697
                                   (valueT) 0, &zero_address_frag);
698
       }
699
     return GOT_symbol;
700
   }
701
  return 0;
702
}
703
 
704
/* Process machine-dependent command line options.  Called once for
705
   each option on the command line that the machine-independent part of
706
   GAS does not understand.  */
707
 
708
int
709
md_parse_option (int c ATTRIBUTE_UNUSED, char *arg ATTRIBUTE_UNUSED)
710
{
711
  return 0;
712
}
713
 
714
/* Machine-dependent usage-output.  */
715
 
716
void
717
md_show_usage (FILE *stream ATTRIBUTE_UNUSED)
718
{
719
  return;
720
}
721
 
722
char *
723
md_atof (int type, char *litP, int *sizeP)
724
{
725
  return ieee_md_atof (type, litP, sizeP, target_big_endian);
726
}
727
 
728
/* Apply a fixS (fixup of an instruction or data that we didn't have
729
   enough info to complete immediately) to the data in a frag.
730
   Since linkrelax is nonzero and TC_LINKRELAX_FIXUP is defined to disable
731
   relaxation of debug sections, this function is called only when
732
   fixuping relocations of debug sections.  */
733
 
734
void
735
md_apply_fix (fixS *fixP, valueT *valP, segT seg)
736
{
737
  valueT val = * valP;
738
 
739
  if (fixP->fx_addsy == NULL
740
      && fixP->fx_pcrel == 0)
741
    fixP->fx_done = 1;
742
  else if (fixP->fx_pcrel == 1
743
      && fixP->fx_addsy != NULL
744
      && S_GET_SEGMENT (fixP->fx_addsy) == seg)
745
    fixP->fx_done = 1;
746
  else
747
    fixP->fx_done = 0;
748
 
749
  if (fixP->fx_addsy != NULL && !fixP->fx_pcrel)
750
    {
751
      val = fixP->fx_offset;
752
      fixP->fx_done = 1;
753
    }
754
 
755
  if (fixP->fx_done)
756
    {
757
      char *buf = fixP->fx_frag->fr_literal + fixP->fx_where;
758
 
759
      fixP->fx_offset = 0;
760
 
761
      switch (fixP->fx_r_type)
762
        {
763
        case BFD_RELOC_CR16_NUM8:
764
          bfd_put_8 (stdoutput, (unsigned char) val, buf);
765
          break;
766
        case BFD_RELOC_CR16_NUM16:
767
          bfd_put_16 (stdoutput, val, buf);
768
          break;
769
        case BFD_RELOC_CR16_NUM32:
770
          bfd_put_32 (stdoutput, val, buf);
771
          break;
772
        case BFD_RELOC_CR16_NUM32a:
773
          bfd_put_32 (stdoutput, val, buf);
774
          break;
775
        default:
776
          /* We shouldn't ever get here because linkrelax is nonzero.  */
777
          abort ();
778
          break;
779
        }
780
      fixP->fx_done = 0;
781
    }
782
  else
783
    fixP->fx_offset = * valP;
784
}
785
 
786
/* The location from which a PC relative jump should be calculated,
787
   given a PC relative reloc.  */
788
 
789
long
790
md_pcrel_from (fixS *fixp)
791
{
792
  return fixp->fx_frag->fr_address + fixp->fx_where;
793
}
794
 
795
static void
796
initialise_reg_hash_table (struct hash_control ** hash_table,
797
                           const reg_entry * register_table,
798
                           const unsigned int num_entries)
799
{
800
  const reg_entry * reg;
801
  const char *hashret;
802
 
803
  if ((* hash_table = hash_new ()) == NULL)
804
    as_fatal (_("Virtual memory exhausted"));
805
 
806
  for (reg = register_table;
807
       reg < (register_table + num_entries);
808
       reg++)
809
    {
810
      hashret = hash_insert (* hash_table, reg->name, (char *) reg);
811
      if (hashret)
812
        as_fatal (_("Internal Error:  Can't hash %s: %s"),
813
                  reg->name, hashret);
814
    }
815
}
816
 
817
/* This function is called once, at assembler startup time.  This should
818
   set up all the tables, etc that the MD part of the assembler needs.  */
819
 
820
void
821
md_begin (void)
822
{
823
  int i = 0;
824
 
825
  /* Set up a hash table for the instructions.  */
826
  if ((cr16_inst_hash = hash_new ()) == NULL)
827
    as_fatal (_("Virtual memory exhausted"));
828
 
829
  while (cr16_instruction[i].mnemonic != NULL)
830
    {
831
      const char *hashret;
832
      const char *mnemonic = cr16_instruction[i].mnemonic;
833
 
834
      hashret = hash_insert (cr16_inst_hash, mnemonic,
835
                             (char *)(cr16_instruction + i));
836
 
837
      if (hashret != NULL && *hashret != '\0')
838
        as_fatal (_("Can't hash `%s': %s\n"), cr16_instruction[i].mnemonic,
839
                  *hashret == 0 ? _("(unknown reason)") : hashret);
840
 
841
      /* Insert unique names into hash table.  The CR16 instruction set
842
         has many identical opcode names that have different opcodes based
843
         on the operands.  This hash table then provides a quick index to
844
         the first opcode with a particular name in the opcode table.  */
845
      do
846
        {
847
          ++i;
848
        }
849
      while (cr16_instruction[i].mnemonic != NULL
850
             && streq (cr16_instruction[i].mnemonic, mnemonic));
851
    }
852
 
853
  /* Initialize reg_hash hash table.  */
854
  initialise_reg_hash_table (& reg_hash, cr16_regtab, NUMREGS);
855
  /* Initialize regp_hash hash table.  */
856
  initialise_reg_hash_table (& regp_hash, cr16_regptab, NUMREGPS);
857
  /* Initialize preg_hash hash table.  */
858
  initialise_reg_hash_table (& preg_hash, cr16_pregtab, NUMPREGS);
859
  /* Initialize pregp_hash hash table.  */
860
  initialise_reg_hash_table (& pregp_hash, cr16_pregptab, NUMPREGPS);
861
 
862
  /*  Set linkrelax here to avoid fixups in most sections.  */
863
  linkrelax = 1;
864
}
865
 
866
/* Process constants (immediate/absolute)
867
   and labels (jump targets/Memory locations).  */
868
 
869
static void
870
process_label_constant (char *str, ins * cr16_ins)
871
{
872
  char *saved_input_line_pointer;
873
  int symbol_with_at = 0;
874
  int symbol_with_s = 0;
875
  int symbol_with_m = 0;
876
  int symbol_with_l = 0;
877
  int symbol_with_at_got = 0;
878
  int symbol_with_at_gotc = 0;
879
  argument *cur_arg = cr16_ins->arg + cur_arg_num;  /* Current argument.  */
880
 
881
  saved_input_line_pointer = input_line_pointer;
882
  input_line_pointer = str;
883
 
884
  expression (&cr16_ins->exp);
885
 
886
  switch (cr16_ins->exp.X_op)
887
    {
888
    case O_big:
889
    case O_absent:
890
      /* Missing or bad expr becomes absolute 0.  */
891
      as_bad (_("missing or invalid displacement expression `%s' taken as 0"),
892
              str);
893
      cr16_ins->exp.X_op = O_constant;
894
      cr16_ins->exp.X_add_number = 0;
895
      cr16_ins->exp.X_add_symbol = NULL;
896
      cr16_ins->exp.X_op_symbol = NULL;
897
      /* Fall through.  */
898
 
899
    case O_constant:
900
      cur_arg->X_op = O_constant;
901
      cur_arg->constant = cr16_ins->exp.X_add_number;
902
      break;
903
 
904
    case O_symbol:
905
    case O_subtract:
906
    case O_add:
907
      cur_arg->X_op = O_symbol;
908
      cur_arg->constant = cr16_ins->exp.X_add_number;
909
      cr16_ins->exp.X_add_number = 0;
910
      cr16_ins->rtype = BFD_RELOC_NONE;
911
      relocatable = 1;
912
 
913
      if (strneq (input_line_pointer, "@c", 2))
914
        symbol_with_at = 1;
915
 
916
      if (strneq (input_line_pointer, "@l", 2)
917
          || strneq (input_line_pointer, ":l", 2))
918
        symbol_with_l = 1;
919
 
920
      if (strneq (input_line_pointer, "@m", 2)
921
          || strneq (input_line_pointer, ":m", 2))
922
        symbol_with_m = 1;
923
 
924
      if (strneq (input_line_pointer, "@s", 2)
925
          || strneq (input_line_pointer, ":s", 2))
926
        symbol_with_s = 1;
927
 
928
      if (strneq (input_line_pointer, "@cGOT", 5)
929
          || strneq (input_line_pointer, "@cgot", 5))
930
        {
931
          if (GOT_symbol == NULL)
932
           GOT_symbol = symbol_find_or_make (GLOBAL_OFFSET_TABLE_NAME);
933
 
934
          symbol_with_at_gotc = 1;
935
        }
936
      else if (strneq (input_line_pointer, "@GOT", 4)
937
          || strneq (input_line_pointer, "@got", 4))
938
        {
939
          if ((strneq (input_line_pointer, "+", 1))
940
               || (strneq (input_line_pointer, "-", 1)))
941
           as_warn (_("GOT bad expression with %s."), input_line_pointer);
942
 
943
          if (GOT_symbol == NULL)
944
           GOT_symbol = symbol_find_or_make (GLOBAL_OFFSET_TABLE_NAME);
945
 
946
          symbol_with_at_got = 1;
947
        }
948
 
949
      switch (cur_arg->type)
950
        {
951
        case arg_cr:
952
          if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
953
            {
954
              if (symbol_with_at_got)
955
                  cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
956
              else if (symbol_with_at_gotc)
957
                  cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
958
              else if (cur_arg->size == 20)
959
                cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
960
              else
961
                cr16_ins->rtype = BFD_RELOC_CR16_REGREL20a;
962
            }
963
          break;
964
 
965
        case arg_crp:
966
          if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
967
           {
968
            if (symbol_with_at_got)
969
              cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
970
            else if (symbol_with_at_gotc)
971
              cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
972
           } else {
973
            switch (instruction->size)
974
              {
975
              case 1:
976
                switch (cur_arg->size)
977
                  {
978
                  case 0:
979
                    cr16_ins->rtype = BFD_RELOC_CR16_REGREL0;
980
                    break;
981
                  case 4:
982
                    if (IS_INSN_MNEMONIC ("loadb") || IS_INSN_MNEMONIC ("storb"))
983
                      cr16_ins->rtype = BFD_RELOC_CR16_REGREL4;
984
                    else
985
                      cr16_ins->rtype = BFD_RELOC_CR16_REGREL4a;
986
                    break;
987
                  default: break;
988
                  }
989
                break;
990
              case 2:
991
                cr16_ins->rtype = BFD_RELOC_CR16_REGREL16;
992
                break;
993
              case 3:
994
                if (cur_arg->size == 20)
995
                  cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
996
                else
997
                  cr16_ins->rtype = BFD_RELOC_CR16_REGREL20a;
998
                break;
999
              default:
1000
                break;
1001
              }
1002
            }
1003
          break;
1004
 
1005
        case arg_idxr:
1006
          if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
1007
            {
1008
              if (symbol_with_at_got)
1009
                cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
1010
              else if (symbol_with_at_gotc)
1011
                cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
1012
              else
1013
                cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
1014
            }
1015
          break;
1016
 
1017
        case arg_idxrp:
1018
          if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
1019
            {
1020
            if (symbol_with_at_got)
1021
              cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
1022
            else if (symbol_with_at_gotc)
1023
              cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
1024
            else {
1025
            switch (instruction->size)
1026
              {
1027
              case 1: cr16_ins->rtype = BFD_RELOC_CR16_REGREL0; break;
1028
              case 2: cr16_ins->rtype = BFD_RELOC_CR16_REGREL14; break;
1029
              case 3: cr16_ins->rtype = BFD_RELOC_CR16_REGREL20; break;
1030
              default: break;
1031
              }
1032
            }
1033
           }
1034
          break;
1035
 
1036
        case arg_c:
1037
          if (IS_INSN_MNEMONIC ("bal"))
1038
            cr16_ins->rtype = BFD_RELOC_CR16_DISP24;
1039
          else if (IS_INSN_TYPE (BRANCH_INS))
1040
            {
1041
              if (symbol_with_l)
1042
                cr16_ins->rtype = BFD_RELOC_CR16_DISP24;
1043
              else if (symbol_with_m)
1044
                cr16_ins->rtype = BFD_RELOC_CR16_DISP16;
1045
              else
1046
                cr16_ins->rtype = BFD_RELOC_CR16_DISP8;
1047
            }
1048
          else if (IS_INSN_TYPE (STOR_IMM_INS) || IS_INSN_TYPE (LD_STOR_INS)
1049
                   || IS_INSN_TYPE (CSTBIT_INS))
1050
            {
1051
              if (symbol_with_s)
1052
                as_bad (_("operand %d: illegal use expression: `%s`"), cur_arg_num + 1, str);
1053
              if (symbol_with_at_got)
1054
                cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
1055
              else if (symbol_with_at_gotc)
1056
                cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
1057
              else if (symbol_with_m)
1058
                cr16_ins->rtype = BFD_RELOC_CR16_ABS20;
1059
              else /* Default to (symbol_with_l) */
1060
                cr16_ins->rtype = BFD_RELOC_CR16_ABS24;
1061
            }
1062
          else if (IS_INSN_TYPE (BRANCH_NEQ_INS))
1063
            cr16_ins->rtype = BFD_RELOC_CR16_DISP4;
1064
          break;
1065
 
1066
        case arg_ic:
1067
          if (IS_INSN_TYPE (ARITH_INS))
1068
            {
1069
              if (symbol_with_at_got)
1070
                cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
1071
              else if (symbol_with_at_gotc)
1072
                cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
1073
              else if (symbol_with_s)
1074
                cr16_ins->rtype = BFD_RELOC_CR16_IMM4;
1075
              else if (symbol_with_m)
1076
                cr16_ins->rtype = BFD_RELOC_CR16_IMM20;
1077
              else if (symbol_with_at)
1078
                cr16_ins->rtype = BFD_RELOC_CR16_IMM32a;
1079
              else /* Default to (symbol_with_l) */
1080
                cr16_ins->rtype = BFD_RELOC_CR16_IMM32;
1081
            }
1082
          else if (IS_INSN_TYPE (ARITH_BYTE_INS))
1083
            {
1084
              cr16_ins->rtype = BFD_RELOC_CR16_IMM16;
1085
            }
1086
          break;
1087
        default:
1088
          break;
1089
        }
1090
      break;
1091
 
1092
    default:
1093
      cur_arg->X_op = cr16_ins->exp.X_op;
1094
      break;
1095
    }
1096
 
1097
  input_line_pointer = saved_input_line_pointer;
1098
  return;
1099
}
1100
 
1101
/* Retrieve the opcode image of a given register.
1102
   If the register is illegal for the current instruction,
1103
   issue an error.  */
1104
 
1105
static int
1106
getreg_image (reg r)
1107
{
1108
  const reg_entry *reg;
1109
  char *reg_name;
1110
  int is_procreg = 0; /* Nonzero means argument should be processor reg.  */
1111
 
1112
  /* Check whether the register is in registers table.  */
1113
  if (r < MAX_REG)
1114
    reg = cr16_regtab + r;
1115
  else /* Register not found.  */
1116
    {
1117
      as_bad (_("Unknown register: `%d'"), r);
1118
      return 0;
1119
    }
1120
 
1121
  reg_name = reg->name;
1122
 
1123
/* Issue a error message when register is illegal.  */
1124
#define IMAGE_ERR \
1125
  as_bad (_("Illegal register (`%s') in Instruction: `%s'"), \
1126
            reg_name, ins_parse);                            \
1127
  break;
1128
 
1129
  switch (reg->type)
1130
    {
1131
    case CR16_R_REGTYPE:
1132
      if (! is_procreg)
1133
        return reg->image;
1134
      else
1135
        IMAGE_ERR;
1136
 
1137
    case CR16_P_REGTYPE:
1138
      return reg->image;
1139
      break;
1140
 
1141
    default:
1142
      IMAGE_ERR;
1143
    }
1144
 
1145
  return 0;
1146
}
1147
 
1148
/* Parsing different types of operands
1149
   -> constants             Immediate/Absolute/Relative numbers
1150
   -> Labels                Relocatable symbols
1151
   -> (reg pair base)       Register pair base
1152
   -> (rbase)               Register base
1153
   -> disp(rbase)           Register relative
1154
   -> [rinx]disp(reg pair)  Register index with reg pair mode
1155
   -> disp(rbase,ridx,scl)  Register index mode.  */
1156
 
1157
static void
1158
set_operand (char *operand, ins * cr16_ins)
1159
{
1160
  char *operandS; /* Pointer to start of sub-opearand.  */
1161
  char *operandE; /* Pointer to end of sub-opearand.  */
1162
 
1163
  argument *cur_arg = &cr16_ins->arg[cur_arg_num]; /* Current argument.  */
1164
 
1165
  /* Initialize pointers.  */
1166
  operandS = operandE = operand;
1167
 
1168
  switch (cur_arg->type)
1169
    {
1170
    case arg_ic:    /* Case $0x18.  */
1171
      operandS++;
1172
    case arg_c:     /* Case 0x18.  */
1173
      /* Set constant.  */
1174
      process_label_constant (operandS, cr16_ins);
1175
 
1176
      if (cur_arg->type != arg_ic)
1177
        cur_arg->type = arg_c;
1178
      break;
1179
 
1180
    case arg_icr:   /* Case $0x18(r1).  */
1181
      operandS++;
1182
    case arg_cr:    /* Case 0x18(r1).   */
1183
      /* Set displacement constant.  */
1184
      while (*operandE != '(')
1185
        operandE++;
1186
      *operandE = '\0';
1187
      process_label_constant (operandS, cr16_ins);
1188
      operandS = operandE;
1189
    case arg_rbase: /* Case (r1) or (r1,r0).  */
1190
      operandS++;
1191
      /* Set register base.  */
1192
      while (*operandE != ')')
1193
        operandE++;
1194
      *operandE = '\0';
1195
      if ((cur_arg->r = get_register (operandS)) == nullregister)
1196
         as_bad (_("Illegal register `%s' in Instruction `%s'"),
1197
              operandS, ins_parse);
1198
 
1199
      /* set the arg->rp, if reg is "r12" or "r13" or "14" or "15" */
1200
      if ((cur_arg->type != arg_rbase)
1201
          && ((getreg_image (cur_arg->r) == 12)
1202
              || (getreg_image (cur_arg->r) == 13)
1203
              || (getreg_image (cur_arg->r) == 14)
1204
              || (getreg_image (cur_arg->r) == 15)))
1205
         {
1206
           cur_arg->type = arg_crp;
1207
           cur_arg->rp = cur_arg->r;
1208
         }
1209
      break;
1210
 
1211
    case arg_crp:    /* Case 0x18(r1,r0).   */
1212
      /* Set displacement constant.  */
1213
      while (*operandE != '(')
1214
        operandE++;
1215
      *operandE = '\0';
1216
      process_label_constant (operandS, cr16_ins);
1217
      operandS = operandE;
1218
      operandS++;
1219
      /* Set register pair base.  */
1220
      while (*operandE != ')')
1221
        operandE++;
1222
      *operandE = '\0';
1223
      if ((cur_arg->rp = get_register_pair (operandS)) == nullregister)
1224
         as_bad (_("Illegal register pair `%s' in Instruction `%s'"),
1225
              operandS, ins_parse);
1226
      break;
1227
 
1228
    case arg_idxr:
1229
      /* Set register pair base.  */
1230
      if ((strchr (operandS,'(') != NULL))
1231
        {
1232
         while ((*operandE != '(') && (! ISSPACE (*operandE)))
1233
           operandE++;
1234
         if ((cur_arg->rp = get_index_register_pair (operandE)) == nullregister)
1235
              as_bad (_("Illegal register pair `%s' in Instruction `%s'"),
1236
                            operandS, ins_parse);
1237
         *operandE++ = '\0';
1238
         cur_arg->type = arg_idxrp;
1239
        }
1240
      else
1241
        cur_arg->rp = -1;
1242
 
1243
       operandE = operandS;
1244
      /* Set displacement constant.  */
1245
      while (*operandE != ']')
1246
        operandE++;
1247
      process_label_constant (++operandE, cr16_ins);
1248
      *operandE++ = '\0';
1249
      operandE = operandS;
1250
 
1251
      /* Set index register .  */
1252
      operandS = strchr (operandE,'[');
1253
      if (operandS != NULL)
1254
        { /* Eliminate '[', detach from rest of operand.  */
1255
          *operandS++ = '\0';
1256
 
1257
          operandE = strchr (operandS, ']');
1258
 
1259
          if (operandE == NULL)
1260
            as_bad (_("unmatched '['"));
1261
          else
1262
            { /* Eliminate ']' and make sure it was the last thing
1263
                 in the string.  */
1264
              *operandE = '\0';
1265
              if (*(operandE + 1) != '\0')
1266
                as_bad (_("garbage after index spec ignored"));
1267
            }
1268
        }
1269
 
1270
      if ((cur_arg->i_r = get_index_register (operandS)) == nullregister)
1271
        as_bad (_("Illegal register `%s' in Instruction `%s'"),
1272
                operandS, ins_parse);
1273
      *operandE = '\0';
1274
      *operandS = '\0';
1275
      break;
1276
 
1277
    default:
1278
      break;
1279
    }
1280
}
1281
 
1282
/* Parse a single operand.
1283
   operand - Current operand to parse.
1284
   cr16_ins - Current assembled instruction.  */
1285
 
1286
static void
1287
parse_operand (char *operand, ins * cr16_ins)
1288
{
1289
  int ret_val;
1290
  argument *cur_arg = cr16_ins->arg + cur_arg_num; /* Current argument.  */
1291
 
1292
  /* Initialize the type to NULL before parsing.  */
1293
  cur_arg->type = nullargs;
1294
 
1295
  /* Check whether this is a condition code .  */
1296
  if ((IS_INSN_MNEMONIC ("b")) && ((ret_val = get_cc (operand)) != -1))
1297
    {
1298
      cur_arg->type = arg_cc;
1299
      cur_arg->cc = ret_val;
1300
      cur_arg->X_op = O_register;
1301
      return;
1302
    }
1303
 
1304
  /* Check whether this is a general processor register.  */
1305
  if ((ret_val = get_register (operand)) != nullregister)
1306
    {
1307
      cur_arg->type = arg_r;
1308
      cur_arg->r = ret_val;
1309
      cur_arg->X_op = 0;
1310
      return;
1311
    }
1312
 
1313
  /* Check whether this is a general processor register pair.  */
1314
  if ((operand[0] == '(')
1315
      && ((ret_val = get_register_pair (operand)) != nullregister))
1316
    {
1317
      cur_arg->type = arg_rp;
1318
      cur_arg->rp = ret_val;
1319
      cur_arg->X_op = O_register;
1320
      return;
1321
    }
1322
 
1323
  /* Check whether the operand is a processor register.
1324
     For "lprd" and "sprd" instruction, only 32 bit
1325
     processor registers used.  */
1326
  if (!(IS_INSN_MNEMONIC ("lprd") || (IS_INSN_MNEMONIC ("sprd")))
1327
      && ((ret_val = get_pregister (operand)) != nullpregister))
1328
    {
1329
      cur_arg->type = arg_pr;
1330
      cur_arg->pr = ret_val;
1331
      cur_arg->X_op = O_register;
1332
      return;
1333
    }
1334
 
1335
  /* Check whether this is a processor register - 32 bit.  */
1336
  if ((ret_val = get_pregisterp (operand)) != nullpregister)
1337
    {
1338
      cur_arg->type = arg_prp;
1339
      cur_arg->prp = ret_val;
1340
      cur_arg->X_op = O_register;
1341
      return;
1342
    }
1343
 
1344
  /* Deal with special characters.  */
1345
  switch (operand[0])
1346
    {
1347
    case '$':
1348
      if (strchr (operand, '(') != NULL)
1349
        cur_arg->type = arg_icr;
1350
      else
1351
        cur_arg->type = arg_ic;
1352
      goto set_params;
1353
      break;
1354
 
1355
    case '(':
1356
      cur_arg->type = arg_rbase;
1357
      goto set_params;
1358
      break;
1359
 
1360
    case '[':
1361
      cur_arg->type = arg_idxr;
1362
      goto set_params;
1363
      break;
1364
 
1365
    default:
1366
      break;
1367
    }
1368
 
1369
  if (strchr (operand, '(') != NULL)
1370
    {
1371
      if (strchr (operand, ',') != NULL
1372
          && (strchr (operand, ',') > strchr (operand, '(')))
1373
        cur_arg->type = arg_crp;
1374
      else
1375
        cur_arg->type = arg_cr;
1376
    }
1377
  else
1378
    cur_arg->type = arg_c;
1379
 
1380
/* Parse an operand according to its type.  */
1381
 set_params:
1382
  cur_arg->constant = 0;
1383
  set_operand (operand, cr16_ins);
1384
}
1385
 
1386
/* Parse the various operands. Each operand is then analyzed to fillup
1387
   the fields in the cr16_ins data structure.  */
1388
 
1389
static void
1390
parse_operands (ins * cr16_ins, char *operands)
1391
{
1392
  char *operandS;            /* Operands string.  */
1393
  char *operandH, *operandT; /* Single operand head/tail pointers.  */
1394
  int allocated = 0;         /* Indicates a new operands string was allocated.*/
1395
  char *operand[MAX_OPERANDS];/* Separating the operands.  */
1396
  int op_num = 0;             /* Current operand number we are parsing.  */
1397
  int bracket_flag = 0;       /* Indicates a bracket '(' was found.  */
1398
  int sq_bracket_flag = 0;    /* Indicates a square bracket '[' was found.  */
1399
 
1400
  /* Preprocess the list of registers, if necessary.  */
1401
  operandS = operandH = operandT = operands;
1402
 
1403
  while (*operandT != '\0')
1404
    {
1405
      if (*operandT == ',' && bracket_flag != 1 && sq_bracket_flag != 1)
1406
        {
1407
          *operandT++ = '\0';
1408
          operand[op_num++] = strdup (operandH);
1409
          operandH = operandT;
1410
          continue;
1411
        }
1412
 
1413
      if (*operandT == ' ')
1414
        as_bad (_("Illegal operands (whitespace): `%s'"), ins_parse);
1415
 
1416
      if (*operandT == '(')
1417
        bracket_flag = 1;
1418
      else if (*operandT == '[')
1419
        sq_bracket_flag = 1;
1420
 
1421
      if (*operandT == ')')
1422
        {
1423
          if (bracket_flag)
1424
            bracket_flag = 0;
1425
          else
1426
            as_fatal (_("Missing matching brackets : `%s'"), ins_parse);
1427
        }
1428
      else if (*operandT == ']')
1429
        {
1430
          if (sq_bracket_flag)
1431
            sq_bracket_flag = 0;
1432
          else
1433
            as_fatal (_("Missing matching brackets : `%s'"), ins_parse);
1434
        }
1435
 
1436
      if (bracket_flag == 1 && *operandT == ')')
1437
        bracket_flag = 0;
1438
      else if (sq_bracket_flag == 1 && *operandT == ']')
1439
        sq_bracket_flag = 0;
1440
 
1441
      operandT++;
1442
    }
1443
 
1444
  /* Adding the last operand.  */
1445
  operand[op_num++] = strdup (operandH);
1446
  cr16_ins->nargs = op_num;
1447
 
1448
  /* Verifying correct syntax of operands (all brackets should be closed).  */
1449
  if (bracket_flag || sq_bracket_flag)
1450
    as_fatal (_("Missing matching brackets : `%s'"), ins_parse);
1451
 
1452
  /* Now we parse each operand separately.  */
1453
  for (op_num = 0; op_num < cr16_ins->nargs; op_num++)
1454
    {
1455
      cur_arg_num = op_num;
1456
      parse_operand (operand[op_num], cr16_ins);
1457
      free (operand[op_num]);
1458
    }
1459
 
1460
  if (allocated)
1461
    free (operandS);
1462
}
1463
 
1464
/* Get the trap index in dispatch table, given its name.
1465
   This routine is used by assembling the 'excp' instruction.  */
1466
 
1467
static int
1468
gettrap (char *s)
1469
{
1470
  const trap_entry *trap;
1471
 
1472
  for (trap = cr16_traps; trap < (cr16_traps + NUMTRAPS); trap++)
1473
    if (strcasecmp (trap->name, s) == 0)
1474
      return trap->entry;
1475
 
1476
  /* To make compatable with CR16 4.1 tools, the below 3-lines of
1477
   * code added. Refer: Development Tracker item #123 */
1478
  for (trap = cr16_traps; trap < (cr16_traps + NUMTRAPS); trap++)
1479
    if (trap->entry  == (unsigned int) atoi (s))
1480
      return trap->entry;
1481
 
1482
  as_bad (_("Unknown exception: `%s'"), s);
1483
  return 0;
1484
}
1485
 
1486
/* Top level module where instruction parsing starts.
1487
   cr16_ins - data structure holds some information.
1488
   operands - holds the operands part of the whole instruction.  */
1489
 
1490
static void
1491
parse_insn (ins *insn, char *operands)
1492
{
1493
  int i;
1494
 
1495
  /* Handle instructions with no operands.  */
1496
  for (i = 0; cr16_no_op_insn[i] != NULL; i++)
1497
  {
1498
    if (streq (cr16_no_op_insn[i], instruction->mnemonic))
1499
    {
1500
      insn->nargs = 0;
1501
      return;
1502
    }
1503
  }
1504
 
1505
  /* Handle 'excp' instructions.  */
1506
  if (IS_INSN_MNEMONIC ("excp"))
1507
    {
1508
      insn->nargs = 1;
1509
      insn->arg[0].type = arg_ic;
1510
      insn->arg[0].constant = gettrap (operands);
1511
      insn->arg[0].X_op = O_constant;
1512
      return;
1513
    }
1514
 
1515
  if (operands != NULL)
1516
    parse_operands (insn, operands);
1517
}
1518
 
1519
/* bCC instruction requires special handling.  */
1520
static char *
1521
get_b_cc (char * op)
1522
{
1523
  unsigned int i;
1524
  char op1[5];
1525
 
1526
  for (i = 1; i < strlen (op); i++)
1527
     op1[i-1] = op[i];
1528
 
1529
  op1[i-1] = '\0';
1530
 
1531
  for (i = 0; i < cr16_num_cc ; i++)
1532
    if (streq (op1, cr16_b_cond_tab[i]))
1533
      return (char *) cr16_b_cond_tab[i];
1534
 
1535
   return NULL;
1536
}
1537
 
1538
/* bCC instruction requires special handling.  */
1539
static int
1540
is_bcc_insn (char * op)
1541
{
1542
  if (!(streq (op, "bal") || streq (op, "beq0b") || streq (op, "bnq0b")
1543
        || streq (op, "beq0w") || streq (op, "bnq0w")))
1544
    if ((op[0] == 'b') && (get_b_cc (op) != NULL))
1545
      return 1;
1546
  return 0;
1547
}
1548
 
1549
/* Cinv instruction requires special handling.  */
1550
 
1551
static int
1552
check_cinv_options (char * operand)
1553
{
1554
  char *p = operand;
1555
  int i_used = 0, u_used = 0, d_used = 0;
1556
 
1557
  while (*++p != ']')
1558
    {
1559
      if (*p == ',' || *p == ' ')
1560
        continue;
1561
 
1562
      else if (*p == 'i')
1563
        i_used = 1;
1564
      else if (*p == 'u')
1565
        u_used = 1;
1566
      else if (*p == 'd')
1567
        d_used = 1;
1568
      else
1569
        as_bad (_("Illegal `cinv' parameter: `%c'"), *p);
1570
    }
1571
 
1572
  return 0;
1573
}
1574
 
1575
/* Retrieve the opcode image of a given register pair.
1576
   If the register is illegal for the current instruction,
1577
   issue an error.  */
1578
 
1579
static int
1580
getregp_image (reg r)
1581
{
1582
  const reg_entry *reg;
1583
  char *reg_name;
1584
 
1585
  /* Check whether the register is in registers table.  */
1586
  if (r < MAX_REG)
1587
    reg = cr16_regptab + r;
1588
  /* Register not found.  */
1589
  else
1590
    {
1591
      as_bad (_("Unknown register pair: `%d'"), r);
1592
      return 0;
1593
    }
1594
 
1595
  reg_name = reg->name;
1596
 
1597
/* Issue a error message when register  pair is illegal.  */
1598
#define RPAIR_IMAGE_ERR \
1599
  as_bad (_("Illegal register pair (`%s') in Instruction: `%s'"), \
1600
            reg_name, ins_parse);                                 \
1601
  break;
1602
 
1603
  switch (reg->type)
1604
    {
1605
    case CR16_RP_REGTYPE:
1606
      return reg->image;
1607
    default:
1608
      RPAIR_IMAGE_ERR;
1609
    }
1610
 
1611
  return 0;
1612
}
1613
 
1614
/* Retrieve the opcode image of a given index register pair.
1615
   If the register is illegal for the current instruction,
1616
   issue an error.  */
1617
 
1618
static int
1619
getidxregp_image (reg r)
1620
{
1621
  const reg_entry *reg;
1622
  char *reg_name;
1623
 
1624
  /* Check whether the register is in registers table.  */
1625
  if (r < MAX_REG)
1626
    reg = cr16_regptab + r;
1627
  /* Register not found.  */
1628
  else
1629
    {
1630
      as_bad (_("Unknown register pair: `%d'"), r);
1631
      return 0;
1632
    }
1633
 
1634
  reg_name = reg->name;
1635
 
1636
/* Issue a error message when register  pair is illegal.  */
1637
#define IDX_RPAIR_IMAGE_ERR \
1638
  as_bad (_("Illegal index register pair (`%s') in Instruction: `%s'"), \
1639
            reg_name, ins_parse);                                       \
1640
 
1641
  if (reg->type == CR16_RP_REGTYPE)
1642
    {
1643
      switch (reg->image)
1644
        {
1645
        case 0:  return 0; break;
1646
        case 2:  return 1; break;
1647
        case 4:  return 2; break;
1648
        case 6:  return 3; break;
1649
        case 8:  return 4; break;
1650
        case 10: return 5; break;
1651
        case 3:  return 6; break;
1652
        case 5:  return 7; break;
1653
        default:
1654
          break;
1655
        }
1656
    }
1657
 
1658
  IDX_RPAIR_IMAGE_ERR;
1659
  return 0;
1660
}
1661
 
1662
/* Retrieve the opcode image of a given processort register.
1663
   If the register is illegal for the current instruction,
1664
   issue an error.  */
1665
static int
1666
getprocreg_image (reg r)
1667
{
1668
  const reg_entry *reg;
1669
  char *reg_name;
1670
 
1671
  /* Check whether the register is in registers table.  */
1672
  if (r < MAX_PREG)
1673
    reg = &cr16_pregtab[r - MAX_REG];
1674
  /* Register not found.  */
1675
  else
1676
    {
1677
      as_bad (_("Unknown processor register : `%d'"), r);
1678
      return 0;
1679
    }
1680
 
1681
  reg_name = reg->name;
1682
 
1683
/* Issue a error message when register  pair is illegal.  */
1684
#define PROCREG_IMAGE_ERR \
1685
  as_bad (_("Illegal processor register (`%s') in Instruction: `%s'"), \
1686
            reg_name, ins_parse);                                      \
1687
  break;
1688
 
1689
  switch (reg->type)
1690
    {
1691
    case CR16_P_REGTYPE:
1692
      return reg->image;
1693
    default:
1694
      PROCREG_IMAGE_ERR;
1695
    }
1696
 
1697
  return 0;
1698
}
1699
 
1700
/* Retrieve the opcode image of a given processort register.
1701
   If the register is illegal for the current instruction,
1702
   issue an error.  */
1703
static int
1704
getprocregp_image (reg r)
1705
{
1706
  const reg_entry *reg;
1707
  char *reg_name;
1708
  int pregptab_disp = 0;
1709
 
1710
  /* Check whether the register is in registers table.  */
1711
  if (r < MAX_PREG)
1712
    {
1713
      r = r - MAX_REG;
1714
      switch (r)
1715
        {
1716
        case 4: pregptab_disp = 1;  break;
1717
        case 6: pregptab_disp = 2;  break;
1718
        case 8:
1719
        case 9:
1720
        case 10:
1721
          pregptab_disp = 3;  break;
1722
        case 12:
1723
          pregptab_disp = 4;  break;
1724
        case 14:
1725
          pregptab_disp = 5;  break;
1726
        default: break;
1727
        }
1728
      reg = &cr16_pregptab[r - pregptab_disp];
1729
    }
1730
  /* Register not found.  */
1731
  else
1732
    {
1733
      as_bad (_("Unknown processor register (32 bit) : `%d'"), r);
1734
      return 0;
1735
    }
1736
 
1737
  reg_name = reg->name;
1738
 
1739
/* Issue a error message when register  pair is illegal.  */
1740
#define PROCREGP_IMAGE_ERR \
1741
  as_bad (_("Illegal 32 bit - processor register (`%s') in Instruction: `%s'"),\
1742
            reg_name, ins_parse);                                              \
1743
  break;
1744
 
1745
  switch (reg->type)
1746
    {
1747
    case CR16_P_REGTYPE:
1748
      return reg->image;
1749
    default:
1750
      PROCREGP_IMAGE_ERR;
1751
    }
1752
 
1753
  return 0;
1754
}
1755
 
1756
/* Routine used to represent integer X using NBITS bits.  */
1757
 
1758
static long
1759
getconstant (long x, int nbits)
1760
{
1761
  /* The following expression avoids overflow if
1762
     'nbits' is the number of bits in 'bfd_vma'.  */
1763
  return (x & ((((1 << (nbits - 1)) - 1) << 1) | 1));
1764
}
1765
 
1766
/* Print a constant value to 'output_opcode':
1767
   ARG holds the operand's type and value.
1768
   SHIFT represents the location of the operand to be print into.
1769
   NBITS determines the size (in bits) of the constant.  */
1770
 
1771
static void
1772
print_constant (int nbits, int shift, argument *arg)
1773
{
1774
  unsigned long mask = 0;
1775
 
1776
  long constant = getconstant (arg->constant, nbits);
1777
 
1778
  switch (nbits)
1779
    {
1780
    case 32:
1781
    case 28:
1782
      /* mask the upper part of the constant, that is, the bits
1783
         going to the lowest byte of output_opcode[0].
1784
         The upper part of output_opcode[1] is always filled,
1785
         therefore it is always masked with 0xFFFF.  */
1786
      mask = (1 << (nbits - 16)) - 1;
1787
      /* Divide the constant between two consecutive words :
1788
 
1789
         +---------+---------+---------+---------+
1790
         |         | X X X X | x X x X |         |
1791
         +---------+---------+---------+---------+
1792
         output_opcode[0]    output_opcode[1]     */
1793
 
1794
      CR16_PRINT (0, (constant >> WORD_SHIFT) & mask, 0);
1795
      CR16_PRINT (1, (constant & 0xFFFF), WORD_SHIFT);
1796
      break;
1797
 
1798
    case 21:
1799
      if ((nbits == 21) && (IS_INSN_TYPE (LD_STOR_INS))) nbits = 20;
1800
    case 24:
1801
    case 22:
1802
    case 20:
1803
      /* mask the upper part of the constant, that is, the bits
1804
         going to the lowest byte of output_opcode[0].
1805
         The upper part of output_opcode[1] is always filled,
1806
         therefore it is always masked with 0xFFFF.  */
1807
      mask = (1 << (nbits - 16)) - 1;
1808
      /* Divide the constant between two consecutive words :
1809
 
1810
         +---------+---------+---------+---------+
1811
         |         | X X X X | - X - X |         |
1812
         +---------+---------+---------+---------+
1813
         output_opcode[0]    output_opcode[1]     */
1814
 
1815
      if ((instruction->size > 2) && (shift == WORD_SHIFT))
1816
        {
1817
          if (arg->type == arg_idxrp)
1818
            {
1819
              CR16_PRINT (0, ((constant >> WORD_SHIFT) & mask) << 8, 0);
1820
              CR16_PRINT (1, (constant & 0xFFFF), WORD_SHIFT);
1821
            }
1822
          else
1823
            {
1824
              CR16_PRINT (0, (((((constant >> WORD_SHIFT) & mask) << 8) & 0x0f00) | ((((constant >> WORD_SHIFT) & mask) >> 4) & 0xf)),0);
1825
              CR16_PRINT (1, (constant & 0xFFFF), WORD_SHIFT);
1826
            }
1827
        }
1828
      else
1829
        CR16_PRINT (0, constant, shift);
1830
      break;
1831
 
1832
    case 14:
1833
      if (arg->type == arg_idxrp)
1834
        {
1835
          if (instruction->size == 2)
1836
            {
1837
              CR16_PRINT (0, ((constant)      & 0xf), shift);        /* 0-3 bits.  */
1838
              CR16_PRINT (0, ((constant >> 4) & 0x3), (shift + 20)); /* 4-5 bits.  */
1839
              CR16_PRINT (0, ((constant >> 6) & 0x3), (shift + 14)); /* 6-7 bits.  */
1840
              CR16_PRINT (0, ((constant >> 8) & 0x3f), (shift + 8)); /* 8-13 bits.  */
1841
            }
1842
          else
1843
            CR16_PRINT (0, constant, shift);
1844
        }
1845
      break;
1846
 
1847
    case 16:
1848
    case 12:
1849
      /* When instruction size is 3 and 'shift' is 16, a 16-bit constant is
1850
         always filling the upper part of output_opcode[1]. If we mistakenly
1851
         write it to output_opcode[0], the constant prefix (that is, 'match')
1852
         will be overriden.
1853
 
1854
         +---------+---------+---------+---------+
1855
         | 'match' |         | X X X X |         |
1856
         +---------+---------+---------+---------+
1857
         output_opcode[0]    output_opcode[1]     */
1858
 
1859
      if ((instruction->size > 2) && (shift == WORD_SHIFT))
1860
        CR16_PRINT (1, constant, WORD_SHIFT);
1861
      else
1862
        CR16_PRINT (0, constant, shift);
1863
      break;
1864
 
1865
    case 8:
1866
      CR16_PRINT (0, ((constant / 2) & 0xf), shift);
1867
      CR16_PRINT (0, ((constant / 2) >> 4), (shift + 8));
1868
      break;
1869
 
1870
    default:
1871
      CR16_PRINT (0, constant,  shift);
1872
      break;
1873
    }
1874
}
1875
 
1876
/* Print an operand to 'output_opcode', which later on will be
1877
   printed to the object file:
1878
   ARG holds the operand's type, size and value.
1879
   SHIFT represents the printing location of operand.
1880
   NBITS determines the size (in bits) of a constant operand.  */
1881
 
1882
static void
1883
print_operand (int nbits, int shift, argument *arg)
1884
{
1885
  switch (arg->type)
1886
    {
1887
    case arg_cc:
1888
      CR16_PRINT (0, arg->cc, shift);
1889
      break;
1890
 
1891
    case arg_r:
1892
      CR16_PRINT (0, getreg_image (arg->r), shift);
1893
      break;
1894
 
1895
    case arg_rp:
1896
      CR16_PRINT (0, getregp_image (arg->rp), shift);
1897
      break;
1898
 
1899
    case arg_pr:
1900
      CR16_PRINT (0, getprocreg_image (arg->pr), shift);
1901
      break;
1902
 
1903
    case arg_prp:
1904
      CR16_PRINT (0, getprocregp_image (arg->prp), shift);
1905
      break;
1906
 
1907
    case arg_idxrp:
1908
      /*    16      12      8    6      0
1909
            +-----------------------------+
1910
            | r_index | disp  | rp_base   |
1911
            +-----------------------------+          */
1912
 
1913
      if (instruction->size == 3)
1914
        {
1915
          CR16_PRINT (0, getidxregp_image (arg->rp), 0);
1916
          if (getreg_image (arg->i_r) == 12)
1917
            CR16_PRINT (0, 0, 3);
1918
          else
1919
            CR16_PRINT (0, 1, 3);
1920
        }
1921
      else
1922
        {
1923
          CR16_PRINT (0, getidxregp_image (arg->rp), 16);
1924
          if (getreg_image (arg->i_r) == 12)
1925
            CR16_PRINT (0, 0, 19);
1926
          else
1927
            CR16_PRINT (0, 1, 19);
1928
        }
1929
      print_constant (nbits, shift, arg);
1930
      break;
1931
 
1932
    case arg_idxr:
1933
      if (getreg_image (arg->i_r) == 12)
1934
        if (IS_INSN_MNEMONIC ("cbitb") || IS_INSN_MNEMONIC ("sbitb")
1935
            || IS_INSN_MNEMONIC ("tbitb"))
1936
          CR16_PRINT (0, 0, 23);
1937
        else CR16_PRINT (0, 0, 24);
1938
      else
1939
        if (IS_INSN_MNEMONIC ("cbitb") || IS_INSN_MNEMONIC ("sbitb")
1940
            || IS_INSN_MNEMONIC ("tbitb"))
1941
          CR16_PRINT (0, 1, 23);
1942
        else CR16_PRINT (0, 1, 24);
1943
 
1944
      print_constant (nbits, shift, arg);
1945
      break;
1946
 
1947
    case arg_ic:
1948
    case arg_c:
1949
      print_constant (nbits, shift, arg);
1950
      break;
1951
 
1952
    case arg_rbase:
1953
      CR16_PRINT (0, getreg_image (arg->r), shift);
1954
      break;
1955
 
1956
    case arg_cr:
1957
      print_constant (nbits, shift , arg);
1958
      /* Add the register argument to the output_opcode.  */
1959
      CR16_PRINT (0, getreg_image (arg->r), (shift+16));
1960
      break;
1961
 
1962
    case arg_crp:
1963
      print_constant (nbits, shift , arg);
1964
      if (instruction->size > 1)
1965
        CR16_PRINT (0, getregp_image (arg->rp), (shift + 16));
1966
      else if (IS_INSN_TYPE (LD_STOR_INS) || (IS_INSN_TYPE (CSTBIT_INS)))
1967
        {
1968
          if (instruction->size == 2)
1969
            CR16_PRINT (0, getregp_image (arg->rp), (shift - 8));
1970
          else if (instruction->size == 1)
1971
            CR16_PRINT (0, getregp_image (arg->rp), 16);
1972
        }
1973
      else
1974
        CR16_PRINT (0, getregp_image (arg->rp), shift);
1975
      break;
1976
 
1977
    default:
1978
      break;
1979
    }
1980
}
1981
 
1982
/* Retrieve the number of operands for the current assembled instruction.  */
1983
 
1984
static int
1985
get_number_of_operands (void)
1986
{
1987
  int i;
1988
 
1989
  for (i = 0; instruction->operands[i].op_type && i < MAX_OPERANDS; i++)
1990
    ;
1991
  return i;
1992
}
1993
 
1994
/* Verify that the number NUM can be represented in BITS bits (that is,
1995
   within its permitted range), based on the instruction's FLAGS.
1996
   If UPDATE is nonzero, update the value of NUM if necessary.
1997
   Return OP_LEGAL upon success, actual error type upon failure.  */
1998
 
1999
static op_err
2000
check_range (long *num, int bits, int unsigned flags, int update)
2001
{
2002
  long min, max;
2003
  int retval = OP_LEGAL;
2004
  long value = *num;
2005
 
2006
  if (bits == 0 && value > 0) return OP_OUT_OF_RANGE;
2007
 
2008
  /* For hosts witah longs bigger than 32-bits make sure that the top
2009
     bits of a 32-bit negative value read in by the parser are set,
2010
     so that the correct comparisons are made.  */
2011
  if (value & 0x80000000)
2012
    value |= (-1L << 31);
2013
 
2014
 
2015
  /* Verify operand value is even.  */
2016
  if (flags & OP_EVEN)
2017
    {
2018
      if (value % 2)
2019
        return OP_NOT_EVEN;
2020
    }
2021
 
2022
  if (flags & OP_DEC)
2023
    {
2024
      value -= 1;
2025
      if (update)
2026
        *num = value;
2027
    }
2028
 
2029
  if (flags & OP_SHIFT)
2030
    {
2031
      value >>= 1;
2032
      if (update)
2033
        *num = value;
2034
    }
2035
  else if (flags & OP_SHIFT_DEC)
2036
    {
2037
      value = (value >> 1) - 1;
2038
      if (update)
2039
        *num = value;
2040
    }
2041
 
2042
  if (flags & OP_ABS20)
2043
    {
2044
      if (value > 0xEFFFF)
2045
        return OP_OUT_OF_RANGE;
2046
    }
2047
 
2048
  if (flags & OP_ESC)
2049
    {
2050
      if (value == 0xB || value == 0x9)
2051
        return OP_OUT_OF_RANGE;
2052
      else if (value == -1)
2053
        {
2054
          if (update)
2055
            *num = 9;
2056
          return retval;
2057
        }
2058
    }
2059
 
2060
  if (flags & OP_ESC1)
2061
    {
2062
      if (value > 13)
2063
        return OP_OUT_OF_RANGE;
2064
    }
2065
 
2066
   if (flags & OP_SIGNED)
2067
     {
2068
       max = (1 << (bits - 1)) - 1;
2069
       min = - (1 << (bits - 1));
2070
       if ((value > max) || (value < min))
2071
         retval = OP_OUT_OF_RANGE;
2072
     }
2073
   else if (flags & OP_UNSIGNED)
2074
     {
2075
       max = ((((1 << (bits - 1)) - 1) << 1) | 1);
2076
       min = 0;
2077
       if (((unsigned long) value > (unsigned long) max)
2078
            || ((unsigned long) value < (unsigned long) min))
2079
         retval = OP_OUT_OF_RANGE;
2080
     }
2081
   else if (flags & OP_NEG)
2082
     {
2083
       max = - 1;
2084
       min = - ((1 << (bits - 1)) - 1);
2085
       if ((value > max) || (value < min))
2086
         retval = OP_OUT_OF_RANGE;
2087
     }
2088
   return retval;
2089
}
2090
 
2091
/* Bunch of error checkings.
2092
   The checks are made after a matching instruction was found.  */
2093
 
2094
static void
2095
warn_if_needed (ins *insn)
2096
{
2097
  /* If the post-increment address mode is used and the load/store
2098
     source register is the same as rbase, the result of the
2099
     instruction is undefined.  */
2100
  if (IS_INSN_TYPE (LD_STOR_INS_INC))
2101
    {
2102
      /* Enough to verify that one of the arguments is a simple reg.  */
2103
      if ((insn->arg[0].type == arg_r) || (insn->arg[1].type == arg_r))
2104
        if (insn->arg[0].r == insn->arg[1].r)
2105
          as_bad (_("Same src/dest register is used (`r%d'), result is undefined"), insn->arg[0].r);
2106
    }
2107
 
2108
  if (IS_INSN_MNEMONIC ("pop")
2109
      || IS_INSN_MNEMONIC ("push")
2110
      || IS_INSN_MNEMONIC ("popret"))
2111
    {
2112
      unsigned int count = insn->arg[0].constant, reg_val;
2113
 
2114
      /* Check if count operand caused to save/retrive the RA twice
2115
         to generate warning message.  */
2116
     if (insn->nargs > 2)
2117
       {
2118
         reg_val = getreg_image (insn->arg[1].r);
2119
 
2120
         if (   ((reg_val == 9) &&  (count > 7))
2121
             || ((reg_val == 10) && (count > 6))
2122
             || ((reg_val == 11) && (count > 5))
2123
             || ((reg_val == 12) && (count > 4))
2124
             || ((reg_val == 13) && (count > 2))
2125
             || ((reg_val == 14) && (count > 0)))
2126
           as_warn (_("RA register is saved twice."));
2127
 
2128
         /* Check if the third operand is "RA" or "ra" */
2129
         if (!(((insn->arg[2].r) == ra) || ((insn->arg[2].r) == RA)))
2130
           as_bad (_("`%s' Illegal use of registers."), ins_parse);
2131
       }
2132
 
2133
      if (insn->nargs > 1)
2134
       {
2135
         reg_val = getreg_image (insn->arg[1].r);
2136
 
2137
         /* If register is a register pair ie r12/r13/r14 in operand1, then
2138
            the count constant should be validated.  */
2139
         if (((reg_val == 11) && (count > 7))
2140
             || ((reg_val == 12) && (count > 6))
2141
             || ((reg_val == 13) && (count > 4))
2142
             || ((reg_val == 14) && (count > 2))
2143
             || ((reg_val == 15) && (count > 0)))
2144
           as_bad (_("`%s' Illegal count-register combination."), ins_parse);
2145
       }
2146
     else
2147
       {
2148
         /* Check if the operand is "RA" or "ra" */
2149
         if (!(((insn->arg[0].r) == ra) || ((insn->arg[0].r) == RA)))
2150
           as_bad (_("`%s' Illegal use of register."), ins_parse);
2151
       }
2152
    }
2153
 
2154
  /* Some instruction assume the stack pointer as rptr operand.
2155
     Issue an error when the register to be loaded is also SP.  */
2156
  if (instruction->flags & NO_SP)
2157
    {
2158
      if (getreg_image (insn->arg[1].r) == getreg_image (sp))
2159
        as_bad (_("`%s' has undefined result"), ins_parse);
2160
    }
2161
 
2162
  /* If the rptr register is specified as one of the registers to be loaded,
2163
     the final contents of rptr are undefined. Thus, we issue an error.  */
2164
  if (instruction->flags & NO_RPTR)
2165
    {
2166
      if ((1 << getreg_image (insn->arg[0].r)) & insn->arg[1].constant)
2167
        as_bad (_("Same src/dest register is used (`r%d'),result is undefined"),
2168
                  getreg_image (insn->arg[0].r));
2169
    }
2170
}
2171
 
2172
/* In some cases, we need to adjust the instruction pointer although a
2173
   match was already found. Here, we gather all these cases.
2174
   Returns 1 if instruction pointer was adjusted, otherwise 0.  */
2175
 
2176
static int
2177
adjust_if_needed (ins *insn ATTRIBUTE_UNUSED)
2178
{
2179
  int ret_value = 0;
2180
 
2181
  if ((IS_INSN_TYPE (CSTBIT_INS)) || (IS_INSN_TYPE (LD_STOR_INS)))
2182
    {
2183
      if ((instruction->operands[0].op_type == abs24)
2184
           && ((insn->arg[0].constant) > 0xF00000))
2185
        {
2186
          insn->arg[0].constant &= 0xFFFFF;
2187
          instruction--;
2188
          ret_value = 1;
2189
        }
2190
    }
2191
 
2192
  return ret_value;
2193
}
2194
 
2195
/* Assemble a single instruction:
2196
   INSN is already parsed (that is, all operand values and types are set).
2197
   For instruction to be assembled, we need to find an appropriate template in
2198
   the instruction table, meeting the following conditions:
2199
    1: Has the same number of operands.
2200
    2: Has the same operand types.
2201
    3: Each operand size is sufficient to represent the instruction's values.
2202
   Returns 1 upon success, 0 upon failure.  */
2203
 
2204
static int
2205
assemble_insn (char *mnemonic, ins *insn)
2206
{
2207
  /* Type of each operand in the current template.  */
2208
  argtype cur_type[MAX_OPERANDS];
2209
  /* Size (in bits) of each operand in the current template.  */
2210
  unsigned int cur_size[MAX_OPERANDS];
2211
  /* Flags of each operand in the current template.  */
2212
  unsigned int cur_flags[MAX_OPERANDS];
2213
  /* Instruction type to match.  */
2214
  unsigned int ins_type;
2215
  /* Boolean flag to mark whether a match was found.  */
2216
  int match = 0;
2217
  int i;
2218
  /* Nonzero if an instruction with same number of operands was found.  */
2219
  int found_same_number_of_operands = 0;
2220
  /* Nonzero if an instruction with same argument types was found.  */
2221
  int found_same_argument_types = 0;
2222
  /* Nonzero if a constant was found within the required range.  */
2223
  int found_const_within_range  = 0;
2224
  /* Argument number of an operand with invalid type.  */
2225
  int invalid_optype = -1;
2226
  /* Argument number of an operand with invalid constant value.  */
2227
  int invalid_const  = -1;
2228
  /* Operand error (used for issuing various constant error messages).  */
2229
  op_err op_error, const_err = OP_LEGAL;
2230
 
2231
/* Retrieve data (based on FUNC) for each operand of a given instruction.  */
2232
#define GET_CURRENT_DATA(FUNC, ARRAY)                           \
2233
  for (i = 0; i < insn->nargs; i++)                             \
2234
    ARRAY[i] = FUNC (instruction->operands[i].op_type)
2235
 
2236
#define GET_CURRENT_TYPE    GET_CURRENT_DATA (get_optype, cur_type)
2237
#define GET_CURRENT_SIZE    GET_CURRENT_DATA (get_opbits, cur_size)
2238
#define GET_CURRENT_FLAGS   GET_CURRENT_DATA (get_opflags, cur_flags)
2239
 
2240
  /* Instruction has no operands -> only copy the constant opcode.   */
2241
  if (insn->nargs == 0)
2242
    {
2243
      output_opcode[0] = BIN (instruction->match, instruction->match_bits);
2244
      return 1;
2245
    }
2246
 
2247
  /* In some case, same mnemonic can appear with different instruction types.
2248
     For example, 'storb' is supported with 3 different types :
2249
     LD_STOR_INS, LD_STOR_INS_INC, STOR_IMM_INS.
2250
     We assume that when reaching this point, the instruction type was
2251
     pre-determined. We need to make sure that the type stays the same
2252
     during a search for matching instruction.  */
2253
  ins_type = CR16_INS_TYPE (instruction->flags);
2254
 
2255
  while (/* Check that match is still not found.  */
2256
         match != 1
2257
         /* Check we didn't get to end of table.  */
2258
         && instruction->mnemonic != NULL
2259
         /* Check that the actual mnemonic is still available.  */
2260
         && IS_INSN_MNEMONIC (mnemonic)
2261
         /* Check that the instruction type wasn't changed.  */
2262
         && IS_INSN_TYPE (ins_type))
2263
    {
2264
      /* Check whether number of arguments is legal.  */
2265
      if (get_number_of_operands () != insn->nargs)
2266
        goto next_insn;
2267
      found_same_number_of_operands = 1;
2268
 
2269
      /* Initialize arrays with data of each operand in current template.  */
2270
      GET_CURRENT_TYPE;
2271
      GET_CURRENT_SIZE;
2272
      GET_CURRENT_FLAGS;
2273
 
2274
      /* Check for type compatibility.  */
2275
      for (i = 0; i < insn->nargs; i++)
2276
        {
2277
          if (cur_type[i] != insn->arg[i].type)
2278
            {
2279
              if (invalid_optype == -1)
2280
                invalid_optype = i + 1;
2281
              goto next_insn;
2282
            }
2283
        }
2284
      found_same_argument_types = 1;
2285
 
2286
      for (i = 0; i < insn->nargs; i++)
2287
        {
2288
          /* If 'bal' instruction size is '2' and reg operand is not 'ra'
2289
             then goto next instruction.  */
2290
          if (IS_INSN_MNEMONIC ("bal") && (i == 0)
2291
              && (instruction->size == 2) && (insn->arg[i].rp != 14))
2292
            goto next_insn;
2293
 
2294
          /* If 'storb' instruction with 'sp' reg and 16-bit disp of
2295
           * reg-pair, leads to undifined trap, so this should use
2296
           * 20-bit disp of reg-pair.  */
2297
          if (IS_INSN_MNEMONIC ("storb") && (instruction->size == 2)
2298
              && (insn->arg[i].r == 15) && (insn->arg[i + 1].type == arg_crp))
2299
            goto next_insn;
2300
 
2301
          /* Only check range - don't update the constant's value, since the
2302
             current instruction may not be the last we try to match.
2303
             The constant's value will be updated later, right before printing
2304
             it to the object file.  */
2305
          if ((insn->arg[i].X_op == O_constant)
2306
              && (op_error = check_range (&insn->arg[i].constant, cur_size[i],
2307
                                          cur_flags[i], 0)))
2308
            {
2309
              if (invalid_const == -1)
2310
                {
2311
                  invalid_const = i + 1;
2312
                  const_err = op_error;
2313
                }
2314
              goto next_insn;
2315
            }
2316
          /* For symbols, we make sure the relocation size (which was already
2317
             determined) is sufficient.  */
2318
          else if ((insn->arg[i].X_op == O_symbol)
2319
                   && ((bfd_reloc_type_lookup (stdoutput, insn->rtype))->bitsize
2320
                       > cur_size[i]))
2321
                  goto next_insn;
2322
        }
2323
      found_const_within_range = 1;
2324
 
2325
      /* If we got till here -> Full match is found.  */
2326
      match = 1;
2327
      break;
2328
 
2329
/* Try again with next instruction.  */
2330
next_insn:
2331
      instruction++;
2332
    }
2333
 
2334
  if (!match)
2335
    {
2336
      /* We haven't found a match - instruction can't be assembled.  */
2337
      if (!found_same_number_of_operands)
2338
        as_bad (_("Incorrect number of operands"));
2339
      else if (!found_same_argument_types)
2340
        as_bad (_("Illegal type of operand (arg %d)"), invalid_optype);
2341
      else if (!found_const_within_range)
2342
        {
2343
          switch (const_err)
2344
            {
2345
            case OP_OUT_OF_RANGE:
2346
              as_bad (_("Operand out of range (arg %d)"), invalid_const);
2347
              break;
2348
            case OP_NOT_EVEN:
2349
              as_bad (_("Operand has odd displacement (arg %d)"), invalid_const);
2350
              break;
2351
            default:
2352
              as_bad (_("Illegal operand (arg %d)"), invalid_const);
2353
              break;
2354
            }
2355
        }
2356
 
2357
       return 0;
2358
    }
2359
  else
2360
    /* Full match - print the encoding to output file.  */
2361
    {
2362
      /* Make further checkings (such that couldn't be made earlier).
2363
         Warn the user if necessary.  */
2364
      warn_if_needed (insn);
2365
 
2366
      /* Check whether we need to adjust the instruction pointer.  */
2367
      if (adjust_if_needed (insn))
2368
        /* If instruction pointer was adjusted, we need to update
2369
           the size of the current template operands.  */
2370
        GET_CURRENT_SIZE;
2371
 
2372
      for (i = 0; i < insn->nargs; i++)
2373
        {
2374
          int j = instruction->flags & REVERSE_MATCH ?
2375
                  i == 0 ? 1 :
2376
                  i == 1 ? 0 : i :
2377
                  i;
2378
 
2379
          /* This time, update constant value before printing it.  */
2380
            if ((insn->arg[j].X_op == O_constant)
2381
               && (check_range (&insn->arg[j].constant, cur_size[j],
2382
                                cur_flags[j], 1) != OP_LEGAL))
2383
              as_fatal (_("Illegal operand (arg %d)"), j+1);
2384
        }
2385
 
2386
      /* First, copy the instruction's opcode.  */
2387
      output_opcode[0] = BIN (instruction->match, instruction->match_bits);
2388
 
2389
      for (i = 0; i < insn->nargs; i++)
2390
        {
2391
         /* For BAL (ra),disp17 instuction only. And also set the
2392
            DISP24a relocation type.  */
2393
         if (IS_INSN_MNEMONIC ("bal") && (instruction->size == 2) && i == 0)
2394
           {
2395
             insn->rtype = BFD_RELOC_CR16_DISP24a;
2396
             continue;
2397
           }
2398
          cur_arg_num = i;
2399
          print_operand (cur_size[i], instruction->operands[i].shift,
2400
                         &insn->arg[i]);
2401
        }
2402
    }
2403
 
2404
  return 1;
2405
}
2406
 
2407
/* Print the instruction.
2408
   Handle also cases where the instruction is relaxable/relocatable.  */
2409
 
2410
static void
2411
print_insn (ins *insn)
2412
{
2413
  unsigned int i, j, insn_size;
2414
  char *this_frag;
2415
  unsigned short words[4];
2416
  int addr_mod;
2417
 
2418
  /* Arrange the insn encodings in a WORD size array.  */
2419
  for (i = 0, j = 0; i < 2; i++)
2420
    {
2421
      words[j++] = (output_opcode[i] >> 16) & 0xFFFF;
2422
      words[j++] = output_opcode[i] & 0xFFFF;
2423
    }
2424
 
2425
    /* Handle relocation.  */
2426
    if ((instruction->flags & RELAXABLE) && relocatable)
2427
      {
2428
        int relax_subtype;
2429
        /* Write the maximal instruction size supported.  */
2430
        insn_size = INSN_MAX_SIZE;
2431
 
2432
        if (IS_INSN_TYPE (BRANCH_INS))
2433
          {
2434
            switch (insn->rtype)
2435
              {
2436
              case BFD_RELOC_CR16_DISP24:
2437
                relax_subtype = 2;
2438
                break;
2439
              case BFD_RELOC_CR16_DISP16:
2440
                relax_subtype = 1;
2441
                break;
2442
              default:
2443
                relax_subtype = 0;
2444
                break;
2445
              }
2446
          }
2447
        else
2448
          abort ();
2449
 
2450
        this_frag = frag_var (rs_machine_dependent, insn_size *2,
2451
                              4, relax_subtype,
2452
                              insn->exp.X_add_symbol,
2453
                              0,
2454
                              0);
2455
      }
2456
    else
2457
      {
2458
        insn_size = instruction->size;
2459
        this_frag = frag_more (insn_size * 2);
2460
 
2461
        if ((relocatable) && (insn->rtype != BFD_RELOC_NONE))
2462
          {
2463
             reloc_howto_type *reloc_howto;
2464
             int size;
2465
 
2466
             reloc_howto = bfd_reloc_type_lookup (stdoutput, insn->rtype);
2467
 
2468
             if (!reloc_howto)
2469
               abort ();
2470
 
2471
             size = bfd_get_reloc_size (reloc_howto);
2472
 
2473
             if (size < 1 || size > 4)
2474
               abort ();
2475
 
2476
             fix_new_exp (frag_now, this_frag - frag_now->fr_literal,
2477
                          size, &insn->exp, reloc_howto->pc_relative,
2478
                          insn->rtype);
2479
          }
2480
      }
2481
 
2482
  /* Verify a 2-byte code alignment.  */
2483
  addr_mod = frag_now_fix () & 1;
2484
  if (frag_now->has_code && frag_now->insn_addr != addr_mod)
2485
    as_bad (_("instruction address is not a multiple of 2"));
2486
  frag_now->insn_addr = addr_mod;
2487
  frag_now->has_code = 1;
2488
 
2489
  /* Write the instruction encoding to frag.  */
2490
  for (i = 0; i < insn_size; i++)
2491
    {
2492
      md_number_to_chars (this_frag, (valueT) words[i], 2);
2493
      this_frag += 2;
2494
    }
2495
}
2496
 
2497
/* This is the guts of the machine-dependent assembler.  OP points to a
2498
   machine dependent instruction.  This function is supposed to emit
2499
   the frags/bytes it assembles to.  */
2500
 
2501
void
2502
md_assemble (char *op)
2503
{
2504
  ins cr16_ins;
2505
  char *param, param1[32];
2506
  char c;
2507
 
2508
  /* Reset global variables for a new instruction.  */
2509
  reset_vars (op);
2510
 
2511
  /* Strip the mnemonic.  */
2512
  for (param = op; *param != 0 && !ISSPACE (*param); param++)
2513
    ;
2514
  c = *param;
2515
  *param++ = '\0';
2516
 
2517
  /* bCC instuctions and adjust the mnemonic by adding extra white spaces.  */
2518
  if (is_bcc_insn (op))
2519
    {
2520
      strcpy (param1, get_b_cc (op));
2521
      op = "b";
2522
      strcat (param1,",");
2523
      strcat (param1, param);
2524
      param = (char *) &param1;
2525
    }
2526
 
2527
  /* Checking the cinv options and adjust the mnemonic by removing the
2528
     extra white spaces.  */
2529
  if (streq ("cinv", op))
2530
    {
2531
     /* Validate the cinv options.  */
2532
      check_cinv_options (param);
2533
      strcat (op, param);
2534
    }
2535
 
2536
  /* MAPPING - SHIFT INSN, if imm4/imm16 positive values
2537
     lsh[b/w] imm4/imm6, reg ==> ashu[b/w] imm4/imm16, reg
2538
     as CR16 core doesn't support lsh[b/w] right shift operaions.  */
2539
  if ((streq ("lshb", op) || streq ("lshw", op) || streq ("lshd", op))
2540
      && (param [0] == '$'))
2541
    {
2542
      strcpy (param1, param);
2543
      /* Find the instruction.  */
2544
      instruction = (const inst *) hash_find (cr16_inst_hash, op);
2545
       parse_operands (&cr16_ins, param1);
2546
      if (((&cr16_ins)->arg[0].type == arg_ic)
2547
          && ((&cr16_ins)->arg[0].constant >= 0))
2548
        {
2549
           if (streq ("lshb", op))
2550
             op = "ashub";
2551
           else if (streq ("lshd", op))
2552
             op = "ashud";
2553
           else
2554
             op = "ashuw";
2555
        }
2556
    }
2557
 
2558
  /* Find the instruction.  */
2559
  instruction = (const inst *) hash_find (cr16_inst_hash, op);
2560
  if (instruction == NULL)
2561
    {
2562
      as_bad (_("Unknown opcode: `%s'"), op);
2563
      return;
2564
    }
2565
 
2566
  /* Tie dwarf2 debug info to the address at the start of the insn.  */
2567
  dwarf2_emit_insn (0);
2568
 
2569
  /* Parse the instruction's operands.  */
2570
  parse_insn (&cr16_ins, param);
2571
 
2572
  /* Assemble the instruction - return upon failure.  */
2573
  if (assemble_insn (op, &cr16_ins) == 0)
2574
    return;
2575
 
2576
  /* Print the instruction.  */
2577
  print_insn (&cr16_ins);
2578
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.