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

Subversion Repositories open8_urisc

[/] [open8_urisc/] [trunk/] [gnu/] [binutils/] [opcodes/] [mep-dis.c] - Blame information for rev 80

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

Line No. Rev Author Line
1 18 khays
/* Disassembler interface for targets using CGEN. -*- C -*-
2
   CGEN: Cpu tools GENerator
3
 
4
   THIS FILE IS MACHINE GENERATED WITH CGEN.
5
   - the resultant file is machine generated, cgen-dis.in isn't
6
 
7
   Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2005, 2007,
8
   2008, 2010  Free Software Foundation, Inc.
9
 
10
   This file is part of libopcodes.
11
 
12
   This library is free software; you can redistribute it and/or modify
13
   it under the terms of the GNU General Public License as published by
14
   the Free Software Foundation; either version 3, or (at your option)
15
   any later version.
16
 
17
   It is distributed in the hope that it will be useful, but WITHOUT
18
   ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
19
   or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
20
   License for more details.
21
 
22
   You should have received a copy of the GNU General Public License
23
   along with this program; if not, write to the Free Software Foundation, Inc.,
24
   51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
25
 
26
/* ??? Eventually more and more of this stuff can go to cpu-independent files.
27
   Keep that in mind.  */
28
 
29
#include "sysdep.h"
30
#include <stdio.h>
31
#include "ansidecl.h"
32
#include "dis-asm.h"
33
#include "bfd.h"
34
#include "symcat.h"
35
#include "libiberty.h"
36
#include "mep-desc.h"
37
#include "mep-opc.h"
38
#include "opintl.h"
39
 
40
/* Default text to print if an instruction isn't recognized.  */
41
#define UNKNOWN_INSN_MSG _("*unknown*")
42
 
43
static void print_normal
44
  (CGEN_CPU_DESC, void *, long, unsigned int, bfd_vma, int);
45
static void print_address
46
  (CGEN_CPU_DESC, void *, bfd_vma, unsigned int, bfd_vma, int) ATTRIBUTE_UNUSED;
47
static void print_keyword
48
  (CGEN_CPU_DESC, void *, CGEN_KEYWORD *, long, unsigned int) ATTRIBUTE_UNUSED;
49
static void print_insn_normal
50
  (CGEN_CPU_DESC, void *, const CGEN_INSN *, CGEN_FIELDS *, bfd_vma, int);
51
static int print_insn
52
  (CGEN_CPU_DESC, bfd_vma,  disassemble_info *, bfd_byte *, unsigned);
53
static int default_print_insn
54
  (CGEN_CPU_DESC, bfd_vma, disassemble_info *) ATTRIBUTE_UNUSED;
55
static int read_insn
56
  (CGEN_CPU_DESC, bfd_vma, disassemble_info *, bfd_byte *, int, CGEN_EXTRACT_INFO *,
57
   unsigned long *);
58
 
59
/* -- disassembler routines inserted here.  */
60
 
61
/* -- dis.c */
62
 
63
#include "elf/mep.h"
64
#include "elf-bfd.h"
65
 
66
#define CGEN_VALIDATE_INSN_SUPPORTED
67
 
68
static void print_tpreg (CGEN_CPU_DESC, PTR, CGEN_KEYWORD *, long, unsigned int);
69
static void print_spreg (CGEN_CPU_DESC, PTR, CGEN_KEYWORD *, long, unsigned int);
70
 
71
static void
72
print_tpreg (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED, PTR dis_info,
73
             CGEN_KEYWORD *table ATTRIBUTE_UNUSED, long val ATTRIBUTE_UNUSED,
74
             unsigned int flags ATTRIBUTE_UNUSED)
75
{
76
  disassemble_info *info = (disassemble_info *) dis_info;
77
 
78
  (*info->fprintf_func) (info->stream, "$tp");
79
}
80
 
81
static void
82
print_spreg (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED, PTR dis_info,
83
             CGEN_KEYWORD *table ATTRIBUTE_UNUSED, long val ATTRIBUTE_UNUSED,
84
             unsigned int flags ATTRIBUTE_UNUSED)
85
{
86
  disassemble_info *info = (disassemble_info *) dis_info;
87
 
88
  (*info->fprintf_func) (info->stream, "$sp");
89
}
90
 
91
/* begin-cop-ip-print-handlers */
92
static void
93
print_ivc2_cr (CGEN_CPU_DESC,
94
        void *,
95
        CGEN_KEYWORD *,
96
        long,
97
        unsigned int) ATTRIBUTE_UNUSED;
98
static void
99
print_ivc2_cr (CGEN_CPU_DESC cd,
100
        void *dis_info,
101
        CGEN_KEYWORD *keyword_table ATTRIBUTE_UNUSED,
102
        long value,
103
        unsigned int attrs)
104
{
105
  print_keyword (cd, dis_info, & mep_cgen_opval_h_cr_ivc2, value, attrs);
106
}
107
static void
108
print_ivc2_ccr (CGEN_CPU_DESC,
109
        void *,
110
        CGEN_KEYWORD *,
111
        long,
112
        unsigned int) ATTRIBUTE_UNUSED;
113
static void
114
print_ivc2_ccr (CGEN_CPU_DESC cd,
115
        void *dis_info,
116
        CGEN_KEYWORD *keyword_table ATTRIBUTE_UNUSED,
117
        long value,
118
        unsigned int attrs)
119
{
120
  print_keyword (cd, dis_info, & mep_cgen_opval_h_ccr_ivc2, value, attrs);
121
}
122
/* end-cop-ip-print-handlers */
123
 
124
/************************************************************\
125
*********************** Experimental *************************
126
\************************************************************/
127
 
128
#undef  CGEN_PRINT_INSN
129
#define CGEN_PRINT_INSN mep_print_insn
130
 
131
static int
132
mep_print_vliw_insns (CGEN_CPU_DESC cd, bfd_vma pc, disassemble_info *info,
133
                      bfd_byte *buf, int corelength, int copro1length,
134
                      int copro2length ATTRIBUTE_UNUSED)
135
{
136
  int i;
137
  int status = 0;
138
  /* char insnbuf[CGEN_MAX_INSN_SIZE]; */
139
  bfd_byte insnbuf[64];
140
 
141
  /* If corelength > 0 then there is a core insn present. It
142
     will be at the beginning of the buffer.  After printing
143
     the core insn, we need to print the + on the next line.  */
144
  if (corelength > 0)
145
    {
146
      int my_status = 0;
147
 
148
      for (i = 0; i < corelength; i++ )
149
        insnbuf[i] = buf[i];
150
      cd->isas = & MEP_CORE_ISA;
151
 
152
      my_status = print_insn (cd, pc, info, insnbuf, corelength);
153
      if (my_status != corelength)
154
        {
155
          (*info->fprintf_func) (info->stream, UNKNOWN_INSN_MSG);
156
          my_status = corelength;
157
        }
158
      status += my_status;
159
 
160
      /* Print the + to indicate that the following copro insn is   */
161
      /* part of a vliw group.                                      */
162
      if (copro1length > 0)
163
        (*info->fprintf_func) (info->stream, " + ");
164
    }
165
 
166
  /* Now all that is left to be processed is the coprocessor insns
167
     In vliw mode, there will always be one.  Its positioning will
168
     be from byte corelength to byte corelength+copro1length -1.
169
     No need to check for existence.   Also, the first vliw insn,
170
     will, as spec'd, always be at least as long as the core insn
171
     so we don't need to flush the buffer.  */
172
  if (copro1length > 0)
173
    {
174
      int my_status = 0;
175
 
176
      for (i = corelength; i < corelength + copro1length; i++ )
177
        insnbuf[i - corelength] = buf[i];
178
 
179
      switch (copro1length)
180
        {
181
        case 0:
182
          break;
183
        case 2:
184
          cd->isas = & MEP_COP16_ISA;
185
          break;
186
        case 4:
187
          cd->isas = & MEP_COP32_ISA;
188
          break;
189
        case 6:
190
          cd->isas = & MEP_COP48_ISA;
191
          break;
192
        case 8:
193
          cd->isas = & MEP_COP64_ISA;
194
          break;
195
        default:
196
          /* Shouldn't be anything but 16,32,48,64.  */
197
          break;
198
        }
199
 
200
      my_status = print_insn (cd, pc, info, insnbuf, copro1length);
201
 
202
      if (my_status != copro1length)
203
        {
204
          (*info->fprintf_func) (info->stream, UNKNOWN_INSN_MSG);
205
          my_status = copro1length;
206
        }
207
      status += my_status;
208
    }
209
 
210
#if 0
211
  /* Now we need to process the second copro insn if it exists. We
212
     have no guarantee that the second copro insn will be longer
213
     than the first, so we have to flush the buffer if we are have
214
     a second copro insn to process.  If present, this insn will
215
     be in the position from byte corelength+copro1length to byte
216
     corelength+copro1length+copro2length-1 (which better equal 8
217
     or else we're in big trouble.  */
218
  if (copro2length > 0)
219
    {
220
      int my_status = 0;
221
 
222
      for (i = 0; i < 64 ; i++)
223
        insnbuf[i] = 0;
224
 
225
      for (i = corelength + copro1length; i < 64; i++)
226
        insnbuf[i - (corelength + copro1length)] = buf[i];
227
 
228
      switch (copro2length)
229
        {
230
        case 2:
231
          cd->isas = 1 << ISA_EXT_COP1_16;
232
          break;
233
        case 4:
234
          cd->isas = 1 << ISA_EXT_COP1_32;
235
          break;
236
        case 6:
237
          cd->isas = 1 << ISA_EXT_COP1_48;
238
          break;
239
        case 8:
240
          cd->isas = 1 << ISA_EXT_COP1_64;
241
          break;
242
        default:
243
          /* Shouldn't be anything but 16,32,48,64.  */
244
          break;
245
        }
246
 
247
      my_status = print_insn (cd, pc, info, insnbuf, copro2length);
248
 
249
      if (my_status != copro2length)
250
        {
251
          (*info->fprintf_func) (info->stream, UNKNOWN_INSN_MSG);
252
          my_status = copro2length;
253
        }
254
 
255
      status += my_status;
256
    }
257
#endif
258
 
259
  /* Status should now be the number of bytes that were printed
260
     which should be 4 for VLIW32 mode and 64 for VLIW64 mode.  */
261
 
262
  if ((!MEP_VLIW64 && (status != 4)) || (MEP_VLIW64 && (status != 8)))
263
    return -1;
264
  else
265
    return status;
266
}
267
 
268
/* The two functions mep_examine_vliw[32,64]_insns are used find out
269
   which vliw combinaion (16 bit core with 48 bit copro, 32 bit core
270
   with 32 bit copro, etc.) is present.  Later on, when internally
271
   parallel coprocessors are handled, only these functions should
272
   need to be changed.
273
 
274
   At this time only the following combinations are supported:
275
 
276
   VLIW32 Mode:
277
   16 bit core insn (core) and 16 bit coprocessor insn (cop1)
278
   32 bit core insn (core)
279
   32 bit coprocessor insn (cop1)
280
   Note: As of this time, I do not believe we have enough information
281
         to distinguish a 32 bit core insn from a 32 bit cop insn. Also,
282
         no 16 bit coprocessor insns have been specified.
283
 
284
   VLIW64 Mode:
285
   16 bit core insn (core) and 48 bit coprocessor insn (cop1)
286
   32 bit core insn (core) and 32 bit coprocessor insn (cop1)
287
   64 bit coprocessor insn (cop1)
288
 
289
   The framework for an internally parallel coprocessor is also
290
   present (2nd coprocessor insn is cop2), but at this time it
291
   is not used.  This only appears to be valid in VLIW64 mode.  */
292
 
293
static int
294
mep_examine_vliw32_insns (CGEN_CPU_DESC cd, bfd_vma pc, disassemble_info *info)
295
{
296
  int status;
297
  int buflength;
298
  int corebuflength;
299
  int cop1buflength;
300
  int cop2buflength;
301
  bfd_byte buf[CGEN_MAX_INSN_SIZE];
302
  char indicator16[1];
303
  char indicatorcop32[2];
304
 
305
  /* At this time we're not supporting internally parallel coprocessors,
306
     so cop2buflength will always be 0.  */
307
  cop2buflength = 0;
308
 
309
  /* Read in 32 bits.  */
310
  buflength = 4; /* VLIW insn spans 4 bytes.  */
311
  status = (*info->read_memory_func) (pc, buf, buflength, info);
312
 
313
  if (status != 0)
314
    {
315
      (*info->memory_error_func) (status, pc, info);
316
      return -1;
317
    }
318
 
319
  /* Put the big endian representation of the bytes to be examined
320
     in the temporary buffers for examination.  */
321
 
322
  if (info->endian == BFD_ENDIAN_BIG)
323
    {
324
      indicator16[0] = buf[0];
325
      indicatorcop32[0] = buf[0];
326
      indicatorcop32[1] = buf[1];
327
    }
328
  else
329
    {
330
      indicator16[0] = buf[1];
331
      indicatorcop32[0] = buf[1];
332
      indicatorcop32[1] = buf[0];
333
    }
334
 
335
  /* If the two high order bits are 00, 01 or 10, we have a 16 bit
336
     core insn and a 48 bit copro insn.  */
337
 
338
  if ((indicator16[0] & 0x80) && (indicator16[0] & 0x40))
339
    {
340
      if ((indicatorcop32[0] & 0xf0) == 0xf0 && (indicatorcop32[1] & 0x07) == 0x07)
341
        {
342
          /* We have a 32 bit copro insn.  */
343
          corebuflength = 0;
344
          /* All 4 4ytes are one copro insn. */
345
          cop1buflength = 4;
346
        }
347
      else
348
        {
349
          /* We have a 32 bit core.  */
350
          corebuflength = 4;
351
          cop1buflength = 0;
352
        }
353
    }
354
  else
355
    {
356
      /* We have a 16 bit core insn and a 16 bit copro insn.  */
357
      corebuflength = 2;
358
      cop1buflength = 2;
359
    }
360
 
361
  /* Now we have the distrubution set.  Print them out.  */
362
  status = mep_print_vliw_insns (cd, pc, info, buf, corebuflength,
363
                                 cop1buflength, cop2buflength);
364
 
365
  return status;
366
}
367
 
368
static int
369
mep_examine_vliw64_insns (CGEN_CPU_DESC cd, bfd_vma pc, disassemble_info *info)
370
{
371
  int status;
372
  int buflength;
373
  int corebuflength;
374
  int cop1buflength;
375
  int cop2buflength;
376
  bfd_byte buf[CGEN_MAX_INSN_SIZE];
377
  char indicator16[1];
378
  char indicator64[4];
379
 
380
  /* At this time we're not supporting internally parallel
381
     coprocessors, so cop2buflength will always be 0.  */
382
  cop2buflength = 0;
383
 
384
  /* Read in 64 bits.  */
385
  buflength = 8; /* VLIW insn spans 8 bytes.  */
386
  status = (*info->read_memory_func) (pc, buf, buflength, info);
387
 
388
  if (status != 0)
389
    {
390
      (*info->memory_error_func) (status, pc, info);
391
      return -1;
392
    }
393
 
394
  /* We have all 64 bits in the buffer now.  We have to figure out
395
     what combination of instruction sizes are present.  The two
396
     high order bits will indicate whether or not we have a 16 bit
397
     core insn or not.  If not, then we have to look at the 7,8th
398
     bytes to tell whether we have 64 bit copro insn or a 32 bit
399
     core insn with a 32 bit copro insn.  Endianness will make a
400
     difference here.  */
401
 
402
  /* Put the big endian representation of the bytes to be examined
403
     in the temporary buffers for examination.  */
404
 
405
  /* indicator16[0] = buf[0];  */
406
  if (info->endian == BFD_ENDIAN_BIG)
407
    {
408
      indicator16[0] = buf[0];
409
      indicator64[0] = buf[0];
410
      indicator64[1] = buf[1];
411
      indicator64[2] = buf[2];
412
      indicator64[3] = buf[3];
413
    }
414
  else
415
    {
416
      indicator16[0] = buf[1];
417
      indicator64[0] = buf[1];
418
      indicator64[1] = buf[0];
419
      indicator64[2] = buf[3];
420
      indicator64[3] = buf[2];
421
    }
422
 
423
  /* If the two high order bits are 00, 01 or 10, we have a 16 bit
424
     core insn and a 48 bit copro insn.  */
425
 
426
  if ((indicator16[0] & 0x80) && (indicator16[0] & 0x40))
427
    {
428
      if ((indicator64[0] & 0xf0) == 0xf0 && (indicator64[1] & 0x07) == 0x07
429
          && ((indicator64[2] & 0xfe) != 0xf0 || (indicator64[3] & 0xf4) != 0))
430
        {
431
          /* We have a 64 bit copro insn.  */
432
          corebuflength = 0;
433
          /* All 8 bytes are one copro insn.  */
434
          cop1buflength = 8;
435
        }
436
      else
437
        {
438
          /* We have a 32 bit core insn and a 32 bit copro insn.  */
439
          corebuflength = 4;
440
          cop1buflength = 4;
441
        }
442
    }
443
  else
444
    {
445
      /* We have a 16 bit core insn and a 48 bit copro insn.  */
446
      corebuflength = 2;
447
      cop1buflength = 6;
448
    }
449
 
450
  /* Now we have the distrubution set.  Print them out. */
451
  status = mep_print_vliw_insns (cd, pc, info, buf, corebuflength,
452
                                 cop1buflength, cop2buflength);
453
 
454
  return status;
455
}
456
 
457
#ifdef MEP_IVC2_SUPPORTED
458
 
459
static int
460
print_slot_insn (CGEN_CPU_DESC cd,
461
                 bfd_vma pc,
462
                 disassemble_info *info,
463
                 SLOTS_ATTR slot,
464
                 bfd_byte *buf)
465
{
466
  const CGEN_INSN_LIST *insn_list;
467
  CGEN_INSN_INT insn_value;
468
  CGEN_EXTRACT_INFO ex_info;
469
 
470
  insn_value = cgen_get_insn_value (cd, buf, 32);
471
 
472
  /* Fill in ex_info fields like read_insn would.  Don't actually call
473
     read_insn, since the incoming buffer is already read (and possibly
474
     modified a la m32r).  */
475
  ex_info.valid = (1 << 8) - 1;
476
  ex_info.dis_info = info;
477
  ex_info.insn_bytes = buf;
478
 
479
  /* The instructions are stored in hash lists.
480
     Pick the first one and keep trying until we find the right one.  */
481
 
482
  insn_list = CGEN_DIS_LOOKUP_INSN (cd, (char *) buf, insn_value);
483
  while (insn_list != NULL)
484
    {
485
      const CGEN_INSN *insn = insn_list->insn;
486
      CGEN_FIELDS fields;
487
      int length;
488
 
489
      if ((CGEN_INSN_ATTR_VALUE (insn, CGEN_INSN_CONFIG)
490
           && CGEN_INSN_ATTR_VALUE (insn, CGEN_INSN_CONFIG) != MEP_CONFIG)
491
          || ! (CGEN_ATTR_CGEN_INSN_SLOTS_VALUE (CGEN_INSN_ATTRS (insn)) & (1 << slot)))
492
        {
493
          insn_list = CGEN_DIS_NEXT_INSN (insn_list);
494
          continue;
495
        }
496
 
497
      if ((insn_value & CGEN_INSN_BASE_MASK (insn))
498
          == CGEN_INSN_BASE_VALUE (insn))
499
        {
500
          /* Printing is handled in two passes.  The first pass parses the
501
             machine insn and extracts the fields.  The second pass prints
502
             them.  */
503
 
504
          length = CGEN_EXTRACT_FN (cd, insn)
505
            (cd, insn, &ex_info, insn_value, &fields, pc);
506
 
507
          /* Length < 0 -> error.  */
508
          if (length < 0)
509
            return length;
510
          if (length > 0)
511
            {
512
              CGEN_PRINT_FN (cd, insn) (cd, info, insn, &fields, pc, length);
513
              /* Length is in bits, result is in bytes.  */
514
              return length / 8;
515
            }
516
        }
517
 
518
      insn_list = CGEN_DIS_NEXT_INSN (insn_list);
519
    }
520
 
521
  if (slot == SLOTS_P0S)
522
    (*info->fprintf_func) (info->stream, "*unknown-p0s*");
523
  else if (slot == SLOTS_P0)
524
    (*info->fprintf_func) (info->stream, "*unknown-p0*");
525
  else if (slot == SLOTS_P1)
526
    (*info->fprintf_func) (info->stream, "*unknown-p1*");
527
  else if (slot == SLOTS_C3)
528
    (*info->fprintf_func) (info->stream, "*unknown-c3*");
529
  return 0;
530
}
531
 
532
static int
533
mep_examine_ivc2_insns (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED, bfd_vma pc ATTRIBUTE_UNUSED, disassemble_info *info ATTRIBUTE_UNUSED)
534
{
535
  int status;
536
  int buflength;
537
  bfd_byte buf[8];
538
  bfd_byte insn[8];
539
  int e;
540
 
541
  /* Read in 64 bits.  */
542
  buflength = 8; /* VLIW insn spans 8 bytes.  */
543
  status = (*info->read_memory_func) (pc, buf, buflength, info);
544
 
545
  if (status != 0)
546
    {
547
      (*info->memory_error_func) (status, pc, info);
548
      return -1;
549
    }
550
 
551
  if (info->endian == BFD_ENDIAN_LITTLE)
552
    e = 1;
553
  else
554
    e = 0;
555
 
556
  if (((unsigned char)buf[0^e] & 0xf0) < 0xc0)
557
    {
558
      /*      <--00--><--11--><--22--><--33--><--44--><--55--><--66--><--77--> */
559
      /* V1   [-----core-----][--------p0s-------][------------p1------------] */
560
 
561
      print_insn (cd, pc, info, buf, 2);
562
 
563
      insn[0^e] = 0;
564
      insn[1^e] = buf[2^e];
565
      insn[2^e] = buf[3^e];
566
      insn[3^e] = buf[4^e] & 0xf0;
567
      (*info->fprintf_func) (info->stream, " + ");
568
      print_slot_insn (cd, pc, info, SLOTS_P0S, insn);
569
 
570
      insn[0^e] = buf[4^e] << 4 | buf[5^e] >> 4;
571
      insn[1^e] = buf[5^e] << 4 | buf[6^e] >> 4;
572
      insn[2^e] = buf[6^e] << 4 | buf[7^e] >> 4;
573
      insn[3^e] = buf[7^e] << 4;
574
      (*info->fprintf_func) (info->stream, " + ");
575
      print_slot_insn (cd, pc, info, SLOTS_P1, insn);
576
    }
577
  else if ((buf[0^e] & 0xf0) == 0xf0 && (buf[1^e] & 0x0f) == 0x07)
578
    {
579
      /*      <--00--><--11--><--22--><--33--><--44--><--55--><--66--><--77--> */
580
      /* V3   1111[--p0--]0111[--------p0--------][------------p1------------] */
581
      /*                                          00000000111111112222222233333333 */
582
 
583
      insn[0^e] = buf[0^e] << 4 | buf[1^e] >> 4;
584
      insn[1^e] = buf[2^e];
585
      insn[2^e] = buf[3^e];
586
      insn[3^e] = buf[4^e] & 0xf0;
587
      print_slot_insn (cd, pc, info, SLOTS_P0, insn);
588
 
589
      insn[0^e] = buf[4^e] << 4 | buf[5^e] >> 4;
590
      insn[1^e] = buf[5^e] << 4 | buf[6^e] >> 4;
591
      insn[2^e] = buf[6^e] << 4 | buf[7^e] >> 4;
592
      insn[3^e] = buf[7^e] << 4;
593
      (*info->fprintf_func) (info->stream, " + ");
594
      print_slot_insn (cd, pc, info, SLOTS_P1, insn);
595
    }
596
  else
597
    {
598
      /*      <--00--><--11--><--22--><--33--><--44--><--55--><--66--><--77--> */
599
      /* V2   [-------------core-------------]xxxx[------------p1------------] */
600
      print_insn (cd, pc, info, buf, 4);
601
 
602
      insn[0^e] = buf[4^e] << 4 | buf[5^e] >> 4;
603
      insn[1^e] = buf[5^e] << 4 | buf[6^e] >> 4;
604
      insn[2^e] = buf[6^e] << 4 | buf[7^e] >> 4;
605
      insn[3^e] = buf[7^e] << 4;
606
      (*info->fprintf_func) (info->stream, " + ");
607
      print_slot_insn (cd, pc, info, SLOTS_P1, insn);
608
    }
609
 
610
  return 8;
611
}
612
 
613
#endif /* MEP_IVC2_SUPPORTED */
614
 
615
/* This is a hack.  SID calls this to update the disassembler as the
616
   CPU changes modes.  */
617
static int mep_ivc2_disassemble_p = 0;
618
static int mep_ivc2_vliw_disassemble_p = 0;
619
 
620
void
621
mep_print_insn_set_ivc2_mode (int ivc2_p, int vliw_p, int cfg_idx);
622
void
623
mep_print_insn_set_ivc2_mode (int ivc2_p, int vliw_p, int cfg_idx)
624
{
625
  mep_ivc2_disassemble_p = ivc2_p;
626
  mep_ivc2_vliw_disassemble_p = vliw_p;
627
  mep_config_index = cfg_idx;
628
}
629
 
630
static int
631
mep_print_insn (CGEN_CPU_DESC cd, bfd_vma pc, disassemble_info *info)
632
{
633
  int status;
634
  int cop_type;
635
  int ivc2 = 0;
636
  static CGEN_ATTR_VALUE_BITSET_TYPE *ivc2_core_isa = NULL;
637
 
638
  if (ivc2_core_isa == NULL)
639
    {
640
      /* IVC2 has some core-only coprocessor instructions.  We
641
         use COP32 to flag those, and COP64 for the VLIW ones,
642
         since they have the same names.  */
643
      ivc2_core_isa = cgen_bitset_create (MAX_ISAS);
644
    }
645
 
646
  /* Extract and adapt to configuration number, if available. */
647
  if (info->section && info->section->owner)
648
    {
649
      bfd *abfd = info->section->owner;
650
      mep_config_index = abfd->tdata.elf_obj_data->elf_header->e_flags & EF_MEP_INDEX_MASK;
651
      /* This instantly redefines MEP_CONFIG, MEP_OMASK, .... MEP_VLIW64 */
652
 
653
      cop_type = abfd->tdata.elf_obj_data->elf_header->e_flags & EF_MEP_COP_MASK;
654
      if (cop_type == EF_MEP_COP_IVC2)
655
        ivc2 = 1;
656
    }
657
 
658
  /* Picking the right ISA bitmask for the current context is tricky.  */
659
  if (info->section)
660
    {
661
      if (info->section->flags & SEC_MEP_VLIW)
662
        {
663
#ifdef MEP_IVC2_SUPPORTED
664
          if (ivc2)
665
            {
666
              /* ivc2 has its own way of selecting its functions.  */
667
              cd->isas = & MEP_CORE_ISA;
668
              status = mep_examine_ivc2_insns (cd, pc, info);
669
            }
670
          else
671
#endif
672
            /* Are we in 32 or 64 bit vliw mode?  */
673
            if (MEP_VLIW64)
674
              status = mep_examine_vliw64_insns (cd, pc, info);
675
            else
676
              status = mep_examine_vliw32_insns (cd, pc, info);
677
          /* Both the above branches set their own isa bitmasks.  */
678
        }
679
      else
680
        {
681
          if (ivc2)
682
            {
683
              cgen_bitset_clear (ivc2_core_isa);
684
              cgen_bitset_union (ivc2_core_isa, &MEP_CORE_ISA, ivc2_core_isa);
685
              cgen_bitset_union (ivc2_core_isa, &MEP_COP32_ISA, ivc2_core_isa);
686
              cd->isas = ivc2_core_isa;
687
            }
688
          else
689
            cd->isas = & MEP_CORE_ISA;
690
          status = default_print_insn (cd, pc, info);
691
        }
692
    }
693
  else /* sid or gdb */
694
    {
695
#ifdef MEP_IVC2_SUPPORTED
696
      if (mep_ivc2_disassemble_p)
697
        {
698
          if (mep_ivc2_vliw_disassemble_p)
699
            {
700
              cd->isas = & MEP_CORE_ISA;
701
              status = mep_examine_ivc2_insns (cd, pc, info);
702
              return status;
703
            }
704
          else
705
            {
706
              if (ivc2)
707
                cd->isas = ivc2_core_isa;
708
            }
709
        }
710
#endif
711
 
712
      status = default_print_insn (cd, pc, info);
713
    }
714
 
715
  return status;
716
}
717
 
718
 
719
/* -- opc.c */
720
 
721
void mep_cgen_print_operand
722
  (CGEN_CPU_DESC, int, PTR, CGEN_FIELDS *, void const *, bfd_vma, int);
723
 
724
/* Main entry point for printing operands.
725
   XINFO is a `void *' and not a `disassemble_info *' to not put a requirement
726
   of dis-asm.h on cgen.h.
727
 
728
   This function is basically just a big switch statement.  Earlier versions
729
   used tables to look up the function to use, but
730
   - if the table contains both assembler and disassembler functions then
731
     the disassembler contains much of the assembler and vice-versa,
732
   - there's a lot of inlining possibilities as things grow,
733
   - using a switch statement avoids the function call overhead.
734
 
735
   This function could be moved into `print_insn_normal', but keeping it
736
   separate makes clear the interface between `print_insn_normal' and each of
737
   the handlers.  */
738
 
739
void
740
mep_cgen_print_operand (CGEN_CPU_DESC cd,
741
                           int opindex,
742
                           void * xinfo,
743
                           CGEN_FIELDS *fields,
744
                           void const *attrs ATTRIBUTE_UNUSED,
745
                           bfd_vma pc,
746
                           int length)
747
{
748
  disassemble_info *info = (disassemble_info *) xinfo;
749
 
750
  switch (opindex)
751
    {
752
    case MEP_OPERAND_ADDR24A4 :
753
      print_normal (cd, info, fields->f_24u8a4n, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
754
      break;
755
    case MEP_OPERAND_C5RMUIMM20 :
756
      print_normal (cd, info, fields->f_c5_rmuimm20, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
757
      break;
758
    case MEP_OPERAND_C5RNMUIMM24 :
759
      print_normal (cd, info, fields->f_c5_rnmuimm24, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
760
      break;
761
    case MEP_OPERAND_CALLNUM :
762
      print_normal (cd, info, fields->f_callnum, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
763
      break;
764
    case MEP_OPERAND_CCCC :
765
      print_normal (cd, info, fields->f_rm, 0, pc, length);
766
      break;
767
    case MEP_OPERAND_CCRN :
768
      print_keyword (cd, info, & mep_cgen_opval_h_ccr, fields->f_ccrn, 0|(1<<CGEN_OPERAND_VIRTUAL));
769
      break;
770
    case MEP_OPERAND_CDISP10 :
771
      print_normal (cd, info, fields->f_cdisp10, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
772
      break;
773
    case MEP_OPERAND_CDISP10A2 :
774
      print_normal (cd, info, fields->f_cdisp10, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
775
      break;
776
    case MEP_OPERAND_CDISP10A4 :
777
      print_normal (cd, info, fields->f_cdisp10, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
778
      break;
779
    case MEP_OPERAND_CDISP10A8 :
780
      print_normal (cd, info, fields->f_cdisp10, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
781
      break;
782
    case MEP_OPERAND_CDISP12 :
783
      print_normal (cd, info, fields->f_12s20, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
784
      break;
785
    case MEP_OPERAND_CIMM4 :
786
      print_normal (cd, info, fields->f_rn, 0, pc, length);
787
      break;
788
    case MEP_OPERAND_CIMM5 :
789
      print_normal (cd, info, fields->f_5u24, 0, pc, length);
790
      break;
791
    case MEP_OPERAND_CODE16 :
792
      print_normal (cd, info, fields->f_16u16, 0, pc, length);
793
      break;
794
    case MEP_OPERAND_CODE24 :
795
      print_normal (cd, info, fields->f_24u4n, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
796
      break;
797
    case MEP_OPERAND_CP_FLAG :
798
      print_keyword (cd, info, & mep_cgen_opval_h_ccr, 0, 0);
799
      break;
800
    case MEP_OPERAND_CRN :
801
      print_keyword (cd, info, & mep_cgen_opval_h_cr, fields->f_crn, 0);
802
      break;
803
    case MEP_OPERAND_CRN64 :
804
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_crn, 0);
805
      break;
806
    case MEP_OPERAND_CRNX :
807
      print_keyword (cd, info, & mep_cgen_opval_h_cr, fields->f_crnx, 0|(1<<CGEN_OPERAND_VIRTUAL));
808
      break;
809
    case MEP_OPERAND_CRNX64 :
810
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_crnx, 0|(1<<CGEN_OPERAND_VIRTUAL));
811
      break;
812
    case MEP_OPERAND_CROC :
813
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u7, 0);
814
      break;
815
    case MEP_OPERAND_CROP :
816
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u23, 0);
817
      break;
818
    case MEP_OPERAND_CRPC :
819
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u26, 0);
820
      break;
821
    case MEP_OPERAND_CRPP :
822
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u18, 0);
823
      break;
824
    case MEP_OPERAND_CRQC :
825
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u21, 0);
826
      break;
827
    case MEP_OPERAND_CRQP :
828
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_5u13, 0);
829
      break;
830
    case MEP_OPERAND_CSRN :
831
      print_keyword (cd, info, & mep_cgen_opval_h_csr, fields->f_csrn, 0|(1<<CGEN_OPERAND_VIRTUAL));
832
      break;
833
    case MEP_OPERAND_CSRN_IDX :
834
      print_normal (cd, info, fields->f_csrn, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
835
      break;
836
    case MEP_OPERAND_DBG :
837
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
838
      break;
839
    case MEP_OPERAND_DEPC :
840
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
841
      break;
842
    case MEP_OPERAND_EPC :
843
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
844
      break;
845
    case MEP_OPERAND_EXC :
846
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
847
      break;
848
    case MEP_OPERAND_HI :
849
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
850
      break;
851
    case MEP_OPERAND_IMM16P0 :
852
      print_normal (cd, info, fields->f_ivc2_imm16p0, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
853
      break;
854
    case MEP_OPERAND_IMM3P12 :
855
      print_normal (cd, info, fields->f_ivc2_3u12, 0, pc, length);
856
      break;
857
    case MEP_OPERAND_IMM3P25 :
858
      print_normal (cd, info, fields->f_ivc2_3u25, 0, pc, length);
859
      break;
860
    case MEP_OPERAND_IMM3P4 :
861
      print_normal (cd, info, fields->f_ivc2_3u4, 0, pc, length);
862
      break;
863
    case MEP_OPERAND_IMM3P5 :
864
      print_normal (cd, info, fields->f_ivc2_3u5, 0, pc, length);
865
      break;
866
    case MEP_OPERAND_IMM3P9 :
867
      print_normal (cd, info, fields->f_ivc2_3u9, 0, pc, length);
868
      break;
869
    case MEP_OPERAND_IMM4P10 :
870
      print_normal (cd, info, fields->f_ivc2_4u10, 0, pc, length);
871
      break;
872
    case MEP_OPERAND_IMM4P4 :
873
      print_normal (cd, info, fields->f_ivc2_4u4, 0, pc, length);
874
      break;
875
    case MEP_OPERAND_IMM4P8 :
876
      print_normal (cd, info, fields->f_ivc2_4u8, 0, pc, length);
877
      break;
878
    case MEP_OPERAND_IMM5P23 :
879
      print_normal (cd, info, fields->f_ivc2_5u23, 0, pc, length);
880
      break;
881
    case MEP_OPERAND_IMM5P3 :
882
      print_normal (cd, info, fields->f_ivc2_5u3, 0, pc, length);
883
      break;
884
    case MEP_OPERAND_IMM5P7 :
885
      print_normal (cd, info, fields->f_ivc2_5u7, 0, pc, length);
886
      break;
887
    case MEP_OPERAND_IMM5P8 :
888
      print_normal (cd, info, fields->f_ivc2_5u8, 0, pc, length);
889
      break;
890
    case MEP_OPERAND_IMM6P2 :
891
      print_normal (cd, info, fields->f_ivc2_6u2, 0, pc, length);
892
      break;
893
    case MEP_OPERAND_IMM6P6 :
894
      print_normal (cd, info, fields->f_ivc2_6u6, 0, pc, length);
895
      break;
896
    case MEP_OPERAND_IMM8P0 :
897
      print_normal (cd, info, fields->f_ivc2_8u0, 0, pc, length);
898
      break;
899
    case MEP_OPERAND_IMM8P20 :
900
      print_normal (cd, info, fields->f_ivc2_8u20, 0, pc, length);
901
      break;
902
    case MEP_OPERAND_IMM8P4 :
903
      print_normal (cd, info, fields->f_ivc2_8u4, 0, pc, length);
904
      break;
905
    case MEP_OPERAND_IVC_X_0_2 :
906
      print_normal (cd, info, fields->f_ivc2_2u0, 0, pc, length);
907
      break;
908
    case MEP_OPERAND_IVC_X_0_3 :
909
      print_normal (cd, info, fields->f_ivc2_3u0, 0, pc, length);
910
      break;
911
    case MEP_OPERAND_IVC_X_0_4 :
912
      print_normal (cd, info, fields->f_ivc2_4u0, 0, pc, length);
913
      break;
914
    case MEP_OPERAND_IVC_X_0_5 :
915
      print_normal (cd, info, fields->f_ivc2_5u0, 0, pc, length);
916
      break;
917
    case MEP_OPERAND_IVC_X_6_1 :
918
      print_normal (cd, info, fields->f_ivc2_1u6, 0, pc, length);
919
      break;
920
    case MEP_OPERAND_IVC_X_6_2 :
921
      print_normal (cd, info, fields->f_ivc2_2u6, 0, pc, length);
922
      break;
923
    case MEP_OPERAND_IVC_X_6_3 :
924
      print_normal (cd, info, fields->f_ivc2_3u6, 0, pc, length);
925
      break;
926
    case MEP_OPERAND_IVC2_ACC0_0 :
927
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
928
      break;
929
    case MEP_OPERAND_IVC2_ACC0_1 :
930
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
931
      break;
932
    case MEP_OPERAND_IVC2_ACC0_2 :
933
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
934
      break;
935
    case MEP_OPERAND_IVC2_ACC0_3 :
936
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
937
      break;
938
    case MEP_OPERAND_IVC2_ACC0_4 :
939
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
940
      break;
941
    case MEP_OPERAND_IVC2_ACC0_5 :
942
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
943
      break;
944
    case MEP_OPERAND_IVC2_ACC0_6 :
945
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
946
      break;
947
    case MEP_OPERAND_IVC2_ACC0_7 :
948
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
949
      break;
950
    case MEP_OPERAND_IVC2_ACC1_0 :
951
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
952
      break;
953
    case MEP_OPERAND_IVC2_ACC1_1 :
954
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
955
      break;
956
    case MEP_OPERAND_IVC2_ACC1_2 :
957
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
958
      break;
959
    case MEP_OPERAND_IVC2_ACC1_3 :
960
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
961
      break;
962
    case MEP_OPERAND_IVC2_ACC1_4 :
963
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
964
      break;
965
    case MEP_OPERAND_IVC2_ACC1_5 :
966
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
967
      break;
968
    case MEP_OPERAND_IVC2_ACC1_6 :
969
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
970
      break;
971
    case MEP_OPERAND_IVC2_ACC1_7 :
972
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
973
      break;
974
    case MEP_OPERAND_IVC2_CC :
975
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
976
      break;
977
    case MEP_OPERAND_IVC2_COFA0 :
978
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
979
      break;
980
    case MEP_OPERAND_IVC2_COFA1 :
981
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
982
      break;
983
    case MEP_OPERAND_IVC2_COFR0 :
984
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
985
      break;
986
    case MEP_OPERAND_IVC2_COFR1 :
987
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
988
      break;
989
    case MEP_OPERAND_IVC2_CSAR0 :
990
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
991
      break;
992
    case MEP_OPERAND_IVC2_CSAR1 :
993
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, 0, 0);
994
      break;
995
    case MEP_OPERAND_IVC2C3CCRN :
996
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, fields->f_ivc2_ccrn_c3, 0|(1<<CGEN_OPERAND_VIRTUAL));
997
      break;
998
    case MEP_OPERAND_IVC2CCRN :
999
      print_keyword (cd, info, & mep_cgen_opval_h_ccr_ivc2, fields->f_ivc2_ccrn, 0|(1<<CGEN_OPERAND_VIRTUAL));
1000
      break;
1001
    case MEP_OPERAND_IVC2CRN :
1002
      print_keyword (cd, info, & mep_cgen_opval_h_cr64, fields->f_ivc2_crnx, 0|(1<<CGEN_OPERAND_VIRTUAL));
1003
      break;
1004
    case MEP_OPERAND_IVC2RM :
1005
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_ivc2_crm, 0);
1006
      break;
1007
    case MEP_OPERAND_LO :
1008
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1009
      break;
1010
    case MEP_OPERAND_LP :
1011
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1012
      break;
1013
    case MEP_OPERAND_MB0 :
1014
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1015
      break;
1016
    case MEP_OPERAND_MB1 :
1017
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1018
      break;
1019
    case MEP_OPERAND_ME0 :
1020
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1021
      break;
1022
    case MEP_OPERAND_ME1 :
1023
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1024
      break;
1025
    case MEP_OPERAND_NPC :
1026
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1027
      break;
1028
    case MEP_OPERAND_OPT :
1029
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1030
      break;
1031
    case MEP_OPERAND_PCABS24A2 :
1032
      print_address (cd, info, fields->f_24u5a2n, 0|(1<<CGEN_OPERAND_ABS_ADDR)|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
1033
      break;
1034
    case MEP_OPERAND_PCREL12A2 :
1035
      print_address (cd, info, fields->f_12s4a2, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_RELAX)|(1<<CGEN_OPERAND_PCREL_ADDR), pc, length);
1036
      break;
1037
    case MEP_OPERAND_PCREL17A2 :
1038
      print_address (cd, info, fields->f_17s16a2, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_RELAX)|(1<<CGEN_OPERAND_PCREL_ADDR), pc, length);
1039
      break;
1040
    case MEP_OPERAND_PCREL24A2 :
1041
      print_address (cd, info, fields->f_24s5a2n, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_PCREL_ADDR)|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
1042
      break;
1043
    case MEP_OPERAND_PCREL8A2 :
1044
      print_address (cd, info, fields->f_8s8a2, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_RELAX)|(1<<CGEN_OPERAND_PCREL_ADDR), pc, length);
1045
      break;
1046
    case MEP_OPERAND_PSW :
1047
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1048
      break;
1049
    case MEP_OPERAND_R0 :
1050
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1051
      break;
1052
    case MEP_OPERAND_R1 :
1053
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1054
      break;
1055
    case MEP_OPERAND_RL :
1056
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rl, 0);
1057
      break;
1058
    case MEP_OPERAND_RL5 :
1059
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rl5, 0);
1060
      break;
1061
    case MEP_OPERAND_RM :
1062
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rm, 0);
1063
      break;
1064
    case MEP_OPERAND_RMA :
1065
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rm, 0);
1066
      break;
1067
    case MEP_OPERAND_RN :
1068
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1069
      break;
1070
    case MEP_OPERAND_RN3 :
1071
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1072
      break;
1073
    case MEP_OPERAND_RN3C :
1074
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1075
      break;
1076
    case MEP_OPERAND_RN3L :
1077
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1078
      break;
1079
    case MEP_OPERAND_RN3S :
1080
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1081
      break;
1082
    case MEP_OPERAND_RN3UC :
1083
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1084
      break;
1085
    case MEP_OPERAND_RN3UL :
1086
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1087
      break;
1088
    case MEP_OPERAND_RN3US :
1089
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn3, 0);
1090
      break;
1091
    case MEP_OPERAND_RNC :
1092
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1093
      break;
1094
    case MEP_OPERAND_RNL :
1095
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1096
      break;
1097
    case MEP_OPERAND_RNS :
1098
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1099
      break;
1100
    case MEP_OPERAND_RNUC :
1101
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1102
      break;
1103
    case MEP_OPERAND_RNUL :
1104
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1105
      break;
1106
    case MEP_OPERAND_RNUS :
1107
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, fields->f_rn, 0);
1108
      break;
1109
    case MEP_OPERAND_SAR :
1110
      print_keyword (cd, info, & mep_cgen_opval_h_csr, 0, 0);
1111
      break;
1112
    case MEP_OPERAND_SDISP16 :
1113
      print_normal (cd, info, fields->f_16s16, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1114
      break;
1115
    case MEP_OPERAND_SIMM16 :
1116
      print_normal (cd, info, fields->f_16s16, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1117
      break;
1118
    case MEP_OPERAND_SIMM16P0 :
1119
      print_normal (cd, info, fields->f_ivc2_simm16p0, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
1120
      break;
1121
    case MEP_OPERAND_SIMM6 :
1122
      print_normal (cd, info, fields->f_6s8, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1123
      break;
1124
    case MEP_OPERAND_SIMM8 :
1125
      print_normal (cd, info, fields->f_8s8, 0|(1<<CGEN_OPERAND_SIGNED)|(1<<CGEN_OPERAND_RELOC_IMPLIES_OVERFLOW), pc, length);
1126
      break;
1127
    case MEP_OPERAND_SIMM8P0 :
1128
      print_normal (cd, info, fields->f_ivc2_8s0, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1129
      break;
1130
    case MEP_OPERAND_SIMM8P20 :
1131
      print_normal (cd, info, fields->f_ivc2_8s20, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1132
      break;
1133
    case MEP_OPERAND_SIMM8P4 :
1134
      print_normal (cd, info, fields->f_ivc2_8s4, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1135
      break;
1136
    case MEP_OPERAND_SP :
1137
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1138
      break;
1139
    case MEP_OPERAND_SPR :
1140
      print_spreg (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1141
      break;
1142
    case MEP_OPERAND_TP :
1143
      print_keyword (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1144
      break;
1145
    case MEP_OPERAND_TPR :
1146
      print_tpreg (cd, info, & mep_cgen_opval_h_gpr, 0, 0);
1147
      break;
1148
    case MEP_OPERAND_UDISP2 :
1149
      print_normal (cd, info, fields->f_2u6, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1150
      break;
1151
    case MEP_OPERAND_UDISP7 :
1152
      print_normal (cd, info, fields->f_7u9, 0, pc, length);
1153
      break;
1154
    case MEP_OPERAND_UDISP7A2 :
1155
      print_normal (cd, info, fields->f_7u9a2, 0, pc, length);
1156
      break;
1157
    case MEP_OPERAND_UDISP7A4 :
1158
      print_normal (cd, info, fields->f_7u9a4, 0, pc, length);
1159
      break;
1160
    case MEP_OPERAND_UIMM16 :
1161
      print_normal (cd, info, fields->f_16u16, 0, pc, length);
1162
      break;
1163
    case MEP_OPERAND_UIMM2 :
1164
      print_normal (cd, info, fields->f_2u10, 0, pc, length);
1165
      break;
1166
    case MEP_OPERAND_UIMM24 :
1167
      print_normal (cd, info, fields->f_24u8n, 0|(1<<CGEN_OPERAND_VIRTUAL), pc, length);
1168
      break;
1169
    case MEP_OPERAND_UIMM3 :
1170
      print_normal (cd, info, fields->f_3u5, 0, pc, length);
1171
      break;
1172
    case MEP_OPERAND_UIMM4 :
1173
      print_normal (cd, info, fields->f_4u8, 0, pc, length);
1174
      break;
1175
    case MEP_OPERAND_UIMM5 :
1176
      print_normal (cd, info, fields->f_5u8, 0, pc, length);
1177
      break;
1178
    case MEP_OPERAND_UIMM7A4 :
1179
      print_normal (cd, info, fields->f_7u9a4, 0, pc, length);
1180
      break;
1181
    case MEP_OPERAND_ZERO :
1182
      print_normal (cd, info, 0, 0|(1<<CGEN_OPERAND_SIGNED), pc, length);
1183
      break;
1184
 
1185
    default :
1186
      /* xgettext:c-format */
1187
      fprintf (stderr, _("Unrecognized field %d while printing insn.\n"),
1188
               opindex);
1189
    abort ();
1190
  }
1191
}
1192
 
1193
cgen_print_fn * const mep_cgen_print_handlers[] =
1194
{
1195
  print_insn_normal,
1196
};
1197
 
1198
 
1199
void
1200
mep_cgen_init_dis (CGEN_CPU_DESC cd)
1201
{
1202
  mep_cgen_init_opcode_table (cd);
1203
  mep_cgen_init_ibld_table (cd);
1204
  cd->print_handlers = & mep_cgen_print_handlers[0];
1205
  cd->print_operand = mep_cgen_print_operand;
1206
}
1207
 
1208
 
1209
/* Default print handler.  */
1210
 
1211
static void
1212
print_normal (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED,
1213
              void *dis_info,
1214
              long value,
1215
              unsigned int attrs,
1216
              bfd_vma pc ATTRIBUTE_UNUSED,
1217
              int length ATTRIBUTE_UNUSED)
1218
{
1219
  disassemble_info *info = (disassemble_info *) dis_info;
1220
 
1221
  /* Print the operand as directed by the attributes.  */
1222
  if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_SEM_ONLY))
1223
    ; /* nothing to do */
1224
  else if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_SIGNED))
1225
    (*info->fprintf_func) (info->stream, "%ld", value);
1226
  else
1227
    (*info->fprintf_func) (info->stream, "0x%lx", value);
1228
}
1229
 
1230
/* Default address handler.  */
1231
 
1232
static void
1233
print_address (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED,
1234
               void *dis_info,
1235
               bfd_vma value,
1236
               unsigned int attrs,
1237
               bfd_vma pc ATTRIBUTE_UNUSED,
1238
               int length ATTRIBUTE_UNUSED)
1239
{
1240
  disassemble_info *info = (disassemble_info *) dis_info;
1241
 
1242
  /* Print the operand as directed by the attributes.  */
1243
  if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_SEM_ONLY))
1244
    ; /* Nothing to do.  */
1245
  else if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_PCREL_ADDR))
1246
    (*info->print_address_func) (value, info);
1247
  else if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_ABS_ADDR))
1248
    (*info->print_address_func) (value, info);
1249
  else if (CGEN_BOOL_ATTR (attrs, CGEN_OPERAND_SIGNED))
1250
    (*info->fprintf_func) (info->stream, "%ld", (long) value);
1251
  else
1252
    (*info->fprintf_func) (info->stream, "0x%lx", (long) value);
1253
}
1254
 
1255
/* Keyword print handler.  */
1256
 
1257
static void
1258
print_keyword (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED,
1259
               void *dis_info,
1260
               CGEN_KEYWORD *keyword_table,
1261
               long value,
1262
               unsigned int attrs ATTRIBUTE_UNUSED)
1263
{
1264
  disassemble_info *info = (disassemble_info *) dis_info;
1265
  const CGEN_KEYWORD_ENTRY *ke;
1266
 
1267
  ke = cgen_keyword_lookup_value (keyword_table, value);
1268
  if (ke != NULL)
1269
    (*info->fprintf_func) (info->stream, "%s", ke->name);
1270
  else
1271
    (*info->fprintf_func) (info->stream, "???");
1272
}
1273
 
1274
/* Default insn printer.
1275
 
1276
   DIS_INFO is defined as `void *' so the disassembler needn't know anything
1277
   about disassemble_info.  */
1278
 
1279
static void
1280
print_insn_normal (CGEN_CPU_DESC cd,
1281
                   void *dis_info,
1282
                   const CGEN_INSN *insn,
1283
                   CGEN_FIELDS *fields,
1284
                   bfd_vma pc,
1285
                   int length)
1286
{
1287
  const CGEN_SYNTAX *syntax = CGEN_INSN_SYNTAX (insn);
1288
  disassemble_info *info = (disassemble_info *) dis_info;
1289
  const CGEN_SYNTAX_CHAR_TYPE *syn;
1290
 
1291
  CGEN_INIT_PRINT (cd);
1292
 
1293
  for (syn = CGEN_SYNTAX_STRING (syntax); *syn; ++syn)
1294
    {
1295
      if (CGEN_SYNTAX_MNEMONIC_P (*syn))
1296
        {
1297
          (*info->fprintf_func) (info->stream, "%s", CGEN_INSN_MNEMONIC (insn));
1298
          continue;
1299
        }
1300
      if (CGEN_SYNTAX_CHAR_P (*syn))
1301
        {
1302
          (*info->fprintf_func) (info->stream, "%c", CGEN_SYNTAX_CHAR (*syn));
1303
          continue;
1304
        }
1305
 
1306
      /* We have an operand.  */
1307
      mep_cgen_print_operand (cd, CGEN_SYNTAX_FIELD (*syn), info,
1308
                                 fields, CGEN_INSN_ATTRS (insn), pc, length);
1309
    }
1310
}
1311
 
1312
/* Subroutine of print_insn. Reads an insn into the given buffers and updates
1313
   the extract info.
1314
   Returns 0 if all is well, non-zero otherwise.  */
1315
 
1316
static int
1317
read_insn (CGEN_CPU_DESC cd ATTRIBUTE_UNUSED,
1318
           bfd_vma pc,
1319
           disassemble_info *info,
1320
           bfd_byte *buf,
1321
           int buflen,
1322
           CGEN_EXTRACT_INFO *ex_info,
1323
           unsigned long *insn_value)
1324
{
1325
  int status = (*info->read_memory_func) (pc, buf, buflen, info);
1326
 
1327
  if (status != 0)
1328
    {
1329
      (*info->memory_error_func) (status, pc, info);
1330
      return -1;
1331
    }
1332
 
1333
  ex_info->dis_info = info;
1334
  ex_info->valid = (1 << buflen) - 1;
1335
  ex_info->insn_bytes = buf;
1336
 
1337
  *insn_value = bfd_get_bits (buf, buflen * 8, info->endian == BFD_ENDIAN_BIG);
1338
  return 0;
1339
}
1340
 
1341
/* Utility to print an insn.
1342
   BUF is the base part of the insn, target byte order, BUFLEN bytes long.
1343
   The result is the size of the insn in bytes or zero for an unknown insn
1344
   or -1 if an error occurs fetching data (memory_error_func will have
1345
   been called).  */
1346
 
1347
static int
1348
print_insn (CGEN_CPU_DESC cd,
1349
            bfd_vma pc,
1350
            disassemble_info *info,
1351
            bfd_byte *buf,
1352
            unsigned int buflen)
1353
{
1354
  CGEN_INSN_INT insn_value;
1355
  const CGEN_INSN_LIST *insn_list;
1356
  CGEN_EXTRACT_INFO ex_info;
1357
  int basesize;
1358
 
1359
  /* Extract base part of instruction, just in case CGEN_DIS_* uses it. */
1360
  basesize = cd->base_insn_bitsize < buflen * 8 ?
1361
                                     cd->base_insn_bitsize : buflen * 8;
1362
  insn_value = cgen_get_insn_value (cd, buf, basesize);
1363
 
1364
 
1365
  /* Fill in ex_info fields like read_insn would.  Don't actually call
1366
     read_insn, since the incoming buffer is already read (and possibly
1367
     modified a la m32r).  */
1368
  ex_info.valid = (1 << buflen) - 1;
1369
  ex_info.dis_info = info;
1370
  ex_info.insn_bytes = buf;
1371
 
1372
  /* The instructions are stored in hash lists.
1373
     Pick the first one and keep trying until we find the right one.  */
1374
 
1375
  insn_list = CGEN_DIS_LOOKUP_INSN (cd, (char *) buf, insn_value);
1376
  while (insn_list != NULL)
1377
    {
1378
      const CGEN_INSN *insn = insn_list->insn;
1379
      CGEN_FIELDS fields;
1380
      int length;
1381
      unsigned long insn_value_cropped;
1382
 
1383
#ifdef CGEN_VALIDATE_INSN_SUPPORTED 
1384
      /* Not needed as insn shouldn't be in hash lists if not supported.  */
1385
      /* Supported by this cpu?  */
1386
      if (! mep_cgen_insn_supported (cd, insn))
1387
        {
1388
          insn_list = CGEN_DIS_NEXT_INSN (insn_list);
1389
          continue;
1390
        }
1391
#endif
1392
 
1393
      /* Basic bit mask must be correct.  */
1394
      /* ??? May wish to allow target to defer this check until the extract
1395
         handler.  */
1396
 
1397
      /* Base size may exceed this instruction's size.  Extract the
1398
         relevant part from the buffer. */
1399
      if ((unsigned) (CGEN_INSN_BITSIZE (insn) / 8) < buflen &&
1400
          (unsigned) (CGEN_INSN_BITSIZE (insn) / 8) <= sizeof (unsigned long))
1401
        insn_value_cropped = bfd_get_bits (buf, CGEN_INSN_BITSIZE (insn),
1402
                                           info->endian == BFD_ENDIAN_BIG);
1403
      else
1404
        insn_value_cropped = insn_value;
1405
 
1406
      if ((insn_value_cropped & CGEN_INSN_BASE_MASK (insn))
1407
          == CGEN_INSN_BASE_VALUE (insn))
1408
        {
1409
          /* Printing is handled in two passes.  The first pass parses the
1410
             machine insn and extracts the fields.  The second pass prints
1411
             them.  */
1412
 
1413
          /* Make sure the entire insn is loaded into insn_value, if it
1414
             can fit.  */
1415
          if (((unsigned) CGEN_INSN_BITSIZE (insn) > cd->base_insn_bitsize) &&
1416
              (unsigned) (CGEN_INSN_BITSIZE (insn) / 8) <= sizeof (unsigned long))
1417
            {
1418
              unsigned long full_insn_value;
1419
              int rc = read_insn (cd, pc, info, buf,
1420
                                  CGEN_INSN_BITSIZE (insn) / 8,
1421
                                  & ex_info, & full_insn_value);
1422
              if (rc != 0)
1423
                return rc;
1424
              length = CGEN_EXTRACT_FN (cd, insn)
1425
                (cd, insn, &ex_info, full_insn_value, &fields, pc);
1426
            }
1427
          else
1428
            length = CGEN_EXTRACT_FN (cd, insn)
1429
              (cd, insn, &ex_info, insn_value_cropped, &fields, pc);
1430
 
1431
          /* Length < 0 -> error.  */
1432
          if (length < 0)
1433
            return length;
1434
          if (length > 0)
1435
            {
1436
              CGEN_PRINT_FN (cd, insn) (cd, info, insn, &fields, pc, length);
1437
              /* Length is in bits, result is in bytes.  */
1438
              return length / 8;
1439
            }
1440
        }
1441
 
1442
      insn_list = CGEN_DIS_NEXT_INSN (insn_list);
1443
    }
1444
 
1445
  return 0;
1446
}
1447
 
1448
/* Default value for CGEN_PRINT_INSN.
1449
   The result is the size of the insn in bytes or zero for an unknown insn
1450
   or -1 if an error occured fetching bytes.  */
1451
 
1452
#ifndef CGEN_PRINT_INSN
1453
#define CGEN_PRINT_INSN default_print_insn
1454
#endif
1455
 
1456
static int
1457
default_print_insn (CGEN_CPU_DESC cd, bfd_vma pc, disassemble_info *info)
1458
{
1459
  bfd_byte buf[CGEN_MAX_INSN_SIZE];
1460
  int buflen;
1461
  int status;
1462
 
1463
  /* Attempt to read the base part of the insn.  */
1464
  buflen = cd->base_insn_bitsize / 8;
1465
  status = (*info->read_memory_func) (pc, buf, buflen, info);
1466
 
1467
  /* Try again with the minimum part, if min < base.  */
1468
  if (status != 0 && (cd->min_insn_bitsize < cd->base_insn_bitsize))
1469
    {
1470
      buflen = cd->min_insn_bitsize / 8;
1471
      status = (*info->read_memory_func) (pc, buf, buflen, info);
1472
    }
1473
 
1474
  if (status != 0)
1475
    {
1476
      (*info->memory_error_func) (status, pc, info);
1477
      return -1;
1478
    }
1479
 
1480
  return print_insn (cd, pc, info, buf, buflen);
1481
}
1482
 
1483
/* Main entry point.
1484
   Print one instruction from PC on INFO->STREAM.
1485
   Return the size of the instruction (in bytes).  */
1486
 
1487
typedef struct cpu_desc_list
1488
{
1489
  struct cpu_desc_list *next;
1490
  CGEN_BITSET *isa;
1491
  int mach;
1492
  int endian;
1493
  CGEN_CPU_DESC cd;
1494
} cpu_desc_list;
1495
 
1496
int
1497
print_insn_mep (bfd_vma pc, disassemble_info *info)
1498
{
1499
  static cpu_desc_list *cd_list = 0;
1500
  cpu_desc_list *cl = 0;
1501
  static CGEN_CPU_DESC cd = 0;
1502
  static CGEN_BITSET *prev_isa;
1503
  static int prev_mach;
1504
  static int prev_endian;
1505
  int length;
1506
  CGEN_BITSET *isa;
1507
  int mach;
1508
  int endian = (info->endian == BFD_ENDIAN_BIG
1509
                ? CGEN_ENDIAN_BIG
1510
                : CGEN_ENDIAN_LITTLE);
1511
  enum bfd_architecture arch;
1512
 
1513
  /* ??? gdb will set mach but leave the architecture as "unknown" */
1514
#ifndef CGEN_BFD_ARCH
1515
#define CGEN_BFD_ARCH bfd_arch_mep
1516
#endif
1517
  arch = info->arch;
1518
  if (arch == bfd_arch_unknown)
1519
    arch = CGEN_BFD_ARCH;
1520
 
1521
  /* There's no standard way to compute the machine or isa number
1522
     so we leave it to the target.  */
1523
#ifdef CGEN_COMPUTE_MACH
1524
  mach = CGEN_COMPUTE_MACH (info);
1525
#else
1526
  mach = info->mach;
1527
#endif
1528
 
1529
#ifdef CGEN_COMPUTE_ISA
1530
  {
1531
    static CGEN_BITSET *permanent_isa;
1532
 
1533
    if (!permanent_isa)
1534
      permanent_isa = cgen_bitset_create (MAX_ISAS);
1535
    isa = permanent_isa;
1536
    cgen_bitset_clear (isa);
1537
    cgen_bitset_add (isa, CGEN_COMPUTE_ISA (info));
1538
  }
1539
#else
1540
  isa = info->insn_sets;
1541
#endif
1542
 
1543
  /* If we've switched cpu's, try to find a handle we've used before */
1544
  if (cd
1545
      && (cgen_bitset_compare (isa, prev_isa) != 0
1546
          || mach != prev_mach
1547
          || endian != prev_endian))
1548
    {
1549
      cd = 0;
1550
      for (cl = cd_list; cl; cl = cl->next)
1551
        {
1552
          if (cgen_bitset_compare (cl->isa, isa) == 0 &&
1553
              cl->mach == mach &&
1554
              cl->endian == endian)
1555
            {
1556
              cd = cl->cd;
1557
              prev_isa = cd->isas;
1558
              break;
1559
            }
1560
        }
1561
    }
1562
 
1563
  /* If we haven't initialized yet, initialize the opcode table.  */
1564
  if (! cd)
1565
    {
1566
      const bfd_arch_info_type *arch_type = bfd_lookup_arch (arch, mach);
1567
      const char *mach_name;
1568
 
1569
      if (!arch_type)
1570
        abort ();
1571
      mach_name = arch_type->printable_name;
1572
 
1573
      prev_isa = cgen_bitset_copy (isa);
1574
      prev_mach = mach;
1575
      prev_endian = endian;
1576
      cd = mep_cgen_cpu_open (CGEN_CPU_OPEN_ISAS, prev_isa,
1577
                                 CGEN_CPU_OPEN_BFDMACH, mach_name,
1578
                                 CGEN_CPU_OPEN_ENDIAN, prev_endian,
1579
                                 CGEN_CPU_OPEN_END);
1580
      if (!cd)
1581
        abort ();
1582
 
1583
      /* Save this away for future reference.  */
1584
      cl = xmalloc (sizeof (struct cpu_desc_list));
1585
      cl->cd = cd;
1586
      cl->isa = prev_isa;
1587
      cl->mach = mach;
1588
      cl->endian = endian;
1589
      cl->next = cd_list;
1590
      cd_list = cl;
1591
 
1592
      mep_cgen_init_dis (cd);
1593
    }
1594
 
1595
  /* We try to have as much common code as possible.
1596
     But at this point some targets need to take over.  */
1597
  /* ??? Some targets may need a hook elsewhere.  Try to avoid this,
1598
     but if not possible try to move this hook elsewhere rather than
1599
     have two hooks.  */
1600
  length = CGEN_PRINT_INSN (cd, pc, info);
1601
  if (length > 0)
1602
    return length;
1603
  if (length < 0)
1604
    return -1;
1605
 
1606
  (*info->fprintf_func) (info->stream, UNKNOWN_INSN_MSG);
1607
  return cd->default_insn_bitsize / 8;
1608
}

powered by: WebSVN 2.1.0

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