2 Copyright (C) 2010-2025 Free Software Foundation, Inc.
3 Contributed by Joseph Myers <joseph@codesourcery.com>
4 Bernd Schmidt <bernds@codesourcery.com>
6 This file is part of GAS, the GNU Assembler.
8 GAS is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
13 GAS is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with GAS; see the file COPYING. If not, write to the Free
20 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
24 #include "dwarf2dbg.h"
25 #include "dw2gencfi.h"
26 #include "safe-ctype.h"
28 #include "opcode/tic6x.h"
29 #include "elf/tic6x.h"
30 #include "elf32-tic6x.h"
32 /* Truncate and sign-extend at 32 bits, so that building on a 64-bit
33 host gives identical results to a 32-bit host. */
34 #define TRUNC(X) ((valueT) (X) & 0xffffffffU)
35 #define SEXT(X) ((TRUNC (X) ^ 0x80000000U) - 0x80000000U)
37 #define streq(a, b) (strcmp (a, b) == 0)
39 /* Stuff for .scomm symbols. */
40 static segT sbss_section
;
41 static asection scom_section
;
42 static asymbol scom_symbol
;
44 const char comment_chars
[] = ";";
45 const char line_comment_chars
[] = "#*;";
46 const char line_separator_chars
[] = "@";
48 const char EXP_CHARS
[] = "eE";
49 const char FLT_CHARS
[] = "dDfF";
51 const char md_shortopts
[] = "";
55 OPTION_MARCH
= OPTION_MD_BASE
,
57 OPTION_MLITTLE_ENDIAN
,
66 const struct option md_longopts
[] =
68 { "march", required_argument
, NULL
, OPTION_MARCH
},
69 { "mbig-endian", no_argument
, NULL
, OPTION_MBIG_ENDIAN
},
70 { "mlittle-endian", no_argument
, NULL
, OPTION_MLITTLE_ENDIAN
},
71 { "mdsbt", no_argument
, NULL
, OPTION_MDSBT
},
72 { "mno-dsbt", no_argument
, NULL
, OPTION_MNO_DSBT
},
73 { "mpid", required_argument
, NULL
, OPTION_MPID
},
74 { "mpic", no_argument
, NULL
, OPTION_MPIC
},
75 { "mno-pic", no_argument
, NULL
, OPTION_MNO_PIC
},
76 { "mgenerate-rel", no_argument
, NULL
, OPTION_MGENERATE_REL
},
77 { NULL
, no_argument
, NULL
, 0 }
79 const size_t md_longopts_size
= sizeof (md_longopts
);
81 /* The instructions enabled based only on the selected architecture
82 (all instructions, if no architecture specified). */
83 static unsigned short tic6x_arch_enable
= (TIC6X_INSN_C62X
90 /* The instructions enabled based on the current set of features
91 (architecture, as modified by other options). */
92 static unsigned short tic6x_features
;
94 /* The architecture attribute value, or C6XABI_Tag_ISA_none if
96 static int tic6x_arch_attribute
= C6XABI_Tag_ISA_none
;
98 /* Whether any instructions at all have been seen. Once any
99 instructions have been seen, architecture attributes merge into the
100 previous attribute value rather than replacing it. */
101 static bool tic6x_seen_insns
= false;
103 /* The number of registers in each register file supported by the
104 current architecture. */
105 static unsigned int tic6x_num_registers
;
107 /* Whether predication on A0 is possible. */
108 static bool tic6x_predicate_a0
;
110 /* Whether execute packets can cross fetch packet boundaries. */
111 static bool tic6x_can_cross_fp_boundary
;
113 /* Whether there are constraints on simultaneous reads and writes of
115 static bool tic6x_long_data_constraints
;
117 /* Whether compact instructions are available. */
118 static bool tic6x_compact_insns
;
120 /* Whether to generate RELA relocations. */
121 static bool tic6x_generate_rela
= true;
123 /* Whether the code uses DSBT addressing. */
124 static bool tic6x_dsbt
;
126 /* Types of position-independent data (attribute values for
135 /* The type of data addressing used in this code. */
136 static tic6x_pid_type tic6x_pid
;
138 /* Whether the code uses position-independent code. */
139 static bool tic6x_pic
;
141 /* Table of supported architecture variants. */
146 unsigned short features
;
148 static const tic6x_arch_table tic6x_arches
[] =
150 { "c62x", C6XABI_Tag_ISA_C62X
, TIC6X_INSN_C62X
},
151 { "c64x", C6XABI_Tag_ISA_C64X
, TIC6X_INSN_C62X
| TIC6X_INSN_C64X
},
152 { "c64x+", C6XABI_Tag_ISA_C64XP
, (TIC6X_INSN_C62X
154 | TIC6X_INSN_C64XP
) },
155 { "c67x", C6XABI_Tag_ISA_C67X
, TIC6X_INSN_C62X
| TIC6X_INSN_C67X
},
156 { "c67x+", C6XABI_Tag_ISA_C67XP
, (TIC6X_INSN_C62X
158 | TIC6X_INSN_C67XP
) },
159 { "c674x", C6XABI_Tag_ISA_C674X
, (TIC6X_INSN_C62X
164 | TIC6X_INSN_C674X
) }
167 /* Caller saved register encodings. The standard frame layout uses this
168 order, starting from the highest address. There must be
169 TIC6X_NUM_UNWIND_REGS values. */
187 static void tic6x_output_unwinding (bool need_extab
);
189 /* Return the frame unwind state for the current function, allocating
192 static tic6x_unwind_info
*tic6x_get_unwind (void)
194 tic6x_unwind_info
*unwind
;
196 unwind
= seg_info (now_seg
)->tc_segment_info_data
.unwind
;
200 unwind
= seg_info (now_seg
)->tc_segment_info_data
.text_unwind
;
204 unwind
=XNEW (tic6x_unwind_info
);
205 seg_info (now_seg
)->tc_segment_info_data
.unwind
= unwind
;
206 memset (unwind
, 0, sizeof (*unwind
));
210 /* Update the selected architecture based on ARCH, giving an error if
211 ARCH is an invalid value. Does not call tic6x_update_features; the
212 caller must do that if necessary. */
215 tic6x_use_arch (const char *arch
)
219 for (i
= 0; i
< ARRAY_SIZE (tic6x_arches
); i
++)
220 if (strcmp (arch
, tic6x_arches
[i
].arch
) == 0)
222 tic6x_arch_enable
= tic6x_arches
[i
].features
;
223 if (tic6x_seen_insns
)
225 = elf32_tic6x_merge_arch_attributes (tic6x_arch_attribute
,
226 tic6x_arches
[i
].attr
);
228 tic6x_arch_attribute
= tic6x_arches
[i
].attr
;
232 as_bad (_("unknown architecture '%s'"), arch
);
235 /* Table of supported -mpid arguments. */
240 } tic6x_pid_type_table
;
241 static const tic6x_pid_type_table tic6x_pid_types
[] =
243 { "no", tic6x_pid_no
},
244 { "near", tic6x_pid_near
},
245 { "far", tic6x_pid_far
}
248 /* Handle -mpid=ARG. */
251 tic6x_use_pid (const char *arg
)
255 for (i
= 0; i
< ARRAY_SIZE (tic6x_pid_types
); i
++)
256 if (strcmp (arg
, tic6x_pid_types
[i
].arg
) == 0)
258 tic6x_pid
= tic6x_pid_types
[i
].attr
;
262 as_bad (_("unknown -mpid= argument '%s'"), arg
);
265 /* Parse a target-specific option. */
268 md_parse_option (int c
, const char *arg
)
273 tic6x_use_arch (arg
);
276 case OPTION_MBIG_ENDIAN
:
277 target_big_endian
= 1;
280 case OPTION_MLITTLE_ENDIAN
:
281 target_big_endian
= 0;
288 case OPTION_MNO_DSBT
:
304 case OPTION_MGENERATE_REL
:
305 tic6x_generate_rela
= false;
315 md_show_usage (FILE *stream ATTRIBUTE_UNUSED
)
319 fputc ('\n', stream
);
320 fprintf (stream
, _("TMS320C6000 options:\n"));
321 fprintf (stream
, _(" -march=ARCH enable instructions from architecture ARCH\n"));
322 fprintf (stream
, _(" -mbig-endian generate big-endian code\n"));
323 fprintf (stream
, _(" -mlittle-endian generate little-endian code\n"));
324 fprintf (stream
, _(" -mdsbt code uses DSBT addressing\n"));
325 fprintf (stream
, _(" -mno-dsbt code does not use DSBT addressing\n"));
326 fprintf (stream
, _(" -mpid=no code uses position-dependent data addressing\n"));
327 fprintf (stream
, _(" -mpid=near code uses position-independent data addressing,\n"
328 " GOT accesses use near DP addressing\n"));
329 fprintf (stream
, _(" -mpid=far code uses position-independent data addressing,\n"
330 " GOT accesses use far DP addressing\n"));
331 fprintf (stream
, _(" -mpic code addressing is position-independent\n"));
332 fprintf (stream
, _(" -mno-pic code addressing is position-dependent\n"));
333 /* -mgenerate-rel is only for testsuite use and is deliberately
336 fputc ('\n', stream
);
337 fprintf (stream
, _("Supported ARCH values are:"));
338 for (i
= 0; i
< ARRAY_SIZE (tic6x_arches
); i
++)
339 fprintf (stream
, " %s", tic6x_arches
[i
].arch
);
340 fputc ('\n', stream
);
343 /* Update enabled features based on the current architecture and
346 tic6x_update_features (void)
348 tic6x_features
= tic6x_arch_enable
;
351 = (tic6x_arch_enable
& (TIC6X_INSN_C64X
| TIC6X_INSN_C67XP
)) ? 32 : 16;
353 tic6x_predicate_a0
= (tic6x_arch_enable
& TIC6X_INSN_C64X
) != 0;
355 tic6x_can_cross_fp_boundary
356 = (tic6x_arch_enable
& (TIC6X_INSN_C64X
| TIC6X_INSN_C67XP
)) != 0;
358 tic6x_long_data_constraints
= (tic6x_arch_enable
& TIC6X_INSN_C64X
) == 0;
360 tic6x_compact_insns
= (tic6x_arch_enable
& TIC6X_INSN_C64XP
) != 0;
363 /* Do configuration after all options have been parsed. */
366 tic6x_after_parse_args (void)
368 tic6x_update_features ();
371 /* Parse a .cantunwind directive. */
373 s_tic6x_cantunwind (int ignored ATTRIBUTE_UNUSED
)
375 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
377 /* GCC sometimes spits out superfluous .cantunwind directives, so ignore
379 if (unwind
->data_bytes
== 0)
382 if (unwind
->data_bytes
!= -1)
384 as_bad (_("unexpected .cantunwind directive"));
388 demand_empty_rest_of_line ();
390 if (unwind
->personality_routine
|| unwind
->personality_index
!= -1)
391 as_bad (_("personality routine specified for cantunwind frame"));
393 unwind
->personality_index
= -2;
396 /* Parse a .handlerdata directive. */
398 s_tic6x_handlerdata (int ignored ATTRIBUTE_UNUSED
)
400 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
402 if (!unwind
->saved_seg
)
404 as_bad (_("unexpected .handlerdata directive"));
408 if (unwind
->table_entry
|| unwind
->personality_index
== -2)
410 as_bad (_("duplicate .handlerdata directive"));
414 if (unwind
->personality_index
== -1 && unwind
->personality_routine
== NULL
)
416 as_bad (_("personality routine required before .handlerdata directive"));
420 tic6x_output_unwinding (true);
423 /* Parse a .endp directive. */
425 s_tic6x_endp (int ignored ATTRIBUTE_UNUSED
)
427 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
429 if (unwind
->data_bytes
!= 0)
431 /* Output a .exidx entry if we have not already done so.
432 Then switch back to the text section. */
433 if (!unwind
->table_entry
)
434 tic6x_output_unwinding (false);
436 subseg_set (unwind
->saved_seg
, unwind
->saved_subseg
);
439 unwind
->saved_seg
= NULL
;
440 unwind
->table_entry
= NULL
;
441 unwind
->data_bytes
= 0;
444 /* Parse a .personalityindex directive. */
446 s_tic6x_personalityindex (int ignored ATTRIBUTE_UNUSED
)
448 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
451 if (unwind
->personality_routine
|| unwind
->personality_index
!= -1)
452 as_bad (_("duplicate .personalityindex directive"));
456 if (exp
.X_op
!= O_constant
457 || exp
.X_add_number
< 0 || exp
.X_add_number
> 15)
459 as_bad (_("bad personality routine number"));
460 ignore_rest_of_line ();
464 unwind
->personality_index
= exp
.X_add_number
;
466 demand_empty_rest_of_line ();
470 s_tic6x_personality (int ignored ATTRIBUTE_UNUSED
)
473 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
475 if (unwind
->personality_routine
|| unwind
->personality_index
!= -1)
476 as_bad (_("duplicate .personality directive"));
478 c
= get_symbol_name (&name
);
479 unwind
->personality_routine
= symbol_find_or_make (name
);
480 (void) restore_line_pointer (c
);
481 demand_empty_rest_of_line ();
484 /* Parse a .arch directive. */
486 s_tic6x_arch (int ignored ATTRIBUTE_UNUSED
)
491 arch
= input_line_pointer
;
492 while (*input_line_pointer
&& !ISSPACE (*input_line_pointer
))
493 input_line_pointer
++;
494 c
= *input_line_pointer
;
495 *input_line_pointer
= 0;
497 tic6x_use_arch (arch
);
498 tic6x_update_features ();
499 *input_line_pointer
= c
;
500 demand_empty_rest_of_line ();
503 /* Parse a .ehtype directive. */
506 s_tic6x_ehtype (int ignored ATTRIBUTE_UNUSED
)
511 #ifdef md_flush_pending_output
512 md_flush_pending_output ();
515 if (is_it_end_of_statement ())
517 demand_empty_rest_of_line ();
528 if (exp
.X_op
!= O_symbol
)
530 as_bad (_("expected symbol"));
536 fix_new_exp (frag_now
, p
- frag_now
->fr_literal
, 4,
537 &exp
, 0, BFD_RELOC_C6000_EHTYPE
);
539 demand_empty_rest_of_line ();
542 /* Parse a .nocmp directive. */
545 s_tic6x_nocmp (int ignored ATTRIBUTE_UNUSED
)
547 seg_info (now_seg
)->tc_segment_info_data
.nocmp
= true;
548 demand_empty_rest_of_line ();
551 /* .scomm pseudo-op handler.
553 This is a new pseudo-op to handle putting objects in .scommon.
554 By doing this the linker won't need to do any work,
555 and more importantly it removes the implicit -G arg necessary to
556 correctly link the object file. */
559 s_tic6x_scomm (int ignore ATTRIBUTE_UNUSED
)
569 c
= get_symbol_name (&name
);
571 /* Just after name is now '\0'. */
572 p
= input_line_pointer
;
573 (void) restore_line_pointer (c
);
575 if (*input_line_pointer
!= ',')
577 as_bad (_("expected comma after symbol name"));
578 ignore_rest_of_line ();
583 input_line_pointer
++;
584 if ((size
= get_absolute_expression ()) < 0)
586 /* xgettext:c-format */
587 as_warn (_("invalid length for .scomm directive"));
588 ignore_rest_of_line ();
592 /* The third argument to .scomm is the alignment. */
593 if (*input_line_pointer
!= ',')
597 ++input_line_pointer
;
598 align
= get_absolute_expression ();
601 as_warn (_("alignment is not a positive number"));
606 /* Convert to a power of 2 alignment. */
609 for (align2
= 0; (align
& 1) == 0; align
>>= 1, ++align2
)
613 as_bad (_("alignment is not a power of 2"));
614 ignore_rest_of_line ();
622 symbolP
= symbol_find_or_make (name
);
625 if (S_IS_DEFINED (symbolP
))
627 /* xgettext:c-format */
628 as_bad (_("attempt to re-define symbol `%s'"),
629 S_GET_NAME (symbolP
));
630 ignore_rest_of_line ();
634 if (S_GET_VALUE (symbolP
) && S_GET_VALUE (symbolP
) != (valueT
) size
)
636 /* xgettext:c-format */
637 as_bad (_("attempt to redefine `%s' with a different length"),
638 S_GET_NAME (symbolP
));
640 ignore_rest_of_line ();
644 if (symbol_get_obj (symbolP
)->local
)
646 segT old_sec
= now_seg
;
647 int old_subsec
= now_subseg
;
650 record_alignment (sbss_section
, align2
);
651 subseg_set (sbss_section
, 0);
654 frag_align (align2
, 0, 0);
656 if (S_GET_SEGMENT (symbolP
) == sbss_section
)
657 symbol_get_frag (symbolP
)->fr_symbol
= 0;
659 symbol_set_frag (symbolP
, frag_now
);
661 pfrag
= frag_var (rs_org
, 1, 1, (relax_substateT
) 0, symbolP
, size
,
664 S_SET_SIZE (symbolP
, size
);
665 S_SET_SEGMENT (symbolP
, sbss_section
);
666 S_CLEAR_EXTERNAL (symbolP
);
667 subseg_set (old_sec
, old_subsec
);
671 S_SET_VALUE (symbolP
, (valueT
) size
);
672 S_SET_ALIGN (symbolP
, 1 << align2
);
673 S_SET_EXTERNAL (symbolP
);
674 S_SET_SEGMENT (symbolP
, &scom_section
);
677 symbol_get_bfdsym (symbolP
)->flags
|= BSF_OBJECT
;
679 demand_empty_rest_of_line ();
682 /* Track for each attribute whether it has been set explicitly (and so
683 should not have a default value set by the assembler). */
684 static bool tic6x_attributes_set_explicitly
[NUM_KNOWN_OBJ_ATTRIBUTES
];
686 /* Parse a .c6xabi_attribute directive. */
689 s_tic6x_c6xabi_attribute (int ignored ATTRIBUTE_UNUSED
)
691 int tag
= obj_elf_vendor_attribute (OBJ_ATTR_PROC
);
693 if (tag
< NUM_KNOWN_OBJ_ATTRIBUTES
)
694 tic6x_attributes_set_explicitly
[tag
] = true;
701 } tic6x_attribute_table
;
703 static const tic6x_attribute_table tic6x_attributes
[] =
705 #define TAG(tag, value) { #tag, tag },
706 #include "elf/tic6x-attrs.h"
710 /* Convert an attribute name to a number. */
713 tic6x_convert_symbolic_attribute (const char *name
)
717 for (i
= 0; i
< ARRAY_SIZE (tic6x_attributes
); i
++)
718 if (strcmp (name
, tic6x_attributes
[i
].name
) == 0)
719 return tic6x_attributes
[i
].tag
;
724 const pseudo_typeS md_pseudo_table
[] =
726 { "arch", s_tic6x_arch
, 0 },
727 { "c6xabi_attribute", s_tic6x_c6xabi_attribute
, 0 },
728 { "nocmp", s_tic6x_nocmp
, 0 },
729 { "scomm", s_tic6x_scomm
, 0 },
731 { "ehtype", s_tic6x_ehtype
, 0 },
732 { "endp", s_tic6x_endp
, 0 },
733 { "handlerdata", s_tic6x_handlerdata
, 0 },
734 { "personalityindex", s_tic6x_personalityindex
, 0 },
735 { "personality", s_tic6x_personality
, 0 },
736 { "cantunwind", s_tic6x_cantunwind
, 0 },
740 /* Hash table of opcodes. For each opcode name, this stores a pointer
741 to a tic6x_opcode_list listing (in an arbitrary order) all opcode
742 table entries with that name. */
743 static htab_t opcode_hash
;
745 /* Initialize the assembler (called once at assembler startup). */
755 bfd_set_arch_mach (stdoutput
, TARGET_ARCH
, 0);
757 /* Insert opcodes into the hash table. */
758 opcode_hash
= str_htab_create ();
759 for (id
= 0; id
< tic6x_opcode_max
; id
++)
761 tic6x_opcode_list
*opc
= XNEW (tic6x_opcode_list
);
764 opc
->next
= str_hash_find (opcode_hash
, tic6x_opcode_table
[id
].name
);
765 str_hash_insert (opcode_hash
, tic6x_opcode_table
[id
].name
, opc
, 1);
768 /* Save the current subseg so we can restore it [it's the default one and
769 we don't want the initial section to be .sbss]. */
773 /* The sbss section is for local .scomm symbols. */
774 sbss_section
= subseg_new (".bss", 0);
775 seg_info (sbss_section
)->bss
= 1;
777 /* This is copied from perform_an_assembly_pass. */
778 applicable
= bfd_applicable_section_flags (stdoutput
);
779 bfd_set_section_flags (sbss_section
, applicable
& SEC_ALLOC
);
781 subseg_set (seg
, subseg
);
783 /* We must construct a fake section similar to bfd_com_section
784 but with the name .scommon. */
785 scom_section
= *bfd_com_section_ptr
;
786 scom_section
.name
= ".scommon";
787 scom_section
.output_section
= & scom_section
;
788 scom_section
.symbol
= & scom_symbol
;
789 scom_symbol
= * bfd_com_section_ptr
->symbol
;
790 scom_symbol
.name
= ".scommon";
791 scom_symbol
.section
= & scom_section
;
794 /* Whether the current line being parsed had the "||" parallel bars. */
795 static bool tic6x_line_parallel
;
797 /* Whether the current line being parsed started "||^" to indicate an
798 SPMASKed parallel instruction. */
799 static bool tic6x_line_spmask
;
801 /* If the current line being parsed had an instruction predicate, the
802 creg value for that predicate (which must be nonzero); otherwise
804 static unsigned int tic6x_line_creg
;
806 /* If the current line being parsed had an instruction predicate, the
807 z value for that predicate; otherwise 0. */
808 static unsigned int tic6x_line_z
;
810 /* Return 1 (updating input_line_pointer as appropriate) if the line
811 starting with C (immediately before input_line_pointer) starts with
812 pre-opcode text appropriate for this target, 0 otherwise. */
815 tic6x_unrecognized_line (int c
)
825 if (input_line_pointer
[0] == '|')
827 if (input_line_pointer
[1] == '^')
829 tic6x_line_spmask
= true;
830 input_line_pointer
+= 2;
833 input_line_pointer
+= 1;
834 if (tic6x_line_parallel
)
835 as_bad (_("multiple '||' on same line"));
836 tic6x_line_parallel
= true;
838 as_bad (_("'||' after predicate"));
844 /* If it doesn't look like a predicate at all, just return 0.
845 If it looks like one but not a valid one, give a better
847 p
= input_line_pointer
;
848 while (*p
!= ']' && !is_end_of_line
[(unsigned char) *p
])
853 p
= input_line_pointer
;
855 bad_predicate
= false;
861 if (*p
== 'A' || *p
== 'a')
863 else if (*p
== 'B' || *p
== 'b')
867 areg
= true; /* Avoid uninitialized warning. */
868 bad_predicate
= true;
873 if (*p
!= '0' && *p
!= '1' && *p
!= '2')
874 bad_predicate
= true;
875 else if (p
[1] != ']')
876 bad_predicate
= true;
878 input_line_pointer
= p
+ 2;
882 as_bad (_("multiple predicates on same line"));
888 as_bad (_("bad predicate '%s'"), input_line_pointer
- 1);
890 input_line_pointer
= endp
;
897 tic6x_line_creg
= (areg
? 6 : 1);
898 if (areg
&& !tic6x_predicate_a0
)
899 as_bad (_("predication on A0 not supported on this architecture"));
903 tic6x_line_creg
= (areg
? 4 : 2);
907 tic6x_line_creg
= (areg
? 5 : 3);
922 /* Do any target-specific handling of a label required. */
925 tic6x_frob_label (symbolS
*sym
)
927 segment_info_type
*si
;
928 tic6x_label_list
*list
;
930 if (tic6x_line_parallel
)
932 as_bad (_("label after '||'"));
933 tic6x_line_parallel
= false;
934 tic6x_line_spmask
= false;
938 as_bad (_("label after predicate"));
943 si
= seg_info (now_seg
);
944 list
= si
->tc_segment_info_data
.label_list
;
945 si
->tc_segment_info_data
.label_list
= XNEW (tic6x_label_list
);
946 si
->tc_segment_info_data
.label_list
->next
= list
;
947 si
->tc_segment_info_data
.label_list
->label
= sym
;
949 /* Defining tc_frob_label overrides the ELF definition of
950 obj_frob_label, so we need to apply its effects here. */
951 dwarf2_emit_label (sym
);
954 /* At end-of-line, give errors for start-of-line decorations that
955 needed an instruction but were not followed by one. */
958 tic6x_end_of_line (void)
960 if (tic6x_line_parallel
)
962 as_bad (_("'||' not followed by instruction"));
963 tic6x_line_parallel
= false;
964 tic6x_line_spmask
= false;
968 as_bad (_("predicate not followed by instruction"));
974 /* Do any target-specific handling of the start of a logical line. */
977 tic6x_start_line_hook (void)
979 tic6x_end_of_line ();
982 /* Do target-specific handling immediately after an input file from
983 the command line, and any other inputs it includes, have been
989 tic6x_end_of_line ();
992 /* Do target-specific initialization after arguments have been
993 processed and the output file created. */
996 tic6x_init_after_args (void)
998 elf32_tic6x_set_use_rela_p (stdoutput
, tic6x_generate_rela
);
1001 /* Free LIST of labels (possibly NULL). */
1004 tic6x_free_label_list (tic6x_label_list
*list
)
1008 tic6x_label_list
*old
= list
;
1015 /* Handle a data alignment of N bytes. */
1018 tic6x_cons_align (int n ATTRIBUTE_UNUSED
)
1020 segment_info_type
*seginfo
= seg_info (now_seg
);
1022 /* Data means there is no current execute packet, and that any label
1023 applies to that data rather than a subsequent instruction. */
1024 tic6x_free_label_list (seginfo
->tc_segment_info_data
.label_list
);
1025 seginfo
->tc_segment_info_data
.label_list
= NULL
;
1026 seginfo
->tc_segment_info_data
.execute_packet_frag
= NULL
;
1027 seginfo
->tc_segment_info_data
.last_insn_lsb
= NULL
;
1028 seginfo
->tc_segment_info_data
.spmask_addr
= NULL
;
1029 seginfo
->tc_segment_info_data
.func_units_used
= 0;
1032 /* Handle an alignment directive. Return TRUE if the
1033 machine-independent frag generation should be skipped. */
1036 tic6x_do_align (int n
, char *fill
, int len ATTRIBUTE_UNUSED
, int max
)
1038 /* Given code alignments of 4, 8, 16 or 32 bytes, we try to handle
1039 them in the md_finish pass by inserting NOPs in parallel with
1040 previous instructions. We only do this in sections containing
1041 nothing but instructions. Code alignments of 1 or 2 bytes have
1042 no effect in such sections (but we record them with
1043 machine-dependent frags anyway so they can be skipped or
1044 converted to machine-independent), while those of more than 64
1045 bytes cannot reliably be handled in this way. */
1051 && subseg_text_p (now_seg
))
1059 /* Machine-independent code would generate a frag here, but we
1060 wish to handle it in a machine-dependent way. */
1061 if (frag_now_fix () != 0)
1063 if (frag_now
->fr_type
!= rs_machine_dependent
)
1064 frag_wane (frag_now
);
1069 align_frag
= frag_now
;
1070 p
= frag_var (rs_machine_dependent
, 32, 32, max
, NULL
, n
, NULL
);
1071 /* This must be the same as the frag to which a pointer was just
1073 if (p
!= align_frag
->fr_literal
)
1075 align_frag
->tc_frag_data
.is_insns
= false;
1082 /* Types of operand for parsing purposes. These are used as bit-masks
1083 to tell tic6x_parse_operand what forms of operand are
1085 #define TIC6X_OP_EXP 0x0001u
1086 #define TIC6X_OP_REG 0x0002u
1087 #define TIC6X_OP_REGPAIR 0x0004u
1088 #define TIC6X_OP_IRP 0x0008u
1089 #define TIC6X_OP_NRP 0x0010u
1090 /* With TIC6X_OP_MEM_NOUNREG, the contents of a () offset are always
1091 interpreted as an expression, which may be a symbol with the same
1092 name as a register that ends up being implicitly DP-relative. With
1093 TIC6X_OP_MEM_UNREG, the contents of a () offset are interpreted as
1094 a register if they match one, and failing that as an expression,
1095 which must be constant. */
1096 #define TIC6X_OP_MEM_NOUNREG 0x0020u
1097 #define TIC6X_OP_MEM_UNREG 0x0040u
1098 #define TIC6X_OP_CTRL 0x0080u
1099 #define TIC6X_OP_FUNC_UNIT 0x0100u
1101 /* A register or register pair read by the assembler. */
1104 /* The side the register is on (1 or 2). */
1106 /* The register number (0 to 31). */
1110 /* Types of modification of a base address. */
1115 tic6x_mem_mod_minus
,
1116 tic6x_mem_mod_preinc
,
1117 tic6x_mem_mod_predec
,
1118 tic6x_mem_mod_postinc
,
1119 tic6x_mem_mod_postdec
1122 /* Scaled [] or unscaled () nature of an offset. */
1126 tic6x_offset_scaled
,
1127 tic6x_offset_unscaled
1128 } tic6x_mem_scaling
;
1130 /* A memory operand read by the assembler. */
1133 /* The base register. */
1134 tic6x_register base_reg
;
1135 /* How the base register is modified. */
1137 /* Whether there is an offset (required with plain "+" and "-"), and
1138 whether it is scaled or unscaled if so. */
1139 tic6x_mem_scaling scaled
;
1140 /* Whether the offset is a register (TRUE) or an expression
1151 /* A functional unit in SPMASK operands read by the assembler. */
1154 /* The basic unit. */
1155 tic6x_func_unit_base base
;
1156 /* The side (1 or 2). */
1158 } tic6x_func_unit_operand
;
1160 /* An operand read by the assembler. */
1163 /* The syntactic form of the operand, as one of the bit-masks
1166 /* The operand value. */
1169 /* An expression: TIC6X_OP_EXP. */
1171 /* A register: TIC6X_OP_REG, TIC6X_OP_REGPAIR. */
1173 /* A memory reference: TIC6X_OP_MEM_NOUNREG,
1174 TIC6X_OP_MEM_UNREG. */
1176 /* A control register: TIC6X_OP_CTRL. */
1178 /* A functional unit: TIC6X_OP_FUNC_UNIT. */
1179 tic6x_func_unit_operand func_unit
;
1183 #define skip_whitespace(str) do { if (*(str) == ' ') ++(str); } while (0)
1185 /* Parse a register operand, or part of an operand, starting at *P.
1186 If syntactically OK (including that the number is in the range 0 to
1187 31, but not necessarily in range for this architecture), return
1188 TRUE, putting the register side and number in *REG and update *P to
1189 point immediately after the register number; otherwise return FALSE
1190 without changing *P (but possibly changing *REG). Do not print any
1194 tic6x_parse_register (char **p
, tic6x_register
*reg
)
1215 if (*r
>= '0' && *r
<= '9')
1217 reg
->num
= *r
- '0';
1223 if (reg
->num
> 0 && *r
>= '0' && *r
<= '9')
1225 reg
->num
= reg
->num
* 10 + (*r
- '0');
1229 if (*r
>= '0' && *r
<= '9')
1238 /* Parse the initial two characters of a functional unit name starting
1239 at *P. If OK, set *BASE and *SIDE and return true; otherwise,
1243 tic6x_parse_func_unit_base (char *p
, tic6x_func_unit_base
*base
,
1246 bool good_func_unit
= true;
1247 tic6x_func_unit_base maybe_base
= tic6x_func_unit_nfu
;
1248 unsigned int maybe_side
= 0;
1254 maybe_base
= tic6x_func_unit_d
;
1259 maybe_base
= tic6x_func_unit_l
;
1264 maybe_base
= tic6x_func_unit_m
;
1269 maybe_base
= tic6x_func_unit_s
;
1273 good_func_unit
= false;
1289 good_func_unit
= false;
1299 return good_func_unit
;
1302 /* Parse an operand starting at *P. If the operand parses OK, return
1303 TRUE and store the value in *OP; otherwise return FALSE (possibly
1304 changing *OP). In any case, update *P to point to the following
1305 comma or end of line. The possible operand forms are given by
1306 OP_FORMS. For diagnostics, this is operand OPNO of an opcode
1307 starting at STR, length OPC_LEN. */
1310 tic6x_parse_operand (char **p
, tic6x_operand
*op
, unsigned int op_forms
,
1311 char *str
, int opc_len
, unsigned int opno
)
1313 bool operand_parsed
= false;
1316 if ((op_forms
& (TIC6X_OP_MEM_NOUNREG
| TIC6X_OP_MEM_UNREG
))
1317 == (TIC6X_OP_MEM_NOUNREG
| TIC6X_OP_MEM_UNREG
))
1320 /* Check for functional unit names for SPMASK and SPMASKR. */
1321 if (!operand_parsed
&& (op_forms
& TIC6X_OP_FUNC_UNIT
))
1323 tic6x_func_unit_base base
= tic6x_func_unit_nfu
;
1324 unsigned int side
= 0;
1326 if (tic6x_parse_func_unit_base (q
, &base
, &side
))
1330 skip_whitespace (rq
);
1331 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1333 op
->form
= TIC6X_OP_FUNC_UNIT
;
1334 op
->value
.func_unit
.base
= base
;
1335 op
->value
.func_unit
.side
= side
;
1336 operand_parsed
= true;
1342 /* Check for literal "irp". */
1343 if (!operand_parsed
&& (op_forms
& TIC6X_OP_IRP
))
1345 if ((q
[0] == 'i' || q
[0] == 'I')
1346 && (q
[1] == 'r' || q
[1] == 'R')
1347 && (q
[2] == 'p' || q
[2] == 'P'))
1351 skip_whitespace (rq
);
1352 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1354 op
->form
= TIC6X_OP_IRP
;
1355 operand_parsed
= true;
1361 /* Check for literal "nrp". */
1362 if (!operand_parsed
&& (op_forms
& TIC6X_OP_NRP
))
1364 if ((q
[0] == 'n' || q
[0] == 'N')
1365 && (q
[1] == 'r' || q
[1] == 'R')
1366 && (q
[2] == 'p' || q
[2] == 'P'))
1370 skip_whitespace (rq
);
1371 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1373 op
->form
= TIC6X_OP_NRP
;
1374 operand_parsed
= true;
1380 /* Check for control register names. */
1381 if (!operand_parsed
&& (op_forms
& TIC6X_OP_CTRL
))
1385 for (crid
= 0; crid
< tic6x_ctrl_max
; crid
++)
1387 size_t len
= strlen (tic6x_ctrl_table
[crid
].name
);
1389 if (strncasecmp (tic6x_ctrl_table
[crid
].name
, q
, len
) == 0)
1393 skip_whitespace (rq
);
1394 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1396 op
->form
= TIC6X_OP_CTRL
;
1397 op
->value
.ctrl
= crid
;
1398 operand_parsed
= true;
1400 if (!(tic6x_ctrl_table
[crid
].isa_variants
& tic6x_features
))
1401 as_bad (_("control register '%s' not supported "
1402 "on this architecture"),
1403 tic6x_ctrl_table
[crid
].name
);
1409 /* See if this looks like a memory reference. */
1411 && (op_forms
& (TIC6X_OP_MEM_NOUNREG
| TIC6X_OP_MEM_UNREG
)))
1415 tic6x_mem_mod mem_mod
= tic6x_mem_mod_none
;
1416 tic6x_register base_reg
;
1417 bool require_offset
, permit_offset
;
1418 tic6x_mem_scaling scaled
;
1420 expressionS offset_exp
;
1421 tic6x_register offset_reg
;
1430 skip_whitespace (mq
);
1436 mem_mod
= tic6x_mem_mod_preinc
;
1441 mem_mod
= tic6x_mem_mod_plus
;
1449 mem_mod
= tic6x_mem_mod_predec
;
1454 mem_mod
= tic6x_mem_mod_minus
;
1466 skip_whitespace (mq
);
1467 mem_ok
= tic6x_parse_register (&mq
, &base_reg
);
1470 if (mem_ok
&& mem_mod
== tic6x_mem_mod_none
)
1472 skip_whitespace (mq
);
1473 if (mq
[0] == '+' && mq
[1] == '+')
1475 mem_mod
= tic6x_mem_mod_postinc
;
1478 else if (mq
[0] == '-' && mq
[1] == '-')
1480 mem_mod
= tic6x_mem_mod_postdec
;
1485 if (mem_mod
== tic6x_mem_mod_none
)
1486 permit_offset
= false;
1488 permit_offset
= true;
1489 if (mem_mod
== tic6x_mem_mod_plus
|| mem_mod
== tic6x_mem_mod_minus
)
1490 require_offset
= true;
1492 require_offset
= false;
1493 scaled
= tic6x_offset_none
;
1494 offset_is_reg
= false;
1496 if (mem_ok
&& permit_offset
)
1500 skip_whitespace (mq
);
1504 scaled
= tic6x_offset_scaled
;
1510 scaled
= tic6x_offset_unscaled
;
1518 if (scaled
!= tic6x_offset_none
)
1520 skip_whitespace (mq
);
1521 if (scaled
== tic6x_offset_scaled
1522 || (op_forms
& TIC6X_OP_MEM_UNREG
))
1527 reg_ok
= tic6x_parse_register (&rq
, &offset_reg
);
1530 skip_whitespace (rq
);
1534 offset_is_reg
= true;
1540 char *save_input_line_pointer
;
1542 save_input_line_pointer
= input_line_pointer
;
1543 input_line_pointer
= mq
;
1544 expression (&offset_exp
);
1545 mq
= input_line_pointer
;
1546 input_line_pointer
= save_input_line_pointer
;
1548 skip_whitespace (mq
);
1556 if (mem_ok
&& require_offset
&& scaled
== tic6x_offset_none
)
1561 skip_whitespace (mq
);
1562 if (!is_end_of_line
[(unsigned char) *mq
] && *mq
!= ',')
1568 op
->form
= op_forms
& (TIC6X_OP_MEM_NOUNREG
| TIC6X_OP_MEM_UNREG
);
1569 op
->value
.mem
.base_reg
= base_reg
;
1570 op
->value
.mem
.mod
= mem_mod
;
1571 op
->value
.mem
.scaled
= scaled
;
1572 op
->value
.mem
.offset_is_reg
= offset_is_reg
;
1574 op
->value
.mem
.offset
.reg
= offset_reg
;
1576 op
->value
.mem
.offset
.exp
= offset_exp
;
1577 operand_parsed
= true;
1579 if (base_reg
.num
>= tic6x_num_registers
)
1580 as_bad (_("register number %u not supported on this architecture"),
1582 if (offset_is_reg
&& offset_reg
.num
>= tic6x_num_registers
)
1583 as_bad (_("register number %u not supported on this architecture"),
1588 /* See if this looks like a register or register pair. */
1589 if (!operand_parsed
&& (op_forms
& (TIC6X_OP_REG
| TIC6X_OP_REGPAIR
)))
1591 tic6x_register first_reg
, second_reg
;
1595 reg_ok
= tic6x_parse_register (&rq
, &first_reg
);
1599 if (*rq
== ':' && (op_forms
& TIC6X_OP_REGPAIR
))
1602 reg_ok
= tic6x_parse_register (&rq
, &second_reg
);
1605 skip_whitespace (rq
);
1606 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1608 if ((second_reg
.num
& 1)
1609 || (first_reg
.num
!= second_reg
.num
+ 1)
1610 || (first_reg
.side
!= second_reg
.side
))
1611 as_bad (_("register pair for operand %u of '%.*s'"
1612 " not a valid even/odd pair"), opno
,
1614 op
->form
= TIC6X_OP_REGPAIR
;
1615 op
->value
.reg
= second_reg
;
1616 operand_parsed
= true;
1621 else if (op_forms
& TIC6X_OP_REG
)
1623 skip_whitespace (rq
);
1624 if (is_end_of_line
[(unsigned char) *rq
] || *rq
== ',')
1626 op
->form
= TIC6X_OP_REG
;
1627 op
->value
.reg
= first_reg
;
1628 operand_parsed
= true;
1635 if (first_reg
.num
>= tic6x_num_registers
)
1636 as_bad (_("register number %u not supported on this architecture"),
1638 if (op
->form
== TIC6X_OP_REGPAIR
1639 && second_reg
.num
>= tic6x_num_registers
)
1640 as_bad (_("register number %u not supported on this architecture"),
1645 /* Otherwise, parse it as an expression. */
1646 if (!operand_parsed
&& (op_forms
& TIC6X_OP_EXP
))
1648 char *save_input_line_pointer
;
1650 save_input_line_pointer
= input_line_pointer
;
1651 input_line_pointer
= q
;
1652 op
->form
= TIC6X_OP_EXP
;
1653 expression (&op
->value
.exp
);
1654 q
= input_line_pointer
;
1655 input_line_pointer
= save_input_line_pointer
;
1656 operand_parsed
= true;
1661 /* Now the operand has been parsed, there must be nothing more
1662 before the comma or end of line. */
1663 skip_whitespace (q
);
1664 if (!is_end_of_line
[(unsigned char) *q
] && *q
!= ',')
1666 operand_parsed
= false;
1667 as_bad (_("junk after operand %u of '%.*s'"), opno
,
1669 while (!is_end_of_line
[(unsigned char) *q
] && *q
!= ',')
1675 /* This could not be parsed as any acceptable form of
1679 case TIC6X_OP_REG
| TIC6X_OP_REGPAIR
:
1680 as_bad (_("bad register or register pair for operand %u of '%.*s'"),
1681 opno
, opc_len
, str
);
1684 case TIC6X_OP_REG
| TIC6X_OP_CTRL
:
1686 as_bad (_("bad register for operand %u of '%.*s'"),
1687 opno
, opc_len
, str
);
1690 case TIC6X_OP_REGPAIR
:
1691 as_bad (_("bad register pair for operand %u of '%.*s'"),
1692 opno
, opc_len
, str
);
1695 case TIC6X_OP_FUNC_UNIT
:
1696 as_bad (_("bad functional unit for operand %u of '%.*s'"),
1697 opno
, opc_len
, str
);
1701 as_bad (_("bad operand %u of '%.*s'"),
1702 opno
, opc_len
, str
);
1706 while (!is_end_of_line
[(unsigned char) *q
] && *q
!= ',')
1710 return operand_parsed
;
1713 /* Table of assembler operators and associated O_* values. */
1718 } tic6x_operator_table
;
1719 static const tic6x_operator_table tic6x_operators
[] = {
1720 #define O_dsbt_index O_md1
1721 { "dsbt_index", O_dsbt_index
},
1724 #define O_dpr_got O_md3
1725 { "dpr_got", O_dpr_got
},
1726 #define O_dpr_byte O_md4
1727 { "dpr_byte", O_dpr_byte
},
1728 #define O_dpr_hword O_md5
1729 { "dpr_hword", O_dpr_hword
},
1730 #define O_dpr_word O_md6
1731 { "dpr_word", O_dpr_word
},
1732 #define O_pcr_offset O_md7
1733 { "pcr_offset", O_pcr_offset
}
1736 /* Parse a name in some machine-specific way. Used on C6X to handle
1737 assembler operators. */
1740 tic6x_parse_name (const char *name
, expressionS
*exprP
,
1741 enum expr_mode mode ATTRIBUTE_UNUSED
, char *nextchar
)
1743 char *p
= input_line_pointer
;
1744 char c
, *name_start
, *name_end
;
1745 const char *inner_name
;
1747 operatorT op
= O_illegal
;
1748 symbolS
*sym
, *op_sym
= NULL
;
1753 for (i
= 0; i
< ARRAY_SIZE (tic6x_operators
); i
++)
1754 if (strcasecmp (name
+ 1, tic6x_operators
[i
].name
) == 0)
1756 op
= tic6x_operators
[i
].op
;
1760 if (op
== O_illegal
)
1763 *input_line_pointer
= *nextchar
;
1764 skip_whitespace (p
);
1768 *input_line_pointer
= 0;
1772 skip_whitespace (p
);
1774 if (!is_name_beginner (*p
))
1776 *input_line_pointer
= 0;
1782 while (is_part_of_name (*p
))
1785 skip_whitespace (p
);
1787 if (op
== O_pcr_offset
)
1789 char *op_name_start
, *op_name_end
;
1793 *input_line_pointer
= 0;
1797 skip_whitespace (p
);
1799 if (!is_name_beginner (*p
))
1801 *input_line_pointer
= 0;
1807 while (is_part_of_name (*p
))
1810 skip_whitespace (p
);
1814 op_sym
= symbol_find_or_make (op_name_start
);
1820 *input_line_pointer
= 0;
1824 input_line_pointer
= p
+ 1;
1825 *nextchar
= *input_line_pointer
;
1826 *input_line_pointer
= 0;
1830 inner_name
= name_start
;
1831 if (op
== O_dsbt_index
&& strcmp (inner_name
, "__c6xabi_DSBT_BASE") != 0)
1833 as_bad (_("$DSBT_INDEX must be used with __c6xabi_DSBT_BASE"));
1834 inner_name
= "__c6xabi_DSBT_BASE";
1836 sym
= symbol_find_or_make (inner_name
);
1840 exprP
->X_add_symbol
= sym
;
1841 exprP
->X_add_number
= 0;
1842 exprP
->X_op_symbol
= op_sym
;
1848 /* Create a fixup for an expression. Same arguments as fix_new_exp,
1849 plus FIX_ADDA which is TRUE for ADDA instructions (to indicate that
1850 fixes resolving to constants should have those constants implicitly
1851 shifted) and FALSE otherwise, but look for C6X-specific expression
1852 types and adjust the relocations or give errors accordingly. */
1855 tic6x_fix_new_exp (fragS
*frag
, int where
, int size
, expressionS
*exp
,
1856 int pcrel
, bfd_reloc_code_real_type r_type
,
1859 bfd_reloc_code_real_type new_reloc
= BFD_RELOC_UNUSED
;
1860 symbolS
*subsy
= NULL
;
1868 case BFD_RELOC_C6000_SBR_U15_W
:
1869 new_reloc
= BFD_RELOC_C6000_DSBT_INDEX
;
1873 as_bad (_("$DSBT_INDEX not supported in this context"));
1881 case BFD_RELOC_C6000_SBR_U15_W
:
1882 new_reloc
= BFD_RELOC_C6000_SBR_GOT_U15_W
;
1886 as_bad (_("$GOT not supported in this context"));
1894 case BFD_RELOC_C6000_ABS_L16
:
1895 new_reloc
= BFD_RELOC_C6000_SBR_GOT_L16_W
;
1898 case BFD_RELOC_C6000_ABS_H16
:
1899 new_reloc
= BFD_RELOC_C6000_SBR_GOT_H16_W
;
1903 as_bad (_("$DPR_GOT not supported in this context"));
1911 case BFD_RELOC_C6000_ABS_S16
:
1912 new_reloc
= BFD_RELOC_C6000_SBR_S16
;
1915 case BFD_RELOC_C6000_ABS_L16
:
1916 new_reloc
= BFD_RELOC_C6000_SBR_L16_B
;
1919 case BFD_RELOC_C6000_ABS_H16
:
1920 new_reloc
= BFD_RELOC_C6000_SBR_H16_B
;
1924 as_bad (_("$DPR_BYTE not supported in this context"));
1932 case BFD_RELOC_C6000_ABS_L16
:
1933 new_reloc
= BFD_RELOC_C6000_SBR_L16_H
;
1936 case BFD_RELOC_C6000_ABS_H16
:
1937 new_reloc
= BFD_RELOC_C6000_SBR_H16_H
;
1941 as_bad (_("$DPR_HWORD not supported in this context"));
1949 case BFD_RELOC_C6000_ABS_L16
:
1950 new_reloc
= BFD_RELOC_C6000_SBR_L16_W
;
1953 case BFD_RELOC_C6000_ABS_H16
:
1954 new_reloc
= BFD_RELOC_C6000_SBR_H16_W
;
1958 as_bad (_("$DPR_WORD not supported in this context"));
1964 subsy
= exp
->X_op_symbol
;
1967 case BFD_RELOC_C6000_ABS_S16
:
1968 case BFD_RELOC_C6000_ABS_L16
:
1969 new_reloc
= BFD_RELOC_C6000_PCR_L16
;
1972 case BFD_RELOC_C6000_ABS_H16
:
1973 new_reloc
= BFD_RELOC_C6000_PCR_H16
;
1977 as_bad (_("$PCR_OFFSET not supported in this context"));
1988 as_bad (_("invalid PC-relative operand"));
1994 if (new_reloc
== BFD_RELOC_UNUSED
)
1995 fix
= fix_new_exp (frag
, where
, size
, exp
, pcrel
, r_type
);
1997 fix
= fix_new (frag
, where
, size
, exp
->X_add_symbol
, exp
->X_add_number
,
1999 fix
->tc_fix_data
.fix_subsy
= subsy
;
2000 fix
->tc_fix_data
.fix_adda
= fix_adda
;
2003 /* Generate a fix for a constant (.word etc.). Needed to ensure these
2004 go through the error checking in tic6x_fix_new_exp. */
2007 tic6x_cons_fix_new (fragS
*frag
, int where
, int size
, expressionS
*exp
,
2008 bfd_reloc_code_real_type r_type
)
2013 r_type
= BFD_RELOC_8
;
2017 r_type
= BFD_RELOC_16
;
2021 r_type
= BFD_RELOC_32
;
2025 as_bad (_("no %d-byte relocations available"), size
);
2029 tic6x_fix_new_exp (frag
, where
, size
, exp
, 0, r_type
, false);
2032 /* Initialize target-specific fix data. */
2035 tic6x_init_fix_data (fixS
*fixP
)
2037 fixP
->tc_fix_data
.fix_adda
= false;
2038 fixP
->tc_fix_data
.fix_subsy
= NULL
;
2041 /* Return true if the fix can be handled by GAS, false if it must
2042 be passed through to the linker. */
2045 tic6x_fix_adjustable (fixS
*fixP
)
2047 switch (fixP
->fx_r_type
)
2049 /* Adjust_reloc_syms doesn't know about the GOT. */
2050 case BFD_RELOC_C6000_SBR_GOT_U15_W
:
2051 case BFD_RELOC_C6000_SBR_GOT_H16_W
:
2052 case BFD_RELOC_C6000_SBR_GOT_L16_W
:
2053 case BFD_RELOC_C6000_EHTYPE
:
2056 case BFD_RELOC_C6000_PREL31
:
2059 case BFD_RELOC_C6000_PCR_H16
:
2060 case BFD_RELOC_C6000_PCR_L16
:
2068 /* Given the fine-grained form of an operand, return the coarse
2072 tic6x_coarse_operand_form (tic6x_operand_form form
)
2076 case tic6x_operand_asm_const
:
2077 case tic6x_operand_link_const
:
2078 return TIC6X_OP_EXP
;
2080 case tic6x_operand_reg
:
2081 case tic6x_operand_xreg
:
2082 case tic6x_operand_dreg
:
2083 case tic6x_operand_areg
:
2084 case tic6x_operand_retreg
:
2085 return TIC6X_OP_REG
;
2087 case tic6x_operand_regpair
:
2088 case tic6x_operand_xregpair
:
2089 case tic6x_operand_dregpair
:
2090 return TIC6X_OP_REGPAIR
;
2092 case tic6x_operand_irp
:
2093 return TIC6X_OP_IRP
;
2095 case tic6x_operand_nrp
:
2096 return TIC6X_OP_NRP
;
2098 case tic6x_operand_ctrl
:
2099 return TIC6X_OP_CTRL
;
2101 case tic6x_operand_mem_short
:
2102 case tic6x_operand_mem_long
:
2103 case tic6x_operand_mem_deref
:
2104 return TIC6X_OP_MEM_NOUNREG
;
2106 case tic6x_operand_mem_ndw
:
2107 return TIC6X_OP_MEM_UNREG
;
2109 case tic6x_operand_func_unit
:
2110 return TIC6X_OP_FUNC_UNIT
;
2117 /* How an operand may match or not match a desired form. If different
2118 instruction alternatives fail in different ways, the first failure
2119 in this list determines the diagnostic. */
2123 tic6x_match_matches
,
2124 /* Bad coarse form. */
2127 tic6x_match_non_const
,
2128 /* Register on wrong side. */
2129 tic6x_match_wrong_side
,
2130 /* Not a valid address register. */
2131 tic6x_match_bad_address
,
2132 /* Not a valid return address register. */
2133 tic6x_match_bad_return
,
2134 /* Control register not readable. */
2135 tic6x_match_ctrl_write_only
,
2136 /* Control register not writable. */
2137 tic6x_match_ctrl_read_only
,
2138 /* Not a valid memory reference for this instruction. */
2140 } tic6x_operand_match
;
2142 /* Return whether an operand matches the given fine-grained form and
2143 read/write usage, and, if it does not match, how it fails to match.
2144 The main functional unit side is SIDE; the cross-path side is CROSS
2145 (the same as SIDE if a cross path not used); the data side is
2147 static tic6x_operand_match
2148 tic6x_operand_matches_form (const tic6x_operand
*op
, tic6x_operand_form form
,
2149 tic6x_rw rw
, unsigned int side
, unsigned int cross
,
2150 unsigned int data_side
)
2152 unsigned int coarse
= tic6x_coarse_operand_form (form
);
2154 if (coarse
!= op
->form
)
2155 return tic6x_match_coarse
;
2159 case tic6x_operand_asm_const
:
2160 if (op
->value
.exp
.X_op
== O_constant
)
2161 return tic6x_match_matches
;
2163 return tic6x_match_non_const
;
2165 case tic6x_operand_link_const
:
2166 case tic6x_operand_irp
:
2167 case tic6x_operand_nrp
:
2168 case tic6x_operand_func_unit
:
2169 /* All expressions are link-time constants, although there may
2170 not be relocations to express them in the output file. "irp"
2171 and "nrp" are unique operand values. All parsed functional
2172 unit names are valid. */
2173 return tic6x_match_matches
;
2175 case tic6x_operand_reg
:
2176 case tic6x_operand_regpair
:
2177 if (op
->value
.reg
.side
== side
)
2178 return tic6x_match_matches
;
2180 return tic6x_match_wrong_side
;
2182 case tic6x_operand_xreg
:
2183 case tic6x_operand_xregpair
:
2184 if (op
->value
.reg
.side
== cross
)
2185 return tic6x_match_matches
;
2187 return tic6x_match_wrong_side
;
2189 case tic6x_operand_dreg
:
2190 case tic6x_operand_dregpair
:
2191 if (op
->value
.reg
.side
== data_side
)
2192 return tic6x_match_matches
;
2194 return tic6x_match_wrong_side
;
2196 case tic6x_operand_areg
:
2197 if (op
->value
.reg
.side
!= cross
)
2198 return tic6x_match_wrong_side
;
2199 else if (op
->value
.reg
.side
== 2
2200 && (op
->value
.reg
.num
== 14 || op
->value
.reg
.num
== 15))
2201 return tic6x_match_matches
;
2203 return tic6x_match_bad_address
;
2205 case tic6x_operand_retreg
:
2206 if (op
->value
.reg
.side
!= side
)
2207 return tic6x_match_wrong_side
;
2208 else if (op
->value
.reg
.num
!= 3)
2209 return tic6x_match_bad_return
;
2211 return tic6x_match_matches
;
2213 case tic6x_operand_ctrl
:
2217 if (tic6x_ctrl_table
[op
->value
.ctrl
].rw
== tic6x_rw_read
2218 || tic6x_ctrl_table
[op
->value
.ctrl
].rw
== tic6x_rw_read_write
)
2219 return tic6x_match_matches
;
2221 return tic6x_match_ctrl_write_only
;
2223 case tic6x_rw_write
:
2224 if (tic6x_ctrl_table
[op
->value
.ctrl
].rw
== tic6x_rw_write
2225 || tic6x_ctrl_table
[op
->value
.ctrl
].rw
== tic6x_rw_read_write
)
2226 return tic6x_match_matches
;
2228 return tic6x_match_ctrl_read_only
;
2234 case tic6x_operand_mem_deref
:
2235 if (op
->value
.mem
.mod
!= tic6x_mem_mod_none
)
2236 return tic6x_match_bad_mem
;
2237 else if (op
->value
.mem
.scaled
!= tic6x_offset_none
)
2239 else if (op
->value
.mem
.base_reg
.side
!= side
)
2240 return tic6x_match_bad_mem
;
2242 return tic6x_match_matches
;
2244 case tic6x_operand_mem_short
:
2245 case tic6x_operand_mem_ndw
:
2246 if (op
->value
.mem
.base_reg
.side
!= side
)
2247 return tic6x_match_bad_mem
;
2248 if (op
->value
.mem
.mod
== tic6x_mem_mod_none
)
2250 if (op
->value
.mem
.scaled
!= tic6x_offset_none
)
2252 return tic6x_match_matches
;
2254 if (op
->value
.mem
.scaled
== tic6x_offset_none
)
2256 if (op
->value
.mem
.mod
== tic6x_mem_mod_plus
2257 || op
->value
.mem
.mod
== tic6x_mem_mod_minus
)
2259 return tic6x_match_matches
;
2261 if (op
->value
.mem
.offset_is_reg
)
2263 if (op
->value
.mem
.scaled
== tic6x_offset_unscaled
2264 && form
!= tic6x_operand_mem_ndw
)
2266 if (op
->value
.mem
.offset
.reg
.side
== side
)
2267 return tic6x_match_matches
;
2269 return tic6x_match_bad_mem
;
2273 if (op
->value
.mem
.offset
.exp
.X_op
== O_constant
)
2274 return tic6x_match_matches
;
2276 return tic6x_match_bad_mem
;
2279 case tic6x_operand_mem_long
:
2280 if (op
->value
.mem
.base_reg
.side
== 2
2281 && (op
->value
.mem
.base_reg
.num
== 14
2282 || op
->value
.mem
.base_reg
.num
== 15))
2284 switch (op
->value
.mem
.mod
)
2286 case tic6x_mem_mod_none
:
2287 if (op
->value
.mem
.scaled
!= tic6x_offset_none
)
2289 return tic6x_match_matches
;
2291 case tic6x_mem_mod_plus
:
2292 if (op
->value
.mem
.scaled
== tic6x_offset_none
)
2294 if (op
->value
.mem
.offset_is_reg
)
2295 return tic6x_match_bad_mem
;
2296 else if (op
->value
.mem
.scaled
== tic6x_offset_scaled
2297 && op
->value
.mem
.offset
.exp
.X_op
!= O_constant
)
2298 return tic6x_match_bad_mem
;
2300 return tic6x_match_matches
;
2302 case tic6x_mem_mod_minus
:
2303 case tic6x_mem_mod_preinc
:
2304 case tic6x_mem_mod_predec
:
2305 case tic6x_mem_mod_postinc
:
2306 case tic6x_mem_mod_postdec
:
2307 return tic6x_match_bad_mem
;
2315 return tic6x_match_bad_mem
;
2322 /* Return the number of bits shift used with DP-relative coding method
2326 tic6x_dpr_shift (tic6x_coding_method coding
)
2330 case tic6x_coding_ulcst_dpr_byte
:
2333 case tic6x_coding_ulcst_dpr_half
:
2336 case tic6x_coding_ulcst_dpr_word
:
2344 /* Return the relocation used with DP-relative coding method
2347 static bfd_reloc_code_real_type
2348 tic6x_dpr_reloc (tic6x_coding_method coding
)
2352 case tic6x_coding_ulcst_dpr_byte
:
2353 return BFD_RELOC_C6000_SBR_U15_B
;
2355 case tic6x_coding_ulcst_dpr_half
:
2356 return BFD_RELOC_C6000_SBR_U15_H
;
2358 case tic6x_coding_ulcst_dpr_word
:
2359 return BFD_RELOC_C6000_SBR_U15_W
;
2366 /* Given a memory reference *MEM_REF as originally parsed, fill in
2367 defaults for missing offsets. */
2370 tic6x_default_mem_ref (tic6x_mem_ref
*mem_ref
)
2372 switch (mem_ref
->mod
)
2374 case tic6x_mem_mod_none
:
2375 if (mem_ref
->scaled
!= tic6x_offset_none
)
2377 mem_ref
->mod
= tic6x_mem_mod_plus
;
2378 mem_ref
->scaled
= tic6x_offset_unscaled
;
2379 mem_ref
->offset_is_reg
= false;
2380 memset (&mem_ref
->offset
.exp
, 0, sizeof mem_ref
->offset
.exp
);
2381 mem_ref
->offset
.exp
.X_op
= O_constant
;
2382 mem_ref
->offset
.exp
.X_add_number
= 0;
2383 mem_ref
->offset
.exp
.X_unsigned
= 0;
2386 case tic6x_mem_mod_plus
:
2387 case tic6x_mem_mod_minus
:
2388 if (mem_ref
->scaled
== tic6x_offset_none
)
2392 case tic6x_mem_mod_preinc
:
2393 case tic6x_mem_mod_predec
:
2394 case tic6x_mem_mod_postinc
:
2395 case tic6x_mem_mod_postdec
:
2396 if (mem_ref
->scaled
!= tic6x_offset_none
)
2398 mem_ref
->scaled
= tic6x_offset_scaled
;
2399 mem_ref
->offset_is_reg
= false;
2400 memset (&mem_ref
->offset
.exp
, 0, sizeof mem_ref
->offset
.exp
);
2401 mem_ref
->offset
.exp
.X_op
= O_constant
;
2402 mem_ref
->offset
.exp
.X_add_number
= 1;
2403 mem_ref
->offset
.exp
.X_unsigned
= 0;
2411 /* Return the encoding in the 8-bit field of an SPMASK or SPMASKR
2412 instruction of the specified UNIT, side SIDE. */
2415 tic6x_encode_spmask (tic6x_func_unit_base unit
, unsigned int side
)
2419 case tic6x_func_unit_l
:
2420 return 1 << (side
- 1);
2422 case tic6x_func_unit_s
:
2423 return 1 << (side
+ 1);
2425 case tic6x_func_unit_d
:
2426 return 1 << (side
+ 3);
2428 case tic6x_func_unit_m
:
2429 return 1 << (side
+ 5);
2436 /* Try to encode the instruction with opcode number ID and operands
2437 OPERANDS (number NUM_OPERANDS), creg value THIS_LINE_CREG and z
2438 value THIS_LINE_Z; FUNC_UNIT_SIDE, FUNC_UNIT_CROSS and
2439 FUNC_UNIT_DATA_SIDE describe the functional unit specification;
2440 SPLOOP_II is the ii value from the previous SPLOOP-family
2441 instruction, or 0 if not in such a loop; the only possible problems
2442 are operands being out of range (they already match the
2443 fine-grained form), and inappropriate predication. If this
2444 succeeds, return the encoding and set *OK to true; otherwise return
2445 0 and set *OK to FALSE. If a fix is needed, set *FIX_NEEDED to
2446 true and fill in *FIX_EXP, *FIX_PCREL, *FX_R_TYPE and *FIX_ADDA.
2447 Print error messages for failure if PRINT_ERRORS is true; the
2448 opcode starts at STR and has length OPC_LEN. */
2451 tic6x_try_encode (tic6x_opcode_id id
, tic6x_operand
*operands
,
2452 unsigned int num_operands
, unsigned int this_line_creg
,
2453 unsigned int this_line_z
, unsigned int func_unit_side
,
2454 unsigned int func_unit_cross
,
2455 unsigned int func_unit_data_side
, int sploop_ii
,
2456 expressionS
**fix_exp
, int *fix_pcrel
,
2457 bfd_reloc_code_real_type
*fx_r_type
, bool *fix_adda
,
2458 bool *fix_needed
, bool *ok
,
2459 bool print_errors
, char *str
, int opc_len
)
2461 const tic6x_opcode
*opct
;
2462 const tic6x_insn_format
*fmt
;
2463 unsigned int opcode_value
;
2466 opct
= &tic6x_opcode_table
[id
];
2467 fmt
= &tic6x_insn_format_table
[opct
->format
];
2468 opcode_value
= fmt
->cst_bits
;
2470 for (fld
= 0; fld
< opct
->num_fixed_fields
; fld
++)
2472 if (opct
->fixed_fields
[fld
].min_val
== opct
->fixed_fields
[fld
].max_val
)
2474 const tic6x_insn_field
*fldd
;
2475 fldd
= tic6x_field_from_fmt (fmt
, opct
->fixed_fields
[fld
].field_id
);
2478 opcode_value
|= opct
->fixed_fields
[fld
].min_val
<< fldd
->bitfields
[0].low_pos
;
2482 for (fld
= 0; fld
< opct
->num_variable_fields
; fld
++)
2484 const tic6x_insn_field
*fldd
;
2490 unsigned int fcyc_bits
;
2495 fldd
= tic6x_field_from_fmt (fmt
, opct
->variable_fields
[fld
].field_id
);
2498 opno
= opct
->variable_fields
[fld
].operand_num
;
2499 switch (opct
->variable_fields
[fld
].coding_method
)
2501 case tic6x_coding_ucst
:
2502 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2504 if (operands
[opno
].value
.exp
.X_op
!= O_constant
)
2506 ucexp
= operands
[opno
].value
.exp
;
2508 if (ucexp
.X_add_number
< 0
2509 || ucexp
.X_add_number
>= (1 << fldd
->bitfields
[0].width
))
2512 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
2517 value
= ucexp
.X_add_number
;
2520 case tic6x_coding_scst
:
2521 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2523 if (operands
[opno
].value
.exp
.X_op
!= O_constant
)
2526 /* Opcode table should not permit non-constants without
2527 a known relocation for them. */
2528 if (fldd
->bitfields
[0].low_pos
!= 7 || fldd
->bitfields
[0].width
!= 16)
2531 *fix_exp
= &operands
[opno
].value
.exp
;
2533 *fx_r_type
= BFD_RELOC_C6000_ABS_S16
;
2537 sign_value
= SEXT (operands
[opno
].value
.exp
.X_add_number
);
2539 if (sign_value
< -(1 << (fldd
->bitfields
[0].width
- 1))
2540 || (sign_value
>= (1 << (fldd
->bitfields
[0].width
- 1))))
2543 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
2548 value
= sign_value
+ (1 << (fldd
->bitfields
[0].width
- 1));
2549 value
^= (1 << (fldd
->bitfields
[0].width
- 1));
2552 case tic6x_coding_ucst_minus_one
:
2553 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2555 if (operands
[opno
].value
.exp
.X_op
!= O_constant
)
2557 if (operands
[opno
].value
.exp
.X_add_number
<= 0
2558 || operands
[opno
].value
.exp
.X_add_number
> (1 << fldd
->bitfields
[0].width
))
2561 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
2566 value
= operands
[opno
].value
.exp
.X_add_number
- 1;
2569 case tic6x_coding_scst_negate
:
2570 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2572 if (operands
[opno
].value
.exp
.X_op
!= O_constant
)
2574 sign_value
= SEXT (-operands
[opno
].value
.exp
.X_add_number
);
2575 goto signed_constant
;
2577 case tic6x_coding_ulcst_dpr_byte
:
2578 case tic6x_coding_ulcst_dpr_half
:
2579 case tic6x_coding_ulcst_dpr_word
:
2580 bits
= tic6x_dpr_shift (opct
->variable_fields
[fld
].coding_method
);
2581 switch (operands
[opno
].form
)
2584 if (operands
[opno
].value
.exp
.X_op
== O_constant
)
2586 ucexp
= operands
[opno
].value
.exp
;
2587 goto unsigned_constant
;
2589 expp
= &operands
[opno
].value
.exp
;
2592 case TIC6X_OP_MEM_NOUNREG
:
2593 mem
= operands
[opno
].value
.mem
;
2594 tic6x_default_mem_ref (&mem
);
2595 if (mem
.offset_is_reg
)
2597 if (mem
.offset
.exp
.X_op
== O_constant
)
2599 ucexp
= mem
.offset
.exp
;
2600 if (mem
.scaled
== tic6x_offset_unscaled
)
2602 if (ucexp
.X_add_number
& ((1 << bits
) - 1))
2605 as_bad (_("offset in operand %u of '%.*s' not "
2606 "divisible by %u"), opno
+ 1, opc_len
,
2611 ucexp
.X_add_number
>>= bits
;
2613 goto unsigned_constant
;
2615 if (mem
.scaled
!= tic6x_offset_unscaled
)
2617 if (operands
[opno
].value
.mem
.mod
== tic6x_mem_mod_none
2618 || operands
[opno
].value
.mem
.scaled
!= tic6x_offset_unscaled
2619 || operands
[opno
].value
.mem
.offset_is_reg
)
2621 expp
= &operands
[opno
].value
.mem
.offset
.exp
;
2628 /* Opcode table should not use this encoding without a known
2630 if (fldd
->bitfields
[0].low_pos
!= 8 || fldd
->bitfields
[0].width
!= 15)
2632 /* We do not check for offset divisibility here; such a
2633 check is not needed at this point to encode the value,
2634 and if there is eventually a problem it will be detected
2635 either in md_apply_fix or at link time. */
2640 = tic6x_dpr_reloc (opct
->variable_fields
[fld
].coding_method
);
2641 if (operands
[opno
].form
== TIC6X_OP_EXP
)
2647 case tic6x_coding_lcst_low16
:
2648 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2650 if (operands
[opno
].value
.exp
.X_op
== O_constant
)
2651 value
= operands
[opno
].value
.exp
.X_add_number
& 0xffff;
2655 /* Opcode table should not use this encoding without a
2656 known relocation. */
2657 if (fldd
->bitfields
[0].low_pos
!= 7 || fldd
->bitfields
[0].width
!= 16)
2660 *fix_exp
= &operands
[opno
].value
.exp
;
2662 *fx_r_type
= BFD_RELOC_C6000_ABS_L16
;
2667 case tic6x_coding_lcst_high16
:
2668 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2670 if (operands
[opno
].value
.exp
.X_op
== O_constant
)
2671 value
= (operands
[opno
].value
.exp
.X_add_number
>> 16) & 0xffff;
2675 /* Opcode table should not use this encoding without a
2676 known relocation. */
2677 if (fldd
->bitfields
[0].low_pos
!= 7 || fldd
->bitfields
[0].width
!= 16)
2680 *fix_exp
= &operands
[opno
].value
.exp
;
2682 *fx_r_type
= BFD_RELOC_C6000_ABS_H16
;
2687 case tic6x_coding_pcrel
:
2688 case tic6x_coding_pcrel_half
:
2689 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2693 *fix_exp
= &operands
[opno
].value
.exp
;
2695 if (fldd
->bitfields
[0].low_pos
== 7 && fldd
->bitfields
[0].width
== 21)
2696 *fx_r_type
= BFD_RELOC_C6000_PCR_S21
;
2697 else if (fldd
->bitfields
[0].low_pos
== 16 && fldd
->bitfields
[0].width
== 12)
2698 *fx_r_type
= BFD_RELOC_C6000_PCR_S12
;
2699 else if (fldd
->bitfields
[0].low_pos
== 13 && fldd
->bitfields
[0].width
== 10)
2700 *fx_r_type
= BFD_RELOC_C6000_PCR_S10
;
2701 else if (fldd
->bitfields
[0].low_pos
== 16 && fldd
->bitfields
[0].width
== 7)
2702 *fx_r_type
= BFD_RELOC_C6000_PCR_S7
;
2704 /* Opcode table should not use this encoding without a
2705 known relocation. */
2710 case tic6x_coding_regpair_lsb
:
2711 switch (operands
[opno
].form
)
2713 case TIC6X_OP_REGPAIR
:
2714 value
= operands
[opno
].value
.reg
.num
;
2722 case tic6x_coding_regpair_msb
:
2723 switch (operands
[opno
].form
)
2725 case TIC6X_OP_REGPAIR
:
2726 value
= operands
[opno
].value
.reg
.num
+ 1;
2734 case tic6x_coding_reg
:
2735 switch (operands
[opno
].form
)
2738 case TIC6X_OP_REGPAIR
:
2739 value
= operands
[opno
].value
.reg
.num
;
2742 case TIC6X_OP_MEM_NOUNREG
:
2743 case TIC6X_OP_MEM_UNREG
:
2744 value
= operands
[opno
].value
.mem
.base_reg
.num
;
2752 case tic6x_coding_areg
:
2753 switch (operands
[opno
].form
)
2756 value
= (operands
[opno
].value
.reg
.num
== 15 ? 1 : 0);
2759 case TIC6X_OP_MEM_NOUNREG
:
2760 value
= (operands
[opno
].value
.mem
.base_reg
.num
== 15 ? 1 : 0);
2768 case tic6x_coding_crlo
:
2769 if (operands
[opno
].form
!= TIC6X_OP_CTRL
)
2771 value
= tic6x_ctrl_table
[operands
[opno
].value
.ctrl
].crlo
;
2774 case tic6x_coding_crhi
:
2775 if (operands
[opno
].form
!= TIC6X_OP_CTRL
)
2780 case tic6x_coding_reg_shift
:
2781 if (operands
[opno
].form
!= TIC6X_OP_REGPAIR
)
2783 value
= operands
[opno
].value
.reg
.num
>> 1;
2786 case tic6x_coding_mem_offset
:
2787 if (operands
[opno
].form
!= TIC6X_OP_MEM_NOUNREG
)
2789 mem
= operands
[opno
].value
.mem
;
2790 tic6x_default_mem_ref (&mem
);
2791 if (mem
.offset_is_reg
)
2793 if (mem
.scaled
!= tic6x_offset_scaled
)
2795 value
= mem
.offset
.reg
.num
;
2801 if (mem
.offset
.exp
.X_op
!= O_constant
)
2805 case tic6x_offset_scaled
:
2809 case tic6x_offset_unscaled
:
2810 scale
= opct
->operand_info
[opno
].size
;
2811 if (scale
!= 1 && scale
!= 2 && scale
!= 4 && scale
!= 8)
2818 if (mem
.offset
.exp
.X_add_number
< 0
2819 || mem
.offset
.exp
.X_add_number
>= (1 << fldd
->bitfields
[0].width
) * scale
)
2822 as_bad (_("offset in operand %u of '%.*s' out of range"),
2823 opno
+ 1, opc_len
, str
);
2827 if (mem
.offset
.exp
.X_add_number
% scale
)
2830 as_bad (_("offset in operand %u of '%.*s' not "
2832 opno
+ 1, opc_len
, str
, scale
);
2836 value
= mem
.offset
.exp
.X_add_number
/ scale
;
2840 case tic6x_coding_mem_offset_noscale
:
2841 if (operands
[opno
].form
!= TIC6X_OP_MEM_UNREG
)
2843 mem
= operands
[opno
].value
.mem
;
2844 tic6x_default_mem_ref (&mem
);
2845 if (mem
.offset_is_reg
)
2846 value
= mem
.offset
.reg
.num
;
2849 if (mem
.offset
.exp
.X_op
!= O_constant
)
2851 if (mem
.offset
.exp
.X_add_number
< 0
2852 || mem
.offset
.exp
.X_add_number
>= (1 << fldd
->bitfields
[0].width
))
2855 as_bad (_("offset in operand %u of '%.*s' out of range"),
2856 opno
+ 1, opc_len
, str
);
2860 value
= mem
.offset
.exp
.X_add_number
;
2864 case tic6x_coding_mem_mode
:
2865 if (operands
[opno
].form
!= TIC6X_OP_MEM_NOUNREG
2866 && operands
[opno
].form
!= TIC6X_OP_MEM_UNREG
)
2868 mem
= operands
[opno
].value
.mem
;
2869 tic6x_default_mem_ref (&mem
);
2872 case tic6x_mem_mod_plus
:
2876 case tic6x_mem_mod_minus
:
2880 case tic6x_mem_mod_preinc
:
2884 case tic6x_mem_mod_predec
:
2888 case tic6x_mem_mod_postinc
:
2892 case tic6x_mem_mod_postdec
:
2899 value
+= (mem
.offset_is_reg
? 4 : 0);
2902 case tic6x_coding_scaled
:
2903 if (operands
[opno
].form
!= TIC6X_OP_MEM_UNREG
)
2905 mem
= operands
[opno
].value
.mem
;
2906 tic6x_default_mem_ref (&mem
);
2909 case tic6x_offset_unscaled
:
2913 case tic6x_offset_scaled
:
2922 case tic6x_coding_spmask
:
2923 /* The position of such a field is hardcoded in the handling
2925 if (fldd
->bitfields
[0].low_pos
!= 18)
2928 for (opno
= 0; opno
< num_operands
; opno
++)
2932 v
= tic6x_encode_spmask (operands
[opno
].value
.func_unit
.base
,
2933 operands
[opno
].value
.func_unit
.side
);
2937 as_bad (_("functional unit already masked for operand "
2938 "%u of '%.*s'"), opno
+ 1, opc_len
, str
);
2946 case tic6x_coding_reg_unused
:
2947 /* This is a placeholder; correct handling goes along with
2948 resource constraint checks. */
2952 case tic6x_coding_fstg
:
2953 case tic6x_coding_fcyc
:
2954 if (operands
[opno
].form
!= TIC6X_OP_EXP
)
2956 if (operands
[opno
].value
.exp
.X_op
!= O_constant
)
2961 as_bad (_("'%.*s' instruction not in a software "
2970 else if (sploop_ii
<= 2)
2972 else if (sploop_ii
<= 4)
2974 else if (sploop_ii
<= 8)
2976 else if (sploop_ii
<= 14)
2980 if (fcyc_bits
> fldd
->bitfields
[0].width
)
2983 if (opct
->variable_fields
[fld
].coding_method
== tic6x_coding_fstg
)
2986 if (operands
[opno
].value
.exp
.X_add_number
< 0
2987 || (operands
[opno
].value
.exp
.X_add_number
2988 >= (1 << (fldd
->bitfields
[0].width
- fcyc_bits
))))
2991 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
2996 value
= operands
[opno
].value
.exp
.X_add_number
;
2997 for (t
= 0, i
= fcyc_bits
; i
< fldd
->bitfields
[0].width
; i
++)
2999 t
= (t
<< 1) | (value
& 1);
3002 value
= t
<< fcyc_bits
;
3006 if (operands
[opno
].value
.exp
.X_add_number
< 0
3007 || (operands
[opno
].value
.exp
.X_add_number
>= sploop_ii
))
3010 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
3015 value
= operands
[opno
].value
.exp
.X_add_number
;
3019 case tic6x_coding_fu
:
3020 value
= func_unit_side
== 2 ? 1 : 0;
3023 case tic6x_coding_data_fu
:
3024 value
= func_unit_data_side
== 2 ? 1 : 0;
3027 case tic6x_coding_xpath
:
3028 value
= func_unit_cross
;
3035 for (ffld
= 0; ffld
< opct
->num_fixed_fields
; ffld
++)
3036 if ((opct
->fixed_fields
[ffld
].field_id
3037 == opct
->variable_fields
[fld
].field_id
)
3038 && (value
< opct
->fixed_fields
[ffld
].min_val
3039 || value
> opct
->fixed_fields
[ffld
].max_val
))
3042 as_bad (_("operand %u of '%.*s' out of range"), opno
+ 1,
3048 opcode_value
|= value
<< fldd
->bitfields
[0].low_pos
;
3053 const tic6x_insn_field
*creg
;
3054 const tic6x_insn_field
*z
;
3056 creg
= tic6x_field_from_fmt (fmt
, tic6x_field_creg
);
3060 as_bad (_("instruction '%.*s' cannot be predicated"),
3065 z
= tic6x_field_from_fmt (fmt
, tic6x_field_z
);
3066 /* If there is a creg field, there must be a z field; otherwise
3067 there is an error in the format table. */
3071 opcode_value
|= this_line_creg
<< creg
->bitfields
[0].low_pos
;
3072 opcode_value
|= this_line_z
<< z
->bitfields
[0].low_pos
;
3076 return opcode_value
;
3079 /* Convert the target integer stored in N bytes in BUF to a host
3080 integer, returning that value. */
3083 md_chars_to_number (char *buf
, int n
)
3086 unsigned char *p
= (unsigned char *) buf
;
3088 if (target_big_endian
)
3093 result
|= (*p
++ & 0xff);
3101 result
|= (p
[n
] & 0xff);
3108 /* Assemble the instruction starting at STR (an opcode, with the
3109 opcode name all-lowercase). */
3112 md_assemble (char *str
)
3116 bool this_line_parallel
;
3117 bool this_line_spmask
;
3118 unsigned int this_line_creg
;
3119 unsigned int this_line_z
;
3120 tic6x_label_list
*this_insn_label_list
;
3121 segment_info_type
*seginfo
;
3122 tic6x_opcode_list
*opc_list
, *opc
;
3123 tic6x_func_unit_base func_unit_base
= tic6x_func_unit_nfu
;
3124 unsigned int func_unit_side
= 0;
3125 unsigned int func_unit_cross
= 0;
3126 unsigned int cross_side
= 0;
3127 unsigned int func_unit_data_side
= 0;
3128 unsigned int max_matching_opcodes
, num_matching_opcodes
;
3129 tic6x_opcode_id
*opcm
= NULL
;
3130 unsigned int opc_rank
[TIC6X_NUM_PREFER
];
3131 const tic6x_opcode
*opct
= NULL
;
3132 int min_rank
, try_rank
, max_rank
;
3133 bool num_operands_permitted
[TIC6X_MAX_SOURCE_OPERANDS
+ 1] = { false };
3134 unsigned int operand_forms
[TIC6X_MAX_SOURCE_OPERANDS
] = { 0 };
3135 tic6x_operand operands
[TIC6X_MAX_SOURCE_OPERANDS
];
3136 unsigned int max_num_operands
;
3137 unsigned int num_operands_read
;
3138 bool ok_this_arch
, ok_this_fu
, ok_this_arch_fu
;
3139 bool bad_operands
= false;
3140 unsigned int opcode_value
;
3142 bool fix_needed
= false;
3143 expressionS
*fix_exp
= NULL
;
3145 bfd_reloc_code_real_type fx_r_type
= BFD_RELOC_UNUSED
;
3146 bool fix_adda
= false;
3151 while (*p
&& !is_end_of_line
[(unsigned char) *p
] && *p
!= ' ')
3154 /* This function should only have been called when there is actually
3155 an instruction to assemble. */
3159 /* Now an instruction has been seen, architecture attributes from
3160 .arch directives merge with rather than overriding the previous
3162 tic6x_seen_insns
= true;
3163 /* If no .arch directives or -march options have been seen, we are
3164 assessing instruction validity based on the C674X default, so set
3165 the attribute accordingly. */
3166 if (tic6x_arch_attribute
== C6XABI_Tag_ISA_none
)
3167 tic6x_arch_attribute
= C6XABI_Tag_ISA_C674X
;
3169 /* Reset global settings for parallel bars and predicates now to
3170 avoid extra errors if there are problems with this opcode. */
3171 this_line_parallel
= tic6x_line_parallel
;
3172 this_line_spmask
= tic6x_line_spmask
;
3173 this_line_creg
= tic6x_line_creg
;
3174 this_line_z
= tic6x_line_z
;
3175 tic6x_line_parallel
= false;
3176 tic6x_line_spmask
= false;
3177 tic6x_line_creg
= 0;
3179 seginfo
= seg_info (now_seg
);
3180 this_insn_label_list
= seginfo
->tc_segment_info_data
.label_list
;
3181 seginfo
->tc_segment_info_data
.label_list
= NULL
;
3183 opc_list
= str_hash_find_n (opcode_hash
, str
, p
- str
);
3184 if (opc_list
== NULL
)
3188 as_bad (_("unknown opcode '%s'"), str
);
3194 skip_whitespace (p
);
3196 /* See if there is something that looks like a functional unit
3200 bool good_func_unit
;
3201 tic6x_func_unit_base maybe_base
= tic6x_func_unit_nfu
;
3202 unsigned int maybe_side
= 0;
3203 unsigned int maybe_cross
= 0;
3204 unsigned int maybe_data_side
= 0;
3206 good_func_unit
= tic6x_parse_func_unit_base (p
+ 1, &maybe_base
,
3211 if (p
[3] == ' ' || is_end_of_line
[(unsigned char) p
[3]])
3213 else if ((p
[3] == 'x' || p
[3] == 'X')
3214 && (p
[4] == ' ' || is_end_of_line
[(unsigned char) p
[4]]))
3219 else if (maybe_base
== tic6x_func_unit_d
3220 && (p
[3] == 't' || p
[3] == 'T')
3221 && (p
[4] == '1' || p
[4] == '2')
3222 && (p
[5] == ' ' || is_end_of_line
[(unsigned char) p
[5]]))
3224 maybe_data_side
= p
[4] - '0';
3228 good_func_unit
= false;
3233 func_unit_base
= maybe_base
;
3234 func_unit_side
= maybe_side
;
3235 func_unit_cross
= maybe_cross
;
3236 cross_side
= (func_unit_cross
? 3 - func_unit_side
: func_unit_side
);
3237 func_unit_data_side
= maybe_data_side
;
3240 skip_whitespace (p
);
3243 /* Determine which entries in the opcode table match, and the
3244 associated permitted forms of operands. */
3245 max_matching_opcodes
= 0;
3246 for (opc
= opc_list
; opc
; opc
= opc
->next
)
3247 max_matching_opcodes
++;
3248 num_matching_opcodes
= 0;
3249 opcm
= XNEWVEC (tic6x_opcode_id
, max_matching_opcodes
);
3250 max_num_operands
= 0;
3251 ok_this_arch
= false;
3253 ok_this_arch_fu
= false;
3254 for (opc
= opc_list
; opc
; opc
= opc
->next
)
3256 unsigned int num_operands
;
3258 bool this_opc_arch_ok
= true;
3259 bool this_opc_fu_ok
= true;
3261 if (tic6x_insn_format_table
[tic6x_opcode_table
[opc
->id
].format
].num_bits
3264 if (!(tic6x_opcode_table
[opc
->id
].isa_variants
& tic6x_features
))
3265 this_opc_arch_ok
= false;
3266 if (tic6x_opcode_table
[opc
->id
].func_unit
!= func_unit_base
)
3267 this_opc_fu_ok
= false;
3268 if (func_unit_side
== 1
3269 && (tic6x_opcode_table
[opc
->id
].flags
& TIC6X_FLAG_SIDE_B_ONLY
))
3270 this_opc_fu_ok
= false;
3272 && (tic6x_opcode_table
[opc
->id
].flags
& TIC6X_FLAG_NO_CROSS
))
3273 this_opc_fu_ok
= false;
3274 if (!func_unit_data_side
3275 && (tic6x_opcode_table
[opc
->id
].flags
3276 & (TIC6X_FLAG_LOAD
| TIC6X_FLAG_STORE
)))
3277 this_opc_fu_ok
= false;
3278 if (func_unit_data_side
3279 && !(tic6x_opcode_table
[opc
->id
].flags
3280 & (TIC6X_FLAG_LOAD
| TIC6X_FLAG_STORE
)))
3281 this_opc_fu_ok
= false;
3282 if (func_unit_data_side
== 1
3283 && (tic6x_opcode_table
[opc
->id
].flags
& TIC6X_FLAG_SIDE_T2_ONLY
))
3284 this_opc_fu_ok
= false;
3285 if (this_opc_arch_ok
)
3286 ok_this_arch
= true;
3289 if (!this_opc_arch_ok
|| !this_opc_fu_ok
)
3291 ok_this_arch_fu
= true;
3292 opcm
[num_matching_opcodes
] = opc
->id
;
3293 num_matching_opcodes
++;
3294 num_operands
= tic6x_opcode_table
[opc
->id
].num_operands
;
3296 if (tic6x_opcode_table
[opc
->id
].flags
& TIC6X_FLAG_SPMASK
)
3298 if (num_operands
!= 1
3299 || (tic6x_opcode_table
[opc
->id
].operand_info
[0].form
3300 != tic6x_operand_func_unit
))
3303 for (i
= 0; i
< num_operands
; i
++)
3306 |= tic6x_coarse_operand_form (tic6x_operand_func_unit
);
3307 num_operands_permitted
[i
] = true;
3312 for (i
= 0; i
< num_operands
; i
++)
3314 tic6x_operand_form f
3315 = tic6x_opcode_table
[opc
->id
].operand_info
[i
].form
;
3317 operand_forms
[i
] |= tic6x_coarse_operand_form (f
);
3320 num_operands_permitted
[num_operands
] = true;
3321 if (num_operands
> max_num_operands
)
3322 max_num_operands
= num_operands
;
3327 as_bad (_("'%.*s' instruction not supported on this architecture"),
3335 as_bad (_("'%.*s' instruction not supported on this functional unit"),
3341 if (!ok_this_arch_fu
)
3343 as_bad (_("'%.*s' instruction not supported on this functional unit"
3344 " for this architecture"),
3350 /* If there were no instructions matching the above availability
3351 checks, we should now have given an error and returned. */
3352 if (num_matching_opcodes
== 0)
3355 num_operands_read
= 0;
3358 skip_whitespace (p
);
3359 if (is_end_of_line
[(unsigned char) *p
])
3361 if (num_operands_read
> 0)
3363 as_bad (_("missing operand after comma"));
3364 bad_operands
= true;
3369 if (max_num_operands
== 0)
3371 as_bad (_("too many operands to '%.*s'"), opc_len
, str
);
3372 bad_operands
= true;
3376 if (!tic6x_parse_operand (&p
, &operands
[num_operands_read
],
3377 operand_forms
[num_operands_read
], str
, opc_len
,
3378 num_operands_read
+ 1))
3379 bad_operands
= true;
3380 num_operands_read
++;
3382 if (is_end_of_line
[(unsigned char) *p
])
3387 if (num_operands_read
== max_num_operands
)
3389 as_bad (_("too many operands to '%.*s'"), opc_len
, str
);
3390 bad_operands
= true;
3396 /* Operand parsing should consume whole operands. */
3400 if (!bad_operands
&& !num_operands_permitted
[num_operands_read
])
3402 as_bad (_("bad number of operands to '%.*s'"), opc_len
, str
);
3403 bad_operands
= true;
3408 /* Each operand is of the right syntactic form for some opcode
3409 choice, and the number of operands is valid. Check that each
3410 operand is OK in detail for some opcode choice with the right
3411 number of operands. */
3414 for (i
= 0; i
< num_operands_read
; i
++)
3416 bool coarse_ok
= false;
3417 bool fine_ok
= false;
3418 tic6x_operand_match fine_failure
= tic6x_match_matches
;
3421 for (j
= 0; j
< num_matching_opcodes
; j
++)
3423 tic6x_operand_form f
;
3426 tic6x_operand_match this_fine_failure
;
3428 if (tic6x_opcode_table
[opcm
[j
]].flags
& TIC6X_FLAG_SPMASK
)
3430 f
= tic6x_operand_func_unit
;
3435 if (tic6x_opcode_table
[opcm
[j
]].num_operands
3436 != num_operands_read
)
3439 f
= tic6x_opcode_table
[opcm
[j
]].operand_info
[i
].form
;
3440 rw
= tic6x_opcode_table
[opcm
[j
]].operand_info
[i
].rw
;
3442 cf
= tic6x_coarse_operand_form (f
);
3444 if (operands
[i
].form
!= cf
)
3449 = tic6x_operand_matches_form (&operands
[i
], f
, rw
,
3452 func_unit_data_side
);
3453 if (this_fine_failure
== tic6x_match_matches
)
3458 if (fine_failure
== tic6x_match_matches
3459 || fine_failure
> this_fine_failure
)
3460 fine_failure
= this_fine_failure
;
3463 /* No instructions should have operand syntactic forms only
3464 acceptable with certain numbers of operands, so no
3465 diagnostic for this case. */
3471 switch (fine_failure
)
3473 case tic6x_match_non_const
:
3474 as_bad (_("operand %u of '%.*s' not constant"),
3475 i
+ 1, opc_len
, str
);
3478 case tic6x_match_wrong_side
:
3479 as_bad (_("operand %u of '%.*s' on wrong side"),
3480 i
+ 1, opc_len
, str
);
3483 case tic6x_match_bad_return
:
3484 as_bad (_("operand %u of '%.*s' not a valid return "
3485 "address register"),
3486 i
+ 1, opc_len
, str
);
3489 case tic6x_match_ctrl_write_only
:
3490 as_bad (_("operand %u of '%.*s' is write-only"),
3491 i
+ 1, opc_len
, str
);
3494 case tic6x_match_ctrl_read_only
:
3495 as_bad (_("operand %u of '%.*s' is read-only"),
3496 i
+ 1, opc_len
, str
);
3499 case tic6x_match_bad_mem
:
3500 as_bad (_("operand %u of '%.*s' not a valid memory "
3502 i
+ 1, opc_len
, str
);
3505 case tic6x_match_bad_address
:
3506 as_bad (_("operand %u of '%.*s' not a valid base "
3507 "address register"),
3508 i
+ 1, opc_len
, str
);
3514 bad_operands
= true;
3522 /* Each operand is OK for some opcode choice, and the number of
3523 operands is valid. Check whether there is an opcode choice
3524 for which all operands are simultaneously valid. */
3526 bool found_match
= false;
3528 for (i
= 0; i
< TIC6X_NUM_PREFER
; i
++)
3529 opc_rank
[i
] = (unsigned int) -1;
3531 min_rank
= TIC6X_NUM_PREFER
- 1;
3534 for (i
= 0; i
< num_matching_opcodes
; i
++)
3537 bool this_matches
= true;
3539 if (!(tic6x_opcode_table
[opcm
[i
]].flags
& TIC6X_FLAG_SPMASK
)
3540 && tic6x_opcode_table
[opcm
[i
]].num_operands
!= num_operands_read
)
3543 for (j
= 0; j
< num_operands_read
; j
++)
3545 tic6x_operand_form f
;
3548 if (tic6x_opcode_table
[opcm
[i
]].flags
& TIC6X_FLAG_SPMASK
)
3550 f
= tic6x_operand_func_unit
;
3555 f
= tic6x_opcode_table
[opcm
[i
]].operand_info
[j
].form
;
3556 rw
= tic6x_opcode_table
[opcm
[i
]].operand_info
[j
].rw
;
3558 if (tic6x_operand_matches_form (&operands
[j
], f
, rw
,
3561 func_unit_data_side
)
3562 != tic6x_match_matches
)
3564 this_matches
= false;
3571 int rank
= TIC6X_PREFER_VAL (tic6x_opcode_table
[opcm
[i
]].flags
);
3573 if (rank
< min_rank
)
3575 if (rank
> max_rank
)
3578 if (opc_rank
[rank
] == (unsigned int) -1)
3581 /* The opcode table should provide a total ordering
3582 for all cases where multiple matches may get
3592 as_bad (_("bad operand combination for '%.*s'"), opc_len
, str
);
3593 bad_operands
= true;
3605 for (try_rank
= max_rank
; try_rank
>= min_rank
; try_rank
--)
3609 if (opc_rank
[try_rank
] == (unsigned int) -1)
3612 opcode_value
= tic6x_try_encode (opcm
[opc_rank
[try_rank
]], operands
,
3613 num_operands_read
, this_line_creg
,
3614 this_line_z
, func_unit_side
,
3615 func_unit_cross
, func_unit_data_side
,
3616 seginfo
->tc_segment_info_data
.sploop_ii
,
3617 &fix_exp
, &fix_pcrel
, &fx_r_type
,
3618 &fix_adda
, &fix_needed
, &encoded_ok
,
3619 try_rank
== min_rank
,
3623 opct
= &tic6x_opcode_table
[opcm
[opc_rank
[try_rank
]]];
3633 if (this_line_parallel
)
3635 insn_frag
= seginfo
->tc_segment_info_data
.execute_packet_frag
;
3636 if (insn_frag
== NULL
)
3638 as_bad (_("parallel instruction not following another instruction"));
3642 if (insn_frag
->fr_fix
>= 32)
3644 as_bad (_("too many instructions in execute packet"));
3648 if (this_insn_label_list
!= NULL
)
3649 as_bad (_("label not at start of execute packet"));
3651 if (opct
->flags
& TIC6X_FLAG_FIRST
)
3652 as_bad (_("'%.*s' instruction not at start of execute packet"),
3655 *seginfo
->tc_segment_info_data
.last_insn_lsb
|= 0x1;
3656 output
= insn_frag
->fr_literal
+ insn_frag
->fr_fix
;
3660 tic6x_label_list
*l
;
3662 seginfo
->tc_segment_info_data
.spmask_addr
= NULL
;
3663 seginfo
->tc_segment_info_data
.func_units_used
= 0;
3665 /* Start a new frag for this execute packet. */
3666 if (frag_now_fix () != 0)
3668 if (frag_now
->fr_type
!= rs_machine_dependent
)
3669 frag_wane (frag_now
);
3674 insn_frag
= seginfo
->tc_segment_info_data
.execute_packet_frag
= frag_now
;
3675 for (l
= this_insn_label_list
; l
; l
= l
->next
)
3677 symbol_set_frag (l
->label
, frag_now
);
3678 S_SET_VALUE (l
->label
, 0);
3679 S_SET_SEGMENT (l
->label
, now_seg
);
3681 tic6x_free_label_list (this_insn_label_list
);
3682 dwarf2_emit_insn (0);
3683 output
= frag_var (rs_machine_dependent
, 32, 32, 0, NULL
, 0, NULL
);
3684 /* This must be the same as the frag to which a pointer was just
3686 if (output
!= insn_frag
->fr_literal
)
3688 insn_frag
->tc_frag_data
.is_insns
= true;
3689 insn_frag
->tc_frag_data
.can_cross_fp_boundary
3690 = tic6x_can_cross_fp_boundary
;
3693 if (func_unit_base
!= tic6x_func_unit_nfu
)
3695 unsigned int func_unit_enc
;
3697 func_unit_enc
= tic6x_encode_spmask (func_unit_base
, func_unit_side
);
3699 if (seginfo
->tc_segment_info_data
.func_units_used
& func_unit_enc
)
3700 as_bad (_("functional unit already used in this execute packet"));
3702 seginfo
->tc_segment_info_data
.func_units_used
|= func_unit_enc
;
3705 if (opct
->flags
& TIC6X_FLAG_SPLOOP
)
3707 if (seginfo
->tc_segment_info_data
.sploop_ii
)
3708 as_bad (_("nested software pipelined loop"));
3709 if (num_operands_read
!= 1
3710 || operands
[0].form
!= TIC6X_OP_EXP
3711 || operands
[0].value
.exp
.X_op
!= O_constant
)
3713 seginfo
->tc_segment_info_data
.sploop_ii
3714 = operands
[0].value
.exp
.X_add_number
;
3716 else if (opct
->flags
& TIC6X_FLAG_SPKERNEL
)
3718 if (!seginfo
->tc_segment_info_data
.sploop_ii
)
3719 as_bad (_("'%.*s' instruction not in a software pipelined loop"),
3721 seginfo
->tc_segment_info_data
.sploop_ii
= 0;
3724 if (this_line_spmask
)
3726 if (seginfo
->tc_segment_info_data
.spmask_addr
== NULL
)
3727 as_bad (_("'||^' without previous SPMASK"));
3728 else if (func_unit_base
== tic6x_func_unit_nfu
)
3729 as_bad (_("cannot mask instruction using no functional unit"));
3732 unsigned int spmask_opcode
;
3733 unsigned int mask_bit
;
3736 = md_chars_to_number (seginfo
->tc_segment_info_data
.spmask_addr
,
3738 mask_bit
= tic6x_encode_spmask (func_unit_base
, func_unit_side
);
3740 if (spmask_opcode
& mask_bit
)
3741 as_bad (_("functional unit already masked"));
3742 spmask_opcode
|= mask_bit
;
3743 md_number_to_chars (seginfo
->tc_segment_info_data
.spmask_addr
,
3748 record_alignment (now_seg
, 5);
3749 md_number_to_chars (output
, opcode_value
, 4);
3751 tic6x_fix_new_exp (insn_frag
, output
- insn_frag
->fr_literal
, 4, fix_exp
,
3752 fix_pcrel
, fx_r_type
, fix_adda
);
3753 insn_frag
->fr_fix
+= 4;
3754 insn_frag
->fr_var
-= 4;
3755 seginfo
->tc_segment_info_data
.last_insn_lsb
3756 = (target_big_endian
? output
+ 3 : output
);
3757 if (opct
->flags
& TIC6X_FLAG_SPMASK
)
3758 seginfo
->tc_segment_info_data
.spmask_addr
= output
;
3761 /* Modify NEWVAL (32-bit) by inserting VALUE, shifted right by SHIFT
3762 and the least significant BITS bits taken, at position POS. */
3763 #define MODIFY_VALUE(NEWVAL, VALUE, SHIFT, POS, BITS) \
3765 (NEWVAL) &= 0xffffffffU & ~(((1U << (BITS)) - 1) << (POS)); \
3766 (NEWVAL) |= (((VALUE) >> (SHIFT)) & ((1U << (BITS)) - 1)) << (POS); \
3769 /* Apply a fixup to the object file. */
3772 md_apply_fix (fixS
*fixP
, valueT
*valP
, segT seg ATTRIBUTE_UNUSED
)
3774 valueT value
= *valP
;
3775 char *buf
= fixP
->fx_where
+ fixP
->fx_frag
->fr_literal
;
3777 value
= SEXT (value
);
3780 fixP
->fx_offset
= SEXT (fixP
->fx_offset
);
3782 if (fixP
->fx_addsy
== NULL
&& fixP
->fx_pcrel
== 0)
3785 /* We do our own overflow checks. */
3786 fixP
->fx_no_overflow
= 1;
3788 switch (fixP
->fx_r_type
)
3790 case BFD_RELOC_NONE
:
3791 case BFD_RELOC_C6000_EHTYPE
:
3792 /* Force output to the object file. */
3797 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3798 md_number_to_chars (buf
, value
, 4);
3802 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3804 if (value
+ 0x8000 > 0xffff + 0x8000)
3805 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3806 _("value too large for 2-byte field"));
3807 md_number_to_chars (buf
, value
, 2);
3812 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3814 if (value
+ 0x80 > 0xff + 0x80)
3815 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3816 _("value too large for 1-byte field"));
3821 case BFD_RELOC_C6000_ABS_S16
:
3822 case BFD_RELOC_C6000_ABS_L16
:
3823 case BFD_RELOC_C6000_SBR_S16
:
3824 case BFD_RELOC_C6000_SBR_L16_B
:
3825 case BFD_RELOC_C6000_SBR_L16_H
:
3826 case BFD_RELOC_C6000_SBR_L16_W
:
3827 case BFD_RELOC_C6000_SBR_GOT_L16_W
:
3828 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3830 valueT newval
= md_chars_to_number (buf
, 4);
3833 switch (fixP
->fx_r_type
)
3835 case BFD_RELOC_C6000_SBR_L16_H
:
3839 case BFD_RELOC_C6000_SBR_L16_W
:
3840 case BFD_RELOC_C6000_SBR_GOT_L16_W
:
3849 MODIFY_VALUE (newval
, value
, shift
, 7, 16);
3850 if ((value
+ 0x8000 > 0x7fff + 0x8000)
3851 && (fixP
->fx_r_type
== BFD_RELOC_C6000_ABS_S16
3852 || fixP
->fx_r_type
== BFD_RELOC_C6000_SBR_S16
))
3853 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3854 _("immediate offset out of range"));
3856 md_number_to_chars (buf
, newval
, 4);
3859 && fixP
->fx_r_type
!= BFD_RELOC_C6000_ABS_S16
3860 && fixP
->fx_r_type
!= BFD_RELOC_C6000_ABS_L16
)
3864 case BFD_RELOC_C6000_ABS_H16
:
3865 case BFD_RELOC_C6000_SBR_H16_B
:
3866 case BFD_RELOC_C6000_SBR_H16_H
:
3867 case BFD_RELOC_C6000_SBR_H16_W
:
3868 case BFD_RELOC_C6000_SBR_GOT_H16_W
:
3869 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3871 valueT newval
= md_chars_to_number (buf
, 4);
3874 switch (fixP
->fx_r_type
)
3876 case BFD_RELOC_C6000_SBR_H16_H
:
3880 case BFD_RELOC_C6000_SBR_H16_W
:
3881 case BFD_RELOC_C6000_SBR_GOT_H16_W
:
3890 MODIFY_VALUE (newval
, value
, shift
, 7, 16);
3892 md_number_to_chars (buf
, newval
, 4);
3894 if (fixP
->fx_done
&& fixP
->fx_r_type
!= BFD_RELOC_C6000_ABS_H16
)
3898 case BFD_RELOC_C6000_PCR_H16
:
3899 case BFD_RELOC_C6000_PCR_L16
:
3900 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3902 valueT newval
= md_chars_to_number (buf
, 4);
3903 int shift
= fixP
->fx_r_type
== BFD_RELOC_C6000_PCR_H16
? 16 : 0;
3905 MODIFY_VALUE (newval
, value
, shift
, 7, 16);
3907 md_number_to_chars (buf
, newval
, 4);
3911 case BFD_RELOC_C6000_SBR_U15_B
:
3912 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3914 valueT newval
= md_chars_to_number (buf
, 4);
3916 MODIFY_VALUE (newval
, value
, 0, 8, 15);
3918 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3919 _("immediate offset out of range"));
3921 md_number_to_chars (buf
, newval
, 4);
3925 case BFD_RELOC_C6000_SBR_U15_H
:
3926 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3928 valueT newval
= md_chars_to_number (buf
, 4);
3930 /* Constant ADDA operands, processed as constant when the
3931 instruction is parsed, are encoded as-is rather than
3932 shifted. If the operand of an ADDA instruction is now
3933 constant (for example, the difference between two labels
3934 found after the instruction), ensure it is encoded the
3935 same way it would have been if the constant value had
3936 been known when the instruction was parsed. */
3937 if (fixP
->tc_fix_data
.fix_adda
&& fixP
->fx_done
)
3940 MODIFY_VALUE (newval
, value
, 1, 8, 15);
3942 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3943 _("immediate offset not 2-byte-aligned"));
3945 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3946 _("immediate offset out of range"));
3948 md_number_to_chars (buf
, newval
, 4);
3952 case BFD_RELOC_C6000_SBR_U15_W
:
3953 case BFD_RELOC_C6000_SBR_GOT_U15_W
:
3954 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3956 valueT newval
= md_chars_to_number (buf
, 4);
3958 /* Constant ADDA operands, processed as constant when the
3959 instruction is parsed, are encoded as-is rather than
3960 shifted. If the operand of an ADDA instruction is now
3961 constant (for example, the difference between two labels
3962 found after the instruction), ensure it is encoded the
3963 same way it would have been if the constant value had
3964 been known when the instruction was parsed. */
3965 if (fixP
->tc_fix_data
.fix_adda
&& fixP
->fx_done
)
3968 MODIFY_VALUE (newval
, value
, 2, 8, 15);
3970 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3971 _("immediate offset not 4-byte-aligned"));
3972 if (value
> 0x1fffc)
3973 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3974 _("immediate offset out of range"));
3976 md_number_to_chars (buf
, newval
, 4);
3978 if (fixP
->fx_done
&& fixP
->fx_r_type
!= BFD_RELOC_C6000_SBR_U15_W
)
3982 case BFD_RELOC_C6000_DSBT_INDEX
:
3984 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3985 _("addend used with $DSBT_INDEX"));
3990 case BFD_RELOC_C6000_PCR_S21
:
3991 if (fixP
->fx_done
|| !seg
->use_rela_p
)
3993 valueT newval
= md_chars_to_number (buf
, 4);
3995 MODIFY_VALUE (newval
, value
, 2, 7, 21);
3998 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
3999 _("PC-relative offset not 4-byte-aligned"));
4000 if (value
+ 0x400000 > 0x3ffffc + 0x400000)
4001 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4002 _("PC-relative offset out of range"));
4004 md_number_to_chars (buf
, newval
, 4);
4008 case BFD_RELOC_C6000_PCR_S12
:
4009 if (fixP
->fx_done
|| !seg
->use_rela_p
)
4011 valueT newval
= md_chars_to_number (buf
, 4);
4013 MODIFY_VALUE (newval
, value
, 2, 16, 12);
4016 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4017 _("PC-relative offset not 4-byte-aligned"));
4018 if (value
+ 0x2000 > 0x1ffc + 0x2000)
4019 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4020 _("PC-relative offset out of range"));
4022 md_number_to_chars (buf
, newval
, 4);
4026 case BFD_RELOC_C6000_PCR_S10
:
4027 if (fixP
->fx_done
|| !seg
->use_rela_p
)
4029 valueT newval
= md_chars_to_number (buf
, 4);
4031 MODIFY_VALUE (newval
, value
, 2, 13, 10);
4034 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4035 _("PC-relative offset not 4-byte-aligned"));
4036 if (value
+ 0x800 > 0x7fc + 0x800)
4037 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4038 _("PC-relative offset out of range"));
4040 md_number_to_chars (buf
, newval
, 4);
4044 case BFD_RELOC_C6000_PCR_S7
:
4045 if (fixP
->fx_done
|| !seg
->use_rela_p
)
4047 valueT newval
= md_chars_to_number (buf
, 4);
4049 MODIFY_VALUE (newval
, value
, 2, 16, 7);
4052 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4053 _("PC-relative offset not 4-byte-aligned"));
4054 if (value
+ 0x100 > 0xfc + 0x100)
4055 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
4056 _("PC-relative offset out of range"));
4058 md_number_to_chars (buf
, newval
, 4);
4062 case BFD_RELOC_C6000_PREL31
:
4063 /* Force output to the object file. */
4072 /* Convert a floating-point number to target (IEEE) format. */
4075 md_atof (int type
, char *litP
, int *sizeP
)
4077 return ieee_md_atof (type
, litP
, sizeP
, target_big_endian
);
4080 /* Adjust the frags in SECTION (see tic6x_md_finish). */
4083 tic6x_adjust_section (bfd
*abfd ATTRIBUTE_UNUSED
, segT section
,
4084 void *dummy ATTRIBUTE_UNUSED
)
4086 segment_info_type
*info
;
4089 bool have_code
= false;
4090 bool have_non_code
= false;
4092 info
= seg_info (section
);
4096 for (frchp
= info
->frchainP
; frchp
; frchp
= frchp
->frch_next
)
4097 for (fragp
= frchp
->frch_root
; fragp
; fragp
= fragp
->fr_next
)
4098 switch (fragp
->fr_type
)
4100 case rs_machine_dependent
:
4101 if (fragp
->tc_frag_data
.is_insns
)
4107 if (fragp
->fr_fix
> 0)
4108 have_non_code
= true;
4112 have_non_code
= true;
4116 /* Process alignment requirements in a code-only section. */
4117 if (have_code
&& !have_non_code
)
4119 /* If we need to insert an odd number of instructions to meet an
4120 alignment requirement, there must have been an odd number of
4121 instructions since the last 8-byte-aligned execute packet
4122 boundary. So there must have been an execute packet with an
4123 odd number (and so a number fewer than 8) of instructions
4124 into which we can insert a NOP without breaking any previous
4127 If then we need to insert a number 2 mod 4 of instructions,
4128 the number of instructions since the last 16-byte-aligned
4129 execute packet boundary must be 2 mod 4. So between that
4130 boundary and the following 8-byte-aligned boundary there must
4131 either be at least one execute packet with 2-mod-4
4132 instructions, or at least two with an odd number of
4133 instructions; again, greedily inserting NOPs as soon as
4134 possible suffices to meet the alignment requirement.
4136 If then we need to insert 4 instructions, we look between the
4137 last 32-byte-aligned boundary and the following
4138 16-byte-aligned boundary. The sizes of the execute packets
4139 in this range total 4 instructions mod 8, so again there is
4140 room for greedy insertion of NOPs to meet the alignment
4141 requirement, and before any intermediate point with 8-byte
4142 (2-instruction) alignment requirement the sizes of execute
4143 packets (and so the room for NOPs) will total 2 instructions
4144 mod 4 so greedy insertion will not break such alignments.
4146 So we can always meet these alignment requirements by
4147 inserting NOPs in parallel with existing execute packets, and
4148 by induction the approach described above inserts the minimum
4149 number of such NOPs. */
4151 /* The number of NOPs we are currently looking to insert, if we
4152 have gone back to insert NOPs. */
4153 unsigned int want_insert
= 0;
4155 /* Out of that number, the number inserted so far in the current
4156 stage of the above algorithm. */
4157 unsigned int want_insert_done_so_far
= 0;
4159 /* The position mod 32 at the start of the current frag. */
4160 unsigned int pos
= 0;
4162 /* The locations in the frag chain of the most recent frags at
4163 the start of which there is the given alignment. */
4164 frchainS
*frchp_last32
, *frchp_last16
, *frchp_last8
;
4165 fragS
*fragp_last32
, *fragp_last16
, *fragp_last8
;
4166 unsigned int pos_last32
, pos_last16
, pos_last8
;
4168 frchp_last32
= frchp_last16
= frchp_last8
= info
->frchainP
;
4169 fragp_last32
= fragp_last16
= fragp_last8
= info
->frchainP
->frch_root
;
4170 pos_last32
= pos_last16
= pos_last8
= 0;
4172 for (frchp
= info
->frchainP
; frchp
; frchp
= frchp
->frch_next
)
4173 for (fragp
= frchp
->frch_root
; fragp
; fragp
= fragp
->fr_next
)
4176 bool go_back
= false;
4177 frchainS
*frchp_next
;
4180 if (fragp
->fr_type
!= rs_machine_dependent
)
4183 if (fragp
->tc_frag_data
.is_insns
4184 && pos
+ fragp
->fr_fix
> 32
4185 && !fragp
->tc_frag_data
.can_cross_fp_boundary
)
4187 /* As described above, we should always have met an
4188 alignment requirement by the time we come back to
4195 want_insert
= (32 - pos
) >> 2;
4196 if (want_insert
> 7)
4198 want_insert_done_so_far
= 0;
4202 if (!fragp
->tc_frag_data
.is_insns
)
4204 unsigned int would_insert_bytes
;
4206 if (!(pos
& ((1 << fragp
->fr_offset
) - 1)))
4207 /* This alignment requirement is already met. */
4210 /* As described above, we should always have met an
4211 alignment requirement by the time we come back to
4216 /* We may not be able to meet this requirement within
4217 the given number of characters. */
4219 = ((1 << fragp
->fr_offset
)
4220 - (pos
& ((1 << fragp
->fr_offset
) - 1)));
4222 if (fragp
->fr_subtype
!= 0
4223 && would_insert_bytes
> fragp
->fr_subtype
)
4226 /* An unmet alignment must be 8, 16 or 32 bytes;
4227 smaller ones must always be met within code-only
4228 sections and larger ones cause the section not to
4230 if (fragp
->fr_offset
!= 3
4231 && fragp
->fr_offset
!= 4
4232 && fragp
->fr_offset
!= 5)
4235 if (would_insert_bytes
& 3)
4237 want_insert
= would_insert_bytes
>> 2;
4238 if (want_insert
> 7)
4240 want_insert_done_so_far
= 0;
4243 else if (want_insert
&& !go_back
)
4245 unsigned int num_insns
= fragp
->fr_fix
>> 2;
4246 unsigned int max_poss_nops
= 8 - num_insns
;
4250 unsigned int cur_want_nops
, max_want_nops
, do_nops
, i
;
4252 if (want_insert
& 1)
4254 else if (want_insert
& 2)
4256 else if (want_insert
& 4)
4261 max_want_nops
= cur_want_nops
- want_insert_done_so_far
;
4263 do_nops
= (max_poss_nops
< max_want_nops
4266 for (i
= 0; i
< do_nops
; i
++)
4268 md_number_to_chars (fragp
->fr_literal
+ fragp
->fr_fix
,
4270 if (target_big_endian
)
4271 fragp
->fr_literal
[fragp
->fr_fix
- 1] |= 0x1;
4273 fragp
->fr_literal
[fragp
->fr_fix
- 4] |= 0x1;
4277 want_insert_done_so_far
+= do_nops
;
4278 if (want_insert_done_so_far
== cur_want_nops
)
4280 want_insert
-= want_insert_done_so_far
;
4281 want_insert_done_so_far
= 0;
4289 if (want_insert
& 1)
4291 frchp
= frchp_last8
;
4292 fragp
= fragp_last8
;
4295 else if (want_insert
& 2)
4297 frchp
= frchp_last8
= frchp_last16
;
4298 fragp
= fragp_last8
= fragp_last16
;
4299 pos
= pos_last8
= pos_last16
;
4301 else if (want_insert
& 4)
4303 frchp
= frchp_last8
= frchp_last16
= frchp_last32
;
4304 fragp
= fragp_last8
= fragp_last16
= fragp_last32
;
4305 pos
= pos_last8
= pos_last16
= pos_last32
;
4313 /* Update current position for moving past a code
4315 pos
+= fragp
->fr_fix
;
4318 fragp_next
= fragp
->fr_next
;
4319 if (fragp_next
== NULL
)
4321 frchp_next
= frchp
->frch_next
;
4322 if (frchp_next
!= NULL
)
4323 fragp_next
= frchp_next
->frch_root
;
4327 frchp_last8
= frchp_next
;
4328 fragp_last8
= fragp_next
;
4333 frchp_last16
= frchp_next
;
4334 fragp_last16
= fragp_next
;
4339 frchp_last32
= frchp_next
;
4340 fragp_last32
= fragp_next
;
4346 /* Now convert the machine-dependent frags to machine-independent
4348 for (frchp
= info
->frchainP
; frchp
; frchp
= frchp
->frch_next
)
4349 for (fragp
= frchp
->frch_root
; fragp
; fragp
= fragp
->fr_next
)
4351 if (fragp
->fr_type
== rs_machine_dependent
)
4353 if (fragp
->tc_frag_data
.is_insns
)
4357 fragp
->fr_type
= rs_align_code
;
4359 *fragp
->fr_literal
= 0;
4365 /* Initialize the machine-dependent parts of a frag. */
4368 tic6x_frag_init (fragS
*fragp
)
4370 fragp
->tc_frag_data
.is_insns
= false;
4371 fragp
->tc_frag_data
.can_cross_fp_boundary
= false;
4374 /* Set an attribute if it has not already been set by the user. */
4377 tic6x_set_attribute_int (int tag
, int value
)
4380 || tag
>= NUM_KNOWN_OBJ_ATTRIBUTES
)
4382 if (!tic6x_attributes_set_explicitly
[tag
])
4383 if (!bfd_elf_add_proc_attr_int (stdoutput
, tag
, value
))
4384 as_fatal (_("error adding attribute: %s"),
4385 bfd_errmsg (bfd_get_error ()));
4388 /* Set object attributes deduced from the input file and command line
4389 rather than given explicitly. */
4391 tic6x_set_attributes (void)
4393 if (tic6x_arch_attribute
== C6XABI_Tag_ISA_none
)
4394 tic6x_arch_attribute
= C6XABI_Tag_ISA_C674X
;
4396 tic6x_set_attribute_int (Tag_ISA
, tic6x_arch_attribute
);
4397 tic6x_set_attribute_int (Tag_ABI_DSBT
, tic6x_dsbt
);
4398 tic6x_set_attribute_int (Tag_ABI_PID
, tic6x_pid
);
4399 tic6x_set_attribute_int (Tag_ABI_PIC
, tic6x_pic
);
4402 /* Do machine-dependent manipulations of the frag chains after all
4403 input has been read and before the machine-independent sizing and
4407 tic6x_md_finish (void)
4409 /* Set object attributes at this point if not explicitly set. */
4410 tic6x_set_attributes ();
4412 /* Meeting alignment requirements may require inserting NOPs in
4413 parallel in execute packets earlier in the segment. Future
4414 16-bit instruction generation involves whole-segment optimization
4415 to determine the best choice and ordering of 32-bit or 16-bit
4416 instructions. This doesn't fit will in the general relaxation
4417 framework, so handle alignment and 16-bit instruction generation
4419 bfd_map_over_sections (stdoutput
, tic6x_adjust_section
, NULL
);
4422 /* No machine-dependent frags at this stage; all converted in
4426 md_convert_frag (bfd
*abfd ATTRIBUTE_UNUSED
, segT asec ATTRIBUTE_UNUSED
,
4427 fragS
*fragp ATTRIBUTE_UNUSED
)
4432 /* No machine-dependent frags at this stage; all converted in
4436 md_estimate_size_before_relax (fragS
*fragp ATTRIBUTE_UNUSED
,
4437 segT seg ATTRIBUTE_UNUSED
)
4442 /* Put a number into target byte order. */
4445 md_number_to_chars (char *buf
, valueT val
, int n
)
4447 if (target_big_endian
)
4448 number_to_chars_bigendian (buf
, val
, n
);
4450 number_to_chars_littleendian (buf
, val
, n
);
4453 /* Machine-dependent operand parsing not currently needed. */
4456 md_operand (expressionS
*op ATTRIBUTE_UNUSED
)
4460 /* PC-relative operands are relative to the start of the fetch
4464 tic6x_pcrel_from_section (fixS
*fixp
, segT sec
)
4466 if (fixp
->fx_addsy
!= NULL
4467 && (!S_IS_DEFINED (fixp
->fx_addsy
)
4468 || S_GET_SEGMENT (fixp
->fx_addsy
) != sec
))
4470 return (fixp
->fx_where
+ fixp
->fx_frag
->fr_address
) & ~(long) 0x1f;
4473 /* Round up a section size to the appropriate boundary. */
4476 md_section_align (segT segment ATTRIBUTE_UNUSED
,
4479 /* Round up section sizes to ensure that text sections consist of
4480 whole fetch packets. */
4481 int align
= bfd_section_alignment (segment
);
4482 return ((size
+ (1 << align
) - 1) & (-((valueT
) 1 << align
)));
4485 /* No special undefined symbol handling needed for now. */
4488 md_undefined_symbol (char *name ATTRIBUTE_UNUSED
)
4493 /* Translate internal representation of relocation info to BFD target
4497 tc_gen_reloc (asection
*section ATTRIBUTE_UNUSED
, fixS
*fixp
)
4501 bfd_reloc_code_real_type r_type
;
4503 reloc
= notes_alloc (sizeof (arelent
));
4504 reloc
->sym_ptr_ptr
= notes_alloc (sizeof (asymbol
*));
4505 symbol
= symbol_get_bfdsym (fixp
->fx_addsy
);
4506 *reloc
->sym_ptr_ptr
= symbol
;
4507 reloc
->address
= fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
4508 reloc
->addend
= (tic6x_generate_rela
? fixp
->fx_offset
: 0);
4509 r_type
= fixp
->fx_r_type
;
4510 reloc
->howto
= bfd_reloc_type_lookup (stdoutput
, r_type
);
4512 if (reloc
->howto
== NULL
)
4514 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
4515 _("Cannot represent relocation type %s"),
4516 bfd_get_reloc_code_name (r_type
));
4520 /* Correct for adjustments bfd_install_relocation will make. */
4521 if (reloc
->howto
->pcrel_offset
&& reloc
->howto
->partial_inplace
)
4523 reloc
->addend
+= reloc
->address
;
4524 if (!bfd_is_com_section (bfd_asymbol_section (symbol
)))
4525 reloc
->addend
-= symbol
->value
;
4527 if (r_type
== BFD_RELOC_C6000_PCR_H16
4528 || r_type
== BFD_RELOC_C6000_PCR_L16
)
4530 symbolS
*t
= fixp
->tc_fix_data
.fix_subsy
;
4531 segT sub_symbol_segment
;
4533 resolve_symbol_value (t
);
4534 sub_symbol_segment
= S_GET_SEGMENT (t
);
4535 if (sub_symbol_segment
== undefined_section
)
4536 as_bad_where (fixp
->fx_file
, fixp
->fx_line
,
4537 _("undefined symbol %s in PCR relocation"),
4541 reloc
->addend
= reloc
->address
& ~0x1F;
4542 reloc
->addend
-= S_GET_VALUE (t
);
4548 /* Convert REGNAME to a DWARF-2 register number. */
4551 tic6x_regname_to_dw2regnum (char *regname
)
4557 reg_ok
= tic6x_parse_register (&rq
, ®
);
4564 case 1: /* A regs. */
4567 else if (reg
.num
< 32)
4568 return (reg
.num
- 16) + 37;
4572 case 2: /* B regs. */
4574 return reg
.num
+ 16;
4575 else if (reg
.num
< 32)
4576 return (reg
.num
- 16) + 53;
4585 /* Initialize the DWARF-2 unwind information for this procedure. */
4588 tic6x_frame_initial_instructions (void)
4590 /* CFA is initial stack pointer (B15). */
4591 cfi_add_CFA_def_cfa (31, 0);
4594 /* Start an exception table entry. If idx is nonzero this is an index table
4598 tic6x_start_unwind_section (const segT text_seg
, int idx
)
4600 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4601 const char * text_name
;
4602 const char * prefix
;
4603 const char * prefix_once
;
4604 struct elf_section_match match
;
4608 size_t sec_name_len
;
4615 prefix
= ELF_STRING_C6000_unwind
;
4616 prefix_once
= ELF_STRING_C6000_unwind_once
;
4617 type
= SHT_C6000_UNWIND
;
4621 prefix
= ELF_STRING_C6000_unwind_info
;
4622 prefix_once
= ELF_STRING_C6000_unwind_info_once
;
4623 type
= SHT_PROGBITS
;
4626 text_name
= segment_name (text_seg
);
4627 if (streq (text_name
, ".text"))
4630 if (startswith (text_name
, ".gnu.linkonce.t."))
4632 prefix
= prefix_once
;
4633 text_name
+= strlen (".gnu.linkonce.t.");
4636 prefix_len
= strlen (prefix
);
4637 text_len
= strlen (text_name
);
4638 sec_name_len
= prefix_len
+ text_len
;
4639 sec_name
= XNEWVEC (char, sec_name_len
+ 1);
4640 memcpy (sec_name
, prefix
, prefix_len
);
4641 memcpy (sec_name
+ prefix_len
, text_name
, text_len
);
4642 sec_name
[prefix_len
+ text_len
] = '\0';
4646 memset (&match
, 0, sizeof (match
));
4648 /* Handle COMDAT group. */
4649 if (prefix
!= prefix_once
&& (text_seg
->flags
& SEC_LINK_ONCE
) != 0)
4651 match
.group_name
= elf_group_name (text_seg
);
4652 if (match
.group_name
== NULL
)
4654 as_bad (_("group section `%s' has no group signature"),
4655 segment_name (text_seg
));
4656 ignore_rest_of_line ();
4663 obj_elf_change_section (sec_name
, type
, flags
, 0, &match
,
4666 /* Set the section link for index tables. */
4668 elf_linked_to_section (now_seg
) = text_seg
;
4670 seg_info (now_seg
)->tc_segment_info_data
.text_unwind
= unwind
;
4675 tic6x_unwind_frame_regs
[TIC6X_NUM_UNWIND_REGS
] =
4676 /* A15 B15 B14 B13 B12 B11 B10 B3 A14 A13 A12 A11 A10. */
4677 { 15, 31, 30, 29, 28, 27, 26, 19, 14, 13, 12, 11, 10 };
4679 /* Register save offsets for __c6xabi_push_rts. */
4681 tic6x_pop_rts_offset_little
[TIC6X_NUM_UNWIND_REGS
] =
4682 /* A15 B15 B14 B13 B12 B11 B10 B3 A14 A13 A12 A11 A10. */
4683 { -1, 1, 0, -3, -4, -7, -8,-11, -2, -5, -6, -9,-10};
4686 tic6x_pop_rts_offset_big
[TIC6X_NUM_UNWIND_REGS
] =
4687 /* A15 B15 B14 B13 B12 B11 B10 B3 A14 A13 A12 A11 A10. */
4688 { -2, 1, 0, -4, -3, -8, -7,-12, -1, -6, -5,-10, -9};
4690 /* Map from dwarf register number to unwind frame register number. */
4692 tic6x_unwind_reg_from_dwarf (int dwarf
)
4696 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
4698 if (tic6x_unwind_frame_regs
[reg
] == dwarf
)
4705 /* Unwinding bytecode definitions. */
4706 #define UNWIND_OP_ADD_SP 0x00
4707 #define UNWIND_OP_ADD_SP2 0xd2
4708 #define UNWIND_OP2_POP 0x8000
4709 #define UNWIND_OP2_POP_COMPACT 0xa000
4710 #define UNWIND_OP_POP_REG 0xc0
4711 #define UNWIND_OP_MV_FP 0xd0
4712 #define UNWIND_OP_POP_RTS 0xd1
4713 #define UNWIND_OP_RET 0xe0
4715 /* Maximum stack adjustment for __c6xabi_unwind_cpp_pr3/4 */
4716 #define MAX_COMPACT_SP_OFFSET (0x7f << 3)
4719 tic6x_flush_unwind_word (valueT data
)
4721 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4724 /* Create EXTAB entry if it does not exist. */
4725 if (unwind
->table_entry
== NULL
)
4727 tic6x_start_unwind_section (unwind
->saved_seg
, 0);
4728 frag_align (2, 0, 0);
4729 record_alignment (now_seg
, 2);
4730 unwind
->table_entry
= expr_build_dot ();
4731 ptr
= frag_more (4);
4732 unwind
->frag_start
= ptr
;
4736 /* Append additional word of data. */
4737 ptr
= frag_more (4);
4740 md_number_to_chars (ptr
, data
, 4);
4743 /* Add a single byte of unwinding data. */
4746 tic6x_unwind_byte (int byte
)
4748 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4750 unwind
->data_bytes
++;
4751 /* Only flush the first word after we know multiple words are required. */
4752 if (unwind
->data_bytes
== 5)
4754 if (unwind
->personality_index
== -1)
4756 /* At this point we know we are too big for pr0. */
4757 unwind
->personality_index
= 1;
4758 tic6x_flush_unwind_word (0x81000000 | ((unwind
->data
>> 8) & 0xffff));
4759 unwind
->data
= ((unwind
->data
& 0xff) << 8) | byte
;
4760 unwind
->data_bytes
++;
4764 tic6x_flush_unwind_word (unwind
->data
);
4765 unwind
->data
= byte
;
4770 unwind
->data
= (unwind
->data
<< 8) | byte
;
4771 if ((unwind
->data_bytes
& 3) == 0 && unwind
->data_bytes
> 4)
4773 tic6x_flush_unwind_word (unwind
->data
);
4779 /* Add a two-byte unwinding opcode. */
4781 tic6x_unwind_2byte (int bytes
)
4783 tic6x_unwind_byte (bytes
>> 8);
4784 tic6x_unwind_byte (bytes
& 0xff);
4788 tic6x_unwind_uleb (offsetT offset
)
4790 while (offset
> 0x7f)
4792 tic6x_unwind_byte ((offset
& 0x7f) | 0x80);
4795 tic6x_unwind_byte (offset
);
4799 tic6x_cfi_startproc (void)
4801 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4803 unwind
->personality_index
= -1;
4804 unwind
->personality_routine
= NULL
;
4805 if (unwind
->table_entry
)
4806 as_bad (_("missing .endp before .cfi_startproc"));
4808 unwind
->table_entry
= NULL
;
4809 unwind
->data_bytes
= -1;
4813 tic6x_output_exidx_entry (void)
4817 unsigned int marked_pr_dependency
;
4820 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4823 old_subseg
= now_subseg
;
4825 /* Add index table entry. This is two words. */
4826 tic6x_start_unwind_section (unwind
->saved_seg
, 1);
4827 frag_align (2, 0, 0);
4828 record_alignment (now_seg
, 2);
4830 ptr
= frag_more (8);
4832 where
= frag_now_fix () - 8;
4834 /* Self relative offset of the function start. */
4835 fix_new (frag_now
, where
, 4, unwind
->function_start
, 0, 1,
4836 BFD_RELOC_C6000_PREL31
);
4838 /* Indicate dependency on ABI-defined personality routines to the
4839 linker, if it hasn't been done already. */
4840 marked_pr_dependency
4841 = seg_info (now_seg
)->tc_segment_info_data
.marked_pr_dependency
;
4842 if (unwind
->personality_index
>= 0 && unwind
->personality_index
< 5
4843 && !(marked_pr_dependency
& (1 << unwind
->personality_index
)))
4845 static const char *const name
[] =
4847 "__c6xabi_unwind_cpp_pr0",
4848 "__c6xabi_unwind_cpp_pr1",
4849 "__c6xabi_unwind_cpp_pr2",
4850 "__c6xabi_unwind_cpp_pr3",
4851 "__c6xabi_unwind_cpp_pr4"
4853 symbolS
*pr
= symbol_find_or_make (name
[unwind
->personality_index
]);
4854 fix_new (frag_now
, where
, 0, pr
, 0, 1, BFD_RELOC_NONE
);
4855 seg_info (now_seg
)->tc_segment_info_data
.marked_pr_dependency
4856 |= 1 << unwind
->personality_index
;
4859 if (unwind
->table_entry
)
4861 /* Self relative offset of the table entry. */
4862 fix_new (frag_now
, where
+ 4, 4, unwind
->table_entry
, 0, 1,
4863 BFD_RELOC_C6000_PREL31
);
4867 /* Inline exception table entry. */
4868 md_number_to_chars (ptr
+ 4, unwind
->data
, 4);
4871 /* Restore the original section. */
4872 subseg_set (old_seg
, old_subseg
);
4876 tic6x_output_unwinding (bool need_extab
)
4878 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
4879 unsigned safe_mask
= unwind
->safe_mask
;
4880 unsigned compact_mask
= unwind
->compact_mask
;
4881 unsigned reg_saved_mask
= unwind
->reg_saved_mask
;
4882 offsetT cfa_offset
= unwind
->cfa_offset
;
4886 if (unwind
->personality_index
== -2)
4888 /* Function can not be unwound. */
4890 tic6x_output_exidx_entry ();
4894 if (unwind
->personality_index
== -1 && unwind
->personality_routine
== NULL
)
4896 /* Auto-select a personality routine if none specified. */
4897 if (reg_saved_mask
|| cfa_offset
>= MAX_COMPACT_SP_OFFSET
)
4898 unwind
->personality_index
= -1;
4900 unwind
->personality_index
= 3;
4902 unwind
->personality_index
= 4;
4905 /* Calculate unwinding opcodes, and emit to EXTAB if necessary. */
4906 unwind
->table_entry
= NULL
;
4907 if (unwind
->personality_index
== 3 || unwind
->personality_index
== 4)
4909 if (cfa_offset
>= MAX_COMPACT_SP_OFFSET
)
4911 as_bad (_("stack pointer offset too large for personality routine"));
4915 || (unwind
->personality_index
== 3 && compact_mask
!= 0)
4916 || (unwind
->personality_index
== 4 && safe_mask
!= 0))
4918 as_bad (_("stack frame layout does not match personality routine"));
4922 unwind
->data
= (1u << 31) | (unwind
->personality_index
<< 24);
4923 if (unwind
->cfa_reg
== 15)
4924 unwind
->data
|= 0x7f << 17;
4926 unwind
->data
|= cfa_offset
<< (17 - 3);
4928 if (unwind
->personality_index
== 3)
4929 unwind
->data
|= safe_mask
<< 4;
4931 unwind
->data
|= compact_mask
<< 4;
4932 unwind
->data
|= unwind
->return_reg
;
4933 unwind
->data_bytes
= 4;
4937 if (unwind
->personality_routine
)
4940 unwind
->data_bytes
= 5;
4941 tic6x_flush_unwind_word (0);
4942 /* First word is personality routine. */
4943 where
= frag_now_fix () - 4;
4944 fix_new (frag_now
, where
, 4, unwind
->personality_routine
, 0, 1,
4945 BFD_RELOC_C6000_PREL31
);
4947 else if (unwind
->personality_index
> 0)
4949 unwind
->data
= 0x8000 | (unwind
->personality_index
<< 8);
4950 unwind
->data_bytes
= 2;
4952 else /* pr0 or undecided */
4954 unwind
->data
= 0x80;
4955 unwind
->data_bytes
= 1;
4958 if (unwind
->return_reg
!= UNWIND_B3
)
4960 tic6x_unwind_byte (UNWIND_OP_RET
| unwind
->return_reg
);
4963 if (unwind
->cfa_reg
== 15)
4965 tic6x_unwind_byte (UNWIND_OP_MV_FP
);
4967 else if (cfa_offset
!= 0)
4970 if (cfa_offset
> 0x80)
4972 tic6x_unwind_byte (UNWIND_OP_ADD_SP2
);
4973 tic6x_unwind_uleb (cfa_offset
- 0x81);
4975 else if (cfa_offset
> 0x40)
4977 tic6x_unwind_byte (UNWIND_OP_ADD_SP
| 0x3f);
4978 tic6x_unwind_byte (UNWIND_OP_ADD_SP
| (cfa_offset
- 0x40));
4982 tic6x_unwind_byte (UNWIND_OP_ADD_SP
| (cfa_offset
- 1));
4987 tic6x_unwind_2byte (UNWIND_OP2_POP
| unwind
->safe_mask
);
4988 else if (unwind
->pop_rts
)
4989 tic6x_unwind_byte (UNWIND_OP_POP_RTS
);
4990 else if (compact_mask
)
4991 tic6x_unwind_2byte (UNWIND_OP2_POP_COMPACT
| unwind
->compact_mask
);
4992 else if (reg_saved_mask
)
4998 tic6x_unwind_byte (UNWIND_OP_POP_REG
| unwind
->saved_reg_count
);
5000 for (cur_offset
= 0; unwind
->saved_reg_count
> 0; cur_offset
-= 4)
5003 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5005 if (!unwind
->reg_saved
[reg
])
5008 if (unwind
->reg_offset
[reg
] == cur_offset
)
5010 unwind
->saved_reg_count
--;
5015 if ((cur_offset
& 4) == 4)
5016 tic6x_unwind_byte ((last_val
<< 4) | val
);
5020 if ((cur_offset
& 4) == 4)
5021 tic6x_unwind_byte ((last_val
<< 4) | 0xf);
5024 /* Pad with RETURN opcodes. */
5025 while ((unwind
->data_bytes
& 3) != 0)
5026 tic6x_unwind_byte (UNWIND_OP_RET
| UNWIND_B3
);
5028 if (unwind
->personality_index
== -1 && unwind
->personality_routine
== NULL
)
5029 unwind
->personality_index
= 0;
5032 /* Force creation of an EXTAB entry if an LSDA is required. */
5033 if (need_extab
&& !unwind
->table_entry
)
5035 if (unwind
->data_bytes
!= 4)
5038 tic6x_flush_unwind_word (unwind
->data
);
5040 else if (unwind
->table_entry
&& !need_extab
)
5042 /* Add an empty descriptor if there is no user-specified data. */
5043 char *ptr
= frag_more (4);
5044 md_number_to_chars (ptr
, 0, 4);
5047 /* Fill in length of unwinding bytecode. */
5048 if (unwind
->table_entry
)
5051 if (unwind
->data_bytes
> 0x400)
5052 as_bad (_("too many unwinding instructions"));
5054 if (unwind
->personality_index
== -1)
5056 tmp
= md_chars_to_number (unwind
->frag_start
+ 4, 4);
5057 tmp
|= (valueT
) ((unwind
->data_bytes
- 8) >> 2) << 24;
5058 md_number_to_chars (unwind
->frag_start
+ 4, tmp
, 4);
5060 else if (unwind
->personality_index
== 1 || unwind
->personality_index
== 2)
5062 tmp
= md_chars_to_number (unwind
->frag_start
, 4);
5063 tmp
|= ((unwind
->data_bytes
- 4) >> 2) << 16;
5064 md_number_to_chars (unwind
->frag_start
, tmp
, 4);
5067 tic6x_output_exidx_entry ();
5070 /* FIXME: This will get horribly confused if cfi directives are emitted for
5071 function epilogue. */
5073 tic6x_cfi_endproc (struct fde_entry
*fde
)
5075 tic6x_unwind_info
*unwind
= tic6x_get_unwind ();
5076 struct cfi_insn_data
*insn
;
5078 unsigned safe_mask
= 0;
5079 unsigned compact_mask
= 0;
5080 unsigned reg_saved_mask
= 0;
5081 offsetT cfa_offset
= 0;
5082 offsetT save_offset
= 0;
5084 unwind
->cfa_reg
= 31;
5085 unwind
->return_reg
= UNWIND_B3
;
5086 unwind
->saved_reg_count
= 0;
5087 unwind
->pop_rts
= false;
5089 unwind
->saved_seg
= now_seg
;
5090 unwind
->saved_subseg
= now_subseg
;
5092 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5093 unwind
->reg_saved
[reg
] = false;
5095 /* Scan FDE instructions to build up stack frame layout. */
5096 for (insn
= fde
->data
; insn
; insn
= insn
->next
)
5100 case DW_CFA_advance_loc
:
5103 case DW_CFA_def_cfa
:
5104 unwind
->cfa_reg
= insn
->u
.ri
.reg
;
5105 cfa_offset
= insn
->u
.ri
.offset
;
5108 case DW_CFA_def_cfa_register
:
5109 unwind
->cfa_reg
= insn
->u
.r
;
5112 case DW_CFA_def_cfa_offset
:
5113 cfa_offset
= insn
->u
.i
;
5116 case DW_CFA_undefined
:
5117 case DW_CFA_same_value
:
5118 reg
= tic6x_unwind_reg_from_dwarf (insn
->u
.r
);
5120 unwind
->reg_saved
[reg
] = false;
5124 reg
= tic6x_unwind_reg_from_dwarf (insn
->u
.ri
.reg
);
5127 as_bad (_("unable to generate unwinding opcode for reg %d"),
5131 unwind
->reg_saved
[reg
] = true;
5132 unwind
->reg_offset
[reg
] = insn
->u
.ri
.offset
;
5133 if (insn
->u
.ri
.reg
== UNWIND_B3
)
5134 unwind
->return_reg
= UNWIND_B3
;
5137 case DW_CFA_register
:
5138 if (insn
->u
.rr
.reg1
!= 19)
5140 as_bad (_("unable to generate unwinding opcode for reg %d"),
5145 reg
= tic6x_unwind_reg_from_dwarf (insn
->u
.rr
.reg2
);
5148 as_bad (_("unable to generate unwinding opcode for reg %d"),
5153 unwind
->return_reg
= reg
;
5154 unwind
->reg_saved
[UNWIND_B3
] = false;
5155 if (unwind
->reg_saved
[reg
])
5157 as_bad (_("unable to restore return address from "
5158 "previously restored reg"));
5163 case DW_CFA_restore
:
5164 case DW_CFA_remember_state
:
5165 case DW_CFA_restore_state
:
5166 case DW_CFA_GNU_window_save
:
5168 case CFI_val_encoded_addr
:
5169 as_bad (_("unhandled CFA insn for unwinding (%d)"), insn
->insn
);
5177 if (unwind
->cfa_reg
!= 15 && unwind
->cfa_reg
!= 31)
5179 as_bad (_("unable to generate unwinding opcode for frame pointer reg %d"),
5184 if (unwind
->cfa_reg
== 15)
5186 if (cfa_offset
!= 0)
5188 as_bad (_("unable to generate unwinding opcode for "
5189 "frame pointer offset"));
5195 if ((cfa_offset
& 7) != 0)
5197 as_bad (_("unwound stack pointer not doubleword aligned"));
5202 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5204 if (unwind
->reg_saved
[reg
])
5205 reg_saved_mask
|= 1 << (TIC6X_NUM_UNWIND_REGS
- (reg
+ 1));
5208 /* Check for standard "safe debug" frame layout */
5212 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5214 if (!unwind
->reg_saved
[reg
])
5217 if (target_big_endian
5218 && reg
< TIC6X_NUM_UNWIND_REGS
- 1
5219 && unwind
->reg_saved
[reg
+ 1]
5220 && tic6x_unwind_frame_regs
[reg
]
5221 == tic6x_unwind_frame_regs
[reg
+ 1] + 1
5222 && (tic6x_unwind_frame_regs
[reg
] & 1) == 1
5223 && (save_offset
& 4) == 4)
5226 if (save_offset
!= unwind
->reg_offset
[reg
+ 1]
5227 || save_offset
- 4 != unwind
->reg_offset
[reg
])
5234 if (save_offset
!= unwind
->reg_offset
[reg
])
5239 if (reg
== TIC6X_NUM_UNWIND_REGS
)
5241 safe_mask
= reg_saved_mask
;
5246 /* Check for compact frame layout. */
5250 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5254 if (!unwind
->reg_saved
[reg
])
5257 if (reg
< TIC6X_NUM_UNWIND_REGS
- 1)
5261 if (!unwind
->reg_saved
[reg2
]
5262 || tic6x_unwind_frame_regs
[reg
]
5263 != tic6x_unwind_frame_regs
[reg2
] + 1
5264 || (tic6x_unwind_frame_regs
[reg2
] & 1) != 0
5265 || save_offset
== 0)
5274 if (target_big_endian
)
5275 high_offset
= 4; /* lower address = positive stack offset. */
5279 if (save_offset
+ 4 - high_offset
!= unwind
->reg_offset
[reg
]
5280 || save_offset
+ high_offset
!= unwind
->reg_offset
[reg2
])
5288 if (save_offset
!= unwind
->reg_offset
[reg
])
5294 if (reg
== TIC6X_NUM_UNWIND_REGS
)
5296 compact_mask
= reg_saved_mask
;
5301 /* Check for __c6xabi_pop_rts format */
5302 if (reg_saved_mask
== 0x17ff)
5304 const int *pop_rts_offset
= target_big_endian
5305 ? tic6x_pop_rts_offset_big
5306 : tic6x_pop_rts_offset_little
;
5309 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5311 if (reg
== UNWIND_B15
)
5314 if (unwind
->reg_offset
[reg
] != pop_rts_offset
[reg
] * 4)
5318 if (reg
== TIC6X_NUM_UNWIND_REGS
)
5320 unwind
->pop_rts
= true;
5324 /* If all else fails then describe the frame manually. */
5329 for (reg
= 0; reg
< TIC6X_NUM_UNWIND_REGS
; reg
++)
5331 if (!unwind
->reg_saved
[reg
])
5334 unwind
->saved_reg_count
++;
5335 /* Encoding uses 4 bits per word, so size of unwinding opcode data
5336 limits the save area size. The exact cap will be figured out
5337 later due to overflow, the 0x800 here is just a quick sanity
5338 check to weed out obviously excessive offsets. */
5339 if (unwind
->reg_offset
[reg
] > 0 || unwind
->reg_offset
[reg
] < -0x800
5340 || (unwind
->reg_offset
[reg
] & 3) != 0)
5342 as_bad (_("stack frame layout too complex for unwinder"));
5346 if (unwind
->reg_offset
[reg
] < save_offset
)
5347 save_offset
= unwind
->reg_offset
[reg
] - 4;
5351 /* Align to 8-byte boundary (stack grows towards negative offsets). */
5354 if (unwind
->cfa_reg
== 31 && !reg_saved_mask
)
5356 cfa_offset
+= save_offset
;
5359 as_bad (_("unwound frame has negative size"));
5364 unwind
->safe_mask
= safe_mask
;
5365 unwind
->compact_mask
= compact_mask
;
5366 unwind
->reg_saved_mask
= reg_saved_mask
;
5367 unwind
->cfa_offset
= cfa_offset
;
5368 unwind
->function_start
= fde
->start_address
;