1 /* tc-alpha.c - Processor-specific code for the DEC Alpha CPU.
2 Copyright (C) 1989, 1993, 1994 Free Software Foundation, Inc.
3 Contributed by Carnegie Mellon University, 1993.
4 Written by Alessandro Forin, based on earlier gas-1.38 target CPU files.
5 Modified by Ken Raeburn for gas-2.x and ECOFF support.
7 This file is part of GAS, the GNU Assembler.
9 GAS is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2, or (at your option)
14 GAS is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with GAS; see the file COPYING. If not, write to
21 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
24 * Mach Operating System
25 * Copyright (c) 1993 Carnegie Mellon University
26 * All Rights Reserved.
28 * Permission to use, copy, modify and distribute this software and its
29 * documentation is hereby granted, provided that both the copyright
30 * notice and this permission notice appear in all copies of the
31 * software, derivative works or modified versions, and any portions
32 * thereof, and that both notices appear in supporting documentation.
34 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
35 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
36 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
38 * Carnegie Mellon requests users of this software to return to
40 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
41 * School of Computer Science
42 * Carnegie Mellon University
43 * Pittsburgh PA 15213-3890
45 * any improvements or extensions that they make and grant Carnegie the
46 * rights to redistribute these changes.
50 * 5-Oct-93 Alessandro Forin (af) at Carnegie-Mellon University
53 * Author: Alessandro Forin, Carnegie Mellon University
60 #include "alpha-opcode.h"
63 /* @@ Will a simple 0x8000 work here? If not, why not? */
64 #define GP_ADJUSTMENT (0x8000 - 0x10)
66 /* Which machine type is this? Currently stores an integer for the
67 model, one of: 21064, 21066, 21164. */
68 static unsigned long machine
;
70 /* These are exported to relaxing code, even though we don't do any
71 relaxing on this processor currently. */
72 const relax_typeS md_relax_table
[1];
73 int md_short_jump_size
= 4;
74 int md_long_jump_size
= 4;
76 /* handle of the OPCODE hash table */
77 static struct hash_control
*op_hash
;
79 /* Sections and symbols we'll want to keep track of. */
80 static segT lita_sec
, rdata
, sdata
, lit8_sec
, lit4_sec
;
81 static symbolS
*lit8_sym
, *lit4_sym
;
83 /* Setting for ".set [no]{at,macro}". */
84 static int at_ok
= 1, macro_ok
= 1;
86 /* Keep track of global pointer. */
87 valueT alpha_gp_value
;
90 /* We'll probably be using this relocation frequently, and we
91 will want to compare for it. */
92 static const reloc_howto_type
*gpdisp_hi16_howto
;
94 /* These are exported to ECOFF code. */
95 unsigned long alpha_gprmask
, alpha_fprmask
;
97 /* Used for LITUSE relocations. */
98 static expressionS lituse_basereg
, lituse_byteoff
, lituse_jsr
;
100 /* Address size: In OSF/1 1.3, an undocumented "-32addr" option will
101 cause all addresses to be treated as 32-bit values in memory. (The
102 in-register versions are all sign-extended to 64 bits, of course.)
103 Some other systems may want this option too. */
106 /* Imported functions -- they should be defined in header files somewhere. */
107 extern segT
subseg_get ();
108 extern PTR
bfd_alloc_by_size_t ();
109 extern void s_globl (), s_long (), s_short (), s_space (), cons (), s_text (),
110 s_data (), float_cons ();
112 /* Static functions, needing forward declarations. */
113 static void s_base (), s_proc (), s_alpha_set ();
114 static void s_gprel32 (), s_rdata (), s_sdata (), s_alpha_comm ();
115 static int alpha_ip ();
117 static void emit_unaligned_io
PARAMS ((char *, int, valueT
, int));
118 static void emit_load_unal
PARAMS ((int, valueT
, int));
119 static void emit_store_unal
PARAMS ((int, valueT
, int));
120 static void emit_byte_manip_r
PARAMS ((char *, int, int, int, int, int));
121 static void emit_extract_r
PARAMS ((int, int, int, int, int));
122 static void emit_insert_r
PARAMS ((int, int, int, int, int));
123 static void emit_mask_r
PARAMS ((int, int, int, int, int));
124 static void emit_sign_extend
PARAMS ((int, int));
125 static void emit_bis_r
PARAMS ((int, int, int));
126 static int build_mem
PARAMS ((int, int, int, bfd_signed_vma
));
127 static int build_operate_n
PARAMS ((int, int, int, int, int));
128 static void emit_sll_n
PARAMS ((int, int, int));
129 static void emit_ldah_num
PARAMS ((int, bfd_vma
, int));
130 static void emit_addq_r
PARAMS ((int, int, int));
131 static void emit_lda_n
PARAMS ((int, bfd_vma
, int));
132 static void emit_add64
PARAMS ((int, int, bfd_vma
));
133 static int in_range
PARAMS ((bfd_vma
, int, int));
135 const pseudo_typeS md_pseudo_table
[] =
137 {"common", s_comm
, 0}, /* is this used? */
138 {"comm", s_alpha_comm
, 0}, /* osf1 compiler does this */
139 {"rdata", s_rdata
, 0},
140 {"sdata", s_sdata
, 0},
141 {"gprel32", s_gprel32
, 0},
142 {"t_floating", float_cons
, 'd'},
143 {"s_floating", float_cons
, 'f'},
144 {"f_floating", float_cons
, 'F'},
145 {"g_floating", float_cons
, 'G'},
146 {"d_floating", float_cons
, 'D'},
149 {"aproc", s_proc
, 1},
150 {"set", s_alpha_set
, 0},
151 {"reguse", s_ignore
, 0},
152 {"livereg", s_ignore
, 0},
153 {"extern", s_ignore
, 0}, /*??*/
154 {"base", s_base
, 0}, /*??*/
155 {"option", s_ignore
, 0},
156 {"prologue", s_ignore
, 0},
157 {"aent", s_ignore
, 0},
158 {"ugen", s_ignore
, 0},
160 /* We don't do any optimizing, so we can safely ignore these. */
161 {"noalias", s_ignore
, 0},
162 {"alias", s_ignore
, 0},
167 #define SA 21 /* shift for register Ra */
168 #define SB 16 /* shift for register Rb */
169 #define SC 0 /* shift for register Rc */
170 #define SN 13 /* shift for 8 bit immediate # */
176 #define RA 26 /* note: same as T12 */
183 #define OPCODE(X) (((X) >> 26) & 0x3f)
184 #define OP_FCN(X) (((X) >> 5) & 0x7f)
186 #ifndef FIRST_32BIT_QUADRANT
187 #define FIRST_32BIT_QUADRANT 0
190 int first_32bit_quadrant
= FIRST_32BIT_QUADRANT
;
191 int base_register
= FIRST_32BIT_QUADRANT
? ZERO
: GP
;
193 int no_mixed_code
= 0;
196 /* This array holds the chars that always start a comment. If the
197 pre-processor is disabled, these aren't very useful */
198 const char comment_chars
[] = "#";
200 /* This array holds the chars that only start a comment at the beginning of
201 a line. If the line seems to have the form '# 123 filename'
202 .line and .file directives will appear in the pre-processed output */
203 /* Note that input_file.c hand checks for '#' at the beginning of the
204 first line of the input file. This is because the compiler outputs
205 #NO_APP at the beginning of its output. */
206 /* Also note that C style comments are always recognized. */
207 const char line_comment_chars
[] = "#!";
209 /* Chars that can be used to separate mant from exp in floating point nums */
210 const char EXP_CHARS
[] = "eE";
212 const char line_separator_chars
[1];
214 /* Chars that mean this number is a floating point constant, as in
215 "0f12.456" or "0d1.2345e12". */
216 /* @@ Do all of these really get used on the alpha?? */
217 char FLT_CHARS
[] = "rRsSfFdDxXpP";
219 /* Also be aware that MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT may have to be
220 changed in read.c. Ideally it shouldn't have to know about it at all,
221 but nothing is ideal around here. */
226 bfd_reloc_code_real_type code
;
229 /* Occasionally, two relocations will be desired for one address.
230 Mainly only in cases like "jsr $r,foo" where we want both a LITUSE
235 unsigned long opcode
; /* need at least 32 bits */
236 struct reloc_data reloc
[MAX_RELOCS
];
239 static void getExpression (char *str
, struct alpha_it
*insn
);
240 static char *expr_end
;
242 #define note_gpreg(R) (alpha_gprmask |= (1 << (R)))
243 #define note_fpreg(R) (alpha_fprmask |= (1 << (R)))
246 tc_get_register (frame
)
252 if (*input_line_pointer
== '$')
254 input_line_pointer
++;
255 if (input_line_pointer
[0] == 's'
256 && input_line_pointer
[1] == 'p')
258 input_line_pointer
+= 2;
262 framereg
= get_absolute_expression ();
263 framereg
&= 31; /* ? */
266 as_warn ("frame reg expected, using $%d.", framereg
);
268 note_gpreg (framereg
);
278 temp
= get_absolute_expression ();
281 rdata
= subseg_get (".rdata", 0);
282 subseg_set (rdata
, (subsegT
) temp
);
284 rdata
= subseg_new (".rdata", 0);
286 demand_empty_rest_of_line ();
295 temp
= get_absolute_expression ();
298 sdata
= subseg_get (".sdata", 0);
299 subseg_set (sdata
, (subsegT
) temp
);
301 sdata
= subseg_new (".sdata", 0);
303 demand_empty_rest_of_line ();
307 s_alpha_comm (ignore
)
314 register symbolS
*symbolP
;
316 name
= input_line_pointer
;
317 c
= get_symbol_end ();
318 /* just after name is now '\0' */
319 p
= input_line_pointer
;
322 /* Alpha OSF/1 compiler doesn't provide the comma, gcc does. */
323 if (*input_line_pointer
== ',')
325 input_line_pointer
++;
328 if ((temp
= get_absolute_expression ()) < 0)
330 as_warn (".COMMon length (%ld.) <0! Ignored.", (long) temp
);
331 ignore_rest_of_line ();
335 symbolP
= symbol_find_or_make (name
);
337 if (S_IS_DEFINED (symbolP
))
339 as_bad ("Ignoring attempt to re-define symbol");
340 ignore_rest_of_line ();
343 if (S_GET_VALUE (symbolP
))
345 if (S_GET_VALUE (symbolP
) != (valueT
) temp
)
346 as_bad ("Length of .comm \"%s\" is already %ld. Not changed to %ld.",
347 S_GET_NAME (symbolP
),
348 (long) S_GET_VALUE (symbolP
),
353 S_SET_VALUE (symbolP
, (valueT
) temp
);
354 S_SET_EXTERNAL (symbolP
);
357 know (symbolP
->sy_frag
== &zero_address_frag
);
358 demand_empty_rest_of_line ();
362 tc_gen_reloc (sec
, fixp
)
368 reloc
= (arelent
*) bfd_alloc_by_size_t (stdoutput
, sizeof (arelent
));
369 reloc
->sym_ptr_ptr
= &fixp
->fx_addsy
->bsym
;
370 reloc
->address
= fixp
->fx_frag
->fr_address
+ fixp
->fx_where
;
372 if (fixp
->fx_r_type
> BFD_RELOC_UNUSED
)
375 if (fixp
->fx_r_type
== BFD_RELOC_ALPHA_GPDISP_HI16
)
377 if (!gpdisp_hi16_howto
)
378 gpdisp_hi16_howto
= bfd_reloc_type_lookup (stdoutput
,
380 reloc
->howto
= gpdisp_hi16_howto
;
383 reloc
->howto
= bfd_reloc_type_lookup (stdoutput
, fixp
->fx_r_type
);
384 assert (reloc
->howto
!= 0);
385 if (!fixp
->fx_pcrel
!= !reloc
->howto
->pc_relative
)
387 as_fatal ("internal error? cannot generate `%s' relocation",
388 bfd_get_reloc_code_name (fixp
->fx_r_type
));
390 assert (!fixp
->fx_pcrel
== !reloc
->howto
->pc_relative
);
392 if (fixp
->fx_r_type
== BFD_RELOC_ALPHA_LITERAL
)
394 /* fake out bfd_perform_relocation. sigh */
395 reloc
->addend
= -alpha_gp_value
;
397 else if (reloc
->howto
->pc_relative
&& reloc
->howto
->pcrel_offset
)
399 reloc
->addend
= fixp
->fx_offset
- reloc
->address
;
402 reloc
->addend
= fixp
->fx_offset
;
409 if (first_32bit_quadrant
)
411 /* not fatal, but it might not work in the end */
412 as_warn ("File overrides no-base-register option.");
413 first_32bit_quadrant
= 0;
417 if (*input_line_pointer
== '$')
419 input_line_pointer
++;
420 if (*input_line_pointer
== 'r')
421 input_line_pointer
++;
424 base_register
= get_absolute_expression ();
425 if (base_register
< 0 || base_register
> 31)
428 as_warn ("Bad base register, using $%d.", base_register
);
430 demand_empty_rest_of_line ();
433 static int in_range (val
, nbits
, unsignedness
)
435 int nbits
, unsignedness
;
437 /* Look at top bit of value that would be stored, figure out how it
438 would be extended by the hardware, and see if that matches the
439 original supplied value. */
442 bfd_vma top_bit
, stored_value
, missing_bits
;
444 mask
= (one
<< nbits
) - 1;
445 stored_value
= val
& mask
;
446 top_bit
= stored_value
& (one
<< nbits
- 1);
447 missing_bits
= val
& ~mask
;
450 return missing_bits
== 0;
454 /* will sign-extend */
457 /* all remaining bits beyond mask should be one */
458 missing_bits
|= mask
;
459 return missing_bits
+ 1 == 0;
463 /* all other bits should be zero */
464 return missing_bits
== 0;
480 e
.X_add_symbol
= section_symbol (absolute_section
);
491 fix_new_exp (frag_now
, p
- frag_now
->fr_literal
, 4, &e
, 0,
496 create_literal_section (secp
, name
)
500 segT current_section
= now_seg
;
501 int current_subsec
= now_subseg
;
504 *secp
= new_sec
= subseg_new (name
, 0);
505 subseg_set (current_section
, current_subsec
);
506 bfd_set_section_alignment (stdoutput
, new_sec
, 3);
507 bfd_set_section_flags (stdoutput
, new_sec
,
508 SEC_RELOC
| SEC_ALLOC
| SEC_LOAD
| SEC_READONLY
512 #define create_lita_section() create_literal_section (&lita_sec, ".lita")
515 get_lit8_offset (val
)
521 create_literal_section (&lit8_sec
, ".lit8");
522 lit8_sym
= section_symbol (lit8_sec
);
524 retval
= add_to_literal_pool ((symbolS
*) 0, val
, lit8_sec
, 8);
525 if (retval
>= 0xfff0)
526 as_fatal ("overflow in fp literal (.lit8) table");
531 get_lit4_offset (val
)
537 create_literal_section (&lit4_sec
, ".lit4");
538 lit4_sym
= section_symbol (lit4_sec
);
540 retval
= add_to_literal_pool ((symbolS
*) 0, val
, lit4_sec
, 4);
541 if (retval
>= 0xfff0)
542 as_fatal ("overflow in fp literal (.lit4) table");
546 #define load_insn(NAME, OP) (hash_insert (op_hash, (NAME), (PTR) (OP)))
549 load_insn_table (ops
, size
)
550 struct alpha_opcode
*ops
;
553 struct alpha_opcode
*end
= ops
+ size
;
554 struct alpha_opcode
*op
;
557 for (op
= ops
; op
< end
; )
563 retval
= load_insn (op
->name
, op
);
565 as_fatal ("internal error: can't hash opcode `%s': %s",
572 || !strcmp (op
->name
, name
)));
574 /* Some opcodes include modifiers of various sorts with a "/mod"
575 syntax, like the architecture documentation suggests. However,
576 for use with gcc at least, we also need to access those same
577 opcodes without the "/". */
578 for (op
= ops
; op
< end
; )
582 if (strchr (name
, '/'))
587 name2
= xmalloc (strlen (name
));
597 /* Ignore failures -- the opcode table does duplicate some
598 variants in different forms, like "hw_stq" and "hw_st/q".
599 Maybe the variants can be eliminated, and this error checking
601 load_insn (name2
, op
);
608 || !strcmp (op
->name
, name
)));
612 static struct alpha_it clear_insn
;
614 /* This function is called once, at assembler startup time. It should
615 set up all the tables, etc. that the MD part of the assembler will
616 need, that can be determined before arguments are parsed. */
622 op_hash
= hash_new ();
623 load_insn_table (alpha_opcodes
, NUMOPCODES
);
625 /* Default to 21064 PAL instructions. */
633 load_insn_table (alpha_pal21064_opcodes
, NUM21064OPCODES
);
636 load_insn_table (alpha_pal21164_opcodes
, NUM21164OPCODES
);
639 as_fatal ("palcode set unknown (internal error)");
642 lituse_basereg
.X_op
= O_constant
;
643 lituse_basereg
.X_add_number
= 1;
644 lituse_byteoff
.X_op
= O_constant
;
645 lituse_byteoff
.X_add_number
= 2;
646 lituse_jsr
.X_op
= O_constant
;
647 lituse_jsr
.X_add_number
= 3;
649 /* So .sbss will get used for tiny objects. */
650 bfd_set_gp_size (stdoutput
, 8);
651 create_lita_section ();
652 /* For handling the GP, create a symbol that won't be output in the
653 symbol table. We'll edit it out of relocs later. */
654 gp
= symbol_create ("<GP value>", lita_sec
, 0x8000, &zero_address_frag
);
656 memset (&clear_insn
, 0, sizeof (clear_insn
));
657 for (i
= 0; i
< MAX_RELOCS
; i
++)
658 clear_insn
.reloc
[i
].code
= BFD_RELOC_NONE
;
665 struct alpha_it
*insn
;
672 /* put out the opcode */
673 md_number_to_chars (toP
, insn
->opcode
, 4);
675 /* put out the symbol-dependent stuff */
676 for (j
= 0; j
< MAX_RELOCS
; j
++)
678 struct reloc_data
*r
= &insn
->reloc
[j
];
681 if (r
->code
!= BFD_RELOC_NONE
)
683 if (r
->exp
.X_op
== O_constant
)
685 r
->exp
.X_add_symbol
= section_symbol (absolute_section
);
686 r
->exp
.X_op
= O_symbol
;
688 f
= fix_new_exp (frag_now
, (toP
- frag_now
->fr_literal
), 4,
689 &r
->exp
, r
->pcrel
, r
->code
);
691 if (r
->code
== BFD_RELOC_ALPHA_GPDISP_LO16
)
693 static bit_fixS cookie
;
694 /* @@ This'll make the range checking in write.c shut up. */
695 f
->fx_bit_fixP
= &cookie
;
706 struct alpha_it insns
[MAX_INSNS
];
708 count
= alpha_ip (str
, insns
);
712 for (i
= 0; i
< count
; i
++)
713 emit_insn (&insns
[i
]);
723 vma
= bfd_get_section_vma (foo
, sec
);
724 if (vma
&& vma
< alpha_gp_value
)
725 alpha_gp_value
= vma
;
731 if (alpha_gp_value
!= 0)
734 /* Get minus-one in whatever width... */
735 alpha_gp_value
= 0; alpha_gp_value
--;
737 /* Select the smallest VMA of these existing sections. */
738 maybe_set_gp (lita_sec
);
739 /* maybe_set_gp (sdata); Was disabled before -- should we use it? */
741 maybe_set_gp (lit8_sec
);
742 maybe_set_gp (lit4_sec
);
745 alpha_gp_value
+= GP_ADJUSTMENT
;
747 S_SET_VALUE (gp
, alpha_gp_value
);
750 printf ("Chose GP value of %lx\n", alpha_gp_value
);
755 alpha_force_relocation (f
)
758 switch (f
->fx_r_type
)
760 case BFD_RELOC_ALPHA_GPDISP_HI16
:
761 case BFD_RELOC_ALPHA_GPDISP_LO16
:
762 case BFD_RELOC_ALPHA_LITERAL
:
763 case BFD_RELOC_ALPHA_LITUSE
:
764 case BFD_RELOC_GPREL32
:
766 case BFD_RELOC_ALPHA_HINT
:
771 case BFD_RELOC_23_PCREL_S2
:
782 alpha_fix_adjustable (f
)
785 /* Are there any relocation types for which we must generate a reloc
786 but we can adjust the values contained within it? */
787 switch (f
->fx_r_type
)
789 case BFD_RELOC_ALPHA_GPDISP_HI16
:
790 case BFD_RELOC_ALPHA_GPDISP_LO16
:
792 case BFD_RELOC_GPREL32
:
795 return !alpha_force_relocation (f
);
801 md_section_align (seg
, size
)
806 /* This should probably be handled within BFD, or by pulling the
807 number from BFD at least. */
815 /* Add this thing to the .lita section and produce a LITERAL reloc referring
818 /* Are we currently eligible to emit a LITUSE reloc for the literal
819 references just generated? */
820 static int lituse_pending
;
823 load_symbol_address (reg
, insn
)
825 struct alpha_it
*insn
;
827 static symbolS
*lita_sym
;
834 lita_sym
= section_symbol (lita_sec
);
835 S_CLEAR_EXTERNAL (lita_sym
);
838 retval
= add_to_literal_pool (insn
->reloc
[0].exp
.X_add_symbol
,
839 insn
->reloc
[0].exp
.X_add_number
,
842 /* Now emit a LITERAL relocation for the original section. */
843 insn
->reloc
[0].exp
.X_op
= O_symbol
;
844 insn
->reloc
[0].exp
.X_add_symbol
= lita_sym
;
845 insn
->reloc
[0].exp
.X_add_number
= retval
;
846 insn
->reloc
[0].code
= BFD_RELOC_ALPHA_LITERAL
;
849 if (retval
== 0x8000)
851 as_fatal ("overflow in literal (.lita) table");
854 insn
->opcode
= (0xa0000000 /* ldl */
856 | (base_register
<< SB
)
859 insn
->opcode
= (0xa4000000 /* ldq */
861 | (base_register
<< SB
)
863 note_gpreg (base_register
);
866 /* To load an address with a single instruction,
867 emit a LITERAL reloc in this section, and a REFQUAD
868 for the .lita section, so that we'll be able to access
870 lda REG, xx -> ldq REG, -32752(gp)
871 lda REG, xx+4 -> ldq REG, -32752(gp)
874 The offsets need to start near -0x8000, and the generated LITERAL
875 relocations should negate the offset. I don't completely grok the
879 load_expression (reg
, insn
)
881 struct alpha_it
*insn
;
883 valueT addend
, addendhi
, addendlo
;
886 if (insn
->reloc
[0].exp
.X_add_symbol
->bsym
->flags
& BSF_SECTION_SYM
)
892 addend
= insn
->reloc
[0].exp
.X_add_number
;
893 insn
->reloc
[0].exp
.X_add_number
= 0;
895 load_symbol_address (reg
, insn
);
898 if ((addend
& ~0x7fffffff) != 0
899 && (addend
& ~0x7fffffff) + 0x80000000 != 0)
901 as_bad ("assembler not prepared to handle constants >32 bits yet");
904 addendlo
= addend
& 0xffff;
906 addendhi
= addend
>> 16;
907 if (addendlo
& 0x8000)
909 /* It appears that the BASEREG LITUSE reloc should not be used on
910 an LDAH instruction. */
913 insn
[1].opcode
= (0x20000000 /* lda */
916 | (addendlo
& 0xffff));
917 insn
[1].reloc
[0].code
= BFD_RELOC_ALPHA_LITUSE
;
918 insn
[1].reloc
[0].exp
= lituse_basereg
;
923 insn
[num_insns
].opcode
= (0x24000000
926 | (addendhi
& 0xffff));
937 getExpression (str
, this_insn
)
939 struct alpha_it
*this_insn
;
944 #if 0 /* Not converted to bfd yet, and I don't think we need them
945 for ECOFF. Re-adding a.out support will probably require
947 static const struct am
{
949 bfd_reloc_code_real_type reloc
;
951 { "hi", RELOC_48_63
},
952 { "lo", RELOC_0_15
},
953 { "ml", RELOC_16_31
},
954 { "mh", RELOC_32_47
},
955 { "uhi", RELOC_U_48_63
},
956 { "uml", RELOC_U_16_31
},
957 { "umh", RELOC_U_32_47
},
961 /* Handle macros: "%macroname(expr)" */
972 while (*q
&& *p
== *q
)
980 str
= p
; /* keep the '(' */
981 this_insn
->reloc
= m
->reloc
;
986 save_in
= input_line_pointer
;
987 input_line_pointer
= str
;
989 seg
= expression (&this_insn
->reloc
[0].exp
);
990 /* XXX validate seg and exp, make sure they're reasonable */
991 expr_end
= input_line_pointer
;
992 input_line_pointer
= save_in
;
996 emit_unaligned_io (dir
, addr_reg
, addr_offset
, reg
)
1002 sprintf (buf
, "%sq_u $%d,%ld($%d)", dir
, reg
, (long) addr_offset
, addr_reg
);
1007 emit_load_unal (addr_reg
, addr_offset
, reg
)
1011 emit_unaligned_io ("ld", addr_reg
, addr_offset
, reg
);
1015 emit_store_unal (addr_reg
, addr_offset
, reg
)
1019 emit_unaligned_io ("st", addr_reg
, addr_offset
, reg
);
1023 emit_byte_manip_r (op
, in
, mask
, out
, mode
, which
)
1025 int in
, mask
, out
, mode
, which
;
1028 sprintf (buf
, "%s%c%c $%d,$%d,$%d", op
, mode
, which
, in
, mask
, out
);
1033 emit_extract_r (in
, mask
, out
, mode
, which
)
1034 int in
, mask
, out
, mode
, which
;
1036 emit_byte_manip_r ("ext", in
, mask
, out
, mode
, which
);
1040 emit_insert_r (in
, mask
, out
, mode
, which
)
1041 int in
, mask
, out
, mode
, which
;
1043 emit_byte_manip_r ("ins", in
, mask
, out
, mode
, which
);
1047 emit_mask_r (in
, mask
, out
, mode
, which
)
1048 int in
, mask
, out
, mode
, which
;
1050 emit_byte_manip_r ("msk", in
, mask
, out
, mode
, which
);
1054 emit_sign_extend (reg
, size
)
1058 sprintf (buf
, "sll $%d,0x%x,$%d", reg
, 64 - size
, reg
);
1060 sprintf (buf
, "sra $%d,0x%x,$%d", reg
, 64 - size
, reg
);
1065 emit_bis_r (in1
, in2
, out
)
1069 sprintf (buf
, "bis $%d,$%d,$%d", in1
, in2
, out
);
1074 build_mem (opc
, ra
, rb
, disp
)
1076 bfd_signed_vma disp
;
1078 if ((disp
>> 15) != 0
1079 && (disp
>> 15) + 1 != 0)
1081 return ((opc
<< 26) | (ra
<< SA
) | (rb
<< SB
) | (disp
& 0xffff));
1085 build_operate_n (opc
, fn
, ra
, lit
, rc
)
1086 int opc
, fn
, ra
, rc
;
1091 return ((opc
<< 26) | (fn
<< 5) | (ra
<< SA
) | (lit
<< SN
) | (1 << 12) | (rc
<< SC
));
1095 emit_sll_n (dest
, disp
, src
)
1096 int dest
, disp
, src
;
1098 struct alpha_it insn
= clear_insn
;
1099 insn
.opcode
= build_operate_n (0x12, 0x39, src
, disp
, dest
);
1104 emit_ldah_num (dest
, addend
, src
)
1108 struct alpha_it insn
= clear_insn
;
1109 insn
.opcode
= build_mem (0x09, dest
, src
, addend
);
1114 emit_addq_r (in1
, in2
, out
)
1117 struct alpha_it insn
= clear_insn
;
1118 insn
.opcode
= 0x40000400 | (in1
<< SA
) | (in2
<< SB
) | (out
<< SC
);
1123 emit_lda_n (dest
, addend
, src
)
1127 struct alpha_it insn
= clear_insn
;
1128 insn
.opcode
= build_mem (0x08, dest
, src
, addend
);
1133 emit_add64 (in
, out
, num
)
1137 bfd_signed_vma snum
= num
;
1139 if (in_range (num
, 16, 0))
1141 emit_lda_n (out
, num
, in
);
1144 if ((num
& 0xffff) == 0
1146 && in_range (snum
>> 16, 16, 0))
1148 emit_ldah_num (out
, snum
>> 16, in
);
1151 /* I'm not sure this one is getting invoked when it could. */
1152 if ((num
& 1) == 0 && in
== ZERO
)
1154 if (in_range (snum
>> 1, 16, 0))
1156 emit_lda_n (out
, snum
>> 1, in
);
1157 emit_addq_r (out
, out
, out
);
1160 else if (num
& 0x1fffe == 0
1161 && in_range (snum
>> 17, 16, 0))
1163 emit_ldah_num (out
, snum
>> 17, in
);
1164 emit_addq_r (out
, out
, out
);
1168 if (in_range (num
, 32, 0))
1170 bfd_vma lo
= num
& 0xffff;
1174 emit_ldah_num (out
, snum
>> 16, in
);
1176 emit_lda_n (out
, lo
, out
);
1180 if (in
!= ZERO
&& in
!= AT
&& out
!= AT
&& at_ok
)
1182 emit_add64 (ZERO
, AT
, num
);
1183 emit_addq_r (AT
, in
, out
);
1188 as_bad ("load expression too complex to expand");
1190 /* Could check also for loading 16- or 32-bit value and shifting by
1191 arbitrary displacement. */
1194 bfd_vma lo
= snum
& 0xffffffff;
1195 if (lo
& 0x80000000)
1196 lo
-= ((bfd_vma
)0x10000000 << 4);
1198 emit_add64 (ZERO
, out
, snum
>> 32);
1199 emit_sll_n (out
, 32, out
);
1201 emit_add64 (out
, out
, lo
);
1205 /* Note that for now, this function is called recursively (by way of
1206 calling md_assemble again). Some of the macros defined as part of
1207 the assembly language are currently rewritten as sequences of
1208 strings to be assembled. See, for example, the handling of "divq".
1210 For efficiency, this should be fixed someday. */
1212 alpha_ip (str
, insns
)
1214 struct alpha_it insns
[];
1220 struct alpha_opcode
*pattern
;
1222 unsigned int opcode
;
1224 int match
= 0, num_gen
= 1;
1228 islower (*s
) || *s
== '_' || *s
== '/' || *s
== '4' || *s
== '8';
1247 as_warn ("Unknown opcode: `%s'", str
);
1250 if ((pattern
= (struct alpha_opcode
*) hash_find (op_hash
, str
)) == NULL
)
1252 as_warn ("Unknown opcode: `%s'", str
);
1261 opcode
= pattern
->match
;
1263 for (i
= 0; i
< MAX_INSNS
; i
++)
1264 insns
[i
] = clear_insn
;
1266 /* Build the opcode, checking as we go to make sure that the
1268 for (args
= pattern
->args
;; ++args
)
1273 case '\0': /* end of args */
1292 case '(': /* these must match exactly */
1301 case '1': /* next operand must be a register */
1311 case 'a': /* $at: as temporary */
1317 case 'g': /* $gp: base register */
1320 mask
= base_register
;
1323 case 's': /* $sp: stack pointer */
1330 case 'r': /* any register */
1331 if (!isdigit (c
= *s
++))
1348 if ((c
= 10 * (c
- '0') + (*s
++ - '0')) >= 32)
1357 if ((c
== GP
) && first_32bit_quadrant
)
1367 /* Got the register, now figure out where it goes in
1375 opcode
|= mask
<< SA
;
1380 opcode
|= mask
<< SB
;
1389 opcode
|= (mask
<< SA
) | mask
;
1392 case 'R': /* ra and rb are the same */
1393 opcode
|= (mask
<< SA
) | (mask
<< SB
);
1397 opcode
|= (mask
<< SA
) | (mask
<< SB
) | (mask
);
1403 case 'e': /* next operand is a floating point register */
1407 if (*s
++ == '$' && *s
++ == 'f' && isdigit (*s
))
1412 mask
= 10 * (mask
- '0') + (*s
++ - '0');
1423 /* same encoding as gp registers */
1429 case 'h': /* bits 16..31 */
1430 insns
[0].reloc
= RELOC_16_31
;
1434 case 'l': /* bits 0..15 */
1435 insns
[0].reloc
[0].code
= BFD_RELOC_16
;
1438 case 'L': /* 21 bit PC relative immediate */
1439 insns
[0].reloc
[0].code
= BFD_RELOC_23_PCREL_S2
;
1440 insns
[0].reloc
[0].pcrel
= 1;
1443 case 'i': /* 14 bit immediate */
1444 if (OPCODE (opcode
) != 0x1a)
1445 /* Not a jmp variant?? */
1447 else if (opcode
& 0x8000)
1448 /* ret or jsr_coroutine */
1450 insns
[0].reloc
[0].code
= BFD_RELOC_14
;
1451 insns
[0].reloc
[0].pcrel
= 0;
1456 insns
[0].reloc
[0].code
= BFD_RELOC_ALPHA_HINT
;
1457 insns
[0].reloc
[0].pcrel
= 1;
1461 case 'b': /* 8 bit immediate */
1462 insns
[0].reloc
[0].code
= BFD_RELOC_8
;
1465 case 'I': /* 26 bit immediate, for PALcode */
1466 insns
[0].reloc
[0].code
= BFD_RELOC_26
;
1470 case 't': /* 12 bit 0...11 */
1471 insns
[0].reloc
= RELOC_0_12
;
1474 case '8': /* 8 bit 0...7 */
1475 insns
[0].reloc
= RELOC_0_8
;
1478 case 'I': /* 26 bit immediate */
1479 insns
[0].reloc
= RELOC_0_25
;
1490 getExpression (s
, &insns
[0]);
1492 /* Handle overflow in certain instructions by converting
1493 to other instructions. */
1494 if (insns
[0].reloc
[0].code
== BFD_RELOC_8
1495 && insns
[0].reloc
[0].exp
.X_op
== O_constant
1496 && (insns
[0].reloc
[0].exp
.X_add_number
< 0
1497 || insns
[0].reloc
[0].exp
.X_add_number
> 0xff))
1499 if (OPCODE (opcode
) == 0x10
1500 && (OP_FCN (opcode
) == 0x00 /* addl */
1501 || OP_FCN (opcode
) == 0x40 /* addl/v */
1502 || OP_FCN (opcode
) == 0x20 /* addq */
1503 || OP_FCN (opcode
) == 0x60 /* addq/v */
1504 || OP_FCN (opcode
) == 0x09 /* subl */
1505 || OP_FCN (opcode
) == 0x49 /* subl/v */
1506 || OP_FCN (opcode
) == 0x29 /* subq */
1507 || OP_FCN (opcode
) == 0x69 /* subq/v */
1508 || OP_FCN (opcode
) == 0x02 /* s4addl */
1509 || OP_FCN (opcode
) == 0x22 /* s4addq */
1510 || OP_FCN (opcode
) == 0x0b /* s4subl */
1511 || OP_FCN (opcode
) == 0x2b /* s4subq */
1512 || OP_FCN (opcode
) == 0x12 /* s8addl */
1513 || OP_FCN (opcode
) == 0x32 /* s8addq */
1514 || OP_FCN (opcode
) == 0x1b /* s8subl */
1515 || OP_FCN (opcode
) == 0x3b /* s8subq */
1517 /* Can we make it fit by negating? */
1518 && -insns
[0].reloc
[0].exp
.X_add_number
< 0xff
1519 && -insns
[0].reloc
[0].exp
.X_add_number
> 0)
1521 opcode
^= 0x120; /* convert add<=>sub */
1522 insns
[0].reloc
[0].exp
.X_add_number
*= -1;
1524 else if (at_ok
&& macro_ok
)
1526 /* Constant value supplied, but it's too large. */
1527 emit_add64 (ZERO
, AT
,
1528 insns
[0].reloc
[0].exp
.X_add_number
);
1530 opcode
|= (AT
<< SB
);
1531 insns
[0].reloc
[0].code
= BFD_RELOC_NONE
;
1534 as_bad ("overflow in 8-bit literal field in `operate' format insn");
1536 else if (insns
[0].reloc
[0].code
== BFD_RELOC_16
1537 && insns
[0].reloc
[0].exp
.X_op
== O_constant
1538 && !in_range (insns
[0].reloc
[0].exp
.X_add_number
,
1541 bfd_vma val
= insns
[0].reloc
[0].exp
.X_add_number
;
1542 if (OPCODE (opcode
) == 0x08)
1544 emit_add64 (ZERO
, AT
, val
);
1546 opcode
|= (AT
<< SB
);
1547 insns
[0].reloc
[0].code
= BFD_RELOC_NONE
;
1549 else if (OPCODE (opcode
) == 0x09
1550 && in_range (val
>> 16, 16, 0))
1552 /* ldah with high operand - convert to low */
1553 insns
[0].reloc
[0].exp
.X_add_number
>>= 16;
1556 as_bad ("I don't know how to handle 32+ bit constants here yet, sorry.");
1558 else if (insns
[0].reloc
[0].code
== BFD_RELOC_32
1559 && insns
[0].reloc
[0].exp
.X_op
== O_constant
)
1561 bfd_vma val
= insns
[0].reloc
[0].exp
.X_add_number
;
1562 bfd_signed_vma sval
= val
;
1565 && sval
>> 32 != -1)
1566 as_bad ("I don't know how to handle 64 bit constants here yet, sorry.");
1572 int format
, length
, mode
, i
;
1573 char temp
[20 /*MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT*/];
1575 static const char formats
[4] = "FGfd";
1576 bfd_vma bits
, offset
;
1577 char *old_input_line_pointer
= input_line_pointer
;
1579 input_line_pointer
= s
;
1581 memset (temp
, 0, sizeof (temp
));
1582 mode
= (opcode
>> 26) & 3;
1583 format
= formats
[mode
];
1584 err
= md_atof (format
, temp
, &length
);
1587 as_bad ("Bad floating literal: %s", err
);
1592 /* Generate little-endian number from byte sequence. */
1594 for (i
= length
- 1; i
>= 0; i
--)
1595 bits
+= ((bfd_vma
)(temp
[i
] & 0xff)) << (i
* 8);
1600 offset
= get_lit8_offset (bits
) - 0x8000;
1601 insns
[0].reloc
[0].exp
.X_add_symbol
= lit8_sym
;
1602 insns
[0].reloc
[0].exp
.X_add_number
= 0x8000;
1605 offset
= get_lit4_offset (bits
) - 0x8000;
1606 insns
[0].reloc
[0].exp
.X_add_symbol
= lit4_sym
;
1607 insns
[0].reloc
[0].exp
.X_add_number
= 0x8000;
1612 insns
[0].reloc
[0].exp
.X_op
= O_symbol
;
1614 num_gen
= load_expression (AT
, &insns
[0]);
1617 insns
[num_gen
].reloc
[0].code
= BFD_RELOC_ALPHA_LITUSE
;
1618 insns
[num_gen
].reloc
[0].exp
= lituse_basereg
;
1621 insns
[num_gen
++].opcode
= opcode
| (AT
<< SB
) | offset
;
1622 opcode
= insns
[0].opcode
;
1623 s
= input_line_pointer
;
1624 input_line_pointer
= old_input_line_pointer
;
1628 /* The following two.. take advantage of the fact that
1629 opcode already contains most of what we need to know.
1630 We just prepend to the instr an "ldah
1631 $r,%ml(expr)($base)" and turn this one (done later
1632 after we return) into something like "stq
1633 $r,%lo(expr)(at)" or "ldq $r,%lo(expr)($r)".
1635 NOTE: This can fail later on at link time if the
1636 offset from $base actually turns out to be more than
1637 2**31 or 2**47 if use_large_offsets is set. */
1638 case 'P': /* Addressing macros: PUT */
1639 mask
= AT
; /* register 'at' */
1642 case 'G': /* Addressing macros: GET */
1643 /* All it is missing is the expression, which is what we
1648 getExpression (s
, &insns
[0]);
1651 /* Must check for "lda ..,number" too */
1652 if (insns
[0].reloc
[0].exp
.X_op
== O_big
)
1654 as_warn ("Sorry, not yet. Put bignums in .data section yourself.");
1657 if (insns
[0].reloc
[0].exp
.X_op
== O_constant
)
1659 bfd_vma val
= insns
[0].reloc
[0].exp
.X_add_number
;
1662 insns
[0].reloc
[0].code
= BFD_RELOC_NONE
;
1663 insns
[1].reloc
[0].code
= BFD_RELOC_NONE
;
1671 emit_add64 (ZERO
, AT
, top
);
1675 opcode
|= ZERO
<< SB
;
1677 opcode
|= low
& 0xffff;
1679 else if (insns
[0].reloc
[0].exp
.X_op
== O_symbol
)
1681 unsigned long old_opcode
= opcode
;
1685 as_bad ("insn requires expansion but `nomacro' specified");
1686 else if (*args
== 'G')
1689 as_bad ("insn expansion requires AT use, but `noat' specified");
1692 num_gen
= load_expression (tmp_reg
, insns
);
1693 opcode
= insns
[0].opcode
;
1694 /* lda is opcode 8, 0x20000000, and the macros that use
1695 this code have an opcode field of 0. The latter
1696 require further processing, and we don't have the
1697 true opcode here. */
1698 if (OPCODE (old_opcode
) != 0
1699 && OPCODE (old_opcode
) != 0x08)
1702 i
= &insns
[num_gen
++];
1703 i
->opcode
= old_opcode
| (tmp_reg
<< SB
);
1707 i
->reloc
[0].code
= BFD_RELOC_ALPHA_LITUSE
;
1708 i
->reloc
[0].exp
= lituse_basereg
;
1717 insns
[1].reloc
[0].exp
= insns
[0].reloc
[0].exp
;
1719 /* Generate: ldah REG,x1(GP); OP ?,x0(REG) */
1721 abort (); /* relocs need fixing */
1723 insns
[1].reloc
= RELOC_0_15
;
1724 insns
[1].opcode
= opcode
| mask
<< SB
;
1726 insns
[0].reloc
= RELOC_16_31
;
1727 opcode
= 0x24000000 /*ldah*/ | mask
<< SA
| (base_register
<< SB
);
1733 /* Same failure modes as above, actually most of the
1734 same code shared. */
1735 case 'B': /* Builtins */
1740 case 'a': /* ldgp */
1742 if (first_32bit_quadrant
|| no_mixed_code
)
1744 switch (OUTPUT_FLAVOR
)
1746 case bfd_target_aout_flavour
:
1747 /* this is cmu's a.out version */
1748 insns
[0].reloc
[0].code
= BFD_RELOC_NONE
;
1749 /* generate "zap %r,0xf,%r" to take high 32 bits */
1750 opcode
|= 0x48001600 /* zap ?,#,?*/ | (0xf << SN
);
1752 case bfd_target_ecoff_flavour
:
1753 /* Given "ldgp R1,N(R2)", turn it into something
1754 like "ldah R1,###(R2) ; lda R1,###(R1)" with
1755 appropriate constants and relocations. */
1757 unsigned long r1
, r2
;
1758 unsigned long addend
= 0;
1763 insns
[0].reloc
[0].code
= BFD_RELOC_ALPHA_GPDISP_HI16
;
1764 insns
[0].reloc
[0].pcrel
= 1;
1765 insns
[0].reloc
[0].exp
.X_op
= O_symbol
;
1766 insns
[0].reloc
[0].exp
.X_add_symbol
= gp
;
1767 insns
[0].reloc
[0].exp
.X_add_number
= 0;
1768 insns
[0].opcode
= (0x24000000 /* ldah */
1771 insns
[1].reloc
[0].code
= BFD_RELOC_ALPHA_GPDISP_LO16
;
1772 insns
[1].reloc
[0].exp
.X_op
= O_symbol
;
1773 insns
[1].reloc
[0].exp
.X_add_symbol
= gp
;
1774 insns
[1].reloc
[0].exp
.X_add_number
= 4;
1775 insns
[1].reloc
[0].pcrel
= 1;
1776 insns
[1].opcode
= 0x20000000 | (r1
<< SA
) | (r1
<< SB
);
1777 opcode
= insns
[0].opcode
;
1778 /* merge in addend */
1779 insns
[1].opcode
|= addend
& 0xffff;
1780 insns
[0].opcode
|= ((addend
>> 16)
1781 + (addend
& 0x8000 ? 1 : 0));
1783 ecoff_set_gp_prolog_size (0);
1792 case 'b': /* setgp */
1793 switch (OUTPUT_FLAVOR
)
1795 case bfd_target_aout_flavour
:
1796 /* generate "zap %r,0xf,$gp" to take high 32 bits */
1797 opcode
|= 0x48001600 /* zap ?,#,?*/
1798 | (0xf << SN
) | (base_register
);
1805 case 'c': /* jsr $r,foo becomes
1808 Register 27, t12, is used by convention
1811 struct alpha_it
*jsr
;
1813 struct reloc_data
*r
;
1815 /* We still have to parse the function name */
1818 getExpression (s
, &insns
[0]);
1819 etmp
= insns
[0].reloc
[0].exp
;
1821 num_gen
= load_expression (PV
, &insns
[0]);
1824 jsr
= &insns
[num_gen
++];
1825 jsr
->opcode
= (0x68004000 /* jsr */
1831 /* LITUSE wasn't emitted yet */
1832 jsr
->reloc
[0].code
= BFD_RELOC_ALPHA_LITUSE
;
1833 jsr
->reloc
[0].exp
= lituse_jsr
;
1840 r
->code
= BFD_RELOC_ALPHA_HINT
;
1842 opcode
= insns
[0].opcode
;
1847 /* Sub-word loads and stores. We load the address into
1848 $at, which might involve using the `P' parameter
1849 processing too, then emit a sequence to get the job
1850 done, using unaligned memory accesses and byte
1851 manipulation, with t9 and t10 as temporaries. */
1853 /* Characteristics of access. */
1854 int is_load
, is_unsigned
= 0, is_unaligned
= 0;
1855 int mode_size
, mode
;
1856 /* Register operand. */
1858 /* Addend for loads and stores. */
1860 /* Which register do we use for the address? */
1864 /* Pick apart name and set flags. */
1865 const char *s
= pattern
->name
;
1873 if (s
[0] == 'l' && s
[1] == 'd')
1875 else if (s
[0] == 's' && s
[1] == 't')
1878 as_fatal ("unrecognized sub-word access insn `%s'",
1883 if (mode
== 'b') mode_size
= 1;
1884 else if (mode
== 'w') mode_size
= 2;
1885 else if (mode
== 'l') mode_size
= 4;
1886 else if (mode
== 'q') mode_size
= 8;
1897 /* Longwords are always kept sign-extended. */
1898 if (mode
== 'l' && is_unsigned
)
1900 /* There's no special unaligned byte handling. */
1901 if (mode
== 'b' && is_unaligned
)
1903 /* Stores don't care about signedness. */
1904 if (!is_load
&& is_unsigned
)
1908 if (args
[-2] == 'P')
1917 r1 -> (opcode >> SA) & 31
1918 num -> insns->reloc[0].*
1920 We want to emit "lda at,num(r2)", since these
1921 operations require the use of a single register
1922 with the starting address of the memory operand
1925 We could probably get away without doing this
1926 (and use r2 below, with the addend for the
1927 actual reads and writes) in cases where the
1928 addend is known to be a multiple of 8. */
1930 int r1
= (opcode
>> SA
) & 31;
1932 if (insns
[0].reloc
[0].code
== BFD_RELOC_NONE
)
1934 else if (insns
[0].reloc
[0].code
== BFD_RELOC_16
)
1936 if (insns
[0].reloc
[0].exp
.X_op
!= O_constant
)
1938 addend
= insns
[0].reloc
[0].exp
.X_add_number
;
1943 if (addend
+ mode_size
- 1 < 0x7fff
1944 && (addend
% 8) == 0
1945 && (r2
< T9
|| r2
> T12
))
1952 /* Let later relocation processing deal
1953 with the addend field. */
1954 insns
[num_gen
-1].opcode
= (0x20000000 /* lda */
1963 /* Because the emit_* routines append directly to
1964 the current frag, we now need to flush any
1968 for (i
= 0; i
< num_gen
; i
++)
1969 emit_insn (&insns
[i
]);
1978 reg2
= T9
, reg3
= T10
;
1982 emit_load_unal (addr
, addend
, T9
);
1984 emit_load_unal (addr
, addend
+ mode_size
- 1, T10
);
1985 emit_extract_r (T9
, addr
, reg2
, mode
, 'l');
1988 emit_extract_r (T10
, addr
, reg3
, mode
, 'h');
1989 emit_bis_r (T9
, T10
, reg
);
1992 emit_sign_extend (reg
, mode_size
* 8);
1996 /* The second word gets processed first
1997 because if the address does turn out to be
1998 aligned, the processing for the second word
1999 will be pushing around all-zeros, and the
2000 entire value will be handled as the `first'
2001 word. So we want to store the `first' word
2003 /* Pair these up so that the memory loads get
2004 separated from each other, as well as being
2005 well in advance of the uses of the values
2009 emit_load_unal (addr
, addend
+ mode_size
- 1, T11
);
2010 emit_insert_r (reg
, addr
, T12
, mode
, 'h');
2012 emit_load_unal (addr
, addend
, T9
);
2013 emit_insert_r (reg
, addr
, T10
, mode
, 'l');
2015 emit_mask_r (T12
, addr
, T12
, mode
, 'h');
2016 emit_mask_r (T10
, addr
, T10
, mode
, 'l');
2018 emit_bis_r (T11
, T12
, T11
);
2019 emit_bis_r (T9
, T10
, T9
);
2021 emit_store_unal (addr
, addend
+ mode_size
- 1, T11
);
2022 emit_store_unal (addr
, addend
, T9
);
2027 /* DIVISION and MODULUS. Yech.
2028 Convert OP x,y,result
2034 with appropriate optimizations if t10,t11,t12
2035 are the registers specified by the compiler.
2036 We are missing an obvious optimization
2037 opportunity here; if the ldq generated by the
2038 jsr assembly requires a cycle or two to make
2039 the value available, initiating it before one
2040 or two of the mov instructions would result in
2041 faster execution. */
2042 case '0': /* reml */
2043 case '1': /* divl */
2044 case '2': /* remq */
2045 case '3': /* divq */
2046 case '4': /* remlu */
2047 case '5': /* divlu */
2048 case '6': /* remqu */
2049 case '7': /* divqu */
2051 static char func
[8][6] = {
2052 "reml", "divl", "remq", "divq",
2053 "remlu", "divlu", "remqu", "divqu"
2058 /* All regs parsed, in opcode */
2060 /* Do the expansions, one instr at a time */
2062 reg
= (opcode
>> SA
) & 31;
2066 sprintf (expansion
, "mov $%d,$%d", reg
, T10
);
2067 md_assemble (expansion
);
2069 reg
= (opcode
>> SB
) & 31;
2071 /* we already overwrote it! */
2073 else if (reg
!= T11
)
2076 sprintf (expansion
, "mov $%d,$%d", reg
, T11
);
2077 md_assemble (expansion
);
2079 sprintf (expansion
, "lda $%d,__%s", PV
, func
[*args
- '0']);
2080 md_assemble (expansion
);
2081 sprintf (expansion
, "jsr $%d,($%d),__%s", T9
, PV
,
2083 md_assemble (expansion
);
2085 if (!first_32bit_quadrant
)
2090 md_assemble (expansion
);
2093 sprintf (expansion
, "ldgp $%d,0($%d)",
2095 md_assemble (expansion
);
2097 /* Use insns[0] to get at the result */
2098 if ((reg
= (opcode
& 31)) != PV
)
2099 opcode
= (0x47e00400 /* or zero,zero,zero */
2101 | reg
/* Rc */ ); /* pv->z */
2117 /* Args don't match. */
2118 if (&pattern
[1] - alpha_opcodes
< NUMOPCODES
2119 && !strcmp (pattern
->name
, pattern
[1].name
))
2127 as_warn ("Illegal operands");
2133 /* Args match, see if a float instructions and -nofloats */
2134 if (nofloats
&& pattern
->isa_float
)
2140 insns
[0].opcode
= opcode
;
2144 /* Turn a string in input_line_pointer into a floating point constant
2145 of type type, and store the appropriate bytes in *litP. The number
2146 of LITTLENUMS emitted is stored in *sizeP. An error message is
2147 returned, or NULL on OK. */
2149 /* Equal to MAX_PRECISION in atof-ieee.c */
2150 #define MAX_LITTLENUMS 6
2153 md_atof (type
, litP
, sizeP
)
2159 LITTLENUM_TYPE words
[MAX_LITTLENUMS
];
2160 LITTLENUM_TYPE
*wordP
;
2162 char *atof_ieee (), *vax_md_atof ();
2168 /* VAX md_atof doesn't like "G" for some reason. */
2172 return vax_md_atof (type
, litP
, sizeP
);
2195 return "Bad call to MD_ATOF()";
2197 t
= atof_ieee (input_line_pointer
, type
, words
);
2199 input_line_pointer
= t
;
2200 *sizeP
= prec
* sizeof (LITTLENUM_TYPE
);
2202 for (wordP
= words
+ prec
- 1; prec
--;)
2204 md_number_to_chars (litP
, (long) (*wordP
--), sizeof (LITTLENUM_TYPE
));
2205 litP
+= sizeof (LITTLENUM_TYPE
);
2212 md_bignum_to_chars (buf
, bignum
, nchars
)
2214 LITTLENUM_TYPE
*bignum
;
2219 LITTLENUM_TYPE work
= *bignum
++;
2220 int nb
= CHARS_PER_LITTLENUM
;
2224 *buf
++ = work
& ((1 << BITS_PER_CHAR
) - 1);
2227 work
>>= BITS_PER_CHAR
;
2233 CONST
char *md_shortopts
= "Fm:";
2234 struct option md_longopts
[] = {
2235 #define OPTION_32ADDR (OPTION_MD_BASE)
2236 {"32addr", no_argument
, NULL
, OPTION_32ADDR
},
2237 {NULL
, no_argument
, NULL
, 0}
2239 size_t md_longopts_size
= sizeof(md_longopts
);
2242 md_parse_option (c
, arg
)
2260 if (!strcmp (arg
, "21064"))
2262 else if (!strcmp (arg
, "21066"))
2264 else if (!strcmp (arg
, "21164"))
2268 as_bad ("invalid architecture %s", arg
);
2272 if (machine
!= 0 && machine
!= mach
)
2274 as_warn ("machine type %lu already chosen, overriding with %lu",
2289 md_show_usage (stream
)
2294 -32addr treat addresses as 32-bit values\n\
2295 -F lack floating point instructions support\n\
2296 -m21064 | -m21066 | -m21164\n\
2297 specify variant of Alpha architecture\n");
2304 /* XXXX Align to cache linesize XXXXX */
2311 /* Takes ".proc name,nargs" */
2312 name
= input_line_pointer
;
2313 c
= get_symbol_end ();
2314 p
= input_line_pointer
;
2315 symbolP
= symbol_find_or_make (name
);
2318 if (*input_line_pointer
!= ',')
2321 as_warn ("Expected comma after name \"%s\"", name
);
2324 ignore_rest_of_line ();
2328 input_line_pointer
++;
2329 temp
= get_absolute_expression ();
2331 /* symbolP->sy_other = (signed char) temp; */
2332 as_warn ("unhandled: .proc %s,%d", name
, temp
);
2333 demand_empty_rest_of_line ();
2340 char *name
= input_line_pointer
, ch
, *s
;
2343 while (!is_end_of_line
[(unsigned char) *input_line_pointer
])
2344 input_line_pointer
++;
2345 ch
= *input_line_pointer
;
2346 *input_line_pointer
= '\0';
2349 if (s
[0] == 'n' && s
[1] == 'o')
2354 if (!strcmp ("reorder", s
))
2356 else if (!strcmp ("at", s
))
2358 else if (!strcmp ("macro", s
))
2361 as_warn ("Tried to set unrecognized symbol: %s", name
);
2362 *input_line_pointer
= ch
;
2363 demand_empty_rest_of_line ();
2366 /* @@ Is this right?? */
2368 md_pcrel_from (fixP
)
2371 valueT addr
= fixP
->fx_where
+ fixP
->fx_frag
->fr_address
;
2372 switch (fixP
->fx_r_type
)
2374 case BFD_RELOC_ALPHA_GPDISP_HI16
:
2375 case BFD_RELOC_ALPHA_GPDISP_LO16
:
2378 return fixP
->fx_size
+ addr
;
2383 alpha_do_align (n
, fill
)
2388 && (now_seg
== text_section
2389 || !strcmp (now_seg
->name
, ".init")
2390 || !strcmp (now_seg
->name
, ".fini")))
2392 static const unsigned char nop_pattern
[] = { 0x1f, 0x04, 0xff, 0x47 };
2393 frag_align_pattern (n
, nop_pattern
, sizeof (nop_pattern
));
2400 md_apply_fix (fixP
, valueP
)
2407 char *p
= fixP
->fx_frag
->fr_literal
+ fixP
->fx_where
;
2411 switch (fixP
->fx_r_type
)
2413 /* The GPDISP relocations are processed internally with a symbol
2414 referring to the current function; we need to drop in a value
2415 which, when added to the address of the start of the function,
2416 gives the desired GP. */
2417 case BFD_RELOC_ALPHA_GPDISP_HI16
:
2418 case BFD_RELOC_ALPHA_GPDISP_LO16
:
2420 if (fixP
->fx_r_type
== BFD_RELOC_ALPHA_GPDISP_HI16
)
2422 assert (fixP
->fx_next
->fx_r_type
== BFD_RELOC_ALPHA_GPDISP_LO16
);
2425 fprintf_vma (stdout
, addend
);
2428 if (addend
& 0x8000)
2431 fixP
->fx_offset
= 4; /* @@ Compute this using fx_next. */
2437 fprintf_vma (stdout
, addend
);
2441 fixP
->fx_offset
= 0;
2443 md_number_to_chars (fixP
->fx_frag
->fr_literal
+ fixP
->fx_where
,
2445 fixP
->fx_addsy
= section_symbol (absolute_section
);
2446 fixP
->fx_offset
+= fixP
->fx_frag
->fr_address
+ fixP
->fx_where
;
2450 /* Write 8 bits, shifted left 13 bit positions. */
2454 *p
|= (value
<< 5) & 0xe0;
2462 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2463 "overflow in type-%d reloc", (int) fixP
->fx_r_type
);
2473 /* Don't want overflow checking. */
2476 if (fixP
->fx_pcrel
== 0
2477 && fixP
->fx_addsy
== 0)
2479 md_number_to_chars (p
, value
, size
);
2480 /* @@ Overflow checks?? */
2486 if (fixP
->fx_addsy
!= 0
2487 && fixP
->fx_addsy
->bsym
->section
!= absolute_section
)
2488 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2489 "PALcode instructions require immediate constant function code");
2490 else if (value
>> 26 != 0)
2491 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2492 "overflow in 26-bit PALcode function field");
2493 *p
++ = value
& 0xff;
2495 *p
++ = value
& 0xff;
2497 *p
++ = value
& 0xff;
2508 if (fixP
->fx_addsy
!= 0
2509 && fixP
->fx_addsy
->bsym
->section
!= absolute_section
)
2510 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2511 "ret/jsr_coroutine requires constant in displacement field");
2512 else if (value
>> 14 != 0)
2513 as_bad_where (fixP
->fx_file
, fixP
->fx_line
,
2514 "overflow in 14-bit operand field of ret or jsr_coroutine");
2515 *p
++ = value
& 0xff;
2517 *p
= (*p
& 0xc0) | (value
& 0x3f);
2520 case BFD_RELOC_23_PCREL_S2
:
2521 /* Write 21 bits only. */
2523 *p
++ = value
& 0xff;
2525 *p
++ = value
& 0xff;
2528 *p
|= (value
& 0x1f);
2531 case BFD_RELOC_ALPHA_LITERAL
:
2532 case BFD_RELOC_ALPHA_LITUSE
:
2535 case BFD_RELOC_GPREL32
:
2536 assert (fixP
->fx_subsy
== gp
);
2537 value
= - alpha_gp_value
; /* huh? this works... */
2539 md_number_to_chars (p
, value
, 4);
2542 case BFD_RELOC_ALPHA_HINT
:
2543 if (fixP
->fx_addsy
== 0 && fixP
->fx_pcrel
== 0)
2551 as_fatal ("unknown relocation type %d?", fixP
->fx_r_type
);
2555 if (fixP
->fx_addsy
== 0 && fixP
->fx_pcrel
== 0)
2557 printf ("type %d reloc done?\n", fixP
->fx_r_type
);
2567 alpha_frob_ecoff_data ()
2570 /* $zero and $f31 are read-only */
2571 alpha_gprmask
&= ~1;
2572 alpha_fprmask
&= ~1;
2575 /* The Alpha has support for some VAX floating point types, as well as for
2576 IEEE floating point. We consider IEEE to be the primary floating point
2577 format, and sneak in the VAX floating point support here. */
2578 #define md_atof vax_md_atof
2579 #include "config/atof-vax.c"