1 /* tc-alpha.c - Processor-specific code for the DEC Alpha AXP CPU.
2 Copyright 1989, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000,
3 2001, 2002 Free Software Foundation, Inc.
4 Contributed by Carnegie Mellon University, 1993.
5 Written by Alessandro Forin, based on earlier gas-1.38 target CPU files.
6 Modified by Ken Raeburn for gas-2.x and ECOFF support.
7 Modified by Richard Henderson for ELF support.
8 Modified by Klaus K"ampf for EVAX (OpenVMS/Alpha) support.
10 This file is part of GAS, the GNU Assembler.
12 GAS is free software; you can redistribute it and/or modify
13 it under the terms of the GNU General Public License as published by
14 the Free Software Foundation; either version 2, or (at your option)
17 GAS is distributed in the hope that it will be useful,
18 but WITHOUT ANY WARRANTY; without even the implied warranty of
19 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 GNU General Public License for more details.
22 You should have received a copy of the GNU General Public License
23 along with GAS; see the file COPYING. If not, write to the Free
24 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
28 * Mach Operating System
29 * Copyright (c) 1993 Carnegie Mellon University
30 * All Rights Reserved.
32 * Permission to use, copy, modify and distribute this software and its
33 * documentation is hereby granted, provided that both the copyright
34 * notice and this permission notice appear in all copies of the
35 * software, derivative works or modified versions, and any portions
36 * thereof, and that both notices appear in supporting documentation.
38 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
39 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
40 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
42 * Carnegie Mellon requests users of this software to return to
44 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
45 * School of Computer Science
46 * Carnegie Mellon University
47 * Pittsburgh PA 15213-3890
49 * any improvements or extensions that they make and grant Carnegie the
50 * rights to redistribute these changes.
55 #include "struc-symbol.h"
58 #include "opcode/alpha.h"
61 #include "elf/alpha.h"
62 #include "dwarf2dbg.h"
65 #include "safe-ctype.h"
69 #define TOKENIZE_ERROR -1
70 #define TOKENIZE_ERROR_REPORT -2
72 #define MAX_INSN_FIXUPS 2
73 #define MAX_INSN_ARGS 5
77 bfd_reloc_code_real_type reloc;
83 struct alpha_fixup fixups[MAX_INSN_FIXUPS];
87 enum alpha_macro_arg {
99 void (*emit) PARAMS ((const expressionS *, int, const PTR));
101 enum alpha_macro_arg argsets[16];
104 /* Extra expression types. */
106 #define O_pregister O_md1 /* O_register, in parentheses */
107 #define O_cpregister O_md2 /* + a leading comma */
109 /* Note, the alpha_reloc_op table below depends on the ordering
110 of O_literal .. O_gpre16. */
111 #define O_literal O_md3 /* !literal relocation */
112 #define O_lituse_addr O_md4 /* !lituse_addr relocation */
113 #define O_lituse_base O_md5 /* !lituse_base relocation */
114 #define O_lituse_bytoff O_md6 /* !lituse_bytoff relocation */
115 #define O_lituse_jsr O_md7 /* !lituse_jsr relocation */
116 #define O_gpdisp O_md8 /* !gpdisp relocation */
117 #define O_gprelhigh O_md9 /* !gprelhigh relocation */
118 #define O_gprellow O_md10 /* !gprellow relocation */
119 #define O_gprel O_md11 /* !gprel relocation */
120 #define O_samegp O_md12 /* !samegp relocation */
122 #define DUMMY_RELOC_LITUSE_ADDR (BFD_RELOC_UNUSED + 1)
123 #define DUMMY_RELOC_LITUSE_BASE (BFD_RELOC_UNUSED + 2)
124 #define DUMMY_RELOC_LITUSE_BYTOFF (BFD_RELOC_UNUSED + 3)
125 #define DUMMY_RELOC_LITUSE_JSR (BFD_RELOC_UNUSED + 4)
127 #define LITUSE_ADDR 0
128 #define LITUSE_BASE 1
129 #define LITUSE_BYTOFF 2
132 #define USER_RELOC_P(R) ((R) >= O_literal && (R) <= O_samegp)
134 /* Macros for extracting the type and number of encoded register tokens */
136 #define is_ir_num(x) (((x) & 32) == 0)
137 #define is_fpr_num(x) (((x) & 32) != 0)
138 #define regno(x) ((x) & 31)
140 /* Something odd inherited from the old assembler */
142 #define note_gpreg(R) (alpha_gprmask |= (1 << (R)))
143 #define note_fpreg(R) (alpha_fprmask |= (1 << (R)))
145 /* Predicates for 16- and 32-bit ranges */
146 /* XXX: The non-shift version appears to trigger a compiler bug when
147 cross-assembling from x86 w/ gcc 2.7.2. */
150 #define range_signed_16(x) \
151 (((offsetT) (x) >> 15) == 0 || ((offsetT) (x) >> 15) == -1)
152 #define range_signed_32(x) \
153 (((offsetT) (x) >> 31) == 0 || ((offsetT) (x) >> 31) == -1)
155 #define range_signed_16(x) ((offsetT) (x) >= -(offsetT) 0x8000 && \
156 (offsetT) (x) <= (offsetT) 0x7FFF)
157 #define range_signed_32(x) ((offsetT) (x) >= -(offsetT) 0x80000000 && \
158 (offsetT) (x) <= (offsetT) 0x7FFFFFFF)
161 /* Macros for sign extending from 16- and 32-bits. */
162 /* XXX: The cast macros will work on all the systems that I care about,
163 but really a predicate should be found to use the non-cast forms. */
166 #define sign_extend_16(x) ((short) (x))
167 #define sign_extend_32(x) ((int) (x))
169 #define sign_extend_16(x) ((offsetT) (((x) & 0xFFFF) ^ 0x8000) - 0x8000)
170 #define sign_extend_32(x) ((offsetT) (((x) & 0xFFFFFFFF) \
171 ^ 0x80000000) - 0x80000000)
174 /* Macros to build tokens */
176 #define set_tok_reg(t, r) (memset (&(t), 0, sizeof (t)), \
177 (t).X_op = O_register, \
178 (t).X_add_number = (r))
179 #define set_tok_preg(t, r) (memset (&(t), 0, sizeof (t)), \
180 (t).X_op = O_pregister, \
181 (t).X_add_number = (r))
182 #define set_tok_cpreg(t, r) (memset (&(t), 0, sizeof (t)), \
183 (t).X_op = O_cpregister, \
184 (t).X_add_number = (r))
185 #define set_tok_freg(t, r) (memset (&(t), 0, sizeof (t)), \
186 (t).X_op = O_register, \
187 (t).X_add_number = (r) + 32)
188 #define set_tok_sym(t, s, a) (memset (&(t), 0, sizeof (t)), \
189 (t).X_op = O_symbol, \
190 (t).X_add_symbol = (s), \
191 (t).X_add_number = (a))
192 #define set_tok_const(t, n) (memset (&(t), 0, sizeof (t)), \
193 (t).X_op = O_constant, \
194 (t).X_add_number = (n))
196 /* Prototypes for all local functions */
198 static struct alpha_reloc_tag *get_alpha_reloc_tag PARAMS ((long));
199 static void alpha_adjust_symtab_relocs PARAMS ((bfd *, asection *, PTR));
201 static int tokenize_arguments PARAMS ((char *, expressionS *, int));
202 static const struct alpha_opcode *find_opcode_match
203 PARAMS ((const struct alpha_opcode *, const expressionS *, int *, int *));
204 static const struct alpha_macro *find_macro_match
205 PARAMS ((const struct alpha_macro *, const expressionS *, int *));
206 static unsigned insert_operand
207 PARAMS ((unsigned, const struct alpha_operand *, offsetT, char *, unsigned));
208 static void assemble_insn
209 PARAMS ((const struct alpha_opcode *, const expressionS *, int,
210 struct alpha_insn *, bfd_reloc_code_real_type));
211 static void emit_insn PARAMS ((struct alpha_insn *));
212 static void assemble_tokens_to_insn
213 PARAMS ((const char *, const expressionS *, int, struct alpha_insn *));
214 static void assemble_tokens
215 PARAMS ((const char *, const expressionS *, int, int));
217 static long load_expression
218 PARAMS ((int, const expressionS *, int *, expressionS *));
220 static void emit_ldgp PARAMS ((const expressionS *, int, const PTR));
221 static void emit_division PARAMS ((const expressionS *, int, const PTR));
222 static void emit_lda PARAMS ((const expressionS *, int, const PTR));
223 static void emit_ldah PARAMS ((const expressionS *, int, const PTR));
224 static void emit_ir_load PARAMS ((const expressionS *, int, const PTR));
225 static void emit_loadstore PARAMS ((const expressionS *, int, const PTR));
226 static void emit_jsrjmp PARAMS ((const expressionS *, int, const PTR));
227 static void emit_ldX PARAMS ((const expressionS *, int, const PTR));
228 static void emit_ldXu PARAMS ((const expressionS *, int, const PTR));
229 static void emit_uldX PARAMS ((const expressionS *, int, const PTR));
230 static void emit_uldXu PARAMS ((const expressionS *, int, const PTR));
231 static void emit_ldil PARAMS ((const expressionS *, int, const PTR));
232 static void emit_stX PARAMS ((const expressionS *, int, const PTR));
233 static void emit_ustX PARAMS ((const expressionS *, int, const PTR));
234 static void emit_sextX PARAMS ((const expressionS *, int, const PTR));
235 static void emit_retjcr PARAMS ((const expressionS *, int, const PTR));
237 static void s_alpha_text PARAMS ((int));
238 static void s_alpha_data PARAMS ((int));
240 static void s_alpha_comm PARAMS ((int));
241 static void s_alpha_rdata PARAMS ((int));
244 static void s_alpha_sdata PARAMS ((int));
247 static void s_alpha_section PARAMS ((int));
248 static void s_alpha_ent PARAMS ((int));
249 static void s_alpha_end PARAMS ((int));
250 static void s_alpha_mask PARAMS ((int));
251 static void s_alpha_frame PARAMS ((int));
252 static void s_alpha_prologue PARAMS ((int));
253 static void s_alpha_file PARAMS ((int));
254 static void s_alpha_loc PARAMS ((int));
255 static void s_alpha_stab PARAMS ((int));
256 static void s_alpha_coff_wrapper PARAMS ((int));
259 static void s_alpha_section PARAMS ((int));
261 static void s_alpha_gprel32 PARAMS ((int));
262 static void s_alpha_float_cons PARAMS ((int));
263 static void s_alpha_proc PARAMS ((int));
264 static void s_alpha_set PARAMS ((int));
265 static void s_alpha_base PARAMS ((int));
266 static void s_alpha_align PARAMS ((int));
267 static void s_alpha_stringer PARAMS ((int));
268 static void s_alpha_space PARAMS ((int));
269 static void s_alpha_ucons PARAMS ((int));
270 static void s_alpha_arch PARAMS ((int));
272 static void create_literal_section PARAMS ((const char *, segT *, symbolS **));
274 static void select_gp_value PARAMS ((void));
276 static void alpha_align PARAMS ((int, char *, symbolS *, int));
278 /* Generic assembler global variables which must be defined by all
281 /* Characters which always start a comment. */
282 const char comment_chars[] = "#";
284 /* Characters which start a comment at the beginning of a line. */
285 const char line_comment_chars[] = "#";
287 /* Characters which may be used to separate multiple commands on a
289 const char line_separator_chars[] = ";";
291 /* Characters which are used to indicate an exponent in a floating
293 const char EXP_CHARS[] = "eE";
295 /* Characters which mean that a number is a floating point constant,
298 const char FLT_CHARS[] = "dD";
300 /* XXX: Do all of these really get used on the alpha?? */
301 char FLT_CHARS[] = "rRsSfFdDxXpP";
305 const char *md_shortopts = "Fm:g+1h:HG:";
307 const char *md_shortopts = "Fm:gG:";
310 struct option md_longopts[] = {
311 #define OPTION_32ADDR (OPTION_MD_BASE)
312 { "32addr", no_argument, NULL, OPTION_32ADDR },
313 #define OPTION_RELAX (OPTION_32ADDR + 1)
314 { "relax", no_argument, NULL, OPTION_RELAX },
316 #define OPTION_MDEBUG (OPTION_RELAX + 1)
317 #define OPTION_NO_MDEBUG (OPTION_MDEBUG + 1)
318 { "mdebug", no_argument, NULL, OPTION_MDEBUG },
319 { "no-mdebug", no_argument, NULL, OPTION_NO_MDEBUG },
321 { NULL, no_argument, NULL, 0 }
324 size_t md_longopts_size = sizeof (md_longopts);
328 #define AXP_REG_R16 16
329 #define AXP_REG_R17 17
331 #define AXP_REG_T9 22
333 #define AXP_REG_T10 23
335 #define AXP_REG_T11 24
337 #define AXP_REG_T12 25
338 #define AXP_REG_AI 25
340 #define AXP_REG_FP 29
343 #define AXP_REG_GP AXP_REG_PV
344 #endif /* OBJ_EVAX */
346 /* The cpu for which we are generating code */
347 static unsigned alpha_target = AXP_OPCODE_BASE;
348 static const char *alpha_target_name = "<all>";
350 /* The hash table of instruction opcodes */
351 static struct hash_control *alpha_opcode_hash;
353 /* The hash table of macro opcodes */
354 static struct hash_control *alpha_macro_hash;
357 /* The $gp relocation symbol */
358 static symbolS *alpha_gp_symbol;
360 /* XXX: what is this, and why is it exported? */
361 valueT alpha_gp_value;
364 /* The current $gp register */
365 static int alpha_gp_register = AXP_REG_GP;
367 /* A table of the register symbols */
368 static symbolS *alpha_register_table[64];
370 /* Constant sections, or sections of constants */
372 static segT alpha_lita_section;
373 static segT alpha_lit4_section;
376 static segT alpha_link_section;
377 static segT alpha_ctors_section;
378 static segT alpha_dtors_section;
380 static segT alpha_lit8_section;
382 /* Symbols referring to said sections. */
384 static symbolS *alpha_lita_symbol;
385 static symbolS *alpha_lit4_symbol;
388 static symbolS *alpha_link_symbol;
389 static symbolS *alpha_ctors_symbol;
390 static symbolS *alpha_dtors_symbol;
392 static symbolS *alpha_lit8_symbol;
394 /* Literal for .litX+0x8000 within .lita */
396 static offsetT alpha_lit4_literal;
397 static offsetT alpha_lit8_literal;
401 /* The active .ent symbol. */
402 static symbolS *alpha_cur_ent_sym;
405 /* Is the assembler not allowed to use $at? */
406 static int alpha_noat_on = 0;
408 /* Are macros enabled? */
409 static int alpha_macros_on = 1;
411 /* Are floats disabled? */
412 static int alpha_nofloats_on = 0;
414 /* Are addresses 32 bit? */
415 static int alpha_addr32_on = 0;
417 /* Symbol labelling the current insn. When the Alpha gas sees
420 and the section happens to not be on an eight byte boundary, it
421 will align both the symbol and the .quad to an eight byte boundary. */
422 static symbolS *alpha_insn_label;
424 /* Whether we should automatically align data generation pseudo-ops.
425 .align 0 will turn this off. */
426 static int alpha_auto_align_on = 1;
428 /* The known current alignment of the current section. */
429 static int alpha_current_align;
431 /* These are exported to ECOFF code. */
432 unsigned long alpha_gprmask, alpha_fprmask;
434 /* Whether the debugging option was seen. */
435 static int alpha_debug;
438 /* Whether we are emitting an mdebug section. */
439 int alpha_flag_mdebug = -1;
442 /* Don't fully resolve relocations, allowing code movement in the linker. */
443 static int alpha_flag_relax;
445 /* What value to give to bfd_set_gp_size. */
446 static int g_switch_value = 8;
449 /* Collect information about current procedure here. */
451 symbolS *symbol; /* proc pdesc symbol */
453 int framereg; /* register for frame pointer */
454 int framesize; /* size of frame */
464 static int alpha_flag_hash_long_names = 0; /* -+ */
465 static int alpha_flag_show_after_trunc = 0; /* -H */
467 /* If the -+ switch is given, then a hash is appended to any name that is
468 * longer than 64 characters, else longer symbol names are truncated.
474 /* A table to map the spelling of a relocation operand into an appropriate
475 bfd_reloc_code_real_type type. The table is assumed to be ordered such
476 that op-O_literal indexes into it. */
478 #define ALPHA_RELOC_TABLE(op) \
479 (&alpha_reloc_op[ ((!USER_RELOC_P (op)) \
481 : (int) (op) - (int) O_literal) ])
483 #define DEF(NAME, RELOC, REQ, ALLOW) \
484 { #NAME, sizeof(#NAME)-1, O_##NAME, RELOC, REQ, ALLOW}
486 static const struct alpha_reloc_op_tag {
487 const char *name; /* string to lookup */
488 size_t length; /* size of the string */
489 operatorT op; /* which operator to use */
490 bfd_reloc_code_real_type reloc; /* relocation before frob */
491 unsigned int require_seq : 1; /* require a sequence number */
492 unsigned int allow_seq : 1; /* allow a sequence number */
493 } alpha_reloc_op[] = {
494 DEF(literal, BFD_RELOC_ALPHA_ELF_LITERAL, 0, 1),
495 DEF(lituse_addr, DUMMY_RELOC_LITUSE_ADDR, 1, 1),
496 DEF(lituse_base, DUMMY_RELOC_LITUSE_BASE, 1, 1),
497 DEF(lituse_bytoff, DUMMY_RELOC_LITUSE_BYTOFF, 1, 1),
498 DEF(lituse_jsr, DUMMY_RELOC_LITUSE_JSR, 1, 1),
499 DEF(gpdisp, BFD_RELOC_ALPHA_GPDISP, 1, 1),
500 DEF(gprelhigh, BFD_RELOC_ALPHA_GPREL_HI16, 0, 0),
501 DEF(gprellow, BFD_RELOC_ALPHA_GPREL_LO16, 0, 0),
502 DEF(gprel, BFD_RELOC_GPREL16, 0, 0),
503 DEF(samegp, BFD_RELOC_ALPHA_BRSGP, 0, 0)
508 static const int alpha_num_reloc_op
509 = sizeof (alpha_reloc_op) / sizeof (*alpha_reloc_op);
510 #endif /* RELOC_OP_P */
512 /* Maximum # digits needed to hold the largest sequence # */
513 #define ALPHA_RELOC_DIGITS 25
515 /* Structure to hold explict sequence information. */
516 struct alpha_reloc_tag
518 fixS *slaves; /* head of linked list of !literals */
519 segT segment; /* segment relocs are in or undefined_section*/
520 long sequence; /* sequence # */
521 unsigned n_master; /* # of literals */
522 unsigned n_slaves; /* # of lituses */
523 char multi_section_p; /* True if more than one section was used */
524 char string[1]; /* printable form of sequence to hash with */
527 /* Hash table to link up literals with the appropriate lituse */
528 static struct hash_control *alpha_literal_hash;
530 /* Sequence numbers for internal use by macros. */
531 static long next_sequence_num = -1;
533 /* A table of CPU names and opcode sets. */
535 static const struct cpu_type {
539 /* Ad hoc convention: cpu number gets palcode, process code doesn't.
540 This supports usage under DU 4.0b that does ".arch ev4", and
541 usage in MILO that does -m21064. Probably something more
542 specific like -m21064-pal should be used, but oh well. */
544 { "21064", AXP_OPCODE_BASE|AXP_OPCODE_EV4 },
545 { "21064a", AXP_OPCODE_BASE|AXP_OPCODE_EV4 },
546 { "21066", AXP_OPCODE_BASE|AXP_OPCODE_EV4 },
547 { "21068", AXP_OPCODE_BASE|AXP_OPCODE_EV4 },
548 { "21164", AXP_OPCODE_BASE|AXP_OPCODE_EV5 },
549 { "21164a", AXP_OPCODE_BASE|AXP_OPCODE_EV5|AXP_OPCODE_BWX },
550 { "21164pc", (AXP_OPCODE_BASE|AXP_OPCODE_EV5|AXP_OPCODE_BWX
552 { "21264", (AXP_OPCODE_BASE|AXP_OPCODE_EV6|AXP_OPCODE_BWX
553 |AXP_OPCODE_MAX|AXP_OPCODE_CIX) },
555 { "ev4", AXP_OPCODE_BASE },
556 { "ev45", AXP_OPCODE_BASE },
557 { "lca45", AXP_OPCODE_BASE },
558 { "ev5", AXP_OPCODE_BASE },
559 { "ev56", AXP_OPCODE_BASE|AXP_OPCODE_BWX },
560 { "pca56", AXP_OPCODE_BASE|AXP_OPCODE_BWX|AXP_OPCODE_MAX },
561 { "ev6", AXP_OPCODE_BASE|AXP_OPCODE_BWX|AXP_OPCODE_MAX|AXP_OPCODE_CIX },
563 { "all", AXP_OPCODE_BASE },
567 /* The macro table */
569 static const struct alpha_macro alpha_macros[] = {
570 /* Load/Store macros */
571 { "lda", emit_lda, NULL,
572 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
573 { "ldah", emit_ldah, NULL,
574 { MACRO_IR, MACRO_EXP, MACRO_EOA } },
576 { "ldl", emit_ir_load, "ldl",
577 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
578 { "ldl_l", emit_ir_load, "ldl_l",
579 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
580 { "ldq", emit_ir_load, "ldq",
581 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
582 { "ldq_l", emit_ir_load, "ldq_l",
583 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
584 { "ldq_u", emit_ir_load, "ldq_u",
585 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
586 { "ldf", emit_loadstore, "ldf",
587 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
588 { "ldg", emit_loadstore, "ldg",
589 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
590 { "lds", emit_loadstore, "lds",
591 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
592 { "ldt", emit_loadstore, "ldt",
593 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
595 { "ldb", emit_ldX, (PTR) 0,
596 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
597 { "ldbu", emit_ldXu, (PTR) 0,
598 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
599 { "ldw", emit_ldX, (PTR) 1,
600 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
601 { "ldwu", emit_ldXu, (PTR) 1,
602 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
604 { "uldw", emit_uldX, (PTR) 1,
605 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
606 { "uldwu", emit_uldXu, (PTR) 1,
607 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
608 { "uldl", emit_uldX, (PTR) 2,
609 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
610 { "uldlu", emit_uldXu, (PTR) 2,
611 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
612 { "uldq", emit_uldXu, (PTR) 3,
613 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
615 { "ldgp", emit_ldgp, NULL,
616 { MACRO_IR, MACRO_EXP, MACRO_PIR, MACRO_EOA } },
618 { "ldi", emit_lda, NULL,
619 { MACRO_IR, MACRO_EXP, MACRO_EOA } },
620 { "ldil", emit_ldil, NULL,
621 { MACRO_IR, MACRO_EXP, MACRO_EOA } },
622 { "ldiq", emit_lda, NULL,
623 { MACRO_IR, MACRO_EXP, MACRO_EOA } },
625 { "ldif" emit_ldiq, NULL,
626 { MACRO_FPR, MACRO_EXP, MACRO_EOA } },
627 { "ldid" emit_ldiq, NULL,
628 { MACRO_FPR, MACRO_EXP, MACRO_EOA } },
629 { "ldig" emit_ldiq, NULL,
630 { MACRO_FPR, MACRO_EXP, MACRO_EOA } },
631 { "ldis" emit_ldiq, NULL,
632 { MACRO_FPR, MACRO_EXP, MACRO_EOA } },
633 { "ldit" emit_ldiq, NULL,
634 { MACRO_FPR, MACRO_EXP, MACRO_EOA } },
637 { "stl", emit_loadstore, "stl",
638 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
639 { "stl_c", emit_loadstore, "stl_c",
640 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
641 { "stq", emit_loadstore, "stq",
642 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
643 { "stq_c", emit_loadstore, "stq_c",
644 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
645 { "stq_u", emit_loadstore, "stq_u",
646 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
647 { "stf", emit_loadstore, "stf",
648 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
649 { "stg", emit_loadstore, "stg",
650 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
651 { "sts", emit_loadstore, "sts",
652 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
653 { "stt", emit_loadstore, "stt",
654 { MACRO_FPR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
656 { "stb", emit_stX, (PTR) 0,
657 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
658 { "stw", emit_stX, (PTR) 1,
659 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
660 { "ustw", emit_ustX, (PTR) 1,
661 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
662 { "ustl", emit_ustX, (PTR) 2,
663 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
664 { "ustq", emit_ustX, (PTR) 3,
665 { MACRO_IR, MACRO_EXP, MACRO_OPIR, MACRO_EOA } },
667 /* Arithmetic macros */
669 { "absl" emit_absl, 1, { IR } },
670 { "absl" emit_absl, 2, { IR, IR } },
671 { "absl" emit_absl, 2, { EXP, IR } },
672 { "absq" emit_absq, 1, { IR } },
673 { "absq" emit_absq, 2, { IR, IR } },
674 { "absq" emit_absq, 2, { EXP, IR } },
677 { "sextb", emit_sextX, (PTR) 0,
678 { MACRO_IR, MACRO_IR, MACRO_EOA,
680 /* MACRO_EXP, MACRO_IR, MACRO_EOA */ } },
681 { "sextw", emit_sextX, (PTR) 1,
682 { MACRO_IR, MACRO_IR, MACRO_EOA,
684 /* MACRO_EXP, MACRO_IR, MACRO_EOA */ } },
686 { "divl", emit_division, "__divl",
687 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
688 MACRO_IR, MACRO_IR, MACRO_EOA,
689 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
690 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
691 { "divlu", emit_division, "__divlu",
692 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
693 MACRO_IR, MACRO_IR, MACRO_EOA,
694 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
695 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
696 { "divq", emit_division, "__divq",
697 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
698 MACRO_IR, MACRO_IR, MACRO_EOA,
699 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
700 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
701 { "divqu", emit_division, "__divqu",
702 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
703 MACRO_IR, MACRO_IR, MACRO_EOA,
704 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
705 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
706 { "reml", emit_division, "__reml",
707 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
708 MACRO_IR, MACRO_IR, MACRO_EOA,
709 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
710 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
711 { "remlu", emit_division, "__remlu",
712 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
713 MACRO_IR, MACRO_IR, MACRO_EOA,
714 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
715 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
716 { "remq", emit_division, "__remq",
717 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
718 MACRO_IR, MACRO_IR, MACRO_EOA,
719 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
720 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
721 { "remqu", emit_division, "__remqu",
722 { MACRO_IR, MACRO_IR, MACRO_IR, MACRO_EOA,
723 MACRO_IR, MACRO_IR, MACRO_EOA,
724 /* MACRO_IR, MACRO_EXP, MACRO_IR, MACRO_EOA,
725 MACRO_IR, MACRO_EXP, MACRO_EOA */ } },
727 { "jsr", emit_jsrjmp, "jsr",
728 { MACRO_PIR, MACRO_EXP, MACRO_EOA,
729 MACRO_PIR, MACRO_EOA,
730 MACRO_IR, MACRO_EXP, MACRO_EOA,
731 MACRO_EXP, MACRO_EOA } },
732 { "jmp", emit_jsrjmp, "jmp",
733 { MACRO_PIR, MACRO_EXP, MACRO_EOA,
734 MACRO_PIR, MACRO_EOA,
735 MACRO_IR, MACRO_EXP, MACRO_EOA,
736 MACRO_EXP, MACRO_EOA } },
737 { "ret", emit_retjcr, "ret",
738 { MACRO_IR, MACRO_EXP, MACRO_EOA,
740 MACRO_PIR, MACRO_EXP, MACRO_EOA,
741 MACRO_PIR, MACRO_EOA,
742 MACRO_EXP, MACRO_EOA,
744 { "jcr", emit_retjcr, "jcr",
745 { MACRO_IR, MACRO_EXP, MACRO_EOA,
747 MACRO_PIR, MACRO_EXP, MACRO_EOA,
748 MACRO_PIR, MACRO_EOA,
749 MACRO_EXP, MACRO_EOA,
751 { "jsr_coroutine", emit_retjcr, "jcr",
752 { MACRO_IR, MACRO_EXP, MACRO_EOA,
754 MACRO_PIR, MACRO_EXP, MACRO_EOA,
755 MACRO_PIR, MACRO_EOA,
756 MACRO_EXP, MACRO_EOA,
760 static const unsigned int alpha_num_macros
761 = sizeof (alpha_macros) / sizeof (*alpha_macros);
763 /* Public interface functions */
765 /* This function is called once, at assembler startup time. It sets
766 up all the tables, etc. that the MD part of the assembler will
767 need, that can be determined before arguments are parsed. */
774 /* Verify that X_op field is wide enough. */
778 assert (e.X_op == O_max);
781 /* Create the opcode hash table */
783 alpha_opcode_hash = hash_new ();
784 for (i = 0; i < alpha_num_opcodes;)
786 const char *name, *retval, *slash;
788 name = alpha_opcodes[i].name;
789 retval = hash_insert (alpha_opcode_hash, name, (PTR) &alpha_opcodes[i]);
791 as_fatal (_("internal error: can't hash opcode `%s': %s"),
794 /* Some opcodes include modifiers of various sorts with a "/mod"
795 syntax, like the architecture manual suggests. However, for
796 use with gcc at least, we also need access to those same opcodes
799 if ((slash = strchr (name, '/')) != NULL)
801 char *p = xmalloc (strlen (name));
802 memcpy (p, name, slash - name);
803 strcpy (p + (slash - name), slash + 1);
805 (void) hash_insert (alpha_opcode_hash, p, (PTR) &alpha_opcodes[i]);
806 /* Ignore failures -- the opcode table does duplicate some
807 variants in different forms, like "hw_stq" and "hw_st/q". */
810 while (++i < alpha_num_opcodes
811 && (alpha_opcodes[i].name == name
812 || !strcmp (alpha_opcodes[i].name, name)))
816 /* Create the macro hash table */
818 alpha_macro_hash = hash_new ();
819 for (i = 0; i < alpha_num_macros;)
821 const char *name, *retval;
823 name = alpha_macros[i].name;
824 retval = hash_insert (alpha_macro_hash, name, (PTR) &alpha_macros[i]);
826 as_fatal (_("internal error: can't hash macro `%s': %s"),
829 while (++i < alpha_num_macros
830 && (alpha_macros[i].name == name
831 || !strcmp (alpha_macros[i].name, name)))
835 /* Construct symbols for each of the registers */
837 for (i = 0; i < 32; ++i)
840 sprintf (name, "$%d", i);
841 alpha_register_table[i] = symbol_create (name, reg_section, i,
847 sprintf (name, "$f%d", i - 32);
848 alpha_register_table[i] = symbol_create (name, reg_section, i,
852 /* Create the special symbols and sections we'll be using */
854 /* So .sbss will get used for tiny objects. */
855 bfd_set_gp_size (stdoutput, g_switch_value);
858 create_literal_section (".lita", &alpha_lita_section, &alpha_lita_symbol);
860 /* For handling the GP, create a symbol that won't be output in the
861 symbol table. We'll edit it out of relocs later. */
862 alpha_gp_symbol = symbol_create ("<GP value>", alpha_lita_section, 0x8000,
867 create_literal_section (".link", &alpha_link_section, &alpha_link_symbol);
873 segT sec = subseg_new (".mdebug", (subsegT) 0);
874 bfd_set_section_flags (stdoutput, sec, SEC_HAS_CONTENTS | SEC_READONLY);
875 bfd_set_section_alignment (stdoutput, sec, 3);
879 /* Create literal lookup hash table. */
880 alpha_literal_hash = hash_new ();
882 subseg_set (text_section, 0);
885 /* The public interface to the instruction assembler. */
891 char opname[32]; /* current maximum is 13 */
892 expressionS tok[MAX_INSN_ARGS];
896 /* split off the opcode */
897 opnamelen = strspn (str, "abcdefghijklmnopqrstuvwxyz_/46819");
898 trunclen = (opnamelen < sizeof (opname) - 1
900 : sizeof (opname) - 1);
901 memcpy (opname, str, trunclen);
902 opname[trunclen] = '\0';
904 /* tokenize the rest of the line */
905 if ((ntok = tokenize_arguments (str + opnamelen, tok, MAX_INSN_ARGS)) < 0)
907 if (ntok != TOKENIZE_ERROR_REPORT)
908 as_bad (_("syntax error"));
914 assemble_tokens (opname, tok, ntok, alpha_macros_on);
917 /* Round up a section's size to the appropriate boundary. */
920 md_section_align (seg, size)
924 int align = bfd_get_section_alignment (stdoutput, seg);
925 valueT mask = ((valueT) 1 << align) - 1;
927 return (size + mask) & ~mask;
930 /* Turn a string in input_line_pointer into a floating point constant
931 of type TYPE, and store the appropriate bytes in *LITP. The number
932 of LITTLENUMS emitted is stored in *SIZEP. An error message is
933 returned, or NULL on OK. */
935 /* Equal to MAX_PRECISION in atof-ieee.c */
936 #define MAX_LITTLENUMS 6
938 extern char *vax_md_atof PARAMS ((int, char *, int *));
941 md_atof (type, litP, sizeP)
947 LITTLENUM_TYPE words[MAX_LITTLENUMS];
948 LITTLENUM_TYPE *wordP;
955 /* VAX md_atof doesn't like "G" for some reason. */
959 return vax_md_atof (type, litP, sizeP);
982 return _("Bad call to MD_ATOF()");
984 t = atof_ieee (input_line_pointer, type, words);
986 input_line_pointer = t;
987 *sizeP = prec * sizeof (LITTLENUM_TYPE);
989 for (wordP = words + prec - 1; prec--;)
991 md_number_to_chars (litP, (long) (*wordP--), sizeof (LITTLENUM_TYPE));
992 litP += sizeof (LITTLENUM_TYPE);
998 /* Take care of the target-specific command-line options. */
1001 md_parse_option (c, arg)
1008 alpha_nofloats_on = 1;
1012 alpha_addr32_on = 1;
1020 g_switch_value = atoi (arg);
1025 const struct cpu_type *p;
1026 for (p = cpu_types; p->name; ++p)
1027 if (strcmp (arg, p->name) == 0)
1029 alpha_target_name = p->name, alpha_target = p->flags;
1032 as_warn (_("Unknown CPU identifier `%s'"), arg);
1038 case '+': /* For g++. Hash any name > 63 chars long. */
1039 alpha_flag_hash_long_names = 1;
1042 case 'H': /* Show new symbol after hash truncation */
1043 alpha_flag_show_after_trunc = 1;
1046 case 'h': /* for gnu-c/vax compatibility. */
1051 alpha_flag_relax = 1;
1056 alpha_flag_mdebug = 1;
1058 case OPTION_NO_MDEBUG:
1059 alpha_flag_mdebug = 0;
1070 /* Print a description of the command-line options that we accept. */
1073 md_show_usage (stream)
1078 -32addr treat addresses as 32-bit values\n\
1079 -F lack floating point instructions support\n\
1080 -mev4 | -mev45 | -mev5 | -mev56 | -mpca56 | -mev6 | -mall\n\
1081 specify variant of Alpha architecture\n\
1082 -m21064 | -m21066 | -m21164 | -m21164a | -m21164pc | -m21264\n\
1083 these variants include PALcode opcodes\n"),
1088 -+ hash encode (don't truncate) names longer than 64 characters\n\
1089 -H show new symbol after hash truncation\n"),
1094 /* Decide from what point a pc-relative relocation is relative to,
1095 relative to the pc-relative fixup. Er, relatively speaking. */
1098 md_pcrel_from (fixP)
1101 valueT addr = fixP->fx_where + fixP->fx_frag->fr_address;
1102 switch (fixP->fx_r_type)
1104 case BFD_RELOC_ALPHA_GPDISP:
1105 case BFD_RELOC_ALPHA_GPDISP_HI16:
1106 case BFD_RELOC_ALPHA_GPDISP_LO16:
1109 return fixP->fx_size + addr;
1113 /* Attempt to simplify or even eliminate a fixup. The return value is
1114 ignored; perhaps it was once meaningful, but now it is historical.
1115 To indicate that a fixup has been eliminated, set fixP->fx_done.
1117 For ELF, here it is that we transform the GPDISP_HI16 reloc we used
1118 internally into the GPDISP reloc used externally. We had to do
1119 this so that we'd have the GPDISP_LO16 reloc as a tag to compute
1120 the distance to the "lda" instruction for setting the addend to
1124 md_apply_fix3 (fixP, valP, seg)
1129 char * const fixpos = fixP->fx_frag->fr_literal + fixP->fx_where;
1130 valueT value = * valP;
1131 unsigned image, size;
1133 switch (fixP->fx_r_type)
1135 /* The GPDISP relocations are processed internally with a symbol
1136 referring to the current function; we need to drop in a value
1137 which, when added to the address of the start of the function,
1138 gives the desired GP. */
1139 case BFD_RELOC_ALPHA_GPDISP_HI16:
1141 fixS *next = fixP->fx_next;
1143 /* With user-specified !gpdisp relocations, we can be missing
1144 the matching LO16 reloc. We will have already issued an
1147 fixP->fx_offset = (next->fx_frag->fr_address + next->fx_where
1148 - fixP->fx_frag->fr_address - fixP->fx_where);
1150 value = (value - sign_extend_16 (value)) >> 16;
1153 fixP->fx_r_type = BFD_RELOC_ALPHA_GPDISP;
1157 case BFD_RELOC_ALPHA_GPDISP_LO16:
1158 value = sign_extend_16 (value);
1159 fixP->fx_offset = 0;
1165 fixP->fx_addsy = section_symbol (seg);
1166 md_number_to_chars (fixpos, value, 2);
1171 fixP->fx_r_type = BFD_RELOC_16_PCREL;
1176 fixP->fx_r_type = BFD_RELOC_32_PCREL;
1181 fixP->fx_r_type = BFD_RELOC_64_PCREL;
1184 if (fixP->fx_pcrel == 0 && fixP->fx_addsy == 0)
1186 md_number_to_chars (fixpos, value, size);
1192 case BFD_RELOC_GPREL32:
1193 assert (fixP->fx_subsy == alpha_gp_symbol);
1195 /* FIXME: inherited this obliviousness of `value' -- why? */
1196 md_number_to_chars (fixpos, -alpha_gp_value, 4);
1199 case BFD_RELOC_GPREL32:
1201 case BFD_RELOC_GPREL16:
1202 case BFD_RELOC_ALPHA_GPREL_HI16:
1203 case BFD_RELOC_ALPHA_GPREL_LO16:
1206 case BFD_RELOC_23_PCREL_S2:
1207 if (fixP->fx_pcrel == 0 && fixP->fx_addsy == 0)
1209 image = bfd_getl32 (fixpos);
1210 image = (image & ~0x1FFFFF) | ((value >> 2) & 0x1FFFFF);
1215 case BFD_RELOC_ALPHA_HINT:
1216 if (fixP->fx_pcrel == 0 && fixP->fx_addsy == 0)
1218 image = bfd_getl32 (fixpos);
1219 image = (image & ~0x3FFF) | ((value >> 2) & 0x3FFF);
1225 case BFD_RELOC_ALPHA_BRSGP:
1230 case BFD_RELOC_ALPHA_LITERAL:
1231 md_number_to_chars (fixpos, value, 2);
1234 case BFD_RELOC_ALPHA_ELF_LITERAL:
1235 case BFD_RELOC_ALPHA_LITUSE:
1236 case BFD_RELOC_ALPHA_LINKAGE:
1237 case BFD_RELOC_ALPHA_CODEADDR:
1240 case BFD_RELOC_VTABLE_INHERIT:
1241 case BFD_RELOC_VTABLE_ENTRY:
1246 const struct alpha_operand *operand;
1248 if ((int) fixP->fx_r_type >= 0)
1249 as_fatal (_("unhandled relocation type %s"),
1250 bfd_get_reloc_code_name (fixP->fx_r_type));
1252 assert (-(int) fixP->fx_r_type < (int) alpha_num_operands);
1253 operand = &alpha_operands[-(int) fixP->fx_r_type];
1255 /* The rest of these fixups only exist internally during symbol
1256 resolution and have no representation in the object file.
1257 Therefore they must be completely resolved as constants. */
1259 if (fixP->fx_addsy != 0
1260 && S_GET_SEGMENT (fixP->fx_addsy) != absolute_section)
1261 as_bad_where (fixP->fx_file, fixP->fx_line,
1262 _("non-absolute expression in constant field"));
1264 image = bfd_getl32 (fixpos);
1265 image = insert_operand (image, operand, (offsetT) value,
1266 fixP->fx_file, fixP->fx_line);
1271 if (fixP->fx_addsy != 0 || fixP->fx_pcrel != 0)
1275 as_warn_where (fixP->fx_file, fixP->fx_line,
1276 _("type %d reloc done?\n"), (int) fixP->fx_r_type);
1281 md_number_to_chars (fixpos, image, 4);
1287 /* Look for a register name in the given symbol. */
1290 md_undefined_symbol (name)
1295 int is_float = 0, num;
1300 if (name[1] == 'p' && name[2] == '\0')
1301 return alpha_register_table[AXP_REG_FP];
1306 if (!ISDIGIT (*++name))
1310 case '0': case '1': case '2': case '3': case '4':
1311 case '5': case '6': case '7': case '8': case '9':
1312 if (name[1] == '\0')
1313 num = name[0] - '0';
1314 else if (name[0] != '0' && ISDIGIT (name[1]) && name[2] == '\0')
1316 num = (name[0] - '0') * 10 + name[1] - '0';
1323 if (!alpha_noat_on && (num + is_float) == AXP_REG_AT)
1324 as_warn (_("Used $at without \".set noat\""));
1325 return alpha_register_table[num + is_float];
1328 if (name[1] == 't' && name[2] == '\0')
1331 as_warn (_("Used $at without \".set noat\""));
1332 return alpha_register_table[AXP_REG_AT];
1337 if (name[1] == 'p' && name[2] == '\0')
1338 return alpha_register_table[alpha_gp_register];
1342 if (name[1] == 'p' && name[2] == '\0')
1343 return alpha_register_table[AXP_REG_SP];
1351 /* @@@ Magic ECOFF bits. */
1354 alpha_frob_ecoff_data ()
1357 /* $zero and $f31 are read-only */
1358 alpha_gprmask &= ~1;
1359 alpha_fprmask &= ~1;
1363 /* Hook to remember a recently defined label so that the auto-align
1364 code can adjust the symbol after we know what alignment will be
1368 alpha_define_label (sym)
1371 alpha_insn_label = sym;
1374 /* If we have a BRSGP reloc to a local symbol, adjust it to BRADDR and
1375 let it get resolved at assembly time. */
1378 alpha_validate_fix (f)
1385 if (f->fx_r_type != BFD_RELOC_ALPHA_BRSGP)
1388 if (! S_IS_DEFINED (f->fx_addsy))
1391 switch (S_GET_OTHER (f->fx_addsy) & STO_ALPHA_STD_GPLOAD)
1393 case STO_ALPHA_NOPV:
1395 case STO_ALPHA_STD_GPLOAD:
1399 if (S_IS_LOCAL (f->fx_addsy))
1402 name = S_GET_NAME (f->fx_addsy);
1403 as_bad_where (f->fx_file, f->fx_line,
1404 _("!samegp reloc against symbol without .prologue: %s"),
1409 if (! (S_IS_EXTERN (f->fx_addsy) || S_IS_WEAK (f->fx_addsy)))
1411 f->fx_r_type = BFD_RELOC_23_PCREL_S2;
1412 f->fx_offset += offset;
1417 /* Return true if we must always emit a reloc for a type and false if
1418 there is some hope of resolving it at assembly time. */
1421 alpha_force_relocation (f)
1424 if (alpha_flag_relax)
1427 switch (f->fx_r_type)
1429 case BFD_RELOC_ALPHA_GPDISP_HI16:
1430 case BFD_RELOC_ALPHA_GPDISP_LO16:
1431 case BFD_RELOC_ALPHA_GPDISP:
1432 case BFD_RELOC_ALPHA_LITERAL:
1433 case BFD_RELOC_ALPHA_ELF_LITERAL:
1434 case BFD_RELOC_ALPHA_LITUSE:
1435 case BFD_RELOC_GPREL16:
1436 case BFD_RELOC_GPREL32:
1437 case BFD_RELOC_ALPHA_GPREL_HI16:
1438 case BFD_RELOC_ALPHA_GPREL_LO16:
1439 case BFD_RELOC_ALPHA_LINKAGE:
1440 case BFD_RELOC_ALPHA_CODEADDR:
1441 case BFD_RELOC_ALPHA_BRSGP:
1442 case BFD_RELOC_VTABLE_INHERIT:
1443 case BFD_RELOC_VTABLE_ENTRY:
1446 case BFD_RELOC_23_PCREL_S2:
1449 case BFD_RELOC_ALPHA_HINT:
1457 /* Return true if we can partially resolve a relocation now. */
1460 alpha_fix_adjustable (f)
1464 /* Prevent all adjustments to global symbols */
1465 if (S_IS_EXTERN (f->fx_addsy) || S_IS_WEAK (f->fx_addsy))
1469 /* Are there any relocation types for which we must generate a reloc
1470 but we can adjust the values contained within it? */
1471 switch (f->fx_r_type)
1473 case BFD_RELOC_ALPHA_GPDISP_HI16:
1474 case BFD_RELOC_ALPHA_GPDISP_LO16:
1475 case BFD_RELOC_ALPHA_GPDISP:
1476 case BFD_RELOC_ALPHA_BRSGP:
1479 case BFD_RELOC_ALPHA_LITERAL:
1480 case BFD_RELOC_ALPHA_ELF_LITERAL:
1481 case BFD_RELOC_ALPHA_LITUSE:
1482 case BFD_RELOC_ALPHA_LINKAGE:
1483 case BFD_RELOC_ALPHA_CODEADDR:
1486 case BFD_RELOC_VTABLE_ENTRY:
1487 case BFD_RELOC_VTABLE_INHERIT:
1490 case BFD_RELOC_GPREL16:
1491 case BFD_RELOC_GPREL32:
1492 case BFD_RELOC_ALPHA_GPREL_HI16:
1493 case BFD_RELOC_ALPHA_GPREL_LO16:
1494 case BFD_RELOC_23_PCREL_S2:
1497 case BFD_RELOC_ALPHA_HINT:
1506 /* Generate the BFD reloc to be stuck in the object file from the
1507 fixup used internally in the assembler. */
1510 tc_gen_reloc (sec, fixp)
1511 asection *sec ATTRIBUTE_UNUSED;
1516 reloc = (arelent *) xmalloc (sizeof (arelent));
1517 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
1518 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
1519 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
1521 /* Make sure none of our internal relocations make it this far.
1522 They'd better have been fully resolved by this point. */
1523 assert ((int) fixp->fx_r_type > 0);
1525 reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
1526 if (reloc->howto == NULL)
1528 as_bad_where (fixp->fx_file, fixp->fx_line,
1529 _("cannot represent `%s' relocation in object file"),
1530 bfd_get_reloc_code_name (fixp->fx_r_type));
1534 if (!fixp->fx_pcrel != !reloc->howto->pc_relative)
1536 as_fatal (_("internal error? cannot generate `%s' relocation"),
1537 bfd_get_reloc_code_name (fixp->fx_r_type));
1539 assert (!fixp->fx_pcrel == !reloc->howto->pc_relative);
1542 if (fixp->fx_r_type == BFD_RELOC_ALPHA_LITERAL)
1544 /* fake out bfd_perform_relocation. sigh */
1545 reloc->addend = -alpha_gp_value;
1550 reloc->addend = fixp->fx_offset;
1553 * Ohhh, this is ugly. The problem is that if this is a local global
1554 * symbol, the relocation will entirely be performed at link time, not
1555 * at assembly time. bfd_perform_reloc doesn't know about this sort
1556 * of thing, and as a result we need to fake it out here.
1558 if ((S_IS_EXTERN (fixp->fx_addsy) || S_IS_WEAK (fixp->fx_addsy)
1559 || (S_GET_SEGMENT (fixp->fx_addsy)->flags & SEC_MERGE))
1560 && !S_IS_COMMON (fixp->fx_addsy))
1561 reloc->addend -= symbol_get_bfdsym (fixp->fx_addsy)->value;
1568 /* Parse a register name off of the input_line and return a register
1569 number. Gets md_undefined_symbol above to do the register name
1572 Only called as a part of processing the ECOFF .frame directive. */
1575 tc_get_register (frame)
1576 int frame ATTRIBUTE_UNUSED;
1578 int framereg = AXP_REG_SP;
1581 if (*input_line_pointer == '$')
1583 char *s = input_line_pointer;
1584 char c = get_symbol_end ();
1585 symbolS *sym = md_undefined_symbol (s);
1587 *strchr (s, '\0') = c;
1588 if (sym && (framereg = S_GET_VALUE (sym)) <= 31)
1591 as_warn (_("frame reg expected, using $%d."), framereg);
1594 note_gpreg (framereg);
1598 /* This is called before the symbol table is processed. In order to
1599 work with gcc when using mips-tfile, we must keep all local labels.
1600 However, in other cases, we want to discard them. If we were
1601 called with -g, but we didn't see any debugging information, it may
1602 mean that gcc is smuggling debugging information through to
1603 mips-tfile, in which case we must generate all local labels. */
1608 alpha_frob_file_before_adjust ()
1610 if (alpha_debug != 0
1611 && ! ecoff_debugging_seen)
1612 flag_keep_locals = 1;
1615 #endif /* OBJ_ECOFF */
1617 static struct alpha_reloc_tag *
1618 get_alpha_reloc_tag (sequence)
1621 char buffer[ALPHA_RELOC_DIGITS];
1622 struct alpha_reloc_tag *info;
1624 sprintf (buffer, "!%ld", sequence);
1626 info = (struct alpha_reloc_tag *) hash_find (alpha_literal_hash, buffer);
1629 size_t len = strlen (buffer);
1632 info = (struct alpha_reloc_tag *)
1633 xcalloc (sizeof (struct alpha_reloc_tag) + len, 1);
1635 info->segment = now_seg;
1636 info->sequence = sequence;
1637 strcpy (info->string, buffer);
1638 errmsg = hash_insert (alpha_literal_hash, info->string, (PTR) info);
1646 /* Before the relocations are written, reorder them, so that user
1647 supplied !lituse relocations follow the appropriate !literal
1648 relocations, and similarly for !gpdisp relocations. */
1651 alpha_adjust_symtab ()
1653 if (alpha_literal_hash)
1654 bfd_map_over_sections (stdoutput, alpha_adjust_symtab_relocs, NULL);
1658 alpha_adjust_symtab_relocs (abfd, sec, ptr)
1659 bfd *abfd ATTRIBUTE_UNUSED;
1661 PTR ptr ATTRIBUTE_UNUSED;
1663 segment_info_type *seginfo = seg_info (sec);
1668 unsigned long n_slaves = 0;
1670 /* If seginfo is NULL, we did not create this section; don't do
1671 anything with it. By using a pointer to a pointer, we can update
1672 the links in place. */
1673 if (seginfo == NULL)
1676 /* If there are no relocations, skip the section. */
1677 if (! seginfo->fix_root)
1680 /* First rebuild the fixup chain without the expicit lituse and
1681 gpdisp_lo16 relocs. */
1682 prevP = &seginfo->fix_root;
1683 for (fixp = seginfo->fix_root; fixp; fixp = next)
1685 next = fixp->fx_next;
1686 fixp->fx_next = (fixS *) 0;
1688 switch (fixp->fx_r_type)
1690 case BFD_RELOC_ALPHA_LITUSE:
1692 if (fixp->tc_fix_data.info->n_master == 0)
1693 as_bad_where (fixp->fx_file, fixp->fx_line,
1694 _("No !literal!%ld was found"),
1695 fixp->tc_fix_data.info->sequence);
1698 case BFD_RELOC_ALPHA_GPDISP_LO16:
1700 if (fixp->tc_fix_data.info->n_master == 0)
1701 as_bad_where (fixp->fx_file, fixp->fx_line,
1702 _("No ldah !gpdisp!%ld was found"),
1703 fixp->tc_fix_data.info->sequence);
1708 prevP = &fixp->fx_next;
1713 /* If there were any dependent relocations, go and add them back to
1714 the chain. They are linked through the next_reloc field in
1715 reverse order, so as we go through the next_reloc chain, we
1716 effectively reverse the chain once again.
1718 Except if there is more than one !literal for a given sequence
1719 number. In that case, the programmer and/or compiler is not sure
1720 how control flows from literal to lituse, and we can't be sure to
1721 get the relaxation correct.
1723 ??? Well, actually we could, if there are enough lituses such that
1724 we can make each literal have at least one of each lituse type
1725 present. Not implemented.
1727 Also suppress the optimization if the !literals/!lituses are spread
1728 in different segments. This can happen with "intersting" uses of
1729 inline assembly; examples are present in the Linux kernel semaphores. */
1731 for (fixp = seginfo->fix_root; fixp; fixp = next)
1733 next = fixp->fx_next;
1734 switch (fixp->fx_r_type)
1736 case BFD_RELOC_ALPHA_ELF_LITERAL:
1737 if (fixp->tc_fix_data.info->n_master == 1
1738 && ! fixp->tc_fix_data.info->multi_section_p)
1740 for (slave = fixp->tc_fix_data.info->slaves;
1741 slave != (fixS *) 0;
1742 slave = slave->tc_fix_data.next_reloc)
1744 slave->fx_next = fixp->fx_next;
1745 fixp->fx_next = slave;
1750 case BFD_RELOC_ALPHA_GPDISP_HI16:
1751 if (fixp->tc_fix_data.info->n_slaves == 0)
1752 as_bad_where (fixp->fx_file, fixp->fx_line,
1753 _("No lda !gpdisp!%ld was found"),
1754 fixp->tc_fix_data.info->sequence);
1757 slave = fixp->tc_fix_data.info->slaves;
1758 slave->fx_next = next;
1759 fixp->fx_next = slave;
1771 debug_exp (tok, ntok)
1777 fprintf (stderr, "debug_exp: %d tokens", ntok);
1778 for (i = 0; i < ntok; i++)
1780 expressionS *t = &tok[i];
1784 default: name = "unknown"; break;
1785 case O_illegal: name = "O_illegal"; break;
1786 case O_absent: name = "O_absent"; break;
1787 case O_constant: name = "O_constant"; break;
1788 case O_symbol: name = "O_symbol"; break;
1789 case O_symbol_rva: name = "O_symbol_rva"; break;
1790 case O_register: name = "O_register"; break;
1791 case O_big: name = "O_big"; break;
1792 case O_uminus: name = "O_uminus"; break;
1793 case O_bit_not: name = "O_bit_not"; break;
1794 case O_logical_not: name = "O_logical_not"; break;
1795 case O_multiply: name = "O_multiply"; break;
1796 case O_divide: name = "O_divide"; break;
1797 case O_modulus: name = "O_modulus"; break;
1798 case O_left_shift: name = "O_left_shift"; break;
1799 case O_right_shift: name = "O_right_shift"; break;
1800 case O_bit_inclusive_or: name = "O_bit_inclusive_or"; break;
1801 case O_bit_or_not: name = "O_bit_or_not"; break;
1802 case O_bit_exclusive_or: name = "O_bit_exclusive_or"; break;
1803 case O_bit_and: name = "O_bit_and"; break;
1804 case O_add: name = "O_add"; break;
1805 case O_subtract: name = "O_subtract"; break;
1806 case O_eq: name = "O_eq"; break;
1807 case O_ne: name = "O_ne"; break;
1808 case O_lt: name = "O_lt"; break;
1809 case O_le: name = "O_le"; break;
1810 case O_ge: name = "O_ge"; break;
1811 case O_gt: name = "O_gt"; break;
1812 case O_logical_and: name = "O_logical_and"; break;
1813 case O_logical_or: name = "O_logical_or"; break;
1814 case O_index: name = "O_index"; break;
1815 case O_pregister: name = "O_pregister"; break;
1816 case O_cpregister: name = "O_cpregister"; break;
1817 case O_literal: name = "O_literal"; break;
1818 case O_lituse_addr: name = "O_lituse_addr"; break;
1819 case O_lituse_base: name = "O_lituse_base"; break;
1820 case O_lituse_bytoff: name = "O_lituse_bytoff"; break;
1821 case O_lituse_jsr: name = "O_lituse_jsr"; break;
1822 case O_gpdisp: name = "O_gpdisp"; break;
1823 case O_gprelhigh: name = "O_gprelhigh"; break;
1824 case O_gprellow: name = "O_gprellow"; break;
1825 case O_gprel: name = "O_gprel"; break;
1826 case O_samegp: name = "O_samegp"; break;
1827 case O_md13: name = "O_md13"; break;
1828 case O_md14: name = "O_md14"; break;
1829 case O_md15: name = "O_md15"; break;
1830 case O_md16: name = "O_md16"; break;
1833 fprintf (stderr, ", %s(%s, %s, %d)", name,
1834 (t->X_add_symbol) ? S_GET_NAME (t->X_add_symbol) : "--",
1835 (t->X_op_symbol) ? S_GET_NAME (t->X_op_symbol) : "--",
1836 (int) t->X_add_number);
1838 fprintf (stderr, "\n");
1843 /* Parse the arguments to an opcode. */
1846 tokenize_arguments (str, tok, ntok)
1851 expressionS *end_tok = tok + ntok;
1852 char *old_input_line_pointer;
1853 int saw_comma = 0, saw_arg = 0;
1855 expressionS *orig_tok = tok;
1858 const struct alpha_reloc_op_tag *r;
1861 int reloc_found_p = 0;
1863 memset (tok, 0, sizeof (*tok) * ntok);
1865 /* Save and restore input_line_pointer around this function */
1866 old_input_line_pointer = input_line_pointer;
1867 input_line_pointer = str;
1870 /* ??? Wrest control of ! away from the regular expression parser. */
1871 is_end_of_line[(unsigned char) '!'] = 1;
1874 while (tok < end_tok && *input_line_pointer)
1877 switch (*input_line_pointer)
1884 /* A relocation operand can be placed after the normal operand on an
1885 assembly language statement, and has the following form:
1886 !relocation_type!sequence_number. */
1888 { /* only support one relocation op per insn */
1889 as_bad (_("More than one relocation op per insn"));
1896 ++input_line_pointer;
1898 p = input_line_pointer;
1899 c = get_symbol_end ();
1901 /* Parse !relocation_type */
1902 len = input_line_pointer - p;
1905 as_bad (_("No relocation operand"));
1909 r = &alpha_reloc_op[0];
1910 for (i = alpha_num_reloc_op - 1; i >= 0; i--, r++)
1911 if (len == r->length && memcmp (p, r->name, len) == 0)
1915 as_bad (_("Unknown relocation operand: !%s"), p);
1919 *input_line_pointer = c;
1921 if (*input_line_pointer != '!')
1925 as_bad (_("no sequence number after !%s"), p);
1929 tok->X_add_number = 0;
1935 as_bad (_("!%s does not use a sequence number"), p);
1939 input_line_pointer++;
1941 /* Parse !sequence_number */
1943 if (tok->X_op != O_constant || tok->X_add_number <= 0)
1945 as_bad (_("Bad sequence number: !%s!%s"),
1946 r->name, input_line_pointer);
1955 #endif /* RELOC_OP_P */
1958 ++input_line_pointer;
1959 if (saw_comma || !saw_arg)
1966 char *hold = input_line_pointer++;
1968 /* First try for parenthesized register ... */
1970 if (*input_line_pointer == ')' && tok->X_op == O_register)
1972 tok->X_op = (saw_comma ? O_cpregister : O_pregister);
1975 ++input_line_pointer;
1980 /* ... then fall through to plain expression */
1981 input_line_pointer = hold;
1985 if (saw_arg && !saw_comma)
1989 if (tok->X_op == O_illegal || tok->X_op == O_absent)
2002 input_line_pointer = old_input_line_pointer;
2005 debug_exp (orig_tok, ntok - (end_tok - tok));
2008 is_end_of_line[(unsigned char) '!'] = 0;
2011 return ntok - (end_tok - tok);
2015 is_end_of_line[(unsigned char) '!'] = 0;
2017 input_line_pointer = old_input_line_pointer;
2018 return TOKENIZE_ERROR;
2022 is_end_of_line[(unsigned char) '!'] = 0;
2024 input_line_pointer = old_input_line_pointer;
2025 return TOKENIZE_ERROR_REPORT;
2028 /* Search forward through all variants of an opcode looking for a
2031 static const struct alpha_opcode *
2032 find_opcode_match (first_opcode, tok, pntok, pcpumatch)
2033 const struct alpha_opcode *first_opcode;
2034 const expressionS *tok;
2038 const struct alpha_opcode *opcode = first_opcode;
2040 int got_cpu_match = 0;
2044 const unsigned char *opidx;
2047 /* Don't match opcodes that don't exist on this architecture */
2048 if (!(opcode->flags & alpha_target))
2053 for (opidx = opcode->operands; *opidx; ++opidx)
2055 const struct alpha_operand *operand = &alpha_operands[*opidx];
2057 /* only take input from real operands */
2058 if (operand->flags & AXP_OPERAND_FAKE)
2061 /* when we expect input, make sure we have it */
2064 if ((operand->flags & AXP_OPERAND_OPTIONAL_MASK) == 0)
2069 /* match operand type with expression type */
2070 switch (operand->flags & AXP_OPERAND_TYPECHECK_MASK)
2072 case AXP_OPERAND_IR:
2073 if (tok[tokidx].X_op != O_register
2074 || !is_ir_num (tok[tokidx].X_add_number))
2077 case AXP_OPERAND_FPR:
2078 if (tok[tokidx].X_op != O_register
2079 || !is_fpr_num (tok[tokidx].X_add_number))
2082 case AXP_OPERAND_IR | AXP_OPERAND_PARENS:
2083 if (tok[tokidx].X_op != O_pregister
2084 || !is_ir_num (tok[tokidx].X_add_number))
2087 case AXP_OPERAND_IR | AXP_OPERAND_PARENS | AXP_OPERAND_COMMA:
2088 if (tok[tokidx].X_op != O_cpregister
2089 || !is_ir_num (tok[tokidx].X_add_number))
2093 case AXP_OPERAND_RELATIVE:
2094 case AXP_OPERAND_SIGNED:
2095 case AXP_OPERAND_UNSIGNED:
2096 switch (tok[tokidx].X_op)
2111 /* everything else should have been fake */
2117 /* possible match -- did we use all of our input? */
2126 while (++opcode - alpha_opcodes < alpha_num_opcodes
2127 && !strcmp (opcode->name, first_opcode->name));
2130 *pcpumatch = got_cpu_match;
2135 /* Search forward through all variants of a macro looking for a syntax
2138 static const struct alpha_macro *
2139 find_macro_match (first_macro, tok, pntok)
2140 const struct alpha_macro *first_macro;
2141 const expressionS *tok;
2144 const struct alpha_macro *macro = first_macro;
2149 const enum alpha_macro_arg *arg = macro->argsets;
2163 /* index register */
2165 if (tokidx >= ntok || tok[tokidx].X_op != O_register
2166 || !is_ir_num (tok[tokidx].X_add_number))
2171 /* parenthesized index register */
2173 if (tokidx >= ntok || tok[tokidx].X_op != O_pregister
2174 || !is_ir_num (tok[tokidx].X_add_number))
2179 /* optional parenthesized index register */
2181 if (tokidx < ntok && tok[tokidx].X_op == O_pregister
2182 && is_ir_num (tok[tokidx].X_add_number))
2186 /* leading comma with a parenthesized index register */
2188 if (tokidx >= ntok || tok[tokidx].X_op != O_cpregister
2189 || !is_ir_num (tok[tokidx].X_add_number))
2194 /* floating point register */
2196 if (tokidx >= ntok || tok[tokidx].X_op != O_register
2197 || !is_fpr_num (tok[tokidx].X_add_number))
2202 /* normal expression */
2206 switch (tok[tokidx].X_op)
2215 case O_lituse_bytoff:
2231 while (*arg != MACRO_EOA)
2239 while (++macro - alpha_macros < alpha_num_macros
2240 && !strcmp (macro->name, first_macro->name));
2245 /* Insert an operand value into an instruction. */
2248 insert_operand (insn, operand, val, file, line)
2250 const struct alpha_operand *operand;
2255 if (operand->bits != 32 && !(operand->flags & AXP_OPERAND_NOOVERFLOW))
2259 if (operand->flags & AXP_OPERAND_SIGNED)
2261 max = (1 << (operand->bits - 1)) - 1;
2262 min = -(1 << (operand->bits - 1));
2266 max = (1 << operand->bits) - 1;
2270 if (val < min || val > max)
2273 _("operand out of range (%s not between %d and %d)");
2274 char buf[sizeof (val) * 3 + 2];
2276 sprint_value (buf, val);
2278 as_warn_where (file, line, err, buf, min, max);
2280 as_warn (err, buf, min, max);
2284 if (operand->insert)
2286 const char *errmsg = NULL;
2288 insn = (*operand->insert) (insn, val, &errmsg);
2293 insn |= ((val & ((1 << operand->bits) - 1)) << operand->shift);
2299 * Turn an opcode description and a set of arguments into
2300 * an instruction and a fixup.
2304 assemble_insn (opcode, tok, ntok, insn, reloc)
2305 const struct alpha_opcode *opcode;
2306 const expressionS *tok;
2308 struct alpha_insn *insn;
2309 bfd_reloc_code_real_type reloc;
2311 const struct alpha_operand *reloc_operand = NULL;
2312 const expressionS *reloc_exp = NULL;
2313 const unsigned char *argidx;
2317 memset (insn, 0, sizeof (*insn));
2318 image = opcode->opcode;
2320 for (argidx = opcode->operands; *argidx; ++argidx)
2322 const struct alpha_operand *operand = &alpha_operands[*argidx];
2323 const expressionS *t = (const expressionS *) 0;
2325 if (operand->flags & AXP_OPERAND_FAKE)
2327 /* fake operands take no value and generate no fixup */
2328 image = insert_operand (image, operand, 0, NULL, 0);
2334 switch (operand->flags & AXP_OPERAND_OPTIONAL_MASK)
2336 case AXP_OPERAND_DEFAULT_FIRST:
2339 case AXP_OPERAND_DEFAULT_SECOND:
2342 case AXP_OPERAND_DEFAULT_ZERO:
2344 static expressionS zero_exp;
2346 zero_exp.X_op = O_constant;
2347 zero_exp.X_unsigned = 1;
2362 image = insert_operand (image, operand, regno (t->X_add_number),
2367 image = insert_operand (image, operand, t->X_add_number, NULL, 0);
2368 assert (reloc_operand == NULL);
2369 reloc_operand = operand;
2374 /* This is only 0 for fields that should contain registers,
2375 which means this pattern shouldn't have matched. */
2376 if (operand->default_reloc == 0)
2379 /* There is one special case for which an insn receives two
2380 relocations, and thus the user-supplied reloc does not
2381 override the operand reloc. */
2382 if (operand->default_reloc == BFD_RELOC_ALPHA_HINT)
2384 struct alpha_fixup *fixup;
2386 if (insn->nfixups >= MAX_INSN_FIXUPS)
2387 as_fatal (_("too many fixups"));
2389 fixup = &insn->fixups[insn->nfixups++];
2391 fixup->reloc = BFD_RELOC_ALPHA_HINT;
2395 if (reloc == BFD_RELOC_UNUSED)
2396 reloc = operand->default_reloc;
2398 assert (reloc_operand == NULL);
2399 reloc_operand = operand;
2406 if (reloc != BFD_RELOC_UNUSED)
2408 struct alpha_fixup *fixup;
2410 if (insn->nfixups >= MAX_INSN_FIXUPS)
2411 as_fatal (_("too many fixups"));
2413 /* ??? My but this is hacky. But the OSF/1 assembler uses the same
2414 relocation tag for both ldah and lda with gpdisp. Choose the
2415 correct internal relocation based on the opcode. */
2416 if (reloc == BFD_RELOC_ALPHA_GPDISP)
2418 if (strcmp (opcode->name, "ldah") == 0)
2419 reloc = BFD_RELOC_ALPHA_GPDISP_HI16;
2420 else if (strcmp (opcode->name, "lda") == 0)
2421 reloc = BFD_RELOC_ALPHA_GPDISP_LO16;
2423 as_bad (_("invalid relocation for instruction"));
2426 /* If this is a real relocation (as opposed to a lituse hint), then
2427 the relocation width should match the operand width. */
2428 else if (reloc < BFD_RELOC_UNUSED)
2430 reloc_howto_type *reloc_howto
2431 = bfd_reloc_type_lookup (stdoutput, reloc);
2432 if (reloc_howto->bitsize != reloc_operand->bits)
2434 as_bad (_("invalid relocation for field"));
2439 fixup = &insn->fixups[insn->nfixups++];
2441 fixup->exp = *reloc_exp;
2443 fixup->exp.X_op = O_absent;
2444 fixup->reloc = reloc;
2451 * Actually output an instruction with its fixup.
2456 struct alpha_insn *insn;
2461 /* Take care of alignment duties. */
2462 if (alpha_auto_align_on && alpha_current_align < 2)
2463 alpha_align (2, (char *) NULL, alpha_insn_label, 0);
2464 if (alpha_current_align > 2)
2465 alpha_current_align = 2;
2466 alpha_insn_label = NULL;
2468 /* Write out the instruction. */
2470 md_number_to_chars (f, insn->insn, 4);
2473 dwarf2_emit_insn (4);
2476 /* Apply the fixups in order */
2477 for (i = 0; i < insn->nfixups; ++i)
2479 const struct alpha_operand *operand = (const struct alpha_operand *) 0;
2480 struct alpha_fixup *fixup = &insn->fixups[i];
2481 struct alpha_reloc_tag *info;
2485 /* Some fixups are only used internally and so have no howto */
2486 if ((int) fixup->reloc < 0)
2488 operand = &alpha_operands[-(int) fixup->reloc];
2490 pcrel = ((operand->flags & AXP_OPERAND_RELATIVE) != 0);
2492 else if (fixup->reloc > BFD_RELOC_UNUSED
2493 || fixup->reloc == BFD_RELOC_ALPHA_GPDISP_HI16
2494 || fixup->reloc == BFD_RELOC_ALPHA_GPDISP_LO16)
2501 reloc_howto_type *reloc_howto
2502 = bfd_reloc_type_lookup (stdoutput, fixup->reloc);
2503 assert (reloc_howto);
2505 size = bfd_get_reloc_size (reloc_howto);
2506 assert (size >= 1 && size <= 4);
2508 pcrel = reloc_howto->pc_relative;
2511 fixP = fix_new_exp (frag_now, f - frag_now->fr_literal, size,
2512 &fixup->exp, pcrel, fixup->reloc);
2514 /* Turn off complaints that the addend is too large for some fixups,
2515 and copy in the sequence number for the explicit relocations. */
2516 switch (fixup->reloc)
2518 case BFD_RELOC_ALPHA_HINT:
2519 case BFD_RELOC_GPREL32:
2520 case BFD_RELOC_GPREL16:
2521 case BFD_RELOC_ALPHA_GPREL_HI16:
2522 case BFD_RELOC_ALPHA_GPREL_LO16:
2523 fixP->fx_no_overflow = 1;
2526 case BFD_RELOC_ALPHA_GPDISP_HI16:
2527 fixP->fx_no_overflow = 1;
2528 fixP->fx_addsy = section_symbol (now_seg);
2529 fixP->fx_offset = 0;
2531 info = get_alpha_reloc_tag (insn->sequence);
2532 if (++info->n_master > 1)
2533 as_bad (_("too many ldah insns for !gpdisp!%ld"), insn->sequence);
2534 if (info->segment != now_seg)
2535 as_bad (_("both insns for !gpdisp!%ld must be in the same section"),
2537 fixP->tc_fix_data.info = info;
2540 case BFD_RELOC_ALPHA_GPDISP_LO16:
2541 fixP->fx_no_overflow = 1;
2543 info = get_alpha_reloc_tag (insn->sequence);
2544 if (++info->n_slaves > 1)
2545 as_bad (_("too many lda insns for !gpdisp!%ld"), insn->sequence);
2546 if (info->segment != now_seg)
2547 as_bad (_("both insns for !gpdisp!%ld must be in the same section"),
2549 fixP->tc_fix_data.info = info;
2550 info->slaves = fixP;
2553 case BFD_RELOC_ALPHA_LITERAL:
2554 case BFD_RELOC_ALPHA_ELF_LITERAL:
2555 fixP->fx_no_overflow = 1;
2557 info = get_alpha_reloc_tag (insn->sequence);
2559 if (info->segment != now_seg)
2560 info->multi_section_p = 1;
2561 fixP->tc_fix_data.info = info;
2564 case DUMMY_RELOC_LITUSE_ADDR:
2565 fixP->fx_offset = LITUSE_ADDR;
2567 case DUMMY_RELOC_LITUSE_BASE:
2568 fixP->fx_offset = LITUSE_BASE;
2570 case DUMMY_RELOC_LITUSE_BYTOFF:
2571 fixP->fx_offset = LITUSE_BYTOFF;
2573 case DUMMY_RELOC_LITUSE_JSR:
2574 fixP->fx_offset = LITUSE_JSR;
2576 fixP->fx_addsy = section_symbol (now_seg);
2577 fixP->fx_r_type = BFD_RELOC_ALPHA_LITUSE;
2579 info = get_alpha_reloc_tag (insn->sequence);
2581 fixP->tc_fix_data.info = info;
2582 fixP->tc_fix_data.next_reloc = info->slaves;
2583 info->slaves = fixP;
2584 if (info->segment != now_seg)
2585 info->multi_section_p = 1;
2589 if ((int) fixup->reloc < 0)
2591 if (operand->flags & AXP_OPERAND_NOOVERFLOW)
2592 fixP->fx_no_overflow = 1;
2599 /* Given an opcode name and a pre-tokenized set of arguments, assemble
2600 the insn, but do not emit it.
2602 Note that this implies no macros allowed, since we can't store more
2603 than one insn in an insn structure. */
2606 assemble_tokens_to_insn (opname, tok, ntok, insn)
2608 const expressionS *tok;
2610 struct alpha_insn *insn;
2612 const struct alpha_opcode *opcode;
2614 /* search opcodes */
2615 opcode = (const struct alpha_opcode *) hash_find (alpha_opcode_hash, opname);
2619 opcode = find_opcode_match (opcode, tok, &ntok, &cpumatch);
2622 assemble_insn (opcode, tok, ntok, insn, BFD_RELOC_UNUSED);
2626 as_bad (_("inappropriate arguments for opcode `%s'"), opname);
2628 as_bad (_("opcode `%s' not supported for target %s"), opname,
2632 as_bad (_("unknown opcode `%s'"), opname);
2635 /* Given an opcode name and a pre-tokenized set of arguments, take the
2636 opcode all the way through emission. */
2639 assemble_tokens (opname, tok, ntok, local_macros_on)
2641 const expressionS *tok;
2643 int local_macros_on;
2645 int found_something = 0;
2646 const struct alpha_opcode *opcode;
2647 const struct alpha_macro *macro;
2649 bfd_reloc_code_real_type reloc = BFD_RELOC_UNUSED;
2652 /* If a user-specified relocation is present, this is not a macro. */
2653 if (ntok && USER_RELOC_P (tok[ntok - 1].X_op))
2655 reloc = ALPHA_RELOC_TABLE (tok[ntok - 1].X_op)->reloc;
2660 if (local_macros_on)
2662 macro = ((const struct alpha_macro *)
2663 hash_find (alpha_macro_hash, opname));
2666 found_something = 1;
2667 macro = find_macro_match (macro, tok, &ntok);
2670 (*macro->emit) (tok, ntok, macro->arg);
2676 /* search opcodes */
2677 opcode = (const struct alpha_opcode *) hash_find (alpha_opcode_hash, opname);
2680 found_something = 1;
2681 opcode = find_opcode_match (opcode, tok, &ntok, &cpumatch);
2684 struct alpha_insn insn;
2685 assemble_insn (opcode, tok, ntok, &insn, reloc);
2687 /* Copy the sequence number for the reloc from the reloc token. */
2688 if (reloc != BFD_RELOC_UNUSED)
2689 insn.sequence = tok[ntok].X_add_number;
2696 if (found_something)
2699 as_bad (_("inappropriate arguments for opcode `%s'"), opname);
2701 as_bad (_("opcode `%s' not supported for target %s"), opname,
2705 as_bad (_("unknown opcode `%s'"), opname);
2708 /* Some instruction sets indexed by lg(size) */
2709 static const char * const sextX_op[] = { "sextb", "sextw", "sextl", NULL };
2710 static const char * const insXl_op[] = { "insbl", "inswl", "insll", "insql" };
2711 static const char * const insXh_op[] = { NULL, "inswh", "inslh", "insqh" };
2712 static const char * const extXl_op[] = { "extbl", "extwl", "extll", "extql" };
2713 static const char * const extXh_op[] = { NULL, "extwh", "extlh", "extqh" };
2714 static const char * const mskXl_op[] = { "mskbl", "mskwl", "mskll", "mskql" };
2715 static const char * const mskXh_op[] = { NULL, "mskwh", "msklh", "mskqh" };
2716 static const char * const stX_op[] = { "stb", "stw", "stl", "stq" };
2717 static const char * const ldX_op[] = { "ldb", "ldw", "ldll", "ldq" };
2718 static const char * const ldXu_op[] = { "ldbu", "ldwu", NULL, NULL };
2720 /* Implement the ldgp macro. */
2723 emit_ldgp (tok, ntok, unused)
2724 const expressionS *tok;
2725 int ntok ATTRIBUTE_UNUSED;
2726 const PTR unused ATTRIBUTE_UNUSED;
2731 #if defined(OBJ_ECOFF) || defined(OBJ_ELF)
2732 /* from "ldgp r1,n(r2)", generate "ldah r1,X(R2); lda r1,Y(r1)"
2733 with appropriate constants and relocations. */
2734 struct alpha_insn insn;
2735 expressionS newtok[3];
2739 if (regno (tok[2].X_add_number) == AXP_REG_PV)
2740 ecoff_set_gp_prolog_size (0);
2744 set_tok_const (newtok[1], 0);
2747 assemble_tokens_to_insn ("ldah", newtok, 3, &insn);
2752 if (addend.X_op != O_constant)
2753 as_bad (_("can not resolve expression"));
2754 addend.X_op = O_symbol;
2755 addend.X_add_symbol = alpha_gp_symbol;
2759 insn.fixups[0].exp = addend;
2760 insn.fixups[0].reloc = BFD_RELOC_ALPHA_GPDISP_HI16;
2761 insn.sequence = next_sequence_num;
2765 set_tok_preg (newtok[2], tok[0].X_add_number);
2767 assemble_tokens_to_insn ("lda", newtok, 3, &insn);
2770 addend.X_add_number += 4;
2774 insn.fixups[0].exp = addend;
2775 insn.fixups[0].reloc = BFD_RELOC_ALPHA_GPDISP_LO16;
2776 insn.sequence = next_sequence_num--;
2779 #endif /* OBJ_ECOFF || OBJ_ELF */
2784 /* Add symbol+addend to link pool.
2785 Return offset from basesym to entry in link pool.
2787 Add new fixup only if offset isn't 16bit. */
2790 add_to_link_pool (basesym, sym, addend)
2795 segT current_section = now_seg;
2796 int current_subsec = now_subseg;
2798 bfd_reloc_code_real_type reloc_type;
2800 segment_info_type *seginfo = seg_info (alpha_link_section);
2803 offset = - *symbol_get_obj (basesym);
2805 /* @@ This assumes all entries in a given section will be of the same
2806 size... Probably correct, but unwise to rely on. */
2807 /* This must always be called with the same subsegment. */
2809 if (seginfo->frchainP)
2810 for (fixp = seginfo->frchainP->fix_root;
2811 fixp != (fixS *) NULL;
2812 fixp = fixp->fx_next, offset += 8)
2814 if (fixp->fx_addsy == sym && fixp->fx_offset == addend)
2816 if (range_signed_16 (offset))
2823 /* Not found in 16bit signed range. */
2825 subseg_set (alpha_link_section, 0);
2829 fix_new (frag_now, p - frag_now->fr_literal, 8, sym, addend, 0,
2832 subseg_set (current_section, current_subsec);
2833 seginfo->literal_pool_size += 8;
2837 #endif /* OBJ_EVAX */
2839 /* Load a (partial) expression into a target register.
2841 If poffset is not null, after the call it will either contain
2842 O_constant 0, or a 16-bit offset appropriate for any MEM format
2843 instruction. In addition, pbasereg will be modified to point to
2844 the base register to use in that MEM format instruction.
2846 In any case, *pbasereg should contain a base register to add to the
2847 expression. This will normally be either AXP_REG_ZERO or
2848 alpha_gp_register. Symbol addresses will always be loaded via $gp,
2849 so "foo($0)" is interpreted as adding the address of foo to $0;
2850 i.e. "ldq $targ, LIT($gp); addq $targ, $0, $targ". Odd, perhaps,
2851 but this is what OSF/1 does.
2853 If explicit relocations of the form !literal!<number> are allowed,
2854 and used, then explict_reloc with be an expression pointer.
2856 Finally, the return value is nonzero if the calling macro may emit
2857 a LITUSE reloc if otherwise appropriate; the return value is the
2858 sequence number to use. */
2861 load_expression (targreg, exp, pbasereg, poffset)
2863 const expressionS *exp;
2865 expressionS *poffset;
2867 long emit_lituse = 0;
2868 offsetT addend = exp->X_add_number;
2869 int basereg = *pbasereg;
2870 struct alpha_insn insn;
2871 expressionS newtok[3];
2880 /* attempt to reduce .lit load by splitting the offset from
2881 its symbol when possible, but don't create a situation in
2883 if (!range_signed_32 (addend) &&
2884 (alpha_noat_on || targreg == AXP_REG_AT))
2886 lit = add_to_literal_pool (exp->X_add_symbol, addend,
2887 alpha_lita_section, 8);
2892 lit = add_to_literal_pool (exp->X_add_symbol, 0,
2893 alpha_lita_section, 8);
2897 as_fatal (_("overflow in literal (.lita) table"));
2899 /* emit "ldq r, lit(gp)" */
2901 if (basereg != alpha_gp_register && targreg == basereg)
2904 as_bad (_("macro requires $at register while noat in effect"));
2905 if (targreg == AXP_REG_AT)
2906 as_bad (_("macro requires $at while $at in use"));
2908 set_tok_reg (newtok[0], AXP_REG_AT);
2911 set_tok_reg (newtok[0], targreg);
2912 set_tok_sym (newtok[1], alpha_lita_symbol, lit);
2913 set_tok_preg (newtok[2], alpha_gp_register);
2915 assemble_tokens_to_insn ("ldq", newtok, 3, &insn);
2917 assert (insn.nfixups == 1);
2918 insn.fixups[0].reloc = BFD_RELOC_ALPHA_LITERAL;
2919 insn.sequence = emit_lituse = next_sequence_num--;
2920 #endif /* OBJ_ECOFF */
2922 /* emit "ldq r, gotoff(gp)" */
2924 if (basereg != alpha_gp_register && targreg == basereg)
2927 as_bad (_("macro requires $at register while noat in effect"));
2928 if (targreg == AXP_REG_AT)
2929 as_bad (_("macro requires $at while $at in use"));
2931 set_tok_reg (newtok[0], AXP_REG_AT);
2934 set_tok_reg (newtok[0], targreg);
2936 /* XXX: Disable this .got minimizing optimization so that we can get
2937 better instruction offset knowledge in the compiler. This happens
2938 very infrequently anyway. */
2940 || (!range_signed_32 (addend)
2941 && (alpha_noat_on || targreg == AXP_REG_AT)))
2948 set_tok_sym (newtok[1], exp->X_add_symbol, 0);
2951 set_tok_preg (newtok[2], alpha_gp_register);
2953 assemble_tokens_to_insn ("ldq", newtok, 3, &insn);
2955 assert (insn.nfixups == 1);
2956 insn.fixups[0].reloc = BFD_RELOC_ALPHA_ELF_LITERAL;
2957 insn.sequence = emit_lituse = next_sequence_num--;
2958 #endif /* OBJ_ELF */
2962 /* Find symbol or symbol pointer in link section. */
2964 if (exp->X_add_symbol == alpha_evax_proc.symbol)
2966 if (range_signed_16 (addend))
2968 set_tok_reg (newtok[0], targreg);
2969 set_tok_const (newtok[1], addend);
2970 set_tok_preg (newtok[2], basereg);
2971 assemble_tokens_to_insn ("lda", newtok, 3, &insn);
2976 set_tok_reg (newtok[0], targreg);
2977 set_tok_const (newtok[1], 0);
2978 set_tok_preg (newtok[2], basereg);
2979 assemble_tokens_to_insn ("lda", newtok, 3, &insn);
2984 if (!range_signed_32 (addend))
2986 link = add_to_link_pool (alpha_evax_proc.symbol,
2987 exp->X_add_symbol, addend);
2992 link = add_to_link_pool (alpha_evax_proc.symbol,
2993 exp->X_add_symbol, 0);
2995 set_tok_reg (newtok[0], targreg);
2996 set_tok_const (newtok[1], link);
2997 set_tok_preg (newtok[2], basereg);
2998 assemble_tokens_to_insn ("ldq", newtok, 3, &insn);
3000 #endif /* OBJ_EVAX */
3005 if (basereg != alpha_gp_register && basereg != AXP_REG_ZERO)
3007 /* emit "addq r, base, r" */
3009 set_tok_reg (newtok[1], basereg);
3010 set_tok_reg (newtok[2], targreg);
3011 assemble_tokens ("addq", newtok, 3, 0);
3023 /* Assume that this difference expression will be resolved to an
3024 absolute value and that that value will fit in 16 bits. */
3026 set_tok_reg (newtok[0], targreg);
3028 set_tok_preg (newtok[2], basereg);
3029 assemble_tokens ("lda", newtok, 3, 0);
3032 set_tok_const (*poffset, 0);
3036 if (exp->X_add_number > 0)
3037 as_bad (_("bignum invalid; zero assumed"));
3039 as_bad (_("floating point number invalid; zero assumed"));
3044 as_bad (_("can't handle expression"));
3049 if (!range_signed_32 (addend))
3052 long seq_num = next_sequence_num--;
3054 /* For 64-bit addends, just put it in the literal pool. */
3057 /* emit "ldq targreg, lit(basereg)" */
3058 lit = add_to_link_pool (alpha_evax_proc.symbol,
3059 section_symbol (absolute_section), addend);
3060 set_tok_reg (newtok[0], targreg);
3061 set_tok_const (newtok[1], lit);
3062 set_tok_preg (newtok[2], alpha_gp_register);
3063 assemble_tokens ("ldq", newtok, 3, 0);
3066 if (alpha_lit8_section == NULL)
3068 create_literal_section (".lit8",
3069 &alpha_lit8_section,
3070 &alpha_lit8_symbol);
3073 alpha_lit8_literal = add_to_literal_pool (alpha_lit8_symbol, 0x8000,
3074 alpha_lita_section, 8);
3075 if (alpha_lit8_literal >= 0x8000)
3076 as_fatal (_("overflow in literal (.lita) table"));
3080 lit = add_to_literal_pool (NULL, addend, alpha_lit8_section, 8) - 0x8000;
3082 as_fatal (_("overflow in literal (.lit8) table"));
3084 /* emit "lda litreg, .lit8+0x8000" */
3086 if (targreg == basereg)
3089 as_bad (_("macro requires $at register while noat in effect"));
3090 if (targreg == AXP_REG_AT)
3091 as_bad (_("macro requires $at while $at in use"));
3093 set_tok_reg (newtok[0], AXP_REG_AT);
3096 set_tok_reg (newtok[0], targreg);
3098 set_tok_sym (newtok[1], alpha_lita_symbol, alpha_lit8_literal);
3101 set_tok_sym (newtok[1], alpha_lit8_symbol, 0x8000);
3103 set_tok_preg (newtok[2], alpha_gp_register);
3105 assemble_tokens_to_insn ("ldq", newtok, 3, &insn);
3107 assert (insn.nfixups == 1);
3109 insn.fixups[0].reloc = BFD_RELOC_ALPHA_LITERAL;
3112 insn.fixups[0].reloc = BFD_RELOC_ALPHA_ELF_LITERAL;
3114 insn.sequence = seq_num;
3118 /* emit "ldq litreg, lit(litreg)" */
3120 set_tok_const (newtok[1], lit);
3121 set_tok_preg (newtok[2], newtok[0].X_add_number);
3123 assemble_tokens_to_insn ("ldq", newtok, 3, &insn);
3125 assert (insn.nfixups < MAX_INSN_FIXUPS);
3126 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3127 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3129 insn.sequence = seq_num;
3134 /* emit "addq litreg, base, target" */
3136 if (basereg != AXP_REG_ZERO)
3138 set_tok_reg (newtok[1], basereg);
3139 set_tok_reg (newtok[2], targreg);
3140 assemble_tokens ("addq", newtok, 3, 0);
3142 #endif /* !OBJ_EVAX */
3145 set_tok_const (*poffset, 0);
3146 *pbasereg = targreg;
3150 offsetT low, high, extra, tmp;
3152 /* for 32-bit operands, break up the addend */
3154 low = sign_extend_16 (addend);
3156 high = sign_extend_16 (tmp >> 16);
3158 if (tmp - (high << 16))
3162 high = sign_extend_16 (tmp >> 16);
3167 set_tok_reg (newtok[0], targreg);
3168 set_tok_preg (newtok[2], basereg);
3172 /* emit "ldah r, extra(r) */
3173 set_tok_const (newtok[1], extra);
3174 assemble_tokens ("ldah", newtok, 3, 0);
3175 set_tok_preg (newtok[2], basereg = targreg);
3180 /* emit "ldah r, high(r) */
3181 set_tok_const (newtok[1], high);
3182 assemble_tokens ("ldah", newtok, 3, 0);
3184 set_tok_preg (newtok[2], basereg);
3187 if ((low && !poffset) || (!poffset && basereg != targreg))
3189 /* emit "lda r, low(base)" */
3190 set_tok_const (newtok[1], low);
3191 assemble_tokens ("lda", newtok, 3, 0);
3197 set_tok_const (*poffset, low);
3198 *pbasereg = basereg;
3204 /* The lda macro differs from the lda instruction in that it handles
3205 most simple expressions, particualrly symbol address loads and
3209 emit_lda (tok, ntok, unused)
3210 const expressionS *tok;
3212 const PTR unused ATTRIBUTE_UNUSED;
3217 basereg = (tok[1].X_op == O_constant ? AXP_REG_ZERO : alpha_gp_register);
3219 basereg = tok[2].X_add_number;
3221 (void) load_expression (tok[0].X_add_number, &tok[1], &basereg, NULL);
3224 /* The ldah macro differs from the ldah instruction in that it has $31
3225 as an implied base register. */
3228 emit_ldah (tok, ntok, unused)
3229 const expressionS *tok;
3230 int ntok ATTRIBUTE_UNUSED;
3231 const PTR unused ATTRIBUTE_UNUSED;
3233 expressionS newtok[3];
3237 set_tok_preg (newtok[2], AXP_REG_ZERO);
3239 assemble_tokens ("ldah", newtok, 3, 0);
3242 /* Handle all "simple" integer register loads -- ldq, ldq_l, ldq_u,
3243 etc. They differ from the real instructions in that they do simple
3244 expressions like the lda macro. */
3247 emit_ir_load (tok, ntok, opname)
3248 const expressionS *tok;
3254 expressionS newtok[3];
3255 struct alpha_insn insn;
3258 basereg = (tok[1].X_op == O_constant ? AXP_REG_ZERO : alpha_gp_register);
3260 basereg = tok[2].X_add_number;
3262 lituse = load_expression (tok[0].X_add_number, &tok[1], &basereg,
3266 set_tok_preg (newtok[2], basereg);
3268 assemble_tokens_to_insn ((const char *) opname, newtok, 3, &insn);
3272 assert (insn.nfixups < MAX_INSN_FIXUPS);
3273 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3274 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3276 insn.sequence = lituse;
3282 /* Handle fp register loads, and both integer and fp register stores.
3283 Again, we handle simple expressions. */
3286 emit_loadstore (tok, ntok, opname)
3287 const expressionS *tok;
3293 expressionS newtok[3];
3294 struct alpha_insn insn;
3297 basereg = (tok[1].X_op == O_constant ? AXP_REG_ZERO : alpha_gp_register);
3299 basereg = tok[2].X_add_number;
3301 if (tok[1].X_op != O_constant || !range_signed_16 (tok[1].X_add_number))
3304 as_bad (_("macro requires $at register while noat in effect"));
3306 lituse = load_expression (AXP_REG_AT, &tok[1], &basereg, &newtok[1]);
3315 set_tok_preg (newtok[2], basereg);
3317 assemble_tokens_to_insn ((const char *) opname, newtok, 3, &insn);
3321 assert (insn.nfixups < MAX_INSN_FIXUPS);
3322 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3323 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3325 insn.sequence = lituse;
3331 /* Load a half-word or byte as an unsigned value. */
3334 emit_ldXu (tok, ntok, vlgsize)
3335 const expressionS *tok;
3339 if (alpha_target & AXP_OPCODE_BWX)
3340 emit_ir_load (tok, ntok, ldXu_op[(long) vlgsize]);
3343 expressionS newtok[3];
3344 struct alpha_insn insn;
3349 as_bad (_("macro requires $at register while noat in effect"));
3352 basereg = (tok[1].X_op == O_constant
3353 ? AXP_REG_ZERO : alpha_gp_register);
3355 basereg = tok[2].X_add_number;
3357 /* emit "lda $at, exp" */
3359 lituse = load_expression (AXP_REG_AT, &tok[1], &basereg, NULL);
3361 /* emit "ldq_u targ, 0($at)" */
3364 set_tok_const (newtok[1], 0);
3365 set_tok_preg (newtok[2], basereg);
3366 assemble_tokens_to_insn ("ldq_u", newtok, 3, &insn);
3370 assert (insn.nfixups < MAX_INSN_FIXUPS);
3371 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3372 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3374 insn.sequence = lituse;
3379 /* emit "extXl targ, $at, targ" */
3381 set_tok_reg (newtok[1], basereg);
3382 newtok[2] = newtok[0];
3383 assemble_tokens_to_insn (extXl_op[(long) vlgsize], newtok, 3, &insn);
3387 assert (insn.nfixups < MAX_INSN_FIXUPS);
3388 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BYTOFF;
3389 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3391 insn.sequence = lituse;
3398 /* Load a half-word or byte as a signed value. */
3401 emit_ldX (tok, ntok, vlgsize)
3402 const expressionS *tok;
3406 emit_ldXu (tok, ntok, vlgsize);
3407 assemble_tokens (sextX_op[(long) vlgsize], tok, 1, 1);
3410 /* Load an integral value from an unaligned address as an unsigned
3414 emit_uldXu (tok, ntok, vlgsize)
3415 const expressionS *tok;
3419 long lgsize = (long) vlgsize;
3420 expressionS newtok[3];
3423 as_bad (_("macro requires $at register while noat in effect"));
3425 /* emit "lda $at, exp" */
3427 memcpy (newtok, tok, sizeof (expressionS) * ntok);
3428 newtok[0].X_add_number = AXP_REG_AT;
3429 assemble_tokens ("lda", newtok, ntok, 1);
3431 /* emit "ldq_u $t9, 0($at)" */
3433 set_tok_reg (newtok[0], AXP_REG_T9);
3434 set_tok_const (newtok[1], 0);
3435 set_tok_preg (newtok[2], AXP_REG_AT);
3436 assemble_tokens ("ldq_u", newtok, 3, 1);
3438 /* emit "ldq_u $t10, size-1($at)" */
3440 set_tok_reg (newtok[0], AXP_REG_T10);
3441 set_tok_const (newtok[1], (1 << lgsize) - 1);
3442 assemble_tokens ("ldq_u", newtok, 3, 1);
3444 /* emit "extXl $t9, $at, $t9" */
3446 set_tok_reg (newtok[0], AXP_REG_T9);
3447 set_tok_reg (newtok[1], AXP_REG_AT);
3448 set_tok_reg (newtok[2], AXP_REG_T9);
3449 assemble_tokens (extXl_op[lgsize], newtok, 3, 1);
3451 /* emit "extXh $t10, $at, $t10" */
3453 set_tok_reg (newtok[0], AXP_REG_T10);
3454 set_tok_reg (newtok[2], AXP_REG_T10);
3455 assemble_tokens (extXh_op[lgsize], newtok, 3, 1);
3457 /* emit "or $t9, $t10, targ" */
3459 set_tok_reg (newtok[0], AXP_REG_T9);
3460 set_tok_reg (newtok[1], AXP_REG_T10);
3462 assemble_tokens ("or", newtok, 3, 1);
3465 /* Load an integral value from an unaligned address as a signed value.
3466 Note that quads should get funneled to the unsigned load since we
3467 don't have to do the sign extension. */
3470 emit_uldX (tok, ntok, vlgsize)
3471 const expressionS *tok;
3475 emit_uldXu (tok, ntok, vlgsize);
3476 assemble_tokens (sextX_op[(long) vlgsize], tok, 1, 1);
3479 /* Implement the ldil macro. */
3482 emit_ldil (tok, ntok, unused)
3483 const expressionS *tok;
3485 const PTR unused ATTRIBUTE_UNUSED;
3487 expressionS newtok[2];
3489 memcpy (newtok, tok, sizeof (newtok));
3490 newtok[1].X_add_number = sign_extend_32 (tok[1].X_add_number);
3492 assemble_tokens ("lda", newtok, ntok, 1);
3495 /* Store a half-word or byte. */
3498 emit_stX (tok, ntok, vlgsize)
3499 const expressionS *tok;
3503 int lgsize = (int) (long) vlgsize;
3505 if (alpha_target & AXP_OPCODE_BWX)
3506 emit_loadstore (tok, ntok, stX_op[lgsize]);
3509 expressionS newtok[3];
3510 struct alpha_insn insn;
3515 as_bad (_("macro requires $at register while noat in effect"));
3518 basereg = (tok[1].X_op == O_constant
3519 ? AXP_REG_ZERO : alpha_gp_register);
3521 basereg = tok[2].X_add_number;
3523 /* emit "lda $at, exp" */
3525 lituse = load_expression (AXP_REG_AT, &tok[1], &basereg, NULL);
3527 /* emit "ldq_u $t9, 0($at)" */
3529 set_tok_reg (newtok[0], AXP_REG_T9);
3530 set_tok_const (newtok[1], 0);
3531 set_tok_preg (newtok[2], basereg);
3532 assemble_tokens_to_insn ("ldq_u", newtok, 3, &insn);
3536 assert (insn.nfixups < MAX_INSN_FIXUPS);
3537 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3538 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3540 insn.sequence = lituse;
3545 /* emit "insXl src, $at, $t10" */
3548 set_tok_reg (newtok[1], basereg);
3549 set_tok_reg (newtok[2], AXP_REG_T10);
3550 assemble_tokens_to_insn (insXl_op[lgsize], newtok, 3, &insn);
3554 assert (insn.nfixups < MAX_INSN_FIXUPS);
3555 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BYTOFF;
3556 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3558 insn.sequence = lituse;
3563 /* emit "mskXl $t9, $at, $t9" */
3565 set_tok_reg (newtok[0], AXP_REG_T9);
3566 newtok[2] = newtok[0];
3567 assemble_tokens_to_insn (mskXl_op[lgsize], newtok, 3, &insn);
3571 assert (insn.nfixups < MAX_INSN_FIXUPS);
3572 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BYTOFF;
3573 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3575 insn.sequence = lituse;
3580 /* emit "or $t9, $t10, $t9" */
3582 set_tok_reg (newtok[1], AXP_REG_T10);
3583 assemble_tokens ("or", newtok, 3, 1);
3585 /* emit "stq_u $t9, 0($at) */
3587 set_tok_const(newtok[1], 0);
3588 set_tok_preg (newtok[2], AXP_REG_AT);
3589 assemble_tokens_to_insn ("stq_u", newtok, 3, &insn);
3593 assert (insn.nfixups < MAX_INSN_FIXUPS);
3594 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_BASE;
3595 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3597 insn.sequence = lituse;
3604 /* Store an integer to an unaligned address. */
3607 emit_ustX (tok, ntok, vlgsize)
3608 const expressionS *tok;
3612 int lgsize = (int) (long) vlgsize;
3613 expressionS newtok[3];
3615 /* emit "lda $at, exp" */
3617 memcpy (newtok, tok, sizeof (expressionS) * ntok);
3618 newtok[0].X_add_number = AXP_REG_AT;
3619 assemble_tokens ("lda", newtok, ntok, 1);
3621 /* emit "ldq_u $9, 0($at)" */
3623 set_tok_reg (newtok[0], AXP_REG_T9);
3624 set_tok_const (newtok[1], 0);
3625 set_tok_preg (newtok[2], AXP_REG_AT);
3626 assemble_tokens ("ldq_u", newtok, 3, 1);
3628 /* emit "ldq_u $10, size-1($at)" */
3630 set_tok_reg (newtok[0], AXP_REG_T10);
3631 set_tok_const (newtok[1], (1 << lgsize) - 1);
3632 assemble_tokens ("ldq_u", newtok, 3, 1);
3634 /* emit "insXl src, $at, $t11" */
3637 set_tok_reg (newtok[1], AXP_REG_AT);
3638 set_tok_reg (newtok[2], AXP_REG_T11);
3639 assemble_tokens (insXl_op[lgsize], newtok, 3, 1);
3641 /* emit "insXh src, $at, $t12" */
3643 set_tok_reg (newtok[2], AXP_REG_T12);
3644 assemble_tokens (insXh_op[lgsize], newtok, 3, 1);
3646 /* emit "mskXl $t9, $at, $t9" */
3648 set_tok_reg (newtok[0], AXP_REG_T9);
3649 newtok[2] = newtok[0];
3650 assemble_tokens (mskXl_op[lgsize], newtok, 3, 1);
3652 /* emit "mskXh $t10, $at, $t10" */
3654 set_tok_reg (newtok[0], AXP_REG_T10);
3655 newtok[2] = newtok[0];
3656 assemble_tokens (mskXh_op[lgsize], newtok, 3, 1);
3658 /* emit "or $t9, $t11, $t9" */
3660 set_tok_reg (newtok[0], AXP_REG_T9);
3661 set_tok_reg (newtok[1], AXP_REG_T11);
3662 newtok[2] = newtok[0];
3663 assemble_tokens ("or", newtok, 3, 1);
3665 /* emit "or $t10, $t12, $t10" */
3667 set_tok_reg (newtok[0], AXP_REG_T10);
3668 set_tok_reg (newtok[1], AXP_REG_T12);
3669 newtok[2] = newtok[0];
3670 assemble_tokens ("or", newtok, 3, 1);
3672 /* emit "stq_u $t9, 0($at)" */
3674 set_tok_reg (newtok[0], AXP_REG_T9);
3675 set_tok_const (newtok[1], 0);
3676 set_tok_preg (newtok[2], AXP_REG_AT);
3677 assemble_tokens ("stq_u", newtok, 3, 1);
3679 /* emit "stq_u $t10, size-1($at)" */
3681 set_tok_reg (newtok[0], AXP_REG_T10);
3682 set_tok_const (newtok[1], (1 << lgsize) - 1);
3683 assemble_tokens ("stq_u", newtok, 3, 1);
3686 /* Sign extend a half-word or byte. The 32-bit sign extend is
3687 implemented as "addl $31, $r, $t" in the opcode table. */
3690 emit_sextX (tok, ntok, vlgsize)
3691 const expressionS *tok;
3695 long lgsize = (long) vlgsize;
3697 if (alpha_target & AXP_OPCODE_BWX)
3698 assemble_tokens (sextX_op[lgsize], tok, ntok, 0);
3701 int bitshift = 64 - 8 * (1 << lgsize);
3702 expressionS newtok[3];
3704 /* emit "sll src,bits,dst" */
3707 set_tok_const (newtok[1], bitshift);
3708 newtok[2] = tok[ntok - 1];
3709 assemble_tokens ("sll", newtok, 3, 1);
3711 /* emit "sra dst,bits,dst" */
3713 newtok[0] = newtok[2];
3714 assemble_tokens ("sra", newtok, 3, 1);
3718 /* Implement the division and modulus macros. */
3722 /* Make register usage like in normal procedure call.
3723 Don't clobber PV and RA. */
3726 emit_division (tok, ntok, symname)
3727 const expressionS *tok;
3731 /* DIVISION and MODULUS. Yech.
3736 * mov x,R16 # if x != R16
3737 * mov y,R17 # if y != R17
3742 * with appropriate optimizations if R0,R16,R17 are the registers
3743 * specified by the compiler.
3748 expressionS newtok[3];
3750 xr = regno (tok[0].X_add_number);
3751 yr = regno (tok[1].X_add_number);
3756 rr = regno (tok[2].X_add_number);
3758 /* Move the operands into the right place */
3759 if (yr == AXP_REG_R16 && xr == AXP_REG_R17)
3761 /* They are in exactly the wrong order -- swap through AT */
3764 as_bad (_("macro requires $at register while noat in effect"));
3766 set_tok_reg (newtok[0], AXP_REG_R16);
3767 set_tok_reg (newtok[1], AXP_REG_AT);
3768 assemble_tokens ("mov", newtok, 2, 1);
3770 set_tok_reg (newtok[0], AXP_REG_R17);
3771 set_tok_reg (newtok[1], AXP_REG_R16);
3772 assemble_tokens ("mov", newtok, 2, 1);
3774 set_tok_reg (newtok[0], AXP_REG_AT);
3775 set_tok_reg (newtok[1], AXP_REG_R17);
3776 assemble_tokens ("mov", newtok, 2, 1);
3780 if (yr == AXP_REG_R16)
3782 set_tok_reg (newtok[0], AXP_REG_R16);
3783 set_tok_reg (newtok[1], AXP_REG_R17);
3784 assemble_tokens ("mov", newtok, 2, 1);
3787 if (xr != AXP_REG_R16)
3789 set_tok_reg (newtok[0], xr);
3790 set_tok_reg (newtok[1], AXP_REG_R16);
3791 assemble_tokens ("mov", newtok, 2, 1);
3794 if (yr != AXP_REG_R16 && yr != AXP_REG_R17)
3796 set_tok_reg (newtok[0], yr);
3797 set_tok_reg (newtok[1], AXP_REG_R17);
3798 assemble_tokens ("mov", newtok, 2, 1);
3802 sym = symbol_find_or_make ((const char *) symname);
3804 set_tok_reg (newtok[0], AXP_REG_AT);
3805 set_tok_sym (newtok[1], sym, 0);
3806 assemble_tokens ("lda", newtok, 2, 1);
3808 /* Call the division routine */
3809 set_tok_reg (newtok[0], AXP_REG_AT);
3810 set_tok_cpreg (newtok[1], AXP_REG_AT);
3811 set_tok_const (newtok[2], 0);
3812 assemble_tokens ("jsr", newtok, 3, 1);
3814 /* Move the result to the right place */
3815 if (rr != AXP_REG_R0)
3817 set_tok_reg (newtok[0], AXP_REG_R0);
3818 set_tok_reg (newtok[1], rr);
3819 assemble_tokens ("mov", newtok, 2, 1);
3823 #else /* !OBJ_EVAX */
3826 emit_division (tok, ntok, symname)
3827 const expressionS *tok;
3831 /* DIVISION and MODULUS. Yech.
3841 * with appropriate optimizations if t10,t11,t12 are the registers
3842 * specified by the compiler.
3847 expressionS newtok[3];
3849 xr = regno (tok[0].X_add_number);
3850 yr = regno (tok[1].X_add_number);
3855 rr = regno (tok[2].X_add_number);
3857 sym = symbol_find_or_make ((const char *) symname);
3859 /* Move the operands into the right place */
3860 if (yr == AXP_REG_T10 && xr == AXP_REG_T11)
3862 /* They are in exactly the wrong order -- swap through AT */
3865 as_bad (_("macro requires $at register while noat in effect"));
3867 set_tok_reg (newtok[0], AXP_REG_T10);
3868 set_tok_reg (newtok[1], AXP_REG_AT);
3869 assemble_tokens ("mov", newtok, 2, 1);
3871 set_tok_reg (newtok[0], AXP_REG_T11);
3872 set_tok_reg (newtok[1], AXP_REG_T10);
3873 assemble_tokens ("mov", newtok, 2, 1);
3875 set_tok_reg (newtok[0], AXP_REG_AT);
3876 set_tok_reg (newtok[1], AXP_REG_T11);
3877 assemble_tokens ("mov", newtok, 2, 1);
3881 if (yr == AXP_REG_T10)
3883 set_tok_reg (newtok[0], AXP_REG_T10);
3884 set_tok_reg (newtok[1], AXP_REG_T11);
3885 assemble_tokens ("mov", newtok, 2, 1);
3888 if (xr != AXP_REG_T10)
3890 set_tok_reg (newtok[0], xr);
3891 set_tok_reg (newtok[1], AXP_REG_T10);
3892 assemble_tokens ("mov", newtok, 2, 1);
3895 if (yr != AXP_REG_T10 && yr != AXP_REG_T11)
3897 set_tok_reg (newtok[0], yr);
3898 set_tok_reg (newtok[1], AXP_REG_T11);
3899 assemble_tokens ("mov", newtok, 2, 1);
3903 /* Call the division routine */
3904 set_tok_reg (newtok[0], AXP_REG_T9);
3905 set_tok_sym (newtok[1], sym, 0);
3906 assemble_tokens ("jsr", newtok, 2, 1);
3908 /* Reload the GP register */
3912 #if defined(OBJ_ECOFF) || defined(OBJ_ELF)
3913 set_tok_reg (newtok[0], alpha_gp_register);
3914 set_tok_const (newtok[1], 0);
3915 set_tok_preg (newtok[2], AXP_REG_T9);
3916 assemble_tokens ("ldgp", newtok, 3, 1);
3919 /* Move the result to the right place */
3920 if (rr != AXP_REG_T12)
3922 set_tok_reg (newtok[0], AXP_REG_T12);
3923 set_tok_reg (newtok[1], rr);
3924 assemble_tokens ("mov", newtok, 2, 1);
3928 #endif /* !OBJ_EVAX */
3930 /* The jsr and jmp macros differ from their instruction counterparts
3931 in that they can load the target address and default most
3935 emit_jsrjmp (tok, ntok, vopname)
3936 const expressionS *tok;
3940 const char *opname = (const char *) vopname;
3941 struct alpha_insn insn;
3942 expressionS newtok[3];
3946 if (tokidx < ntok && tok[tokidx].X_op == O_register)
3947 r = regno (tok[tokidx++].X_add_number);
3949 r = strcmp (opname, "jmp") == 0 ? AXP_REG_ZERO : AXP_REG_RA;
3951 set_tok_reg (newtok[0], r);
3953 if (tokidx < ntok &&
3954 (tok[tokidx].X_op == O_pregister || tok[tokidx].X_op == O_cpregister))
3955 r = regno (tok[tokidx++].X_add_number);
3957 /* keep register if jsr $n.<sym> */
3961 int basereg = alpha_gp_register;
3962 lituse = load_expression (r = AXP_REG_PV, &tok[tokidx], &basereg, NULL);
3966 set_tok_cpreg (newtok[1], r);
3969 /* FIXME: Add hint relocs to BFD for evax. */
3972 newtok[2] = tok[tokidx];
3975 set_tok_const (newtok[2], 0);
3977 assemble_tokens_to_insn (opname, newtok, 3, &insn);
3981 assert (insn.nfixups < MAX_INSN_FIXUPS);
3982 insn.fixups[insn.nfixups].reloc = DUMMY_RELOC_LITUSE_JSR;
3983 insn.fixups[insn.nfixups].exp.X_op = O_absent;
3985 insn.sequence = lituse;
3991 /* The ret and jcr instructions differ from their instruction
3992 counterparts in that everything can be defaulted. */
3995 emit_retjcr (tok, ntok, vopname)
3996 const expressionS *tok;
4000 const char *opname = (const char *) vopname;
4001 expressionS newtok[3];
4004 if (tokidx < ntok && tok[tokidx].X_op == O_register)
4005 r = regno (tok[tokidx++].X_add_number);
4009 set_tok_reg (newtok[0], r);
4011 if (tokidx < ntok &&
4012 (tok[tokidx].X_op == O_pregister || tok[tokidx].X_op == O_cpregister))
4013 r = regno (tok[tokidx++].X_add_number);
4017 set_tok_cpreg (newtok[1], r);
4020 newtok[2] = tok[tokidx];
4022 set_tok_const (newtok[2], strcmp (opname, "ret") == 0);
4024 assemble_tokens (opname, newtok, 3, 0);
4027 /* Assembler directives */
4029 /* Handle the .text pseudo-op. This is like the usual one, but it
4030 clears alpha_insn_label and restores auto alignment. */
4042 alpha_insn_label = NULL;
4043 alpha_auto_align_on = 1;
4044 alpha_current_align = 0;
4047 /* Handle the .data pseudo-op. This is like the usual one, but it
4048 clears alpha_insn_label and restores auto alignment. */
4059 alpha_insn_label = NULL;
4060 alpha_auto_align_on = 1;
4061 alpha_current_align = 0;
4064 #if defined (OBJ_ECOFF) || defined (OBJ_EVAX)
4066 /* Handle the OSF/1 and openVMS .comm pseudo quirks.
4067 openVMS constructs a section for every common symbol. */
4070 s_alpha_comm (ignore)
4073 register char *name;
4077 register symbolS *symbolP;
4080 segT current_section = now_seg;
4081 int current_subsec = now_subseg;
4085 name = input_line_pointer;
4086 c = get_symbol_end ();
4088 /* just after name is now '\0' */
4089 p = input_line_pointer;
4094 /* Alpha OSF/1 compiler doesn't provide the comma, gcc does. */
4095 if (*input_line_pointer == ',')
4097 input_line_pointer++;
4100 if ((temp = get_absolute_expression ()) < 0)
4102 as_warn (_(".COMMon length (%ld.) <0! Ignored."), (long) temp);
4103 ignore_rest_of_line ();
4108 symbolP = symbol_find_or_make (name);
4111 /* Make a section for the common symbol. */
4112 new_seg = subseg_new (xstrdup (name), 0);
4118 /* alignment might follow */
4119 if (*input_line_pointer == ',')
4123 input_line_pointer++;
4124 align = get_absolute_expression ();
4125 bfd_set_section_alignment (stdoutput, new_seg, align);
4129 if (S_IS_DEFINED (symbolP) && ! S_IS_COMMON (symbolP))
4131 as_bad (_("Ignoring attempt to re-define symbol"));
4132 ignore_rest_of_line ();
4137 if (bfd_section_size (stdoutput, new_seg) > 0)
4139 if (bfd_section_size (stdoutput, new_seg) != temp)
4140 as_bad (_("Length of .comm \"%s\" is already %ld. Not changed to %ld."),
4141 S_GET_NAME (symbolP),
4142 (long) bfd_section_size (stdoutput, new_seg),
4146 if (S_GET_VALUE (symbolP))
4148 if (S_GET_VALUE (symbolP) != (valueT) temp)
4149 as_bad (_("Length of .comm \"%s\" is already %ld. Not changed to %ld."),
4150 S_GET_NAME (symbolP),
4151 (long) S_GET_VALUE (symbolP),
4158 subseg_set (new_seg, 0);
4159 p = frag_more (temp);
4160 new_seg->flags |= SEC_IS_COMMON;
4161 if (! S_IS_DEFINED (symbolP))
4162 S_SET_SEGMENT (symbolP, new_seg);
4164 S_SET_VALUE (symbolP, (valueT) temp);
4166 S_SET_EXTERNAL (symbolP);
4170 subseg_set (current_section, current_subsec);
4173 know (symbol_get_frag (symbolP) == &zero_address_frag);
4175 demand_empty_rest_of_line ();
4178 #endif /* ! OBJ_ELF */
4182 /* Handle the .rdata pseudo-op. This is like the usual one, but it
4183 clears alpha_insn_label and restores auto alignment. */
4186 s_alpha_rdata (ignore)
4191 temp = get_absolute_expression ();
4192 subseg_new (".rdata", 0);
4193 demand_empty_rest_of_line ();
4194 alpha_insn_label = NULL;
4195 alpha_auto_align_on = 1;
4196 alpha_current_align = 0;
4203 /* Handle the .sdata pseudo-op. This is like the usual one, but it
4204 clears alpha_insn_label and restores auto alignment. */
4207 s_alpha_sdata (ignore)
4212 temp = get_absolute_expression ();
4213 subseg_new (".sdata", 0);
4214 demand_empty_rest_of_line ();
4215 alpha_insn_label = NULL;
4216 alpha_auto_align_on = 1;
4217 alpha_current_align = 0;
4223 /* Handle the .section pseudo-op. This is like the usual one, but it
4224 clears alpha_insn_label and restores auto alignment. */
4227 s_alpha_section (ignore)
4230 obj_elf_section (ignore);
4232 alpha_insn_label = NULL;
4233 alpha_auto_align_on = 1;
4234 alpha_current_align = 0;
4239 int dummy ATTRIBUTE_UNUSED;
4241 if (ECOFF_DEBUGGING)
4242 ecoff_directive_ent (0);
4245 char *name, name_end;
4246 name = input_line_pointer;
4247 name_end = get_symbol_end ();
4249 if (! is_name_beginner (*name))
4251 as_warn (_(".ent directive has no name"));
4252 *input_line_pointer = name_end;
4258 if (alpha_cur_ent_sym)
4259 as_warn (_("nested .ent directives"));
4261 sym = symbol_find_or_make (name);
4262 symbol_get_bfdsym (sym)->flags |= BSF_FUNCTION;
4263 alpha_cur_ent_sym = sym;
4265 /* The .ent directive is sometimes followed by a number. Not sure
4266 what it really means, but ignore it. */
4267 *input_line_pointer = name_end;
4269 if (*input_line_pointer == ',')
4271 input_line_pointer++;
4274 if (ISDIGIT (*input_line_pointer) || *input_line_pointer == '-')
4275 (void) get_absolute_expression ();
4277 demand_empty_rest_of_line ();
4283 int dummy ATTRIBUTE_UNUSED;
4285 if (ECOFF_DEBUGGING)
4286 ecoff_directive_end (0);
4289 char *name, name_end;
4290 name = input_line_pointer;
4291 name_end = get_symbol_end ();
4293 if (! is_name_beginner (*name))
4295 as_warn (_(".end directive has no name"));
4296 *input_line_pointer = name_end;
4302 sym = symbol_find (name);
4303 if (sym != alpha_cur_ent_sym)
4304 as_warn (_(".end directive names different symbol than .ent"));
4306 /* Create an expression to calculate the size of the function. */
4309 symbol_get_obj (sym)->size =
4310 (expressionS *) xmalloc (sizeof (expressionS));
4311 symbol_get_obj (sym)->size->X_op = O_subtract;
4312 symbol_get_obj (sym)->size->X_add_symbol
4313 = symbol_new ("L0\001", now_seg, frag_now_fix (), frag_now);
4314 symbol_get_obj (sym)->size->X_op_symbol = sym;
4315 symbol_get_obj (sym)->size->X_add_number = 0;
4318 alpha_cur_ent_sym = NULL;
4320 *input_line_pointer = name_end;
4322 demand_empty_rest_of_line ();
4330 if (ECOFF_DEBUGGING)
4333 ecoff_directive_fmask (0);
4335 ecoff_directive_mask (0);
4338 discard_rest_of_line ();
4342 s_alpha_frame (dummy)
4343 int dummy ATTRIBUTE_UNUSED;
4345 if (ECOFF_DEBUGGING)
4346 ecoff_directive_frame (0);
4348 discard_rest_of_line ();
4352 s_alpha_prologue (ignore)
4353 int ignore ATTRIBUTE_UNUSED;
4358 arg = get_absolute_expression ();
4359 demand_empty_rest_of_line ();
4361 if (ECOFF_DEBUGGING)
4362 sym = ecoff_get_cur_proc_sym ();
4364 sym = alpha_cur_ent_sym;
4369 case 0: /* No PV required. */
4370 S_SET_OTHER (sym, STO_ALPHA_NOPV
4371 | (S_GET_OTHER (sym) & ~STO_ALPHA_STD_GPLOAD));
4373 case 1: /* Std GP load. */
4374 S_SET_OTHER (sym, STO_ALPHA_STD_GPLOAD
4375 | (S_GET_OTHER (sym) & ~STO_ALPHA_STD_GPLOAD));
4377 case 2: /* Non-std use of PV. */
4381 as_bad (_("Invalid argument %d to .prologue."), arg);
4386 static char *first_file_directive;
4389 s_alpha_file (ignore)
4390 int ignore ATTRIBUTE_UNUSED;
4392 /* Save the first .file directive we see, so that we can change our
4393 minds about whether ecoff debugging should or shouldn't be enabled. */
4394 if (alpha_flag_mdebug < 0 && ! first_file_directive)
4396 char *start = input_line_pointer;
4399 discard_rest_of_line ();
4401 len = input_line_pointer - start;
4402 first_file_directive = xmalloc (len + 1);
4403 memcpy (first_file_directive, start, len);
4404 first_file_directive[len] = '\0';
4406 input_line_pointer = start;
4409 if (ECOFF_DEBUGGING)
4410 ecoff_directive_file (0);
4412 dwarf2_directive_file (0);
4416 s_alpha_loc (ignore)
4417 int ignore ATTRIBUTE_UNUSED;
4419 if (ECOFF_DEBUGGING)
4420 ecoff_directive_loc (0);
4422 dwarf2_directive_loc (0);
4429 /* If we've been undecided about mdebug, make up our minds in favour. */
4430 if (alpha_flag_mdebug < 0)
4432 segT sec = subseg_new (".mdebug", 0);
4433 bfd_set_section_flags (stdoutput, sec, SEC_HAS_CONTENTS | SEC_READONLY);
4434 bfd_set_section_alignment (stdoutput, sec, 3);
4436 ecoff_read_begin_hook ();
4438 if (first_file_directive)
4440 char *save_ilp = input_line_pointer;
4441 input_line_pointer = first_file_directive;
4442 ecoff_directive_file (0);
4443 input_line_pointer = save_ilp;
4444 free (first_file_directive);
4447 alpha_flag_mdebug = 1;
4453 s_alpha_coff_wrapper (which)
4456 static void (* const fns[]) PARAMS ((int)) = {
4457 ecoff_directive_begin,
4458 ecoff_directive_bend,
4459 ecoff_directive_def,
4460 ecoff_directive_dim,
4461 ecoff_directive_endef,
4462 ecoff_directive_scl,
4463 ecoff_directive_tag,
4464 ecoff_directive_val,
4467 assert (which >= 0 && which < (int) (sizeof (fns)/sizeof (*fns)));
4469 if (ECOFF_DEBUGGING)
4473 as_bad (_("ECOFF debugging is disabled."));
4474 ignore_rest_of_line ();
4477 #endif /* OBJ_ELF */
4481 /* Handle the section specific pseudo-op. */
4484 s_alpha_section (secid)
4488 #define EVAX_SECTION_COUNT 5
4489 static char *section_name[EVAX_SECTION_COUNT + 1] =
4490 { "NULL", ".rdata", ".comm", ".link", ".ctors", ".dtors" };
4492 if ((secid <= 0) || (secid > EVAX_SECTION_COUNT))
4494 as_fatal (_("Unknown section directive"));
4495 demand_empty_rest_of_line ();
4498 temp = get_absolute_expression ();
4499 subseg_new (section_name[secid], 0);
4500 demand_empty_rest_of_line ();
4501 alpha_insn_label = NULL;
4502 alpha_auto_align_on = 1;
4503 alpha_current_align = 0;
4506 /* Parse .ent directives. */
4509 s_alpha_ent (ignore)
4513 expressionS symexpr;
4515 alpha_evax_proc.pdsckind = 0;
4516 alpha_evax_proc.framereg = -1;
4517 alpha_evax_proc.framesize = 0;
4518 alpha_evax_proc.rsa_offset = 0;
4519 alpha_evax_proc.ra_save = AXP_REG_RA;
4520 alpha_evax_proc.fp_save = -1;
4521 alpha_evax_proc.imask = 0;
4522 alpha_evax_proc.fmask = 0;
4523 alpha_evax_proc.prologue = 0;
4524 alpha_evax_proc.type = 0;
4526 expression (&symexpr);
4528 if (symexpr.X_op != O_symbol)
4530 as_fatal (_(".ent directive has no symbol"));
4531 demand_empty_rest_of_line ();
4535 symbol = make_expr_symbol (&symexpr);
4536 symbol_get_bfdsym (symbol)->flags |= BSF_FUNCTION;
4537 alpha_evax_proc.symbol = symbol;
4539 demand_empty_rest_of_line ();
4543 /* Parse .frame <framreg>,<framesize>,RA,<rsa_offset> directives. */
4546 s_alpha_frame (ignore)
4551 alpha_evax_proc.framereg = tc_get_register (1);
4554 if (*input_line_pointer++ != ','
4555 || get_absolute_expression_and_terminator (&val) != ',')
4557 as_warn (_("Bad .frame directive 1./2. param"));
4558 --input_line_pointer;
4559 demand_empty_rest_of_line ();
4563 alpha_evax_proc.framesize = val;
4565 (void) tc_get_register (1);
4567 if (*input_line_pointer++ != ',')
4569 as_warn (_("Bad .frame directive 3./4. param"));
4570 --input_line_pointer;
4571 demand_empty_rest_of_line ();
4574 alpha_evax_proc.rsa_offset = get_absolute_expression ();
4580 s_alpha_pdesc (ignore)
4590 segment_info_type *seginfo = seg_info (alpha_link_section);
4592 if (now_seg != alpha_link_section)
4594 as_bad (_(".pdesc directive not in link (.link) section"));
4595 demand_empty_rest_of_line ();
4599 if ((alpha_evax_proc.symbol == 0)
4600 || (!S_IS_DEFINED (alpha_evax_proc.symbol)))
4602 as_fatal (_(".pdesc has no matching .ent"));
4603 demand_empty_rest_of_line ();
4607 *symbol_get_obj (alpha_evax_proc.symbol) =
4608 (valueT) seginfo->literal_pool_size;
4611 if (exp.X_op != O_symbol)
4613 as_warn (_(".pdesc directive has no entry symbol"));
4614 demand_empty_rest_of_line ();
4618 entry_sym = make_expr_symbol (&exp);
4619 /* Save bfd symbol of proc desc in function symbol. */
4620 symbol_get_bfdsym (alpha_evax_proc.symbol)->udata.p
4621 = symbol_get_bfdsym (entry_sym);
4624 if (*input_line_pointer++ != ',')
4626 as_warn (_("No comma after .pdesc <entryname>"));
4627 demand_empty_rest_of_line ();
4632 name = input_line_pointer;
4633 name_end = get_symbol_end ();
4635 if (strncmp (name, "stack", 5) == 0)
4637 alpha_evax_proc.pdsckind = PDSC_S_K_KIND_FP_STACK;
4639 else if (strncmp (name, "reg", 3) == 0)
4641 alpha_evax_proc.pdsckind = PDSC_S_K_KIND_FP_REGISTER;
4643 else if (strncmp (name, "null", 4) == 0)
4645 alpha_evax_proc.pdsckind = PDSC_S_K_KIND_NULL;
4649 as_fatal (_("unknown procedure kind"));
4650 demand_empty_rest_of_line ();
4654 *input_line_pointer = name_end;
4655 demand_empty_rest_of_line ();
4657 #ifdef md_flush_pending_output
4658 md_flush_pending_output ();
4661 frag_align (3, 0, 0);
4663 fixp = fix_new (frag_now, p - frag_now->fr_literal, 8, 0, 0, 0, 0);
4665 seginfo->literal_pool_size += 16;
4667 *p = alpha_evax_proc.pdsckind
4668 | ((alpha_evax_proc.framereg == 29) ? PDSC_S_M_BASE_REG_IS_FP : 0);
4669 *(p + 1) = PDSC_S_M_NATIVE | PDSC_S_M_NO_JACKET;
4671 switch (alpha_evax_proc.pdsckind)
4673 case PDSC_S_K_KIND_NULL:
4677 case PDSC_S_K_KIND_FP_REGISTER:
4678 *(p + 2) = alpha_evax_proc.fp_save;
4679 *(p + 3) = alpha_evax_proc.ra_save;
4681 case PDSC_S_K_KIND_FP_STACK:
4682 md_number_to_chars (p + 2, (valueT) alpha_evax_proc.rsa_offset, 2);
4684 default: /* impossible */
4689 *(p + 5) = alpha_evax_proc.type & 0x0f;
4691 /* Signature offset. */
4692 md_number_to_chars (p + 6, (valueT) 0, 2);
4694 fix_new_exp (frag_now, p - frag_now->fr_literal+8, 8, &exp, 0, BFD_RELOC_64);
4696 if (alpha_evax_proc.pdsckind == PDSC_S_K_KIND_NULL)
4699 /* Add dummy fix to make add_to_link_pool work. */
4701 fixp = fix_new (frag_now, p - frag_now->fr_literal, 8, 0, 0, 0, 0);
4703 seginfo->literal_pool_size += 8;
4705 /* pdesc+16: Size. */
4706 md_number_to_chars (p, (valueT) alpha_evax_proc.framesize, 4);
4708 md_number_to_chars (p + 4, (valueT) 0, 2);
4711 md_number_to_chars (p + 6, alpha_evax_proc.prologue, 2);
4713 if (alpha_evax_proc.pdsckind == PDSC_S_K_KIND_FP_REGISTER)
4716 /* Add dummy fix to make add_to_link_pool work. */
4718 fixp = fix_new (frag_now, p - frag_now->fr_literal, 8, 0, 0, 0, 0);
4720 seginfo->literal_pool_size += 8;
4722 /* pdesc+24: register masks. */
4724 md_number_to_chars (p, alpha_evax_proc.imask, 4);
4725 md_number_to_chars (p + 4, alpha_evax_proc.fmask, 4);
4730 /* Support for crash debug on vms. */
4733 s_alpha_name (ignore)
4738 segment_info_type *seginfo = seg_info (alpha_link_section);
4740 if (now_seg != alpha_link_section)
4742 as_bad (_(".name directive not in link (.link) section"));
4743 demand_empty_rest_of_line ();
4748 if (exp.X_op != O_symbol)
4750 as_warn (_(".name directive has no symbol"));
4751 demand_empty_rest_of_line ();
4755 demand_empty_rest_of_line ();
4757 #ifdef md_flush_pending_output
4758 md_flush_pending_output ();
4761 frag_align (3, 0, 0);
4763 seginfo->literal_pool_size += 8;
4765 fix_new_exp (frag_now, p - frag_now->fr_literal, 8, &exp, 0, BFD_RELOC_64);
4771 s_alpha_linkage (ignore)
4777 #ifdef md_flush_pending_output
4778 md_flush_pending_output ();
4782 if (exp.X_op != O_symbol)
4784 as_fatal (_("No symbol after .linkage"));
4788 p = frag_more (LKP_S_K_SIZE);
4789 memset (p, 0, LKP_S_K_SIZE);
4790 fix_new_exp (frag_now, p - frag_now->fr_literal, LKP_S_K_SIZE, &exp, 0,\
4791 BFD_RELOC_ALPHA_LINKAGE);
4793 demand_empty_rest_of_line ();
4799 s_alpha_code_address (ignore)
4805 #ifdef md_flush_pending_output
4806 md_flush_pending_output ();
4810 if (exp.X_op != O_symbol)
4812 as_fatal (_("No symbol after .code_address"));
4818 fix_new_exp (frag_now, p - frag_now->fr_literal, 8, &exp, 0,\
4819 BFD_RELOC_ALPHA_CODEADDR);
4821 demand_empty_rest_of_line ();
4827 s_alpha_fp_save (ignore)
4831 alpha_evax_proc.fp_save = tc_get_register (1);
4833 demand_empty_rest_of_line ();
4838 s_alpha_mask (ignore)
4843 if (get_absolute_expression_and_terminator (&val) != ',')
4845 as_warn (_("Bad .mask directive"));
4846 --input_line_pointer;
4850 alpha_evax_proc.imask = val;
4851 (void) get_absolute_expression ();
4853 demand_empty_rest_of_line ();
4859 s_alpha_fmask (ignore)
4864 if (get_absolute_expression_and_terminator (&val) != ',')
4866 as_warn (_("Bad .fmask directive"));
4867 --input_line_pointer;
4871 alpha_evax_proc.fmask = val;
4872 (void) get_absolute_expression ();
4874 demand_empty_rest_of_line ();
4880 s_alpha_end (ignore)
4885 c = get_symbol_end ();
4886 *input_line_pointer = c;
4887 demand_empty_rest_of_line ();
4888 alpha_evax_proc.symbol = 0;
4894 s_alpha_file (ignore)
4899 static char case_hack[32];
4901 extern char *demand_copy_string PARAMS ((int *lenP));
4903 sprintf (case_hack, "<CASE:%01d%01d>",
4904 alpha_flag_hash_long_names, alpha_flag_show_after_trunc);
4906 s = symbol_find_or_make (case_hack);
4907 symbol_get_bfdsym (s)->flags |= BSF_FILE;
4909 get_absolute_expression ();
4910 s = symbol_find_or_make (demand_copy_string (&length));
4911 symbol_get_bfdsym (s)->flags |= BSF_FILE;
4912 demand_empty_rest_of_line ();
4916 #endif /* OBJ_EVAX */
4918 /* Handle the .gprel32 pseudo op. */
4921 s_alpha_gprel32 (ignore)
4922 int ignore ATTRIBUTE_UNUSED;
4934 e.X_add_symbol = section_symbol (absolute_section);
4947 e.X_add_symbol = section_symbol (absolute_section);
4950 e.X_op = O_subtract;
4951 e.X_op_symbol = alpha_gp_symbol;
4959 if (alpha_auto_align_on && alpha_current_align < 2)
4960 alpha_align (2, (char *) NULL, alpha_insn_label, 0);
4961 if (alpha_current_align > 2)
4962 alpha_current_align = 2;
4963 alpha_insn_label = NULL;
4967 fix_new_exp (frag_now, p - frag_now->fr_literal, 4,
4968 &e, 0, BFD_RELOC_GPREL32);
4971 /* Handle floating point allocation pseudo-ops. This is like the
4972 generic vresion, but it makes sure the current label, if any, is
4973 correctly aligned. */
4976 s_alpha_float_cons (type)
5003 if (alpha_auto_align_on && alpha_current_align < log_size)
5004 alpha_align (log_size, (char *) NULL, alpha_insn_label, 0);
5005 if (alpha_current_align > log_size)
5006 alpha_current_align = log_size;
5007 alpha_insn_label = NULL;
5012 /* Handle the .proc pseudo op. We don't really do much with it except
5016 s_alpha_proc (is_static)
5017 int is_static ATTRIBUTE_UNUSED;
5025 /* Takes ".proc name,nargs" */
5027 name = input_line_pointer;
5028 c = get_symbol_end ();
5029 p = input_line_pointer;
5030 symbolP = symbol_find_or_make (name);
5033 if (*input_line_pointer != ',')
5036 as_warn (_("Expected comma after name \"%s\""), name);
5039 ignore_rest_of_line ();
5043 input_line_pointer++;
5044 temp = get_absolute_expression ();
5046 /* *symbol_get_obj (symbolP) = (signed char) temp; */
5047 as_warn (_("unhandled: .proc %s,%d"), name, temp);
5048 demand_empty_rest_of_line ();
5051 /* Handle the .set pseudo op. This is used to turn on and off most of
5052 the assembler features. */
5056 int x ATTRIBUTE_UNUSED;
5062 name = input_line_pointer;
5063 ch = get_symbol_end ();
5066 if (s[0] == 'n' && s[1] == 'o')
5071 if (!strcmp ("reorder", s))
5073 else if (!strcmp ("at", s))
5074 alpha_noat_on = !yesno;
5075 else if (!strcmp ("macro", s))
5076 alpha_macros_on = yesno;
5077 else if (!strcmp ("move", s))
5079 else if (!strcmp ("volatile", s))
5082 as_warn (_("Tried to .set unrecognized mode `%s'"), name);
5084 *input_line_pointer = ch;
5085 demand_empty_rest_of_line ();
5088 /* Handle the .base pseudo op. This changes the assembler's notion of
5089 the $gp register. */
5092 s_alpha_base (ignore)
5093 int ignore ATTRIBUTE_UNUSED;
5096 if (first_32bit_quadrant)
5098 /* not fatal, but it might not work in the end */
5099 as_warn (_("File overrides no-base-register option."));
5100 first_32bit_quadrant = 0;
5105 if (*input_line_pointer == '$')
5107 input_line_pointer++;
5108 if (*input_line_pointer == 'r')
5109 input_line_pointer++;
5112 alpha_gp_register = get_absolute_expression ();
5113 if (alpha_gp_register < 0 || alpha_gp_register > 31)
5115 alpha_gp_register = AXP_REG_GP;
5116 as_warn (_("Bad base register, using $%d."), alpha_gp_register);
5119 demand_empty_rest_of_line ();
5122 /* Handle the .align pseudo-op. This aligns to a power of two. It
5123 also adjusts any current instruction label. We treat this the same
5124 way the MIPS port does: .align 0 turns off auto alignment. */
5127 s_alpha_align (ignore)
5128 int ignore ATTRIBUTE_UNUSED;
5132 long max_alignment = 15;
5134 align = get_absolute_expression ();
5135 if (align > max_alignment)
5137 align = max_alignment;
5138 as_bad (_("Alignment too large: %d. assumed"), align);
5142 as_warn (_("Alignment negative: 0 assumed"));
5146 if (*input_line_pointer == ',')
5148 input_line_pointer++;
5149 fill = get_absolute_expression ();
5157 alpha_auto_align_on = 1;
5158 alpha_align (align, pfill, alpha_insn_label, 1);
5162 alpha_auto_align_on = 0;
5165 demand_empty_rest_of_line ();
5168 /* Hook the normal string processor to reset known alignment. */
5171 s_alpha_stringer (terminate)
5174 alpha_current_align = 0;
5175 alpha_insn_label = NULL;
5176 stringer (terminate);
5179 /* Hook the normal space processing to reset known alignment. */
5182 s_alpha_space (ignore)
5185 alpha_current_align = 0;
5186 alpha_insn_label = NULL;
5190 /* Hook into cons for auto-alignment. */
5193 alpha_cons_align (size)
5199 while ((size >>= 1) != 0)
5202 if (alpha_auto_align_on && alpha_current_align < log_size)
5203 alpha_align (log_size, (char *) NULL, alpha_insn_label, 0);
5204 if (alpha_current_align > log_size)
5205 alpha_current_align = log_size;
5206 alpha_insn_label = NULL;
5209 /* Here come the .uword, .ulong, and .uquad explicitly unaligned
5210 pseudos. We just turn off auto-alignment and call down to cons. */
5213 s_alpha_ucons (bytes)
5216 int hold = alpha_auto_align_on;
5217 alpha_auto_align_on = 0;
5219 alpha_auto_align_on = hold;
5222 /* Switch the working cpu type. */
5225 s_alpha_arch (ignored)
5226 int ignored ATTRIBUTE_UNUSED;
5229 const struct cpu_type *p;
5232 name = input_line_pointer;
5233 ch = get_symbol_end ();
5235 for (p = cpu_types; p->name; ++p)
5236 if (strcmp (name, p->name) == 0)
5238 alpha_target_name = p->name, alpha_target = p->flags;
5241 as_warn ("Unknown CPU identifier `%s'", name);
5244 *input_line_pointer = ch;
5245 demand_empty_rest_of_line ();
5249 /* print token expression with alpha specific extension. */
5252 alpha_print_token (f, exp)
5254 const expressionS *exp;
5264 expressionS nexp = *exp;
5265 nexp.X_op = O_register;
5266 print_expr (f, &nexp);
5271 print_expr (f, exp);
5278 /* The target specific pseudo-ops which we support. */
5280 const pseudo_typeS md_pseudo_table[] = {
5282 {"comm", s_alpha_comm, 0}, /* osf1 compiler does this */
5283 {"rdata", s_alpha_rdata, 0},
5285 {"text", s_alpha_text, 0},
5286 {"data", s_alpha_data, 0},
5288 {"sdata", s_alpha_sdata, 0},
5291 {"section", s_alpha_section, 0},
5292 {"section.s", s_alpha_section, 0},
5293 {"sect", s_alpha_section, 0},
5294 {"sect.s", s_alpha_section, 0},
5297 { "pdesc", s_alpha_pdesc, 0},
5298 { "name", s_alpha_name, 0},
5299 { "linkage", s_alpha_linkage, 0},
5300 { "code_address", s_alpha_code_address, 0},
5301 { "ent", s_alpha_ent, 0},
5302 { "frame", s_alpha_frame, 0},
5303 { "fp_save", s_alpha_fp_save, 0},
5304 { "mask", s_alpha_mask, 0},
5305 { "fmask", s_alpha_fmask, 0},
5306 { "end", s_alpha_end, 0},
5307 { "file", s_alpha_file, 0},
5308 { "rdata", s_alpha_section, 1},
5309 { "comm", s_alpha_comm, 0},
5310 { "link", s_alpha_section, 3},
5311 { "ctors", s_alpha_section, 4},
5312 { "dtors", s_alpha_section, 5},
5315 /* Frame related pseudos. */
5316 {"ent", s_alpha_ent, 0},
5317 {"end", s_alpha_end, 0},
5318 {"mask", s_alpha_mask, 0},
5319 {"fmask", s_alpha_mask, 1},
5320 {"frame", s_alpha_frame, 0},
5321 {"prologue", s_alpha_prologue, 0},
5322 {"file", s_alpha_file, 5},
5323 {"loc", s_alpha_loc, 9},
5324 {"stabs", s_alpha_stab, 's'},
5325 {"stabn", s_alpha_stab, 'n'},
5326 /* COFF debugging related pseudos. */
5327 {"begin", s_alpha_coff_wrapper, 0},
5328 {"bend", s_alpha_coff_wrapper, 1},
5329 {"def", s_alpha_coff_wrapper, 2},
5330 {"dim", s_alpha_coff_wrapper, 3},
5331 {"endef", s_alpha_coff_wrapper, 4},
5332 {"scl", s_alpha_coff_wrapper, 5},
5333 {"tag", s_alpha_coff_wrapper, 6},
5334 {"val", s_alpha_coff_wrapper, 7},
5336 {"prologue", s_ignore, 0},
5338 {"gprel32", s_alpha_gprel32, 0},
5339 {"t_floating", s_alpha_float_cons, 'd'},
5340 {"s_floating", s_alpha_float_cons, 'f'},
5341 {"f_floating", s_alpha_float_cons, 'F'},
5342 {"g_floating", s_alpha_float_cons, 'G'},
5343 {"d_floating", s_alpha_float_cons, 'D'},
5345 {"proc", s_alpha_proc, 0},
5346 {"aproc", s_alpha_proc, 1},
5347 {"set", s_alpha_set, 0},
5348 {"reguse", s_ignore, 0},
5349 {"livereg", s_ignore, 0},
5350 {"base", s_alpha_base, 0}, /*??*/
5351 {"option", s_ignore, 0},
5352 {"aent", s_ignore, 0},
5353 {"ugen", s_ignore, 0},
5354 {"eflag", s_ignore, 0},
5356 {"align", s_alpha_align, 0},
5357 {"double", s_alpha_float_cons, 'd'},
5358 {"float", s_alpha_float_cons, 'f'},
5359 {"single", s_alpha_float_cons, 'f'},
5360 {"ascii", s_alpha_stringer, 0},
5361 {"asciz", s_alpha_stringer, 1},
5362 {"string", s_alpha_stringer, 1},
5363 {"space", s_alpha_space, 0},
5364 {"skip", s_alpha_space, 0},
5365 {"zero", s_alpha_space, 0},
5367 /* Unaligned data pseudos. */
5368 {"uword", s_alpha_ucons, 2},
5369 {"ulong", s_alpha_ucons, 4},
5370 {"uquad", s_alpha_ucons, 8},
5373 /* Dwarf wants these versions of unaligned. */
5374 {"2byte", s_alpha_ucons, 2},
5375 {"4byte", s_alpha_ucons, 4},
5376 {"8byte", s_alpha_ucons, 8},
5379 /* We don't do any optimizing, so we can safely ignore these. */
5380 {"noalias", s_ignore, 0},
5381 {"alias", s_ignore, 0},
5383 {"arch", s_alpha_arch, 0},
5388 /* Build a BFD section with its flags set appropriately for the .lita,
5389 .lit8, or .lit4 sections. */
5392 create_literal_section (name, secp, symp)
5397 segT current_section = now_seg;
5398 int current_subsec = now_subseg;
5401 *secp = new_sec = subseg_new (name, 0);
5402 subseg_set (current_section, current_subsec);
5403 bfd_set_section_alignment (stdoutput, new_sec, 4);
5404 bfd_set_section_flags (stdoutput, new_sec,
5405 SEC_RELOC | SEC_ALLOC | SEC_LOAD | SEC_READONLY
5408 S_CLEAR_EXTERNAL (*symp = section_symbol (new_sec));
5413 /* @@@ GP selection voodoo. All of this seems overly complicated and
5414 unnecessary; which is the primary reason it's for ECOFF only. */
5423 vma = bfd_get_section_vma (foo, sec);
5424 if (vma && vma < alpha_gp_value)
5425 alpha_gp_value = vma;
5431 assert (alpha_gp_value == 0);
5433 /* Get minus-one in whatever width... */
5437 /* Select the smallest VMA of these existing sections. */
5438 maybe_set_gp (alpha_lita_section);
5440 /* These were disabled before -- should we use them? */
5441 maybe_set_gp (sdata);
5442 maybe_set_gp (lit8_sec);
5443 maybe_set_gp (lit4_sec);
5446 /* @@ Will a simple 0x8000 work here? If not, why not? */
5447 #define GP_ADJUSTMENT (0x8000 - 0x10)
5449 alpha_gp_value += GP_ADJUSTMENT;
5451 S_SET_VALUE (alpha_gp_symbol, alpha_gp_value);
5454 printf (_("Chose GP value of %lx\n"), alpha_gp_value);
5457 #endif /* OBJ_ECOFF */
5460 /* Map 's' to SHF_ALPHA_GPREL. */
5463 alpha_elf_section_letter (letter, ptr_msg)
5468 return SHF_ALPHA_GPREL;
5470 *ptr_msg = _("Bad .section directive: want a,s,w,x,M,S in string");
5474 /* Map SHF_ALPHA_GPREL to SEC_SMALL_DATA. */
5477 alpha_elf_section_flags (flags, attr, type)
5479 int attr, type ATTRIBUTE_UNUSED;
5481 if (attr & SHF_ALPHA_GPREL)
5482 flags |= SEC_SMALL_DATA;
5485 #endif /* OBJ_ELF */
5487 /* Called internally to handle all alignment needs. This takes care
5488 of eliding calls to frag_align if'n the cached current alignment
5489 says we've already got it, as well as taking care of the auto-align
5490 feature wrt labels. */
5493 alpha_align (n, pfill, label, force)
5497 int force ATTRIBUTE_UNUSED;
5499 if (alpha_current_align >= n)
5504 if (subseg_text_p (now_seg))
5505 frag_align_code (n, 0);
5507 frag_align (n, 0, 0);
5510 frag_align (n, *pfill, 0);
5512 alpha_current_align = n;
5514 if (label != NULL && S_GET_SEGMENT (label) == now_seg)
5516 symbol_set_frag (label, frag_now);
5517 S_SET_VALUE (label, (valueT) frag_now_fix ());
5520 record_alignment (now_seg, n);
5522 /* ??? If alpha_flag_relax && force && elf, record the requested alignment
5523 in a reloc for the linker to see. */
5526 /* This is called from HANDLE_ALIGN in write.c. Fill in the contents
5527 of an rs_align_code fragment. */
5530 alpha_handle_align (fragp)
5533 static char const unop[4] = { 0x00, 0x00, 0xfe, 0x2f };
5534 static char const nopunop[8] = {
5535 0x1f, 0x04, 0xff, 0x47,
5536 0x00, 0x00, 0xfe, 0x2f
5542 if (fragp->fr_type != rs_align_code)
5545 bytes = fragp->fr_next->fr_address - fragp->fr_address - fragp->fr_fix;
5546 p = fragp->fr_literal + fragp->fr_fix;
5559 memcpy (p, unop, 4);
5565 memcpy (p, nopunop, 8);
5567 fragp->fr_fix += fix;
5571 /* The Alpha has support for some VAX floating point types, as well as for
5572 IEEE floating point. We consider IEEE to be the primary floating point
5573 format, and sneak in the VAX floating point support here. */
5574 #define md_atof vax_md_atof
5575 #include "config/atof-vax.c"