1 /* tc-bfin.c -- Assembler for the ADI Blackfin.
2 Copyright 2005, 2006, 2007, 2008
3 Free Software Foundation, Inc.
5 This file is part of GAS, the GNU Assembler.
7 GAS is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
12 GAS is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with GAS; see the file COPYING. If not, write to the Free
19 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
23 #include "struc-symbol.h"
24 #include "bfin-defs.h"
26 #include "safe-ctype.h"
28 #include "dwarf2dbg.h"
31 #include "elf/common.h"
34 extern int yyparse (void);
35 struct yy_buffer_state
;
36 typedef struct yy_buffer_state
*YY_BUFFER_STATE
;
37 extern YY_BUFFER_STATE
yy_scan_string (const char *yy_str
);
38 extern void yy_delete_buffer (YY_BUFFER_STATE b
);
39 static parse_state
parse (char *line
);
41 /* Global variables. */
42 struct bfin_insn
*insn
;
45 extern struct obstack mempool
;
48 /* Flags to set in the elf header */
49 #define DEFAULT_FLAGS 0
52 # define DEFAULT_FDPIC EF_BFIN_FDPIC
54 # define DEFAULT_FDPIC 0
57 static flagword bfin_flags
= DEFAULT_FLAGS
| DEFAULT_FDPIC
;
58 static const char *bfin_pic_flag
= DEFAULT_FDPIC
? "-mfdpic" : (const char *)0;
67 static const struct bfin_reg_entry bfin_reg_info
[] = {
189 {"sftreset", REG_sftreset
},
190 {"omode", REG_omode
},
191 {"excause", REG_excause
},
192 {"emucause", REG_emucause
},
193 {"idle_req", REG_idle_req
},
194 {"hwerrcause", REG_hwerrcause
},
198 {"ASTAT", REG_ASTAT
},
204 {"CYCLES", REG_CYCLES
},
205 {"CYCLES2", REG_CYCLES2
},
207 {"SEQSTAT", REG_SEQSTAT
},
208 {"SYSCFG", REG_SYSCFG
},
213 {"EMUDAT", REG_EMUDAT
},
217 /* Blackfin specific function to handle FD-PIC pointer initializations. */
220 bfin_pic_ptr (int nbytes
)
228 #ifdef md_flush_pending_output
229 md_flush_pending_output ();
232 if (is_it_end_of_statement ())
234 demand_empty_rest_of_line ();
239 md_cons_align (nbytes
);
244 bfd_reloc_code_real_type reloc_type
= BFD_RELOC_BFIN_FUNCDESC
;
246 if (strncasecmp (input_line_pointer
, "funcdesc(", 9) == 0)
248 input_line_pointer
+= 9;
250 if (*input_line_pointer
== ')')
251 input_line_pointer
++;
253 as_bad (_("missing ')'"));
256 error ("missing funcdesc in picptr");
260 fix_new_exp (frag_now
, p
- frag_now
->fr_literal
, 4, &exp
, 0,
263 while (*input_line_pointer
++ == ',');
265 input_line_pointer
--; /* Put terminator back into stream. */
266 demand_empty_rest_of_line ();
270 bfin_s_bss (int ignore ATTRIBUTE_UNUSED
)
274 temp
= get_absolute_expression ();
275 subseg_set (bss_section
, (subsegT
) temp
);
276 demand_empty_rest_of_line ();
279 const pseudo_typeS md_pseudo_table
[] = {
280 {"align", s_align_bytes
, 0},
283 {"picptr", bfin_pic_ptr
, 4},
284 {"code", obj_elf_section
, 0},
289 {"pdata", s_ignore
, 0},
290 {"var", s_ignore
, 0},
291 {"bss", bfin_s_bss
, 0},
295 /* Characters that are used to denote comments and line separators. */
296 const char comment_chars
[] = "";
297 const char line_comment_chars
[] = "#";
298 const char line_separator_chars
[] = ";";
300 /* Characters that can be used to separate the mantissa from the
301 exponent in floating point numbers. */
302 const char EXP_CHARS
[] = "eE";
304 /* Characters that mean this number is a floating point constant.
305 As in 0f12.456 or 0d1.2345e12. */
306 const char FLT_CHARS
[] = "fFdDxX";
308 typedef enum bfin_cpu_type
342 bfin_cpu_t bfin_cpu_type
= BFIN_CPU_UNKNOWN
;
343 /* -msi-revision support. There are three special values:
344 -1 -msi-revision=none.
345 0xffff -msi-revision=any. */
346 int bfin_si_revision
;
348 unsigned int bfin_anomaly_checks
= 0;
355 unsigned int anomaly_checks
;
358 struct bfin_cpu bfin_cpus
[] =
360 {"bf512", BFIN_CPU_BF512
, 0x0001, AC_05000074
},
361 {"bf512", BFIN_CPU_BF512
, 0x0000, AC_05000074
},
363 {"bf514", BFIN_CPU_BF514
, 0x0001, AC_05000074
},
364 {"bf514", BFIN_CPU_BF514
, 0x0000, AC_05000074
},
366 {"bf516", BFIN_CPU_BF516
, 0x0001, AC_05000074
},
367 {"bf516", BFIN_CPU_BF516
, 0x0000, AC_05000074
},
369 {"bf518", BFIN_CPU_BF518
, 0x0001, AC_05000074
},
370 {"bf518", BFIN_CPU_BF518
, 0x0000, AC_05000074
},
372 {"bf522", BFIN_CPU_BF522
, 0x0002, AC_05000074
},
373 {"bf522", BFIN_CPU_BF522
, 0x0001, AC_05000074
},
374 {"bf522", BFIN_CPU_BF522
, 0x0000, AC_05000074
},
376 {"bf523", BFIN_CPU_BF523
, 0x0002, AC_05000074
},
377 {"bf523", BFIN_CPU_BF523
, 0x0001, AC_05000074
},
378 {"bf523", BFIN_CPU_BF523
, 0x0000, AC_05000074
},
380 {"bf524", BFIN_CPU_BF524
, 0x0002, AC_05000074
},
381 {"bf524", BFIN_CPU_BF524
, 0x0001, AC_05000074
},
382 {"bf524", BFIN_CPU_BF524
, 0x0000, AC_05000074
},
384 {"bf525", BFIN_CPU_BF525
, 0x0002, AC_05000074
},
385 {"bf525", BFIN_CPU_BF525
, 0x0001, AC_05000074
},
386 {"bf525", BFIN_CPU_BF525
, 0x0000, AC_05000074
},
388 {"bf526", BFIN_CPU_BF526
, 0x0002, AC_05000074
},
389 {"bf526", BFIN_CPU_BF526
, 0x0001, AC_05000074
},
390 {"bf526", BFIN_CPU_BF526
, 0x0000, AC_05000074
},
392 {"bf527", BFIN_CPU_BF527
, 0x0002, AC_05000074
},
393 {"bf527", BFIN_CPU_BF527
, 0x0001, AC_05000074
},
394 {"bf527", BFIN_CPU_BF527
, 0x0000, AC_05000074
},
396 {"bf531", BFIN_CPU_BF531
, 0x0006, AC_05000074
},
397 {"bf531", BFIN_CPU_BF531
, 0x0005, AC_05000074
},
398 {"bf531", BFIN_CPU_BF531
, 0x0004, AC_05000074
},
399 {"bf531", BFIN_CPU_BF531
, 0x0003, AC_05000074
},
401 {"bf532", BFIN_CPU_BF532
, 0x0006, AC_05000074
},
402 {"bf532", BFIN_CPU_BF532
, 0x0005, AC_05000074
},
403 {"bf532", BFIN_CPU_BF532
, 0x0004, AC_05000074
},
404 {"bf532", BFIN_CPU_BF532
, 0x0003, AC_05000074
},
406 {"bf533", BFIN_CPU_BF533
, 0x0006, AC_05000074
},
407 {"bf533", BFIN_CPU_BF533
, 0x0005, AC_05000074
},
408 {"bf533", BFIN_CPU_BF533
, 0x0004, AC_05000074
},
409 {"bf533", BFIN_CPU_BF533
, 0x0003, AC_05000074
},
411 {"bf534", BFIN_CPU_BF534
, 0x0003, AC_05000074
},
412 {"bf534", BFIN_CPU_BF534
, 0x0002, AC_05000074
},
413 {"bf534", BFIN_CPU_BF534
, 0x0001, AC_05000074
},
415 {"bf536", BFIN_CPU_BF536
, 0x0003, AC_05000074
},
416 {"bf536", BFIN_CPU_BF536
, 0x0002, AC_05000074
},
417 {"bf536", BFIN_CPU_BF536
, 0x0001, AC_05000074
},
419 {"bf537", BFIN_CPU_BF537
, 0x0003, AC_05000074
},
420 {"bf537", BFIN_CPU_BF537
, 0x0002, AC_05000074
},
421 {"bf537", BFIN_CPU_BF537
, 0x0001, AC_05000074
},
423 {"bf538", BFIN_CPU_BF538
, 0x0005, AC_05000074
},
424 {"bf538", BFIN_CPU_BF538
, 0x0004, AC_05000074
},
425 {"bf538", BFIN_CPU_BF538
, 0x0003, AC_05000074
},
426 {"bf538", BFIN_CPU_BF538
, 0x0002, AC_05000074
},
428 {"bf539", BFIN_CPU_BF539
, 0x0005, AC_05000074
},
429 {"bf539", BFIN_CPU_BF539
, 0x0004, AC_05000074
},
430 {"bf539", BFIN_CPU_BF539
, 0x0003, AC_05000074
},
431 {"bf539", BFIN_CPU_BF539
, 0x0002, AC_05000074
},
433 {"bf542m", BFIN_CPU_BF542M
, 0x0003, AC_05000074
},
435 {"bf542", BFIN_CPU_BF542
, 0x0002, AC_05000074
},
436 {"bf542", BFIN_CPU_BF542
, 0x0001, AC_05000074
},
437 {"bf542", BFIN_CPU_BF542
, 0x0000, AC_05000074
},
439 {"bf544m", BFIN_CPU_BF544M
, 0x0003, AC_05000074
},
441 {"bf544", BFIN_CPU_BF544
, 0x0002, AC_05000074
},
442 {"bf544", BFIN_CPU_BF544
, 0x0001, AC_05000074
},
443 {"bf544", BFIN_CPU_BF544
, 0x0000, AC_05000074
},
445 {"bf547m", BFIN_CPU_BF547M
, 0x0003, AC_05000074
},
447 {"bf547", BFIN_CPU_BF547
, 0x0002, AC_05000074
},
448 {"bf547", BFIN_CPU_BF547
, 0x0001, AC_05000074
},
449 {"bf547", BFIN_CPU_BF547
, 0x0000, AC_05000074
},
451 {"bf548m", BFIN_CPU_BF548M
, 0x0003, AC_05000074
},
453 {"bf548", BFIN_CPU_BF548
, 0x0002, AC_05000074
},
454 {"bf548", BFIN_CPU_BF548
, 0x0001, AC_05000074
},
455 {"bf548", BFIN_CPU_BF548
, 0x0000, AC_05000074
},
457 {"bf549m", BFIN_CPU_BF549M
, 0x0003, AC_05000074
},
459 {"bf549", BFIN_CPU_BF549
, 0x0002, AC_05000074
},
460 {"bf549", BFIN_CPU_BF549
, 0x0001, AC_05000074
},
461 {"bf549", BFIN_CPU_BF549
, 0x0000, AC_05000074
},
463 {"bf561", BFIN_CPU_BF561
, 0x0005, AC_05000074
},
464 {"bf561", BFIN_CPU_BF561
, 0x0003, AC_05000074
},
465 {"bf561", BFIN_CPU_BF561
, 0x0002, AC_05000074
},
470 /* Define bfin-specific command-line options (there are none). */
471 const char *md_shortopts
= "";
473 #define OPTION_FDPIC (OPTION_MD_BASE)
474 #define OPTION_NOPIC (OPTION_MD_BASE + 1)
475 #define OPTION_MCPU (OPTION_MD_BASE + 2)
477 struct option md_longopts
[] =
479 { "mcpu", required_argument
, NULL
, OPTION_MCPU
},
480 { "mfdpic", no_argument
, NULL
, OPTION_FDPIC
},
481 { "mnopic", no_argument
, NULL
, OPTION_NOPIC
},
482 { "mno-fdpic", no_argument
, NULL
, OPTION_NOPIC
},
483 { NULL
, no_argument
, NULL
, 0 },
486 size_t md_longopts_size
= sizeof (md_longopts
);
490 md_parse_option (int c ATTRIBUTE_UNUSED
, char *arg ATTRIBUTE_UNUSED
)
503 while ((p
= bfin_cpus
[i
].name
) != NULL
)
505 if (strncmp (arg
, p
, strlen (p
)) == 0)
512 error ("-mcpu=%s is not valid", arg
);
516 bfin_cpu_type
= bfin_cpus
[i
].type
;
518 q
= arg
+ strlen (p
);
522 bfin_si_revision
= bfin_cpus
[i
].si_revision
;
523 bfin_anomaly_checks
|= bfin_cpus
[i
].anomaly_checks
;
525 else if (strcmp (q
, "-none") == 0)
526 bfin_si_revision
= -1;
527 else if (strcmp (q
, "-any") == 0)
529 bfin_si_revision
= 0xffff;
530 while (bfin_cpus
[i
].type
== bfin_cpu_type
)
532 bfin_anomaly_checks
|= bfin_cpus
[i
].anomaly_checks
;
538 unsigned int si_major
, si_minor
;
541 rev_len
= strlen (q
);
543 if (sscanf (q
, "-%u.%u%n", &si_major
, &si_minor
, &n
) != 2
545 || si_major
> 0xff || si_minor
> 0xff)
547 invalid_silicon_revision
:
548 error ("-mcpu=%s has invalid silicon revision", arg
);
552 bfin_si_revision
= (si_major
<< 8) | si_minor
;
554 while (bfin_cpus
[i
].type
== bfin_cpu_type
555 && bfin_cpus
[i
].si_revision
!= bfin_si_revision
)
558 if (bfin_cpus
[i
].type
!= bfin_cpu_type
)
559 goto invalid_silicon_revision
;
561 bfin_anomaly_checks
|= bfin_cpus
[i
].anomaly_checks
;
568 bfin_flags
|= EF_BFIN_FDPIC
;
569 bfin_pic_flag
= "-mfdpic";
573 bfin_flags
&= ~(EF_BFIN_FDPIC
);
582 md_show_usage (FILE * stream ATTRIBUTE_UNUSED
)
584 fprintf (stream
, _(" BFIN specific command line options:\n"));
587 /* Perform machine-specific initializations. */
591 /* Set the ELF flags if desired. */
593 bfd_set_private_flags (stdoutput
, bfin_flags
);
595 /* Set the default machine type. */
596 if (!bfd_set_arch_mach (stdoutput
, bfd_arch_bfin
, 0))
597 as_warn (_("Could not set architecture and machine."));
599 /* Ensure that lines can begin with '(', for multiple
600 register stack pops. */
601 lex_type
['('] = LEX_BEGIN_NAME
;
604 record_alignment (text_section
, 2);
605 record_alignment (data_section
, 2);
606 record_alignment (bss_section
, 2);
610 obstack_init (&mempool
);
613 extern int debug_codeselection
;
614 debug_codeselection
= 1;
620 /* Perform the main parsing, and assembly of the input here. Also,
621 call the required routines for alignment and fixups here.
622 This is called for every line that contains real assembly code. */
625 md_assemble (char *line
)
628 extern char *current_inputline
;
630 struct bfin_insn
*tmp_insn
;
632 static size_t buffer_len
= 0;
636 if (len
+ 2 > buffer_len
)
639 free (current_inputline
);
640 buffer_len
= len
+ 40;
641 current_inputline
= xmalloc (buffer_len
);
643 memcpy (current_inputline
, line
, len
);
644 current_inputline
[len
] = ';';
645 current_inputline
[len
+ 1] = '\0';
647 state
= parse (current_inputline
);
648 if (state
== NO_INSN_GENERATED
)
651 for (insn_size
= 0, tmp_insn
= insn
; tmp_insn
; tmp_insn
= tmp_insn
->next
)
652 if (!tmp_insn
->reloc
|| !tmp_insn
->exp
->symbol
)
656 toP
= frag_more (insn_size
);
658 last_insn_size
= insn_size
;
665 if (insn
->reloc
&& insn
->exp
->symbol
)
667 char *prev_toP
= toP
- 2;
670 case BFD_RELOC_BFIN_24_PCREL_JUMP_L
:
671 case BFD_RELOC_24_PCREL
:
672 case BFD_RELOC_BFIN_16_LOW
:
673 case BFD_RELOC_BFIN_16_HIGH
:
680 /* Following if condition checks for the arithmetic relocations.
681 If the case then it doesn't required to generate the code.
682 It has been assumed that, their ID will be contiguous. */
683 if ((BFD_ARELOC_BFIN_PUSH
<= insn
->reloc
684 && BFD_ARELOC_BFIN_COMP
>= insn
->reloc
)
685 || insn
->reloc
== BFD_RELOC_BFIN_16_IMM
)
689 if (insn
->reloc
== BFD_ARELOC_BFIN_CONST
690 || insn
->reloc
== BFD_ARELOC_BFIN_PUSH
)
694 (prev_toP
- frag_now
->fr_literal
),
695 size
, insn
->exp
->symbol
, insn
->exp
->value
,
696 insn
->pcrel
, insn
->reloc
);
700 md_number_to_chars (toP
, insn
->value
, 2);
706 printf (" %02x%02x", ((unsigned char *) &insn
->value
)[0],
707 ((unsigned char *) &insn
->value
)[1]);
713 dwarf2_emit_insn (insn_size
);
717 /* Parse one line of instructions, and generate opcode for it.
718 To parse the line, YACC and LEX are used, because the instruction set
719 syntax doesn't confirm to the AT&T assembly syntax.
720 To call a YACC & LEX generated parser, we must provide the input via
721 a FILE stream, otherwise stdin is used by default. Below the input
722 to the function will be put into a temporary file, then the generated
723 parser uses the temporary file for parsing. */
729 YY_BUFFER_STATE buffstate
;
731 buffstate
= yy_scan_string (line
);
733 /* our lex requires setting the start state to keyword
734 every line as the first word may be a keyword.
735 Fixes a bug where we could not have keywords as labels. */
738 /* Call yyparse here. */
740 if (state
== SEMANTIC_ERROR
)
742 as_bad (_("Parse failed."));
746 yy_delete_buffer (buffstate
);
750 /* We need to handle various expressions properly.
751 Such as, [SP--] = 34, concerned by md_assemble(). */
754 md_operand (expressionS
* expressionP
)
756 if (*input_line_pointer
== '[')
758 as_tsktsk ("We found a '['!");
759 input_line_pointer
++;
760 expression (expressionP
);
764 /* Handle undefined symbols. */
766 md_undefined_symbol (char *name ATTRIBUTE_UNUSED
)
768 return (symbolS
*) 0;
772 md_estimate_size_before_relax (fragS
* fragP ATTRIBUTE_UNUSED
,
773 segT segment ATTRIBUTE_UNUSED
)
778 /* Convert from target byte order to host byte order. */
781 md_chars_to_number (char *val
, int n
)
785 for (retval
= 0; n
--;)
794 md_apply_fix (fixS
*fixP
, valueT
*valueP
, segT seg ATTRIBUTE_UNUSED
)
796 char *where
= fixP
->fx_frag
->fr_literal
+ fixP
->fx_where
;
798 long value
= *valueP
;
801 switch (fixP
->fx_r_type
)
803 case BFD_RELOC_BFIN_GOT
:
804 case BFD_RELOC_BFIN_GOT17M4
:
805 case BFD_RELOC_BFIN_FUNCDESC_GOT17M4
:
806 fixP
->fx_no_overflow
= 1;
807 newval
= md_chars_to_number (where
, 2);
808 newval
|= 0x0 & 0x7f;
809 md_number_to_chars (where
, newval
, 2);
812 case BFD_RELOC_BFIN_10_PCREL
:
815 if (value
< -1024 || value
> 1022)
816 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
817 _("pcrel too far BFD_RELOC_BFIN_10"));
819 /* 11 bit offset even numbered, so we remove right bit. */
821 newval
= md_chars_to_number (where
, 2);
822 newval
|= value
& 0x03ff;
823 md_number_to_chars (where
, newval
, 2);
826 case BFD_RELOC_BFIN_12_PCREL_JUMP
:
827 case BFD_RELOC_BFIN_12_PCREL_JUMP_S
:
828 case BFD_RELOC_12_PCREL
:
832 if (value
< -4096 || value
> 4094)
833 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("pcrel too far BFD_RELOC_BFIN_12"));
834 /* 13 bit offset even numbered, so we remove right bit. */
836 newval
= md_chars_to_number (where
, 2);
837 newval
|= value
& 0xfff;
838 md_number_to_chars (where
, newval
, 2);
841 case BFD_RELOC_BFIN_16_LOW
:
842 case BFD_RELOC_BFIN_16_HIGH
:
843 fixP
->fx_done
= FALSE
;
846 case BFD_RELOC_BFIN_24_PCREL_JUMP_L
:
847 case BFD_RELOC_BFIN_24_PCREL_CALL_X
:
848 case BFD_RELOC_24_PCREL
:
852 if (value
< -16777216 || value
> 16777214)
853 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("pcrel too far BFD_RELOC_BFIN_24"));
855 /* 25 bit offset even numbered, so we remove right bit. */
859 md_number_to_chars (where
- 2, value
>> 16, 1);
860 md_number_to_chars (where
, value
, 1);
861 md_number_to_chars (where
+ 1, value
>> 8, 1);
864 case BFD_RELOC_BFIN_5_PCREL
: /* LSETUP (a, b) : "a" */
867 if (value
< 4 || value
> 30)
868 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("pcrel too far BFD_RELOC_BFIN_5"));
870 newval
= md_chars_to_number (where
, 1);
871 newval
= (newval
& 0xf0) | (value
& 0xf);
872 md_number_to_chars (where
, newval
, 1);
875 case BFD_RELOC_BFIN_11_PCREL
: /* LSETUP (a, b) : "b" */
879 if (value
< 4 || value
> 2046)
880 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("pcrel too far BFD_RELOC_BFIN_11_PCREL"));
881 /* 11 bit unsigned even, so we remove right bit. */
883 newval
= md_chars_to_number (where
, 2);
884 newval
|= value
& 0x03ff;
885 md_number_to_chars (where
, newval
, 2);
889 if (value
< -0x80 || value
>= 0x7f)
890 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("rel too far BFD_RELOC_8"));
891 md_number_to_chars (where
, value
, 1);
894 case BFD_RELOC_BFIN_16_IMM
:
896 if (value
< -0x8000 || value
>= 0x7fff)
897 as_bad_where (fixP
->fx_file
, fixP
->fx_line
, _("rel too far BFD_RELOC_16"));
898 md_number_to_chars (where
, value
, 2);
902 md_number_to_chars (where
, value
, 4);
905 case BFD_RELOC_BFIN_PLTPC
:
906 md_number_to_chars (where
, value
, 2);
909 case BFD_RELOC_BFIN_FUNCDESC
:
910 case BFD_RELOC_VTABLE_INHERIT
:
911 case BFD_RELOC_VTABLE_ENTRY
:
912 fixP
->fx_done
= FALSE
;
916 if ((BFD_ARELOC_BFIN_PUSH
> fixP
->fx_r_type
) || (BFD_ARELOC_BFIN_COMP
< fixP
->fx_r_type
))
918 fprintf (stderr
, "Relocation %d not handled in gas." " Contact support.\n", fixP
->fx_r_type
);
924 fixP
->fx_done
= TRUE
;
928 /* Round up a section size to the appropriate boundary. */
930 md_section_align (segment
, size
)
934 int boundary
= bfd_get_section_alignment (stdoutput
, segment
);
935 return ((size
+ (1 << boundary
) - 1) & (-1 << boundary
));
940 md_atof (int type
, char * litP
, int * sizeP
)
942 return ieee_md_atof (type
, litP
, sizeP
, FALSE
);
946 /* If while processing a fixup, a reloc really needs to be created
947 then it is done here. */
950 tc_gen_reloc (seg
, fixp
)
951 asection
*seg ATTRIBUTE_UNUSED
;
956 reloc
= (arelent
*) xmalloc (sizeof (arelent
));
957 reloc
->sym_ptr_ptr
= (asymbol
**) xmalloc (sizeof (asymbol
*));
958 *reloc
->sym_ptr_ptr
= symbol_get_bfdsym (fixp
->fx_addsy
);
959 reloc
->address
= fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
961 reloc
->addend
= fixp
->fx_offset
;
962 reloc
->howto
= bfd_reloc_type_lookup (stdoutput
, fixp
->fx_r_type
);
964 if (reloc
->howto
== (reloc_howto_type
*) NULL
)
966 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
967 /* xgettext:c-format. */
968 _("reloc %d not supported by object file format"),
969 (int) fixp
->fx_r_type
);
979 /* The location from which a PC relative jump should be calculated,
980 given a PC relative reloc. */
983 md_pcrel_from_section (fixP
, sec
)
987 if (fixP
->fx_addsy
!= (symbolS
*) NULL
988 && (!S_IS_DEFINED (fixP
->fx_addsy
)
989 || S_GET_SEGMENT (fixP
->fx_addsy
) != sec
))
991 /* The symbol is undefined (or is defined but not in this section).
992 Let the linker figure it out. */
995 return fixP
->fx_frag
->fr_address
+ fixP
->fx_where
;
998 /* Return true if the fix can be handled by GAS, false if it must
999 be passed through to the linker. */
1002 bfin_fix_adjustable (fixS
*fixP
)
1004 switch (fixP
->fx_r_type
)
1006 /* Adjust_reloc_syms doesn't know about the GOT. */
1007 case BFD_RELOC_BFIN_GOT
:
1008 case BFD_RELOC_BFIN_GOT17M4
:
1009 case BFD_RELOC_BFIN_FUNCDESC_GOT17M4
:
1010 case BFD_RELOC_BFIN_PLTPC
:
1011 /* We need the symbol name for the VTABLE entries. */
1012 case BFD_RELOC_VTABLE_INHERIT
:
1013 case BFD_RELOC_VTABLE_ENTRY
:
1022 /* Handle the LOOP_BEGIN and LOOP_END statements.
1023 Parse the Loop_Begin/Loop_End and create a label. */
1025 bfin_start_line_hook ()
1027 bfd_boolean maybe_begin
= FALSE
;
1028 bfd_boolean maybe_end
= FALSE
;
1030 char *c1
, *label_name
;
1031 symbolS
*line_label
;
1032 char *c
= input_line_pointer
;
1035 while (ISSPACE (*c
))
1042 /* Look for Loop_Begin or Loop_End statements. */
1044 if (*c
!= 'L' && *c
!= 'l')
1048 if (*c
!= 'O' && *c
!= 'o')
1052 if (*c
!= 'O' && *c
!= 'o')
1056 if (*c
!= 'P' && *c
!= 'p')
1064 if (*c
== 'E' || *c
== 'e')
1066 else if (*c
== 'B' || *c
== 'b')
1074 if (*c
!= 'N' && *c
!= 'n')
1078 if (*c
!= 'D' && *c
!= 'd')
1085 if (*c
!= 'E' && *c
!= 'e')
1089 if (*c
!= 'G' && *c
!= 'g')
1093 if (*c
!= 'I' && *c
!= 'i')
1097 if (*c
!= 'N' && *c
!= 'n')
1102 while (ISSPACE (*c
)) c
++;
1104 while (ISALPHA (*c
) || ISDIGIT (*c
) || *c
== '_') c
++;
1106 if (input_line_pointer
[-1] == '\n')
1107 bump_line_counters ();
1110 bump_line_counters ();
1112 input_line_pointer
= c
;
1115 label_name
= (char *) xmalloc ((c
- c1
) + strlen ("__END") + 5);
1117 strcat (label_name
, "L$L$");
1118 strncat (label_name
, c1
, c
-c1
);
1119 strcat (label_name
, "__END");
1121 else /* maybe_begin. */
1123 label_name
= (char *) xmalloc ((c
- c1
) + strlen ("__BEGIN") + 5);
1125 strcat (label_name
, "L$L$");
1126 strncat (label_name
, c1
, c
-c1
);
1127 strcat (label_name
, "__BEGIN");
1130 line_label
= colon (label_name
);
1132 /* Loop_End follows the last instruction in the loop.
1133 Adjust label address. */
1135 ((struct local_symbol
*) line_label
)->lsy_value
-= last_insn_size
;
1138 /* Special extra functions that help bfin-parse.y perform its job. */
1140 struct obstack mempool
;
1143 conscode (INSTR_T head
, INSTR_T tail
)
1152 conctcode (INSTR_T head
, INSTR_T tail
)
1154 INSTR_T temp
= (head
);
1165 note_reloc (INSTR_T code
, Expr_Node
* symbol
, int reloc
, int pcrel
)
1167 /* Assert that the symbol is not an operator. */
1168 gas_assert (symbol
->type
== Expr_Node_Reloc
);
1170 return note_reloc1 (code
, symbol
->value
.s_value
, reloc
, pcrel
);
1175 note_reloc1 (INSTR_T code
, const char *symbol
, int reloc
, int pcrel
)
1177 code
->reloc
= reloc
;
1178 code
->exp
= mkexpr (0, symbol_find_or_make (symbol
));
1179 code
->pcrel
= pcrel
;
1184 note_reloc2 (INSTR_T code
, const char *symbol
, int reloc
, int value
, int pcrel
)
1186 code
->reloc
= reloc
;
1187 code
->exp
= mkexpr (value
, symbol_find_or_make (symbol
));
1188 code
->pcrel
= pcrel
;
1193 gencode (unsigned long x
)
1195 INSTR_T cell
= obstack_alloc (&mempool
, sizeof (struct bfin_insn
));
1196 memset (cell
, 0, sizeof (struct bfin_insn
));
1208 return obstack_alloc (&mempool
, n
);
1212 Expr_Node_Create (Expr_Node_Type type
,
1213 Expr_Node_Value value
,
1214 Expr_Node
*Left_Child
,
1215 Expr_Node
*Right_Child
)
1219 Expr_Node
*node
= (Expr_Node
*) allocate (sizeof (Expr_Node
));
1221 node
->value
= value
;
1222 node
->Left_Child
= Left_Child
;
1223 node
->Right_Child
= Right_Child
;
1227 static const char *con
= ".__constant";
1228 static const char *op
= ".__operator";
1229 static INSTR_T
Expr_Node_Gen_Reloc_R (Expr_Node
* head
);
1230 INSTR_T
Expr_Node_Gen_Reloc (Expr_Node
*head
, int parent_reloc
);
1233 Expr_Node_Gen_Reloc (Expr_Node
* head
, int parent_reloc
)
1235 /* Top level reloction expression generator VDSP style.
1236 If the relocation is just by itself, generate one item
1237 else generate this convoluted expression. */
1239 INSTR_T note
= NULL_CODE
;
1240 INSTR_T note1
= NULL_CODE
;
1241 int pcrel
= 1; /* Is the parent reloc pcrelative?
1242 This calculation here and HOWTO should match. */
1246 /* If it's 32 bit quantity then 16bit code needs to be added. */
1249 if (head
->type
== Expr_Node_Constant
)
1251 /* If note1 is not null code, we have to generate a right
1252 aligned value for the constant. Otherwise the reloc is
1253 a part of the basic command and the yacc file
1255 value
= head
->value
.i_value
;
1257 switch (parent_reloc
)
1259 /* Some relocations will need to allocate extra words. */
1260 case BFD_RELOC_BFIN_16_IMM
:
1261 case BFD_RELOC_BFIN_16_LOW
:
1262 case BFD_RELOC_BFIN_16_HIGH
:
1263 note1
= conscode (gencode (value
), NULL_CODE
);
1266 case BFD_RELOC_BFIN_PLTPC
:
1267 note1
= conscode (gencode (value
), NULL_CODE
);
1271 case BFD_RELOC_BFIN_GOT
:
1272 case BFD_RELOC_BFIN_GOT17M4
:
1273 case BFD_RELOC_BFIN_FUNCDESC_GOT17M4
:
1274 note1
= conscode (gencode (value
), NULL_CODE
);
1277 case BFD_RELOC_24_PCREL
:
1278 case BFD_RELOC_BFIN_24_PCREL_JUMP_L
:
1279 case BFD_RELOC_BFIN_24_PCREL_CALL_X
:
1280 /* These offsets are even numbered pcrel. */
1281 note1
= conscode (gencode (value
>> 1), NULL_CODE
);
1287 if (head
->type
== Expr_Node_Constant
)
1289 else if (head
->type
== Expr_Node_Reloc
)
1291 note
= note_reloc1 (gencode (0), head
->value
.s_value
, parent_reloc
, pcrel
);
1292 if (note1
!= NULL_CODE
)
1293 note
= conscode (note1
, note
);
1295 else if (head
->type
== Expr_Node_Binop
1296 && (head
->value
.op_value
== Expr_Op_Type_Add
1297 || head
->value
.op_value
== Expr_Op_Type_Sub
)
1298 && head
->Left_Child
->type
== Expr_Node_Reloc
1299 && head
->Right_Child
->type
== Expr_Node_Constant
)
1301 int val
= head
->Right_Child
->value
.i_value
;
1302 if (head
->value
.op_value
== Expr_Op_Type_Sub
)
1304 note
= conscode (note_reloc2 (gencode (0), head
->Left_Child
->value
.s_value
,
1305 parent_reloc
, val
, 0),
1307 if (note1
!= NULL_CODE
)
1308 note
= conscode (note1
, note
);
1312 /* Call the recursive function. */
1313 note
= note_reloc1 (gencode (0), op
, parent_reloc
, pcrel
);
1314 if (note1
!= NULL_CODE
)
1315 note
= conscode (note1
, note
);
1316 note
= conctcode (Expr_Node_Gen_Reloc_R (head
), note
);
1322 Expr_Node_Gen_Reloc_R (Expr_Node
* head
)
1330 case Expr_Node_Constant
:
1331 note
= conscode (note_reloc2 (gencode (0), con
, BFD_ARELOC_BFIN_CONST
, head
->value
.i_value
, 0), NULL_CODE
);
1333 case Expr_Node_Reloc
:
1334 note
= conscode (note_reloc (gencode (0), head
, BFD_ARELOC_BFIN_PUSH
, 0), NULL_CODE
);
1336 case Expr_Node_Binop
:
1337 note1
= conctcode (Expr_Node_Gen_Reloc_R (head
->Left_Child
), Expr_Node_Gen_Reloc_R (head
->Right_Child
));
1338 switch (head
->value
.op_value
)
1340 case Expr_Op_Type_Add
:
1341 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_ADD
, 0), NULL_CODE
));
1343 case Expr_Op_Type_Sub
:
1344 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_SUB
, 0), NULL_CODE
));
1346 case Expr_Op_Type_Mult
:
1347 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_MULT
, 0), NULL_CODE
));
1349 case Expr_Op_Type_Div
:
1350 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_DIV
, 0), NULL_CODE
));
1352 case Expr_Op_Type_Mod
:
1353 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_MOD
, 0), NULL_CODE
));
1355 case Expr_Op_Type_Lshift
:
1356 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_LSHIFT
, 0), NULL_CODE
));
1358 case Expr_Op_Type_Rshift
:
1359 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_RSHIFT
, 0), NULL_CODE
));
1361 case Expr_Op_Type_BAND
:
1362 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_AND
, 0), NULL_CODE
));
1364 case Expr_Op_Type_BOR
:
1365 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_OR
, 0), NULL_CODE
));
1367 case Expr_Op_Type_BXOR
:
1368 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_XOR
, 0), NULL_CODE
));
1370 case Expr_Op_Type_LAND
:
1371 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_LAND
, 0), NULL_CODE
));
1373 case Expr_Op_Type_LOR
:
1374 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_LOR
, 0), NULL_CODE
));
1377 fprintf (stderr
, "%s:%d:Unknown operator found for arithmetic" " relocation", __FILE__
, __LINE__
);
1382 case Expr_Node_Unop
:
1383 note1
= conscode (Expr_Node_Gen_Reloc_R (head
->Left_Child
), NULL_CODE
);
1384 switch (head
->value
.op_value
)
1386 case Expr_Op_Type_NEG
:
1387 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_NEG
, 0), NULL_CODE
));
1389 case Expr_Op_Type_COMP
:
1390 note
= conctcode (note1
, conscode (note_reloc1 (gencode (0), op
, BFD_ARELOC_BFIN_COMP
, 0), NULL_CODE
));
1393 fprintf (stderr
, "%s:%d:Unknown operator found for arithmetic" " relocation", __FILE__
, __LINE__
);
1397 fprintf (stderr
, "%s:%d:Unknown node expression found during " "arithmetic relocation generation", __FILE__
, __LINE__
);
1402 /* Blackfin opcode generation. */
1404 /* These functions are called by the generated parser
1405 (from bfin-parse.y), the register type classification
1406 happens in bfin-lex.l. */
1408 #include "bfin-aux.h"
1409 #include "opcode/bfin.h"
1411 #define INIT(t) t c_code = init_##t
1412 #define ASSIGN(x) c_code.opcode |= ((x & c_code.mask_##x)<<c_code.bits_##x)
1413 #define ASSIGN_R(x) c_code.opcode |= (((x ? (x->regno & CODE_MASK) : 0) & c_code.mask_##x)<<c_code.bits_##x)
1415 #define HI(x) ((x >> 16) & 0xffff)
1416 #define LO(x) ((x ) & 0xffff)
1418 #define GROUP(x) ((x->regno & CLASS_MASK) >> 4)
1420 #define GEN_OPCODE32() \
1421 conscode (gencode (HI (c_code.opcode)), \
1422 conscode (gencode (LO (c_code.opcode)), NULL_CODE))
1424 #define GEN_OPCODE16() \
1425 conscode (gencode (c_code.opcode), NULL_CODE)
1428 /* 32 BIT INSTRUCTIONS. */
1431 /* DSP32 instruction generation. */
1434 bfin_gen_dsp32mac (int op1
, int MM
, int mmod
, int w1
, int P
,
1435 int h01
, int h11
, int h00
, int h10
, int op0
,
1436 REG_T dst
, REG_T src0
, REG_T src1
, int w0
)
1452 /* If we have full reg assignments, mask out LSB to encode
1453 single or simultaneous even/odd register moves. */
1463 return GEN_OPCODE32 ();
1467 bfin_gen_dsp32mult (int op1
, int MM
, int mmod
, int w1
, int P
,
1468 int h01
, int h11
, int h00
, int h10
, int op0
,
1469 REG_T dst
, REG_T src0
, REG_T src1
, int w0
)
1494 return GEN_OPCODE32 ();
1498 bfin_gen_dsp32alu (int HL
, int aopcde
, int aop
, int s
, int x
,
1499 REG_T dst0
, REG_T dst1
, REG_T src0
, REG_T src1
)
1513 return GEN_OPCODE32 ();
1517 bfin_gen_dsp32shift (int sopcde
, REG_T dst0
, REG_T src0
,
1518 REG_T src1
, int sop
, int HLs
)
1530 return GEN_OPCODE32 ();
1534 bfin_gen_dsp32shiftimm (int sopcde
, REG_T dst0
, int immag
,
1535 REG_T src1
, int sop
, int HLs
)
1537 INIT (DSP32ShiftImm
);
1547 return GEN_OPCODE32 ();
1553 bfin_gen_loopsetup (Expr_Node
* psoffset
, REG_T c
, int rop
,
1554 Expr_Node
* peoffset
, REG_T reg
)
1556 int soffset
, eoffset
;
1559 soffset
= (EXPR_VALUE (psoffset
) >> 1);
1561 eoffset
= (EXPR_VALUE (peoffset
) >> 1);
1568 conscode (gencode (HI (c_code
.opcode
)),
1569 conctcode (Expr_Node_Gen_Reloc (psoffset
, BFD_RELOC_BFIN_5_PCREL
),
1570 conctcode (gencode (LO (c_code
.opcode
)), Expr_Node_Gen_Reloc (peoffset
, BFD_RELOC_BFIN_11_PCREL
))));
1577 bfin_gen_calla (Expr_Node
* addr
, int S
)
1585 case 0 : reloc
= BFD_RELOC_BFIN_24_PCREL_JUMP_L
; break;
1586 case 1 : reloc
= BFD_RELOC_24_PCREL
; break;
1587 case 2 : reloc
= BFD_RELOC_BFIN_PLTPC
; break;
1593 val
= EXPR_VALUE (addr
) >> 1;
1594 high_val
= val
>> 16;
1596 return conscode (gencode (HI (c_code
.opcode
) | (high_val
& 0xff)),
1597 Expr_Node_Gen_Reloc (addr
, reloc
));
1601 bfin_gen_linkage (int R
, int framesize
)
1608 return GEN_OPCODE32 ();
1612 /* Load and Store. */
1615 bfin_gen_ldimmhalf (REG_T reg
, int H
, int S
, int Z
, Expr_Node
* phword
, int reloc
)
1618 unsigned val
= EXPR_VALUE (phword
);
1626 grp
= (GROUP (reg
));
1630 return conscode (gencode (HI (c_code
.opcode
)), Expr_Node_Gen_Reloc (phword
, BFD_RELOC_BFIN_16_IMM
));
1632 else if (reloc
== 1)
1634 return conscode (gencode (HI (c_code
.opcode
)), Expr_Node_Gen_Reloc (phword
, IS_H (*reg
) ? BFD_RELOC_BFIN_16_HIGH
: BFD_RELOC_BFIN_16_LOW
));
1641 return GEN_OPCODE32 ();
1645 bfin_gen_ldstidxi (REG_T ptr
, REG_T reg
, int W
, int sz
, int Z
, Expr_Node
* poffset
)
1649 if (!IS_PREG (*ptr
) || (!IS_DREG (*reg
) && !Z
))
1651 fprintf (stderr
, "Warning: possible mixup of Preg/Dreg\n");
1662 if (poffset
->type
!= Expr_Node_Constant
)
1664 /* a GOT relocation such as R0 = [P5 + symbol@GOT] */
1665 /* distinguish between R0 = [P5 + symbol@GOT] and
1666 P5 = [P5 + _current_shared_library_p5_offset_]
1668 if (poffset
->type
== Expr_Node_Reloc
1669 && !strcmp (poffset
->value
.s_value
,
1670 "_current_shared_library_p5_offset_"))
1672 return conscode (gencode (HI (c_code
.opcode
)),
1673 Expr_Node_Gen_Reloc(poffset
, BFD_RELOC_16
));
1675 else if (poffset
->type
!= Expr_Node_GOT_Reloc
)
1678 return conscode (gencode (HI (c_code
.opcode
)),
1679 Expr_Node_Gen_Reloc(poffset
->Left_Child
,
1680 poffset
->value
.i_value
));
1686 { /* load/store access size */
1687 case 0: /* 32 bit */
1688 value
= EXPR_VALUE (poffset
) >> 2;
1690 case 1: /* 16 bit */
1691 value
= EXPR_VALUE (poffset
) >> 1;
1694 value
= EXPR_VALUE (poffset
);
1700 offset
= (value
& 0xffff);
1702 return GEN_OPCODE32 ();
1708 bfin_gen_ldst (REG_T ptr
, REG_T reg
, int aop
, int sz
, int Z
, int W
)
1712 if (!IS_PREG (*ptr
) || (!IS_DREG (*reg
) && !Z
))
1714 fprintf (stderr
, "Warning: possible mixup of Preg/Dreg\n");
1725 return GEN_OPCODE16 ();
1729 bfin_gen_ldstii (REG_T ptr
, REG_T reg
, Expr_Node
* poffset
, int W
, int op
)
1736 if (!IS_PREG (*ptr
))
1738 fprintf (stderr
, "Warning: possible mixup of Preg/Dreg\n");
1746 value
= EXPR_VALUE (poffset
) >> 1;
1750 value
= EXPR_VALUE (poffset
) >> 2;
1762 return GEN_OPCODE16 ();
1766 bfin_gen_ldstiifp (REG_T sreg
, Expr_Node
* poffset
, int W
)
1768 /* Set bit 4 if it's a Preg. */
1769 int reg
= (sreg
->regno
& CODE_MASK
) | (IS_PREG (*sreg
) ? 0x8 : 0x0);
1770 int offset
= ((~(EXPR_VALUE (poffset
) >> 2)) & 0x1f) + 1;
1776 return GEN_OPCODE16 ();
1780 bfin_gen_ldstpmod (REG_T ptr
, REG_T reg
, int aop
, int W
, REG_T idx
)
1790 return GEN_OPCODE16 ();
1794 bfin_gen_dspldst (REG_T i
, REG_T reg
, int aop
, int W
, int m
)
1804 return GEN_OPCODE16 ();
1808 bfin_gen_logi2op (int opc
, int src
, int dst
)
1816 return GEN_OPCODE16 ();
1820 bfin_gen_brcc (int T
, int B
, Expr_Node
* poffset
)
1827 offset
= ((EXPR_VALUE (poffset
) >> 1));
1829 return conscode (gencode (c_code
.opcode
), Expr_Node_Gen_Reloc (poffset
, BFD_RELOC_BFIN_10_PCREL
));
1833 bfin_gen_ujump (Expr_Node
* poffset
)
1838 offset
= ((EXPR_VALUE (poffset
) >> 1));
1841 return conscode (gencode (c_code
.opcode
),
1842 Expr_Node_Gen_Reloc (
1843 poffset
, BFD_RELOC_BFIN_12_PCREL_JUMP_S
));
1847 bfin_gen_alu2op (REG_T dst
, REG_T src
, int opc
)
1855 return GEN_OPCODE16 ();
1859 bfin_gen_compi2opd (REG_T dst
, int src
, int op
)
1867 return GEN_OPCODE16 ();
1871 bfin_gen_compi2opp (REG_T dst
, int src
, int op
)
1879 return GEN_OPCODE16 ();
1883 bfin_gen_dagmodik (REG_T i
, int op
)
1890 return GEN_OPCODE16 ();
1894 bfin_gen_dagmodim (REG_T i
, REG_T m
, int op
, int br
)
1903 return GEN_OPCODE16 ();
1907 bfin_gen_ptr2op (REG_T dst
, REG_T src
, int opc
)
1915 return GEN_OPCODE16 ();
1919 bfin_gen_comp3op (REG_T src0
, REG_T src1
, REG_T dst
, int opc
)
1928 return GEN_OPCODE16 ();
1932 bfin_gen_ccflag (REG_T x
, int y
, int opc
, int I
, int G
)
1942 return GEN_OPCODE16 ();
1946 bfin_gen_ccmv (REG_T src
, REG_T dst
, int T
)
1959 return GEN_OPCODE16 ();
1963 bfin_gen_cc2stat (int cbit
, int op
, int D
)
1971 return GEN_OPCODE16 ();
1975 bfin_gen_regmv (REG_T src
, REG_T dst
)
1988 return GEN_OPCODE16 ();
1992 bfin_gen_cc2dreg (int op
, REG_T reg
)
1999 return GEN_OPCODE16 ();
2003 bfin_gen_progctrl (int prgfunc
, int poprnd
)
2010 return GEN_OPCODE16 ();
2014 bfin_gen_cactrl (REG_T reg
, int a
, int op
)
2022 return GEN_OPCODE16 ();
2026 bfin_gen_pushpopmultiple (int dr
, int pr
, int d
, int p
, int W
)
2028 INIT (PushPopMultiple
);
2036 return GEN_OPCODE16 ();
2040 bfin_gen_pushpopreg (REG_T reg
, int W
)
2046 grp
= (GROUP (reg
));
2050 return GEN_OPCODE16 ();
2053 /* Pseudo Debugging Support. */
2056 bfin_gen_pseudodbg (int fn
, int reg
, int grp
)
2064 return GEN_OPCODE16 ();
2068 bfin_gen_pseudodbg_assert (int dbgop
, REG_T regtest
, int expected
)
2070 INIT (PseudoDbg_Assert
);
2076 return GEN_OPCODE32 ();
2079 /* Multiple instruction generation. */
2082 bfin_gen_multi_instr (INSTR_T dsp32
, INSTR_T dsp16_grp1
, INSTR_T dsp16_grp2
)
2086 /* If it's a 0, convert into MNOP. */
2090 SET_MULTI_INSTRUCTION_BIT (dsp32
);
2094 dsp32
= gencode (0xc803);
2095 walk
= gencode (0x1800);
2101 dsp16_grp1
= gencode (0x0000);
2106 dsp16_grp2
= gencode (0x0000);
2109 walk
->next
= dsp16_grp1
;
2110 dsp16_grp1
->next
= dsp16_grp2
;
2111 dsp16_grp2
->next
= NULL_CODE
;
2117 bfin_gen_loop (Expr_Node
*expr
, REG_T reg
, int rop
, REG_T preg
)
2119 const char *loopsym
;
2120 char *lbeginsym
, *lendsym
;
2121 Expr_Node_Value lbeginval
, lendval
;
2122 Expr_Node
*lbegin
, *lend
;
2124 loopsym
= expr
->value
.s_value
;
2125 lbeginsym
= (char *) xmalloc (strlen (loopsym
) + strlen ("__BEGIN") + 5);
2126 lendsym
= (char *) xmalloc (strlen (loopsym
) + strlen ("__END") + 5);
2131 strcat (lbeginsym
, "L$L$");
2132 strcat (lbeginsym
, loopsym
);
2133 strcat (lbeginsym
, "__BEGIN");
2135 strcat (lendsym
, "L$L$");
2136 strcat (lendsym
, loopsym
);
2137 strcat (lendsym
, "__END");
2139 lbeginval
.s_value
= lbeginsym
;
2140 lendval
.s_value
= lendsym
;
2142 lbegin
= Expr_Node_Create (Expr_Node_Reloc
, lbeginval
, NULL
, NULL
);
2143 lend
= Expr_Node_Create (Expr_Node_Reloc
, lendval
, NULL
, NULL
);
2145 symbol_remove (symbol_find (loopsym
), &symbol_rootP
, &symbol_lastP
);
2147 return bfin_gen_loopsetup(lbegin
, reg
, rop
, lend
, preg
);
2151 bfin_eol_in_insn (char *line
)
2153 /* Allow a new-line to appear in the middle of a multi-issue instruction. */
2160 /* A semi-colon followed by a newline is always the end of a line. */
2161 if (line
[-1] == ';')
2164 if (line
[-1] == '|')
2167 /* If the || is on the next line, there might be leading whitespace. */
2169 while (*temp
== ' ' || *temp
== '\t') temp
++;
2178 bfin_start_label (char *ptr
)
2181 while (!ISSPACE (*ptr
) && !is_end_of_line
[(unsigned char) *ptr
])
2185 if (*ptr
== '(' || *ptr
== '[')
2192 bfin_force_relocation (struct fix
*fixp
)
2194 if (fixp
->fx_r_type
==BFD_RELOC_BFIN_16_LOW
2195 || fixp
->fx_r_type
== BFD_RELOC_BFIN_16_HIGH
)
2198 return generic_force_reloc (fixp
);
2201 /* This is a stripped down version of the disassembler. The only thing it
2202 does is return a mask of registers modified by an instruction. Only
2203 instructions that can occur in a parallel-issue bundle are handled, and
2204 only the registers that can cause a conflict are recorded. */
2206 #define DREG_MASK(n) (0x101 << (n))
2207 #define DREGH_MASK(n) (0x100 << (n))
2208 #define DREGL_MASK(n) (0x001 << (n))
2209 #define IREG_MASK(n) (1 << ((n) + 16))
2212 decode_ProgCtrl_0 (int iw0
)
2220 decode_LDSTpmod_0 (int iw0
)
2223 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2224 | 1 | 0 | 0 | 0 |.W.|.aop...|.reg.......|.idx.......|.ptr.......|
2225 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2226 int W
= ((iw0
>> LDSTpmod_W_bits
) & LDSTpmod_W_mask
);
2227 int aop
= ((iw0
>> LDSTpmod_aop_bits
) & LDSTpmod_aop_mask
);
2228 int idx
= ((iw0
>> LDSTpmod_idx_bits
) & LDSTpmod_idx_mask
);
2229 int ptr
= ((iw0
>> LDSTpmod_ptr_bits
) & LDSTpmod_ptr_mask
);
2230 int reg
= ((iw0
>> LDSTpmod_reg_bits
) & LDSTpmod_reg_mask
);
2232 if (aop
== 1 && W
== 0 && idx
== ptr
)
2233 return DREGL_MASK (reg
);
2234 else if (aop
== 2 && W
== 0 && idx
== ptr
)
2235 return DREGH_MASK (reg
);
2236 else if (aop
== 1 && W
== 1 && idx
== ptr
)
2238 else if (aop
== 2 && W
== 1 && idx
== ptr
)
2240 else if (aop
== 0 && W
== 0)
2241 return DREG_MASK (reg
);
2242 else if (aop
== 1 && W
== 0)
2243 return DREGL_MASK (reg
);
2244 else if (aop
== 2 && W
== 0)
2245 return DREGH_MASK (reg
);
2246 else if (aop
== 3 && W
== 0)
2247 return DREG_MASK (reg
);
2248 else if (aop
== 3 && W
== 1)
2249 return DREG_MASK (reg
);
2250 else if (aop
== 0 && W
== 1)
2252 else if (aop
== 1 && W
== 1)
2254 else if (aop
== 2 && W
== 1)
2263 decode_dagMODim_0 (int iw0
)
2266 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2267 | 1 | 0 | 0 | 1 | 1 | 1 | 1 | 0 |.br| 1 | 1 |.op|.m.....|.i.....|
2268 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2269 int i
= ((iw0
>> DagMODim_i_bits
) & DagMODim_i_mask
);
2270 int op
= ((iw0
>> DagMODim_op_bits
) & DagMODim_op_mask
);
2272 if (op
== 0 || op
== 1)
2273 return IREG_MASK (i
);
2281 decode_dagMODik_0 (int iw0
)
2284 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2285 | 1 | 0 | 0 | 1 | 1 | 1 | 1 | 1 | 0 | 1 | 1 | 0 |.op....|.i.....|
2286 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2287 int i
= ((iw0
>> DagMODik_i_bits
) & DagMODik_i_mask
);
2288 return IREG_MASK (i
);
2293 decode_dspLDST_0 (int iw0
)
2296 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2297 | 1 | 0 | 0 | 1 | 1 | 1 |.W.|.aop...|.m.....|.i.....|.reg.......|
2298 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2299 int i
= ((iw0
>> DspLDST_i_bits
) & DspLDST_i_mask
);
2300 int m
= ((iw0
>> DspLDST_m_bits
) & DspLDST_m_mask
);
2301 int W
= ((iw0
>> DspLDST_W_bits
) & DspLDST_W_mask
);
2302 int aop
= ((iw0
>> DspLDST_aop_bits
) & DspLDST_aop_mask
);
2303 int reg
= ((iw0
>> DspLDST_reg_bits
) & DspLDST_reg_mask
);
2305 if (aop
== 0 && W
== 0 && m
== 0)
2306 return DREG_MASK (reg
) | IREG_MASK (i
);
2307 else if (aop
== 0 && W
== 0 && m
== 1)
2308 return DREGL_MASK (reg
) | IREG_MASK (i
);
2309 else if (aop
== 0 && W
== 0 && m
== 2)
2310 return DREGH_MASK (reg
) | IREG_MASK (i
);
2311 else if (aop
== 1 && W
== 0 && m
== 0)
2312 return DREG_MASK (reg
) | IREG_MASK (i
);
2313 else if (aop
== 1 && W
== 0 && m
== 1)
2314 return DREGL_MASK (reg
) | IREG_MASK (i
);
2315 else if (aop
== 1 && W
== 0 && m
== 2)
2316 return DREGH_MASK (reg
) | IREG_MASK (i
);
2317 else if (aop
== 2 && W
== 0 && m
== 0)
2318 return DREG_MASK (reg
);
2319 else if (aop
== 2 && W
== 0 && m
== 1)
2320 return DREGL_MASK (reg
);
2321 else if (aop
== 2 && W
== 0 && m
== 2)
2322 return DREGH_MASK (reg
);
2323 else if (aop
== 0 && W
== 1 && m
== 0)
2324 return IREG_MASK (i
);
2325 else if (aop
== 0 && W
== 1 && m
== 1)
2326 return IREG_MASK (i
);
2327 else if (aop
== 0 && W
== 1 && m
== 2)
2328 return IREG_MASK (i
);
2329 else if (aop
== 1 && W
== 1 && m
== 0)
2330 return IREG_MASK (i
);
2331 else if (aop
== 1 && W
== 1 && m
== 1)
2332 return IREG_MASK (i
);
2333 else if (aop
== 1 && W
== 1 && m
== 2)
2334 return IREG_MASK (i
);
2335 else if (aop
== 2 && W
== 1 && m
== 0)
2337 else if (aop
== 2 && W
== 1 && m
== 1)
2339 else if (aop
== 2 && W
== 1 && m
== 2)
2341 else if (aop
== 3 && W
== 0)
2342 return DREG_MASK (reg
) | IREG_MASK (i
);
2343 else if (aop
== 3 && W
== 1)
2344 return IREG_MASK (i
);
2351 decode_LDST_0 (int iw0
)
2354 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2355 | 1 | 0 | 0 | 1 |.sz....|.W.|.aop...|.Z.|.ptr.......|.reg.......|
2356 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2357 int Z
= ((iw0
>> LDST_Z_bits
) & LDST_Z_mask
);
2358 int W
= ((iw0
>> LDST_W_bits
) & LDST_W_mask
);
2359 int sz
= ((iw0
>> LDST_sz_bits
) & LDST_sz_mask
);
2360 int aop
= ((iw0
>> LDST_aop_bits
) & LDST_aop_mask
);
2361 int reg
= ((iw0
>> LDST_reg_bits
) & LDST_reg_mask
);
2363 if (aop
== 0 && sz
== 0 && Z
== 0 && W
== 0)
2364 return DREG_MASK (reg
);
2365 else if (aop
== 0 && sz
== 0 && Z
== 1 && W
== 0)
2367 else if (aop
== 0 && sz
== 1 && Z
== 0 && W
== 0)
2368 return DREG_MASK (reg
);
2369 else if (aop
== 0 && sz
== 1 && Z
== 1 && W
== 0)
2370 return DREG_MASK (reg
);
2371 else if (aop
== 0 && sz
== 2 && Z
== 0 && W
== 0)
2372 return DREG_MASK (reg
);
2373 else if (aop
== 0 && sz
== 2 && Z
== 1 && W
== 0)
2374 return DREG_MASK (reg
);
2375 else if (aop
== 1 && sz
== 0 && Z
== 0 && W
== 0)
2376 return DREG_MASK (reg
);
2377 else if (aop
== 1 && sz
== 0 && Z
== 1 && W
== 0)
2379 else if (aop
== 1 && sz
== 1 && Z
== 0 && W
== 0)
2380 return DREG_MASK (reg
);
2381 else if (aop
== 1 && sz
== 1 && Z
== 1 && W
== 0)
2382 return DREG_MASK (reg
);
2383 else if (aop
== 1 && sz
== 2 && Z
== 0 && W
== 0)
2384 return DREG_MASK (reg
);
2385 else if (aop
== 1 && sz
== 2 && Z
== 1 && W
== 0)
2386 return DREG_MASK (reg
);
2387 else if (aop
== 2 && sz
== 0 && Z
== 0 && W
== 0)
2388 return DREG_MASK (reg
);
2389 else if (aop
== 2 && sz
== 0 && Z
== 1 && W
== 0)
2391 else if (aop
== 2 && sz
== 1 && Z
== 0 && W
== 0)
2392 return DREG_MASK (reg
);
2393 else if (aop
== 2 && sz
== 1 && Z
== 1 && W
== 0)
2394 return DREG_MASK (reg
);
2395 else if (aop
== 2 && sz
== 2 && Z
== 0 && W
== 0)
2396 return DREG_MASK (reg
);
2397 else if (aop
== 2 && sz
== 2 && Z
== 1 && W
== 0)
2398 return DREG_MASK (reg
);
2399 else if (aop
== 0 && sz
== 0 && Z
== 0 && W
== 1)
2401 else if (aop
== 0 && sz
== 0 && Z
== 1 && W
== 1)
2403 else if (aop
== 0 && sz
== 1 && Z
== 0 && W
== 1)
2405 else if (aop
== 0 && sz
== 2 && Z
== 0 && W
== 1)
2407 else if (aop
== 1 && sz
== 0 && Z
== 0 && W
== 1)
2409 else if (aop
== 1 && sz
== 0 && Z
== 1 && W
== 1)
2411 else if (aop
== 1 && sz
== 1 && Z
== 0 && W
== 1)
2413 else if (aop
== 1 && sz
== 2 && Z
== 0 && W
== 1)
2415 else if (aop
== 2 && sz
== 0 && Z
== 0 && W
== 1)
2417 else if (aop
== 2 && sz
== 0 && Z
== 1 && W
== 1)
2419 else if (aop
== 2 && sz
== 1 && Z
== 0 && W
== 1)
2421 else if (aop
== 2 && sz
== 2 && Z
== 0 && W
== 1)
2428 decode_LDSTiiFP_0 (int iw0
)
2431 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2432 | 1 | 0 | 1 | 1 | 1 | 0 |.W.|.offset............|.reg...........|
2433 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2434 int reg
= ((iw0
>> LDSTiiFP_reg_bits
) & LDSTiiFP_reg_mask
);
2435 int W
= ((iw0
>> LDSTiiFP_W_bits
) & LDSTiiFP_W_mask
);
2438 return reg
< 8 ? DREG_MASK (reg
) : 0;
2444 decode_LDSTii_0 (int iw0
)
2447 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2448 | 1 | 0 | 1 |.W.|.op....|.offset........|.ptr.......|.reg.......|
2449 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2450 int reg
= ((iw0
>> LDSTii_reg_bit
) & LDSTii_reg_mask
);
2451 int op
= ((iw0
>> LDSTii_op_bit
) & LDSTii_op_mask
);
2452 int W
= ((iw0
>> LDSTii_W_bit
) & LDSTii_W_mask
);
2454 if (W
== 0 && op
!= 3)
2455 return DREG_MASK (reg
);
2456 else if (W
== 0 && op
== 3)
2458 else if (W
== 1 && op
== 0)
2460 else if (W
== 1 && op
== 1)
2462 else if (W
== 1 && op
== 3)
2469 decode_dsp32mac_0 (int iw0
, int iw1
)
2473 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2474 | 1 | 1 | 0 | 0 |.M.| 0 | 0 |.mmod..........|.MM|.P.|.w1|.op1...|
2475 |.h01|.h11|.w0|.op0...|.h00|.h10|.dst.......|.src0......|.src1..|
2476 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2477 int op1
= ((iw0
>> (DSP32Mac_op1_bits
- 16)) & DSP32Mac_op1_mask
);
2478 int w1
= ((iw0
>> (DSP32Mac_w1_bits
- 16)) & DSP32Mac_w1_mask
);
2479 int P
= ((iw0
>> (DSP32Mac_p_bits
- 16)) & DSP32Mac_p_mask
);
2480 int mmod
= ((iw0
>> (DSP32Mac_mmod_bits
- 16)) & DSP32Mac_mmod_mask
);
2481 int w0
= ((iw1
>> DSP32Mac_w0_bits
) & DSP32Mac_w0_mask
);
2482 int MM
= ((iw1
>> DSP32Mac_MM_bits
) & DSP32Mac_MM_mask
);
2483 int dst
= ((iw1
>> DSP32Mac_dst_bits
) & DSP32Mac_dst_mask
);
2484 int op0
= ((iw1
>> DSP32Mac_op0_bits
) & DSP32Mac_op0_mask
);
2486 if (w0
== 0 && w1
== 0 && op1
== 3 && op0
== 3)
2492 if ((w1
|| w0
) && mmod
== M_W32
)
2495 if (((1 << mmod
) & (P
? 0x131b : 0x1b5f)) == 0)
2498 if (w1
== 1 || op1
!= 3)
2503 return DREG_MASK (dst
+ 1);
2505 return DREGH_MASK (dst
);
2509 if (w0
== 1 || op0
!= 3)
2514 return DREG_MASK (dst
);
2516 return DREGL_MASK (dst
);
2524 decode_dsp32mult_0 (int iw0
, int iw1
)
2527 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2528 | 1 | 1 | 0 | 0 |.M.| 0 | 1 |.mmod..........|.MM|.P.|.w1|.op1...|
2529 |.h01|.h11|.w0|.op0...|.h00|.h10|.dst.......|.src0......|.src1..|
2530 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2531 int w1
= ((iw0
>> (DSP32Mac_w1_bits
- 16)) & DSP32Mac_w1_mask
);
2532 int P
= ((iw0
>> (DSP32Mac_p_bits
- 16)) & DSP32Mac_p_mask
);
2533 int mmod
= ((iw0
>> (DSP32Mac_mmod_bits
- 16)) & DSP32Mac_mmod_mask
);
2534 int w0
= ((iw1
>> DSP32Mac_w0_bits
) & DSP32Mac_w0_mask
);
2535 int dst
= ((iw1
>> DSP32Mac_dst_bits
) & DSP32Mac_dst_mask
);
2538 if (w1
== 0 && w0
== 0)
2541 if (((1 << mmod
) & (P
? 0x313 : 0x1b57)) == 0)
2547 return DREG_MASK (dst
| 1);
2549 return DREGH_MASK (dst
);
2555 return DREG_MASK (dst
);
2557 return DREGL_MASK (dst
);
2564 decode_dsp32alu_0 (int iw0
, int iw1
)
2567 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2568 | 1 | 1 | 0 | 0 |.M.| 1 | 0 | - | - | - |.HL|.aopcde............|
2569 |.aop...|.s.|.x.|.dst0......|.dst1......|.src0......|.src1......|
2570 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2571 int s
= ((iw1
>> DSP32Alu_s_bits
) & DSP32Alu_s_mask
);
2572 int x
= ((iw1
>> DSP32Alu_x_bits
) & DSP32Alu_x_mask
);
2573 int aop
= ((iw1
>> DSP32Alu_aop_bits
) & DSP32Alu_aop_mask
);
2574 int dst0
= ((iw1
>> DSP32Alu_dst0_bits
) & DSP32Alu_dst0_mask
);
2575 int dst1
= ((iw1
>> DSP32Alu_dst1_bits
) & DSP32Alu_dst1_mask
);
2576 int HL
= ((iw0
>> (DSP32Alu_HL_bits
- 16)) & DSP32Alu_HL_mask
);
2577 int aopcde
= ((iw0
>> (DSP32Alu_aopcde_bits
- 16)) & DSP32Alu_aopcde_mask
);
2579 if (aop
== 0 && aopcde
== 9 && s
== 0)
2581 else if (aop
== 2 && aopcde
== 9 && HL
== 0 && s
== 0)
2583 else if (aop
>= x
* 2 && aopcde
== 5)
2584 return HL
? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2585 else if (HL
== 0 && aopcde
== 2)
2586 return DREGL_MASK (dst0
);
2587 else if (HL
== 1 && aopcde
== 2)
2588 return DREGH_MASK (dst0
);
2589 else if (HL
== 0 && aopcde
== 3)
2590 return DREGL_MASK (dst0
);
2591 else if (HL
== 1 && aopcde
== 3)
2592 return DREGH_MASK (dst0
);
2594 else if (aop
== 0 && aopcde
== 9 && s
== 1)
2596 else if (aop
== 1 && aopcde
== 9 && s
== 0)
2598 else if (aop
== 2 && aopcde
== 9 && s
== 1)
2600 else if (aop
== 3 && aopcde
== 9 && s
== 0)
2602 else if (aopcde
== 8)
2604 else if (aop
== 0 && aopcde
== 11)
2605 return DREG_MASK (dst0
);
2606 else if (aop
== 1 && aopcde
== 11)
2607 return HL
? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2608 else if (aopcde
== 11)
2610 else if (aopcde
== 22)
2611 return DREG_MASK (dst0
);
2613 else if ((aop
== 0 || aop
== 1) && aopcde
== 14)
2615 else if (aop
== 3 && HL
== 0 && aopcde
== 14)
2618 else if (aop
== 3 && HL
== 0 && aopcde
== 15)
2619 return DREG_MASK (dst0
);
2621 else if (aop
== 1 && aopcde
== 16)
2624 else if (aop
== 0 && aopcde
== 16)
2627 else if (aop
== 3 && HL
== 0 && aopcde
== 16)
2630 else if (aop
== 3 && HL
== 0 && aopcde
== 7)
2631 return DREG_MASK (dst0
);
2632 else if ((aop
== 0 || aop
== 1 || aop
== 2) && aopcde
== 7)
2633 return DREG_MASK (dst0
);
2635 else if (aop
== 0 && aopcde
== 12)
2636 return DREG_MASK (dst0
);
2637 else if (aop
== 1 && aopcde
== 12)
2638 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2639 else if (aop
== 3 && aopcde
== 12)
2640 return HL
? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2642 else if (aopcde
== 0)
2643 return DREG_MASK (dst0
);
2644 else if (aopcde
== 1)
2645 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2647 else if (aop
== 0 && aopcde
== 10)
2648 return DREGL_MASK (dst0
);
2649 else if (aop
== 1 && aopcde
== 10)
2650 return DREGL_MASK (dst0
);
2652 else if ((aop
== 1 || aop
== 0) && aopcde
== 4)
2653 return DREG_MASK (dst0
);
2654 else if (aop
== 2 && aopcde
== 4)
2655 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2657 else if (aop
== 0 && aopcde
== 17)
2658 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2659 else if (aop
== 1 && aopcde
== 17)
2660 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2661 else if (aop
== 0 && aopcde
== 18)
2663 else if (aop
== 3 && aopcde
== 18)
2666 else if ((aop
== 0 || aop
== 1 || aop
== 2) && aopcde
== 6)
2667 return DREG_MASK (dst0
);
2669 else if ((aop
== 0 || aop
== 1) && aopcde
== 20)
2670 return DREG_MASK (dst0
);
2672 else if ((aop
== 0 || aop
== 1) && aopcde
== 21)
2673 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2675 else if (aop
== 0 && aopcde
== 23 && HL
== 1)
2676 return DREG_MASK (dst0
);
2677 else if (aop
== 0 && aopcde
== 23 && HL
== 0)
2678 return DREG_MASK (dst0
);
2680 else if (aop
== 0 && aopcde
== 24)
2681 return DREG_MASK (dst0
);
2682 else if (aop
== 1 && aopcde
== 24)
2683 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2684 else if (aopcde
== 13)
2685 return DREG_MASK (dst0
) | DREG_MASK (dst1
);
2693 decode_dsp32shift_0 (int iw0
, int iw1
)
2696 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2697 | 1 | 1 | 0 | 0 |.M.| 1 | 1 | 0 | 0 | - | - |.sopcde............|
2698 |.sop...|.HLs...|.dst0......| - | - | - |.src0......|.src1......|
2699 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2700 int HLs
= ((iw1
>> DSP32Shift_HLs_bits
) & DSP32Shift_HLs_mask
);
2701 int sop
= ((iw1
>> DSP32Shift_sop_bits
) & DSP32Shift_sop_mask
);
2702 int src0
= ((iw1
>> DSP32Shift_src0_bits
) & DSP32Shift_src0_mask
);
2703 int src1
= ((iw1
>> DSP32Shift_src1_bits
) & DSP32Shift_src1_mask
);
2704 int dst0
= ((iw1
>> DSP32Shift_dst0_bits
) & DSP32Shift_dst0_mask
);
2705 int sopcde
= ((iw0
>> (DSP32Shift_sopcde_bits
- 16)) & DSP32Shift_sopcde_mask
);
2707 if (sop
== 0 && sopcde
== 0)
2708 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2709 else if (sop
== 1 && sopcde
== 0)
2710 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2711 else if (sop
== 2 && sopcde
== 0)
2712 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2713 else if (sop
== 0 && sopcde
== 3)
2715 else if (sop
== 1 && sopcde
== 3)
2717 else if (sop
== 2 && sopcde
== 3)
2719 else if (sop
== 3 && sopcde
== 3)
2720 return DREG_MASK (dst0
);
2721 else if (sop
== 0 && sopcde
== 1)
2722 return DREG_MASK (dst0
);
2723 else if (sop
== 1 && sopcde
== 1)
2724 return DREG_MASK (dst0
);
2725 else if (sop
== 2 && sopcde
== 1)
2726 return DREG_MASK (dst0
);
2727 else if (sopcde
== 2)
2728 return DREG_MASK (dst0
);
2729 else if (sopcde
== 4)
2730 return DREG_MASK (dst0
);
2731 else if (sop
== 0 && sopcde
== 5)
2732 return DREGL_MASK (dst0
);
2733 else if (sop
== 1 && sopcde
== 5)
2734 return DREGL_MASK (dst0
);
2735 else if (sop
== 2 && sopcde
== 5)
2736 return DREGL_MASK (dst0
);
2737 else if (sop
== 0 && sopcde
== 6)
2738 return DREGL_MASK (dst0
);
2739 else if (sop
== 1 && sopcde
== 6)
2740 return DREGL_MASK (dst0
);
2741 else if (sop
== 3 && sopcde
== 6)
2742 return DREGL_MASK (dst0
);
2743 else if (sop
== 0 && sopcde
== 7)
2744 return DREGL_MASK (dst0
);
2745 else if (sop
== 1 && sopcde
== 7)
2746 return DREGL_MASK (dst0
);
2747 else if (sop
== 2 && sopcde
== 7)
2748 return DREGL_MASK (dst0
);
2749 else if (sop
== 3 && sopcde
== 7)
2750 return DREGL_MASK (dst0
);
2751 else if (sop
== 0 && sopcde
== 8)
2752 return DREG_MASK (src0
) | DREG_MASK (src1
);
2755 OUTS (outf
, "BITMUX (");
2756 OUTS (outf
, dregs (src0
));
2758 OUTS (outf
, dregs (src1
));
2759 OUTS (outf
, ", A0) (ASR)");
2762 else if (sop
== 1 && sopcde
== 8)
2763 return DREG_MASK (src0
) | DREG_MASK (src1
);
2766 OUTS (outf
, "BITMUX (");
2767 OUTS (outf
, dregs (src0
));
2769 OUTS (outf
, dregs (src1
));
2770 OUTS (outf
, ", A0) (ASL)");
2773 else if (sopcde
== 9)
2774 return sop
< 2 ? DREGL_MASK (dst0
) : DREG_MASK (dst0
);
2775 else if (sopcde
== 10)
2776 return DREG_MASK (dst0
);
2777 else if (sop
== 0 && sopcde
== 11)
2778 return DREGL_MASK (dst0
);
2779 else if (sop
== 1 && sopcde
== 11)
2780 return DREGL_MASK (dst0
);
2781 else if (sop
== 0 && sopcde
== 12)
2783 else if (sop
== 1 && sopcde
== 12)
2784 return DREGL_MASK (dst0
);
2785 else if (sop
== 0 && sopcde
== 13)
2786 return DREG_MASK (dst0
);
2787 else if (sop
== 1 && sopcde
== 13)
2788 return DREG_MASK (dst0
);
2789 else if (sop
== 2 && sopcde
== 13)
2790 return DREG_MASK (dst0
);
2796 decode_dsp32shiftimm_0 (int iw0
, int iw1
)
2799 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2800 | 1 | 1 | 0 | 0 |.M.| 1 | 1 | 0 | 1 | - | - |.sopcde............|
2801 |.sop...|.HLs...|.dst0......|.immag.................|.src1......|
2802 +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2803 int sop
= ((iw1
>> DSP32ShiftImm_sop_bits
) & DSP32ShiftImm_sop_mask
);
2804 int bit8
= ((iw1
>> 8) & 0x1);
2805 int dst0
= ((iw1
>> DSP32ShiftImm_dst0_bits
) & DSP32ShiftImm_dst0_mask
);
2806 int sopcde
= ((iw0
>> (DSP32ShiftImm_sopcde_bits
- 16)) & DSP32ShiftImm_sopcde_mask
);
2807 int HLs
= ((iw1
>> DSP32ShiftImm_HLs_bits
) & DSP32ShiftImm_HLs_mask
);
2810 if (sop
== 0 && sopcde
== 0)
2811 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2812 else if (sop
== 1 && sopcde
== 0 && bit8
== 0)
2813 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2814 else if (sop
== 1 && sopcde
== 0 && bit8
== 1)
2815 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2816 else if (sop
== 2 && sopcde
== 0 && bit8
== 0)
2817 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2818 else if (sop
== 2 && sopcde
== 0 && bit8
== 1)
2819 return HLs
& 2 ? DREGH_MASK (dst0
) : DREGL_MASK (dst0
);
2820 else if (sop
== 2 && sopcde
== 3 && HLs
== 1)
2822 else if (sop
== 0 && sopcde
== 3 && HLs
== 0 && bit8
== 0)
2824 else if (sop
== 0 && sopcde
== 3 && HLs
== 0 && bit8
== 1)
2826 else if (sop
== 0 && sopcde
== 3 && HLs
== 1 && bit8
== 0)
2828 else if (sop
== 0 && sopcde
== 3 && HLs
== 1 && bit8
== 1)
2830 else if (sop
== 1 && sopcde
== 3 && HLs
== 0)
2832 else if (sop
== 1 && sopcde
== 3 && HLs
== 1)
2834 else if (sop
== 2 && sopcde
== 3 && HLs
== 0)
2836 else if (sop
== 1 && sopcde
== 1 && bit8
== 0)
2837 return DREG_MASK (dst0
);
2838 else if (sop
== 1 && sopcde
== 1 && bit8
== 1)
2839 return DREG_MASK (dst0
);
2840 else if (sop
== 2 && sopcde
== 1 && bit8
== 1)
2841 return DREG_MASK (dst0
);
2842 else if (sop
== 2 && sopcde
== 1 && bit8
== 0)
2843 return DREG_MASK (dst0
);
2844 else if (sop
== 0 && sopcde
== 1)
2845 return DREG_MASK (dst0
);
2846 else if (sop
== 1 && sopcde
== 2)
2847 return DREG_MASK (dst0
);
2848 else if (sop
== 2 && sopcde
== 2 && bit8
== 1)
2849 return DREG_MASK (dst0
);
2850 else if (sop
== 2 && sopcde
== 2 && bit8
== 0)
2851 return DREG_MASK (dst0
);
2852 else if (sop
== 3 && sopcde
== 2)
2853 return DREG_MASK (dst0
);
2854 else if (sop
== 0 && sopcde
== 2)
2855 return DREG_MASK (dst0
);
2861 insn_regmask (int iw0
, int iw1
)
2863 if ((iw0
& 0xf7ff) == 0xc003 && iw1
== 0x1800)
2864 return 0; /* MNOP */
2865 else if ((iw0
& 0xff00) == 0x0000)
2866 return decode_ProgCtrl_0 (iw0
);
2867 else if ((iw0
& 0xffc0) == 0x0240)
2869 else if ((iw0
& 0xff80) == 0x0100)
2871 else if ((iw0
& 0xfe00) == 0x0400)
2873 else if ((iw0
& 0xfe00) == 0x0600)
2875 else if ((iw0
& 0xf800) == 0x0800)
2877 else if ((iw0
& 0xffe0) == 0x0200)
2879 else if ((iw0
& 0xff00) == 0x0300)
2881 else if ((iw0
& 0xf000) == 0x1000)
2883 else if ((iw0
& 0xf000) == 0x2000)
2885 else if ((iw0
& 0xf000) == 0x3000)
2887 else if ((iw0
& 0xfc00) == 0x4000)
2889 else if ((iw0
& 0xfe00) == 0x4400)
2891 else if ((iw0
& 0xf800) == 0x4800)
2893 else if ((iw0
& 0xf000) == 0x5000)
2895 else if ((iw0
& 0xf800) == 0x6000)
2897 else if ((iw0
& 0xf800) == 0x6800)
2899 else if ((iw0
& 0xf000) == 0x8000)
2900 return decode_LDSTpmod_0 (iw0
);
2901 else if ((iw0
& 0xff60) == 0x9e60)
2902 return decode_dagMODim_0 (iw0
);
2903 else if ((iw0
& 0xfff0) == 0x9f60)
2904 return decode_dagMODik_0 (iw0
);
2905 else if ((iw0
& 0xfc00) == 0x9c00)
2906 return decode_dspLDST_0 (iw0
);
2907 else if ((iw0
& 0xf000) == 0x9000)
2908 return decode_LDST_0 (iw0
);
2909 else if ((iw0
& 0xfc00) == 0xb800)
2910 return decode_LDSTiiFP_0 (iw0
);
2911 else if ((iw0
& 0xe000) == 0xA000)
2912 return decode_LDSTii_0 (iw0
);
2913 else if ((iw0
& 0xff80) == 0xe080 && (iw1
& 0x0C00) == 0x0000)
2915 else if ((iw0
& 0xff00) == 0xe100 && (iw1
& 0x0000) == 0x0000)
2917 else if ((iw0
& 0xfe00) == 0xe200 && (iw1
& 0x0000) == 0x0000)
2919 else if ((iw0
& 0xfc00) == 0xe400 && (iw1
& 0x0000) == 0x0000)
2921 else if ((iw0
& 0xfffe) == 0xe800 && (iw1
& 0x0000) == 0x0000)
2923 else if ((iw0
& 0xf600) == 0xc000 && (iw1
& 0x0000) == 0x0000)
2924 return decode_dsp32mac_0 (iw0
, iw1
);
2925 else if ((iw0
& 0xf600) == 0xc200 && (iw1
& 0x0000) == 0x0000)
2926 return decode_dsp32mult_0 (iw0
, iw1
);
2927 else if ((iw0
& 0xf7c0) == 0xc400 && (iw1
& 0x0000) == 0x0000)
2928 return decode_dsp32alu_0 (iw0
, iw1
);
2929 else if ((iw0
& 0xf780) == 0xc600 && (iw1
& 0x01c0) == 0x0000)
2930 return decode_dsp32shift_0 (iw0
, iw1
);
2931 else if ((iw0
& 0xf780) == 0xc680 && (iw1
& 0x0000) == 0x0000)
2932 return decode_dsp32shiftimm_0 (iw0
, iw1
);
2933 else if ((iw0
& 0xff00) == 0xf800)
2935 else if ((iw0
& 0xFFC0) == 0xf000 && (iw1
& 0x0000) == 0x0000)