1/* Disassemble h8300 instructions.
2   Copyright 1993, 1994, 1996, 1998, 2000, 2001, 2002, 2003, 2004, 2005, 2006
3   Free Software Foundation, Inc.
4
5   This program is free software; you can redistribute it and/or modify
6   it under the terms of the GNU General Public License as published by
7   the Free Software Foundation; either version 2 of the License, or
8   (at your option) any later version.
9
10   This program is distributed in the hope that it will be useful,
11   but WITHOUT ANY WARRANTY; without even the implied warranty of
12   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13   GNU General Public License for more details.
14
15   You should have received a copy of the GNU General Public License
16   along with this program; if not, write to the Free Software
17   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
18   MA 02110-1301, USA.  */
19
20#define DEFINE_TABLE
21
22#include "sysdep.h"
23#define h8_opcodes h8ops
24#include "opcode/h8300.h"
25#include "dis-asm.h"
26#include "opintl.h"
27#include "libiberty.h"
28
29struct h8_instruction
30{
31  int length;
32  const struct h8_opcode *opcode;
33};
34
35struct h8_instruction *h8_instructions;
36
37/* Run through the opcodes and sort them into order to make them easy
38   to disassemble.  */
39
40static void
41bfd_h8_disassemble_init (void)
42{
43  unsigned int i;
44  unsigned int nopcodes;
45  const struct h8_opcode *p;
46  struct h8_instruction *pi;
47
48  nopcodes = sizeof (h8_opcodes) / sizeof (struct h8_opcode);
49
50  h8_instructions = xmalloc (nopcodes * sizeof (struct h8_instruction));
51
52  for (p = h8_opcodes, pi = h8_instructions; p->name; p++, pi++)
53    {
54      int n1 = 0;
55      int n2 = 0;
56
57      if ((int) p->data.nib[0] < 16)
58	n1 = (int) p->data.nib[0];
59      else
60	n1 = 0;
61
62      if ((int) p->data.nib[1] < 16)
63	n2 = (int) p->data.nib[1];
64      else
65	n2 = 0;
66
67      /* Just make sure there are an even number of nibbles in it, and
68	 that the count is the same as the length.  */
69      for (i = 0; p->data.nib[i] != (op_type) E; i++)
70	;
71
72      if (i & 1)
73	{
74	  fprintf (stderr, "Internal error, h8_disassemble_init.\n");
75	  abort ();
76	}
77
78      pi->length = i / 2;
79      pi->opcode = p;
80    }
81
82  /* Add entry for the NULL vector terminator.  */
83  pi->length = 0;
84  pi->opcode = p;
85}
86
87static void
88extract_immediate (FILE *stream,
89		   op_type looking_for,
90		   int thisnib,
91		   unsigned char *data,
92		   int *cst,
93		   int *len,
94		   const struct h8_opcode *q)
95{
96  switch (looking_for & SIZE)
97    {
98    case L_2:
99      *len = 2;
100      *cst = thisnib & 3;
101
102      /* DISP2 special treatment.  */
103      if ((looking_for & MODE) == DISP)
104	{
105	  if (OP_KIND (q->how) == O_MOVAB
106	      || OP_KIND (q->how) == O_MOVAW
107	      || OP_KIND (q->how) == O_MOVAL)
108	    {
109	      /* Handling for mova insn.  */
110	      switch (q->args.nib[0] & MODE)
111		{
112		case INDEXB:
113		default:
114		  break;
115		case INDEXW:
116		  *cst *= 2;
117		  break;
118		case INDEXL:
119		  *cst *= 4;
120		  break;
121		}
122	    }
123	  else
124	    {
125	      /* Handling for non-mova insn.  */
126	      switch (OP_SIZE (q->how))
127		{
128		default: break;
129		case SW:
130		  *cst *= 2;
131		  break;
132		case SL:
133		  *cst *= 4;
134		  break;
135		}
136	    }
137	}
138      break;
139    case L_8:
140      *len = 8;
141      *cst = data[0];
142      break;
143    case L_16:
144    case L_16U:
145      *len = 16;
146      *cst = (data[0] << 8) + data [1];
147#if 0
148      if ((looking_for & SIZE) == L_16)
149	*cst = (short) *cst;	/* Sign extend.  */
150#endif
151      break;
152    case L_32:
153      *len = 32;
154      *cst = (data[0] << 24) + (data[1] << 16) + (data[2] << 8) + data[3];
155      break;
156    default:
157      *len = 0;
158      *cst = 0;
159      fprintf (stream, "DISP bad size\n");
160      break;
161    }
162}
163
164static const char *regnames[] =
165{
166  "r0h", "r1h", "r2h", "r3h", "r4h", "r5h", "r6h", "r7h",
167  "r0l", "r1l", "r2l", "r3l", "r4l", "r5l", "r6l", "r7l"
168};
169static const char *wregnames[] =
170{
171  "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7",
172  "e0", "e1", "e2", "e3", "e4", "e5", "e6", "e7"
173};
174static const char *lregnames[] =
175{
176  "er0", "er1", "er2", "er3", "er4", "er5", "er6", "er7",
177  "er0", "er1", "er2", "er3", "er4", "er5", "er6", "er7"
178};
179static const char *cregnames[] =
180{
181  "ccr", "exr", "mach", "macl", "", "", "vbr", "sbr"
182};
183
184static void
185print_one_arg (disassemble_info *info,
186	       bfd_vma addr,
187	       op_type x,
188	       int cst,
189	       int cstlen,
190	       int rdisp_n,
191	       int rn,
192	       const char **pregnames,
193	       int len)
194{
195  void * stream = info->stream;
196  fprintf_ftype outfn = info->fprintf_func;
197
198  if ((x & SIZE) == L_3 || (x & SIZE) == L_3NZ)
199    outfn (stream, "#0x%x", (unsigned) cst);
200  else if ((x & MODE) == IMM)
201    outfn (stream, "#0x%x", (unsigned) cst);
202  else if ((x & MODE) == DBIT || (x & MODE) == KBIT)
203    outfn (stream, "#%d", (unsigned) cst);
204  else if ((x & MODE) == CONST_2)
205    outfn (stream, "#2");
206  else if ((x & MODE) == CONST_4)
207    outfn (stream, "#4");
208  else if ((x & MODE) == CONST_8)
209    outfn (stream, "#8");
210  else if ((x & MODE) == CONST_16)
211    outfn (stream, "#16");
212  else if ((x & MODE) == REG)
213    {
214      switch (x & SIZE)
215	{
216	case L_8:
217	  outfn (stream, "%s", regnames[rn]);
218	  break;
219	case L_16:
220	case L_16U:
221	  outfn (stream, "%s", wregnames[rn]);
222	  break;
223	case L_P:
224	case L_32:
225	  outfn (stream, "%s", lregnames[rn]);
226	  break;
227	}
228    }
229  else if ((x & MODE) == LOWREG)
230    {
231      switch (x & SIZE)
232	{
233	case L_8:
234	  /* Always take low half of reg.  */
235	  outfn (stream, "%s.b", regnames[rn < 8 ? rn + 8 : rn]);
236	  break;
237	case L_16:
238	case L_16U:
239	  /* Always take low half of reg.  */
240	  outfn (stream, "%s.w", wregnames[rn < 8 ? rn : rn - 8]);
241	  break;
242	case L_P:
243	case L_32:
244	  outfn (stream, "%s.l", lregnames[rn]);
245	  break;
246	}
247    }
248  else if ((x & MODE) == POSTINC)
249    outfn (stream, "@%s+", pregnames[rn]);
250
251  else if ((x & MODE) == POSTDEC)
252    outfn (stream, "@%s-", pregnames[rn]);
253
254  else if ((x & MODE) == PREINC)
255    outfn (stream, "@+%s", pregnames[rn]);
256
257  else if ((x & MODE) == PREDEC)
258    outfn (stream, "@-%s", pregnames[rn]);
259
260  else if ((x & MODE) == IND)
261    outfn (stream, "@%s", pregnames[rn]);
262
263  else if ((x & MODE) == ABS || (x & ABSJMP))
264    outfn (stream, "@0x%x:%d", (unsigned) cst, cstlen);
265
266  else if ((x & MODE) == MEMIND)
267    outfn (stream, "@@%d (0x%x)", cst, cst);
268
269  else if ((x & MODE) == VECIND)
270    {
271      /* FIXME Multiplier should be 2 or 4, depending on processor mode,
272	 by which is meant "normal" vs. "middle", "advanced", "maximum".  */
273
274      int offset = (cst + 0x80) * 4;
275      outfn (stream, "@@%d (0x%x)", offset, offset);
276    }
277  else if ((x & MODE) == PCREL)
278    {
279      if ((x & SIZE) == L_16 ||
280	  (x & SIZE) == L_16U)
281	{
282	  outfn (stream, ".%s%d (0x%lx)",
283		   (short) cst > 0 ? "+" : "",
284		   (short) cst,
285		   (long)(addr + (short) cst + len));
286	}
287      else
288	{
289	  outfn (stream, ".%s%d (0x%lx)",
290		   (char) cst > 0 ? "+" : "",
291		   (char) cst,
292		   (long)(addr + (char) cst + len));
293	}
294    }
295  else if ((x & MODE) == DISP)
296    outfn (stream, "@(0x%x:%d,%s)", cst, cstlen, pregnames[rdisp_n]);
297
298  else if ((x & MODE) == INDEXB)
299    /* Always take low half of reg.  */
300    outfn (stream, "@(0x%x:%d,%s.b)", cst, cstlen,
301	   regnames[rdisp_n < 8 ? rdisp_n + 8 : rdisp_n]);
302
303  else if ((x & MODE) == INDEXW)
304    /* Always take low half of reg.  */
305    outfn (stream, "@(0x%x:%d,%s.w)", cst, cstlen,
306	   wregnames[rdisp_n < 8 ? rdisp_n : rdisp_n - 8]);
307
308  else if ((x & MODE) == INDEXL)
309    outfn (stream, "@(0x%x:%d,%s.l)", cst, cstlen, lregnames[rdisp_n]);
310
311  else if (x & CTRL)
312    outfn (stream, cregnames[rn]);
313
314  else if ((x & MODE) == CCR)
315    outfn (stream, "ccr");
316
317  else if ((x & MODE) == EXR)
318    outfn (stream, "exr");
319
320  else if ((x & MODE) == MACREG)
321    outfn (stream, "mac%c", cst ? 'l' : 'h');
322
323  else
324    /* xgettext:c-format */
325    outfn (stream, _("Hmmmm 0x%x"), x);
326}
327
328static unsigned int
329bfd_h8_disassemble (bfd_vma addr, disassemble_info *info, int mach)
330{
331  /* Find the first entry in the table for this opcode.  */
332  int regno[3] = { 0, 0, 0 };
333  int dispregno[3] = { 0, 0, 0 };
334  int cst[3] = { 0, 0, 0 };
335  int cstlen[3] = { 0, 0, 0 };
336  static bfd_boolean init = 0;
337  const struct h8_instruction *qi;
338  char const **pregnames = mach != 0 ? lregnames : wregnames;
339  int status;
340  unsigned int l;
341  unsigned char data[MAX_CODE_NIBBLES];
342  void *stream = info->stream;
343  fprintf_ftype outfn = info->fprintf_func;
344
345  if (!init)
346    {
347      bfd_h8_disassemble_init ();
348      init = 1;
349    }
350
351  status = info->read_memory_func (addr, data, 2, info);
352  if (status != 0)
353    {
354      info->memory_error_func (status, addr, info);
355      return -1;
356    }
357
358  for (l = 2; status == 0 && l < sizeof (data) / 2; l += 2)
359    status = info->read_memory_func (addr + l, data + l, 2, info);
360
361  /* Find the exact opcode/arg combo.  */
362  for (qi = h8_instructions; qi->opcode->name; qi++)
363    {
364      const struct h8_opcode *q = qi->opcode;
365      const op_type *nib = q->data.nib;
366      unsigned int len = 0;
367
368      while (1)
369	{
370	  op_type looking_for = *nib;
371	  int thisnib = data[len / 2];
372	  int opnr;
373
374	  thisnib = (len & 1) ? (thisnib & 0xf) : ((thisnib / 16) & 0xf);
375	  opnr = ((looking_for & OP3) == OP3 ? 2
376		  : (looking_for & DST) == DST ? 1 : 0);
377
378	  if (looking_for < 16 && looking_for >= 0)
379	    {
380	      if (looking_for != thisnib)
381		goto fail;
382	    }
383	  else
384	    {
385	      if ((int) looking_for & (int) B31)
386		{
387		  if (!((thisnib & 0x8) != 0))
388		    goto fail;
389
390		  looking_for = (op_type) ((int) looking_for & ~(int) B31);
391		  thisnib &= 0x7;
392		}
393	      else if ((int) looking_for & (int) B30)
394		{
395		  if (!((thisnib & 0x8) == 0))
396		    goto fail;
397
398		  looking_for = (op_type) ((int) looking_for & ~(int) B30);
399		}
400
401	      if ((int) looking_for & (int) B21)
402		{
403		  if (!((thisnib & 0x4) != 0))
404		    goto fail;
405
406		  looking_for = (op_type) ((int) looking_for & ~(int) B21);
407		  thisnib &= 0xb;
408		}
409	      else if ((int) looking_for & (int) B20)
410		{
411		  if (!((thisnib & 0x4) == 0))
412		    goto fail;
413
414		  looking_for = (op_type) ((int) looking_for & ~(int) B20);
415		}
416	      if ((int) looking_for & (int) B11)
417		{
418		  if (!((thisnib & 0x2) != 0))
419		    goto fail;
420
421		  looking_for = (op_type) ((int) looking_for & ~(int) B11);
422		  thisnib &= 0xd;
423		}
424	      else if ((int) looking_for & (int) B10)
425		{
426		  if (!((thisnib & 0x2) == 0))
427		    goto fail;
428
429		  looking_for = (op_type) ((int) looking_for & ~(int) B10);
430		}
431
432	      if ((int) looking_for & (int) B01)
433		{
434		  if (!((thisnib & 0x1) != 0))
435		    goto fail;
436
437		  looking_for = (op_type) ((int) looking_for & ~(int) B01);
438		  thisnib &= 0xe;
439		}
440	      else if ((int) looking_for & (int) B00)
441		{
442		  if (!((thisnib & 0x1) == 0))
443		    goto fail;
444
445		  looking_for = (op_type) ((int) looking_for & ~(int) B00);
446		}
447
448	      if (looking_for & IGNORE)
449		{
450		  /* Hitachi has declared that IGNORE must be zero.  */
451		  if (thisnib != 0)
452		    goto fail;
453		}
454	      else if ((looking_for & MODE) == DATA)
455		{
456		  ;			/* Skip embedded data.  */
457		}
458	      else if ((looking_for & MODE) == DBIT)
459		{
460		  /* Exclude adds/subs by looking at bit 0 and 2, and
461                     make sure the operand size, either w or l,
462                     matches by looking at bit 1.  */
463		  if ((looking_for & 7) != (thisnib & 7))
464		    goto fail;
465
466		  cst[opnr] = (thisnib & 0x8) ? 2 : 1;
467		}
468	      else if ((looking_for & MODE) == DISP
469		       || (looking_for & MODE) == ABS
470		       || (looking_for & MODE) == PCREL
471		       || (looking_for & MODE) == INDEXB
472		       || (looking_for & MODE) == INDEXW
473		       || (looking_for & MODE) == INDEXL)
474		{
475		  extract_immediate (stream, looking_for, thisnib,
476				     data + len / 2, cst + opnr,
477				     cstlen + opnr, q);
478		  /* Even address == bra, odd == bra/s.  */
479		  if (q->how == O (O_BRAS, SB))
480		    cst[opnr] -= 1;
481		}
482	      else if ((looking_for & MODE) == REG
483		       || (looking_for & MODE) == LOWREG
484		       || (looking_for & MODE) == IND
485		       || (looking_for & MODE) == PREINC
486		       || (looking_for & MODE) == POSTINC
487		       || (looking_for & MODE) == PREDEC
488		       || (looking_for & MODE) == POSTDEC)
489		{
490		  regno[opnr] = thisnib;
491		}
492	      else if (looking_for & CTRL)	/* Control Register.  */
493		{
494		  thisnib &= 7;
495		  if (((looking_for & MODE) == CCR  && (thisnib != C_CCR))
496		      || ((looking_for & MODE) == EXR  && (thisnib != C_EXR))
497		      || ((looking_for & MODE) == MACH && (thisnib != C_MACH))
498		      || ((looking_for & MODE) == MACL && (thisnib != C_MACL))
499		      || ((looking_for & MODE) == VBR  && (thisnib != C_VBR))
500		      || ((looking_for & MODE) == SBR  && (thisnib != C_SBR)))
501		    goto fail;
502		  if (((looking_for & MODE) == CCR_EXR
503		       && (thisnib != C_CCR && thisnib != C_EXR))
504		      || ((looking_for & MODE) == VBR_SBR
505			  && (thisnib != C_VBR && thisnib != C_SBR))
506		      || ((looking_for & MODE) == MACREG
507			  && (thisnib != C_MACH && thisnib != C_MACL)))
508		    goto fail;
509		  if (((looking_for & MODE) == CC_EX_VB_SB
510		       && (thisnib != C_CCR && thisnib != C_EXR
511			   && thisnib != C_VBR && thisnib != C_SBR)))
512		    goto fail;
513
514		  regno[opnr] = thisnib;
515		}
516	      else if ((looking_for & SIZE) == L_5)
517		{
518		  cst[opnr] = data[len / 2] & 31;
519		  cstlen[opnr] = 5;
520		}
521	      else if ((looking_for & SIZE) == L_4)
522		{
523		  cst[opnr] = thisnib;
524		  cstlen[opnr] = 4;
525		}
526	      else if ((looking_for & SIZE) == L_16
527		       || (looking_for & SIZE) == L_16U)
528		{
529		  cst[opnr] = (data[len / 2]) * 256 + data[(len + 2) / 2];
530		  cstlen[opnr] = 16;
531		}
532	      else if ((looking_for & MODE) == MEMIND)
533		{
534		  cst[opnr] = data[1];
535		}
536	      else if ((looking_for & MODE) == VECIND)
537		{
538		  cst[opnr] = data[1] & 0x7f;
539		}
540	      else if ((looking_for & SIZE) == L_32)
541		{
542		  int i = len / 2;
543
544		  cst[opnr] = ((data[i] << 24)
545			       | (data[i + 1] << 16)
546			       | (data[i + 2] << 8)
547			       | (data[i + 3]));
548
549		  cstlen[opnr] = 32;
550		}
551	      else if ((looking_for & SIZE) == L_24)
552		{
553		  int i = len / 2;
554
555		  cst[opnr] =
556		    (data[i] << 16) | (data[i + 1] << 8) | (data[i + 2]);
557		  cstlen[opnr] = 24;
558		}
559	      else if (looking_for & IGNORE)
560		{
561		  ;
562		}
563	      else if (looking_for & DISPREG)
564		{
565		  dispregno[opnr] = thisnib & 7;
566		}
567	      else if ((looking_for & MODE) == KBIT)
568		{
569		  switch (thisnib)
570		    {
571		    case 9:
572		      cst[opnr] = 4;
573		      break;
574		    case 8:
575		      cst[opnr] = 2;
576		      break;
577		    case 0:
578		      cst[opnr] = 1;
579		      break;
580		    default:
581		      goto fail;
582		    }
583		}
584	      else if ((looking_for & SIZE) == L_8)
585		{
586		  cstlen[opnr] = 8;
587		  cst[opnr] = data[len / 2];
588		}
589	      else if ((looking_for & SIZE) == L_3
590		       || (looking_for & SIZE) == L_3NZ)
591		{
592		  cst[opnr] = thisnib & 0x7;
593		  if (cst[opnr] == 0 && (looking_for & SIZE) == L_3NZ)
594		    goto fail;
595		}
596	      else if ((looking_for & SIZE) == L_2)
597		{
598		  cstlen[opnr] = 2;
599		  cst[opnr] = thisnib & 0x3;
600		}
601	      else if ((looking_for & MODE) == MACREG)
602		{
603		  cst[opnr] = (thisnib == 3);
604		}
605	      else if (looking_for == (op_type) E)
606		{
607		  outfn (stream, "%s\t", q->name);
608
609		  /* Gross.  Disgusting.  */
610		  if (strcmp (q->name, "ldm.l") == 0)
611		    {
612		      int count, high;
613
614		      count = (data[1] / 16) & 0x3;
615		      high = regno[1];
616
617		      outfn (stream, "@sp+,er%d-er%d", high - count, high);
618		      return qi->length;
619		    }
620
621		  if (strcmp (q->name, "stm.l") == 0)
622		    {
623		      int count, low;
624
625		      count = (data[1] / 16) & 0x3;
626		      low = regno[0];
627
628		      outfn (stream, "er%d-er%d,@-sp", low, low + count);
629		      return qi->length;
630		    }
631		  if (strcmp (q->name, "rte/l") == 0
632		      || strcmp (q->name, "rts/l") == 0)
633		    {
634		      if (regno[0] == 0)
635			outfn (stream, "er%d", regno[1]);
636		      else
637			outfn (stream, "er%d-er%d", regno[1] - regno[0],
638			       regno[1]);
639		      return qi->length;
640		    }
641		  if (CONST_STRNEQ (q->name, "mova"))
642		    {
643		      const op_type *args = q->args.nib;
644
645		      if (args[1] == (op_type) E)
646			{
647			  /* Short form.  */
648			  print_one_arg (info, addr, args[0], cst[0],
649					 cstlen[0], dispregno[0], regno[0],
650					 pregnames, qi->length);
651			  outfn (stream, ",er%d", dispregno[0]);
652			}
653		      else
654			{
655			  outfn (stream, "@(0x%x:%d,", cst[0], cstlen[0]);
656			  print_one_arg (info, addr, args[1], cst[1],
657					 cstlen[1], dispregno[1], regno[1],
658					 pregnames, qi->length);
659			  outfn (stream, ".%c),",
660				 (args[0] & MODE) == INDEXB ? 'b' : 'w');
661			  print_one_arg (info, addr, args[2], cst[2],
662					 cstlen[2], dispregno[2], regno[2],
663					 pregnames, qi->length);
664			}
665		      return qi->length;
666		    }
667		  /* Fill in the args.  */
668		  {
669		    const op_type *args = q->args.nib;
670		    int hadone = 0;
671		    int nargs;
672
673		    /* Special case handling for the adds and subs instructions
674		       since in H8 mode thay can only take the r0-r7 registers
675		       but in other (higher) modes they can take the er0-er7
676		       registers as well.  */
677		    if (strcmp (qi->opcode->name, "adds") == 0
678			|| strcmp (qi->opcode->name, "subs") == 0)
679		      {
680			outfn (stream, "#%d,%s", cst[0], pregnames[regno[1] & 0x7]);
681			return qi->length;
682		      }
683
684		    for (nargs = 0;
685			 nargs < 3 && args[nargs] != (op_type) E;
686			 nargs++)
687		      {
688			int x = args[nargs];
689
690			if (hadone)
691			  outfn (stream, ",");
692
693			print_one_arg (info, addr, x,
694				       cst[nargs], cstlen[nargs],
695				       dispregno[nargs], regno[nargs],
696				       pregnames, qi->length);
697
698			hadone = 1;
699		      }
700		  }
701
702		  return qi->length;
703		}
704	      else
705		/* xgettext:c-format */
706		outfn (stream, _("Don't understand 0x%x \n"), looking_for);
707	    }
708
709	  len++;
710	  nib++;
711	}
712
713    fail:
714      ;
715    }
716
717  /* Fell off the end.  */
718  outfn (stream, ".word\tH'%x,H'%x", data[0], data[1]);
719  return 2;
720}
721
722int
723print_insn_h8300 (bfd_vma addr, disassemble_info *info)
724{
725  return bfd_h8_disassemble (addr, info, 0);
726}
727
728int
729print_insn_h8300h (bfd_vma addr, disassemble_info *info)
730{
731  return bfd_h8_disassemble (addr, info, 1);
732}
733
734int
735print_insn_h8300s (bfd_vma addr, disassemble_info *info)
736{
737  return bfd_h8_disassemble (addr, info, 2);
738}
739