2b82dd7e3d151e0e19bd21150814c986e5839e79
[deliverable/binutils-gdb.git] / gas / config / tc-alpha.c
1 /* tc-alpha.c - Processor-specific code for the DEC Alpha CPU.
2 Copyright (C) 1989, 1993, 1994 Free Software Foundation, Inc.
3 Contributed by Carnegie Mellon University, 1993.
4 Written by Alessandro Forin, based on earlier gas-1.38 target CPU files.
5 Modified by Ken Raeburn for gas-2.x and ECOFF support.
6
7 This file is part of GAS, the GNU Assembler.
8
9 GAS is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 2, or (at your option)
12 any later version.
13
14 GAS is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
18
19 You should have received a copy of the GNU General Public License
20 along with GAS; see the file COPYING. If not, write to
21 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
22
23 /*
24 * Mach Operating System
25 * Copyright (c) 1993 Carnegie Mellon University
26 * All Rights Reserved.
27 *
28 * Permission to use, copy, modify and distribute this software and its
29 * documentation is hereby granted, provided that both the copyright
30 * notice and this permission notice appear in all copies of the
31 * software, derivative works or modified versions, and any portions
32 * thereof, and that both notices appear in supporting documentation.
33 *
34 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS
35 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
36 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
37 *
38 * Carnegie Mellon requests users of this software to return to
39 *
40 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
41 * School of Computer Science
42 * Carnegie Mellon University
43 * Pittsburgh PA 15213-3890
44 *
45 * any improvements or extensions that they make and grant Carnegie the
46 * rights to redistribute these changes.
47 */
48 /*
49 * HISTORY
50 * 5-Oct-93 Alessandro Forin (af) at Carnegie-Mellon University
51 * First Checkin
52 *
53 * Author: Alessandro Forin, Carnegie Mellon University
54 * Date: Jan 1993
55 */
56
57 #include <ctype.h>
58
59 #include "as.h"
60 #include "alpha-opcode.h"
61 #include "subsegs.h"
62
63 /* @@ Will a simple 0x8000 work here? If not, why not? */
64 #define GP_ADJUSTMENT (0x8000 - 0x10)
65
66 /* Which machine type is this? Currently stores an integer for the
67 model, one of: 21064, 21066, 21164. */
68 static unsigned long machine;
69
70 /* These are exported to relaxing code, even though we don't do any
71 relaxing on this processor currently. */
72 const relax_typeS md_relax_table[1];
73 int md_short_jump_size = 4;
74 int md_long_jump_size = 4;
75
76 /* handle of the OPCODE hash table */
77 static struct hash_control *op_hash;
78
79 /* Sections and symbols we'll want to keep track of. */
80 static segT lita_sec, rdata, sdata, lit8_sec, lit4_sec;
81 static symbolS *lit8_sym, *lit4_sym;
82
83 /* Setting for ".set [no]{at,macro}". */
84 static int at_ok = 1, macro_ok = 1;
85
86 /* Keep track of global pointer. */
87 valueT alpha_gp_value;
88 static symbolS *gp;
89
90 /* We'll probably be using this relocation frequently, and we
91 will want to compare for it. */
92 static const reloc_howto_type *gpdisp_hi16_howto;
93
94 /* These are exported to ECOFF code. */
95 unsigned long alpha_gprmask, alpha_fprmask;
96
97 /* Used for LITUSE relocations. */
98 static expressionS lituse_basereg, lituse_byteoff, lituse_jsr;
99
100 /* Address size: In OSF/1 1.3, an undocumented "-32addr" option will
101 cause all addresses to be treated as 32-bit values in memory. (The
102 in-register versions are all sign-extended to 64 bits, of course.)
103 Some other systems may want this option too. */
104 static int addr32;
105
106 /* Imported functions -- they should be defined in header files somewhere. */
107 extern segT subseg_get ();
108 extern PTR bfd_alloc_by_size_t ();
109 extern void s_globl (), s_long (), s_short (), s_space (), cons (), s_text (),
110 s_data (), float_cons ();
111
112 /* Static functions, needing forward declarations. */
113 static void s_base (), s_proc (), s_alpha_set ();
114 static void s_gprel32 (), s_rdata (), s_sdata (), s_alpha_comm ();
115 static int alpha_ip ();
116
117 static void emit_unaligned_io PARAMS ((char *, int, valueT, int));
118 static void emit_load_unal PARAMS ((int, valueT, int));
119 static void emit_store_unal PARAMS ((int, valueT, int));
120 static void emit_byte_manip_r PARAMS ((char *, int, int, int, int, int));
121 static void emit_extract_r PARAMS ((int, int, int, int, int));
122 static void emit_insert_r PARAMS ((int, int, int, int, int));
123 static void emit_mask_r PARAMS ((int, int, int, int, int));
124 static void emit_sign_extend PARAMS ((int, int));
125 static void emit_bis_r PARAMS ((int, int, int));
126 static int build_mem PARAMS ((int, int, int, bfd_signed_vma));
127 static int build_operate_n PARAMS ((int, int, int, int, int));
128 static void emit_sll_n PARAMS ((int, int, int));
129 static void emit_ldah_num PARAMS ((int, bfd_vma, int));
130 static void emit_addq_r PARAMS ((int, int, int));
131 static void emit_lda_n PARAMS ((int, bfd_vma, int));
132 static void emit_add64 PARAMS ((int, int, bfd_vma));
133 static int in_range PARAMS ((bfd_vma, int, int));
134
135 const pseudo_typeS md_pseudo_table[] =
136 {
137 {"common", s_comm, 0}, /* is this used? */
138 {"comm", s_alpha_comm, 0}, /* osf1 compiler does this */
139 {"rdata", s_rdata, 0},
140 {"sdata", s_sdata, 0},
141 {"gprel32", s_gprel32, 0},
142 {"t_floating", float_cons, 'd'},
143 {"s_floating", float_cons, 'f'},
144 {"f_floating", float_cons, 'F'},
145 {"g_floating", float_cons, 'G'},
146 {"d_floating", float_cons, 'D'},
147
148 {"proc", s_proc, 0},
149 {"aproc", s_proc, 1},
150 {"set", s_alpha_set, 0},
151 {"reguse", s_ignore, 0},
152 {"livereg", s_ignore, 0},
153 {"extern", s_ignore, 0}, /*??*/
154 {"base", s_base, 0}, /*??*/
155 {"option", s_ignore, 0},
156 {"prologue", s_ignore, 0},
157 {"aent", s_ignore, 0},
158 {"ugen", s_ignore, 0},
159
160 /* We don't do any optimizing, so we can safely ignore these. */
161 {"noalias", s_ignore, 0},
162 {"alias", s_ignore, 0},
163
164 {NULL, 0, 0},
165 };
166
167 #define SA 21 /* shift for register Ra */
168 #define SB 16 /* shift for register Rb */
169 #define SC 0 /* shift for register Rc */
170 #define SN 13 /* shift for 8 bit immediate # */
171
172 #define T9 23
173 #define T10 24
174 #define T11 25
175 #define T12 26
176 #define RA 26 /* note: same as T12 */
177 #define PV 27
178 #define AT 28
179 #define GP 29
180 #define SP 30
181 #define ZERO 31
182
183 #define OPCODE(X) (((X) >> 26) & 0x3f)
184 #define OP_FCN(X) (((X) >> 5) & 0x7f)
185
186 #ifndef FIRST_32BIT_QUADRANT
187 #define FIRST_32BIT_QUADRANT 0
188 #endif
189
190 int first_32bit_quadrant = FIRST_32BIT_QUADRANT;
191 int base_register = FIRST_32BIT_QUADRANT ? ZERO : GP;
192
193 int no_mixed_code = 0;
194 int nofloats = 0;
195
196 /* This array holds the chars that always start a comment. If the
197 pre-processor is disabled, these aren't very useful */
198 const char comment_chars[] = "#";
199
200 /* This array holds the chars that only start a comment at the beginning of
201 a line. If the line seems to have the form '# 123 filename'
202 .line and .file directives will appear in the pre-processed output */
203 /* Note that input_file.c hand checks for '#' at the beginning of the
204 first line of the input file. This is because the compiler outputs
205 #NO_APP at the beginning of its output. */
206 /* Also note that C style comments are always recognized. */
207 const char line_comment_chars[] = "#!";
208
209 /* Chars that can be used to separate mant from exp in floating point nums */
210 const char EXP_CHARS[] = "eE";
211
212 const char line_separator_chars[1];
213
214 /* Chars that mean this number is a floating point constant, as in
215 "0f12.456" or "0d1.2345e12". */
216 /* @@ Do all of these really get used on the alpha?? */
217 char FLT_CHARS[] = "rRsSfFdDxXpP";
218
219 /* Also be aware that MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT may have to be
220 changed in read.c. Ideally it shouldn't have to know about it at all,
221 but nothing is ideal around here. */
222
223 struct reloc_data {
224 expressionS exp;
225 int pcrel;
226 bfd_reloc_code_real_type code;
227 };
228
229 /* Occasionally, two relocations will be desired for one address.
230 Mainly only in cases like "jsr $r,foo" where we want both a LITUSE
231 and a HINT reloc. */
232 #define MAX_RELOCS 2
233
234 struct alpha_it {
235 unsigned long opcode; /* need at least 32 bits */
236 struct reloc_data reloc[MAX_RELOCS];
237 };
238
239 static void getExpression (char *str, struct alpha_it *insn);
240 static char *expr_end;
241
242 #define note_gpreg(R) (alpha_gprmask |= (1 << (R)))
243 #define note_fpreg(R) (alpha_fprmask |= (1 << (R)))
244
245 int
246 tc_get_register (frame)
247 int frame;
248 {
249 int framereg = SP;
250
251 SKIP_WHITESPACE ();
252 if (*input_line_pointer == '$')
253 {
254 input_line_pointer++;
255 if (input_line_pointer[0] == 's'
256 && input_line_pointer[1] == 'p')
257 {
258 input_line_pointer += 2;
259 framereg = SP;
260 }
261 else
262 framereg = get_absolute_expression ();
263 framereg &= 31; /* ? */
264 }
265 else
266 as_warn ("frame reg expected, using $%d.", framereg);
267
268 note_gpreg (framereg);
269 return framereg;
270 }
271
272 static void
273 s_rdata (ignore)
274 int ignore;
275 {
276 int temp;
277
278 temp = get_absolute_expression ();
279 #if 0
280 if (!rdata)
281 rdata = subseg_get (".rdata", 0);
282 subseg_set (rdata, (subsegT) temp);
283 #else
284 rdata = subseg_new (".rdata", 0);
285 #endif
286 demand_empty_rest_of_line ();
287 }
288
289 static void
290 s_sdata (ignore)
291 int ignore;
292 {
293 int temp;
294
295 temp = get_absolute_expression ();
296 #if 0
297 if (!sdata)
298 sdata = subseg_get (".sdata", 0);
299 subseg_set (sdata, (subsegT) temp);
300 #else
301 sdata = subseg_new (".sdata", 0);
302 #endif
303 demand_empty_rest_of_line ();
304 }
305
306 static void
307 s_alpha_comm (ignore)
308 int ignore;
309 {
310 register char *name;
311 register char c;
312 register char *p;
313 offsetT temp;
314 register symbolS *symbolP;
315
316 name = input_line_pointer;
317 c = get_symbol_end ();
318 /* just after name is now '\0' */
319 p = input_line_pointer;
320 *p = c;
321 SKIP_WHITESPACE ();
322 /* Alpha OSF/1 compiler doesn't provide the comma, gcc does. */
323 if (*input_line_pointer == ',')
324 {
325 input_line_pointer++;
326 SKIP_WHITESPACE ();
327 }
328 if ((temp = get_absolute_expression ()) < 0)
329 {
330 as_warn (".COMMon length (%ld.) <0! Ignored.", (long) temp);
331 ignore_rest_of_line ();
332 return;
333 }
334 *p = 0;
335 symbolP = symbol_find_or_make (name);
336 *p = c;
337 if (S_IS_DEFINED (symbolP))
338 {
339 as_bad ("Ignoring attempt to re-define symbol");
340 ignore_rest_of_line ();
341 return;
342 }
343 if (S_GET_VALUE (symbolP))
344 {
345 if (S_GET_VALUE (symbolP) != (valueT) temp)
346 as_bad ("Length of .comm \"%s\" is already %ld. Not changed to %ld.",
347 S_GET_NAME (symbolP),
348 (long) S_GET_VALUE (symbolP),
349 (long) temp);
350 }
351 else
352 {
353 S_SET_VALUE (symbolP, (valueT) temp);
354 S_SET_EXTERNAL (symbolP);
355 }
356
357 know (symbolP->sy_frag == &zero_address_frag);
358 demand_empty_rest_of_line ();
359 }
360
361 arelent *
362 tc_gen_reloc (sec, fixp)
363 asection *sec;
364 fixS *fixp;
365 {
366 arelent *reloc;
367
368 reloc = (arelent *) bfd_alloc_by_size_t (stdoutput, sizeof (arelent));
369 reloc->sym_ptr_ptr = &fixp->fx_addsy->bsym;
370 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
371
372 if (fixp->fx_r_type > BFD_RELOC_UNUSED)
373 abort ();
374
375 if (fixp->fx_r_type == BFD_RELOC_ALPHA_GPDISP_HI16)
376 {
377 if (!gpdisp_hi16_howto)
378 gpdisp_hi16_howto = bfd_reloc_type_lookup (stdoutput,
379 fixp->fx_r_type);
380 reloc->howto = gpdisp_hi16_howto;
381 }
382 else
383 reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
384 assert (reloc->howto != 0);
385 if (!fixp->fx_pcrel != !reloc->howto->pc_relative)
386 {
387 as_fatal ("internal error? cannot generate `%s' relocation",
388 bfd_get_reloc_code_name (fixp->fx_r_type));
389 }
390 assert (!fixp->fx_pcrel == !reloc->howto->pc_relative);
391
392 if (fixp->fx_r_type == BFD_RELOC_ALPHA_LITERAL)
393 {
394 /* fake out bfd_perform_relocation. sigh */
395 reloc->addend = -alpha_gp_value;
396 }
397 else if (reloc->howto->pc_relative && reloc->howto->pcrel_offset)
398 {
399 reloc->addend = fixp->fx_offset - reloc->address;
400 }
401 else
402 reloc->addend = fixp->fx_offset;
403 return reloc;
404 }
405
406 static void
407 s_base ()
408 {
409 if (first_32bit_quadrant)
410 {
411 /* not fatal, but it might not work in the end */
412 as_warn ("File overrides no-base-register option.");
413 first_32bit_quadrant = 0;
414 }
415
416 SKIP_WHITESPACE ();
417 if (*input_line_pointer == '$')
418 { /* $rNN form */
419 input_line_pointer++;
420 if (*input_line_pointer == 'r')
421 input_line_pointer++;
422 }
423
424 base_register = get_absolute_expression ();
425 if (base_register < 0 || base_register > 31)
426 {
427 base_register = GP;
428 as_warn ("Bad base register, using $%d.", base_register);
429 }
430 demand_empty_rest_of_line ();
431 }
432
433 static int in_range (val, nbits, unsignedness)
434 bfd_vma val;
435 int nbits, unsignedness;
436 {
437 /* Look at top bit of value that would be stored, figure out how it
438 would be extended by the hardware, and see if that matches the
439 original supplied value. */
440 bfd_vma mask;
441 bfd_vma one = 1;
442 bfd_vma top_bit, stored_value, missing_bits;
443
444 mask = (one << nbits) - 1;
445 stored_value = val & mask;
446 top_bit = stored_value & (one << nbits - 1);
447 missing_bits = val & ~mask;
448 if (unsignedness)
449 {
450 return missing_bits == 0;
451 }
452 else
453 {
454 /* will sign-extend */
455 if (top_bit)
456 {
457 /* all remaining bits beyond mask should be one */
458 missing_bits |= mask;
459 return missing_bits + 1 == 0;
460 }
461 else
462 {
463 /* all other bits should be zero */
464 return missing_bits == 0;
465 }
466 }
467 }
468
469 static void
470 s_gprel32 ()
471 {
472 expressionS e;
473 char *p;
474
475 SKIP_WHITESPACE ();
476 expression (&e);
477 switch (e.X_op)
478 {
479 case O_constant:
480 e.X_add_symbol = section_symbol (absolute_section);
481 /* fall through */
482 case O_symbol:
483 e.X_op = O_subtract;
484 e.X_op_symbol = gp;
485 break;
486 default:
487 abort ();
488 }
489 p = frag_more (4);
490 memset (p, 0, 4);
491 fix_new_exp (frag_now, p - frag_now->fr_literal, 4, &e, 0,
492 BFD_RELOC_GPREL32);
493 }
494
495 static void
496 create_literal_section (secp, name)
497 segT *secp;
498 const char *name;
499 {
500 segT current_section = now_seg;
501 int current_subsec = now_subseg;
502 segT new_sec;
503
504 *secp = new_sec = subseg_new (name, 0);
505 subseg_set (current_section, current_subsec);
506 bfd_set_section_alignment (stdoutput, new_sec, 3);
507 bfd_set_section_flags (stdoutput, new_sec,
508 SEC_RELOC | SEC_ALLOC | SEC_LOAD | SEC_READONLY
509 | SEC_DATA);
510 }
511
512 #define create_lita_section() create_literal_section (&lita_sec, ".lita")
513
514 static valueT
515 get_lit8_offset (val)
516 bfd_vma val;
517 {
518 valueT retval;
519 if (lit8_sec == 0)
520 {
521 create_literal_section (&lit8_sec, ".lit8");
522 lit8_sym = section_symbol (lit8_sec);
523 }
524 retval = add_to_literal_pool ((symbolS *) 0, val, lit8_sec, 8);
525 if (retval >= 0xfff0)
526 as_fatal ("overflow in fp literal (.lit8) table");
527 return retval;
528 }
529
530 static valueT
531 get_lit4_offset (val)
532 bfd_vma val;
533 {
534 valueT retval;
535 if (lit4_sec == 0)
536 {
537 create_literal_section (&lit4_sec, ".lit4");
538 lit4_sym = section_symbol (lit4_sec);
539 }
540 retval = add_to_literal_pool ((symbolS *) 0, val, lit4_sec, 4);
541 if (retval >= 0xfff0)
542 as_fatal ("overflow in fp literal (.lit4) table");
543 return retval;
544 }
545
546 #define load_insn(NAME, OP) (hash_insert (op_hash, (NAME), (PTR) (OP)))
547
548 static void
549 load_insn_table (ops, size)
550 struct alpha_opcode *ops;
551 int size;
552 {
553 struct alpha_opcode *end = ops + size;
554 struct alpha_opcode *op;
555 const char *name;
556
557 for (op = ops; op < end; )
558 {
559 const char *retval;
560
561 name = op->name;
562
563 retval = load_insn (op->name, op);
564 if (retval)
565 as_fatal ("internal error: can't hash opcode `%s': %s",
566 op->name, retval);
567
568 do
569 op++;
570 while (op < end
571 && (op->name == name
572 || !strcmp (op->name, name)));
573 }
574 /* Some opcodes include modifiers of various sorts with a "/mod"
575 syntax, like the architecture documentation suggests. However,
576 for use with gcc at least, we also need to access those same
577 opcodes without the "/". */
578 for (op = ops; op < end; )
579 {
580 name = op->name;
581
582 if (strchr (name, '/'))
583 {
584 char *name2, *p;
585 const char *q;
586
587 name2 = xmalloc (strlen (name));
588 p = name2;
589 q = name;
590
591 while (*q)
592 if (*q == '/')
593 q++;
594 else
595 *p++ = *q++;
596 *p = 0;
597 /* Ignore failures -- the opcode table does duplicate some
598 variants in different forms, like "hw_stq" and "hw_st/q".
599 Maybe the variants can be eliminated, and this error checking
600 restored. */
601 load_insn (name2, op);
602 }
603
604 do
605 op++;
606 while (op < end
607 && (op->name == name
608 || !strcmp (op->name, name)));
609 }
610 }
611
612 static struct alpha_it clear_insn;
613
614 /* This function is called once, at assembler startup time. It should
615 set up all the tables, etc. that the MD part of the assembler will
616 need, that can be determined before arguments are parsed. */
617 void
618 md_begin ()
619 {
620 int i;
621
622 op_hash = hash_new ();
623 load_insn_table (alpha_opcodes, NUMOPCODES);
624
625 /* Default to 21064 PAL instructions. */
626 if (machine == 0)
627 machine = 21064;
628
629 switch (machine)
630 {
631 case 21064:
632 case 21066:
633 load_insn_table (alpha_pal21064_opcodes, NUM21064OPCODES);
634 break;
635 case 21164:
636 load_insn_table (alpha_pal21164_opcodes, NUM21164OPCODES);
637 break;
638 default:
639 as_fatal ("palcode set unknown (internal error)");
640 }
641
642 lituse_basereg.X_op = O_constant;
643 lituse_basereg.X_add_number = 1;
644 lituse_byteoff.X_op = O_constant;
645 lituse_byteoff.X_add_number = 2;
646 lituse_jsr.X_op = O_constant;
647 lituse_jsr.X_add_number = 3;
648
649 /* So .sbss will get used for tiny objects. */
650 bfd_set_gp_size (stdoutput, 8);
651 create_lita_section ();
652 /* For handling the GP, create a symbol that won't be output in the
653 symbol table. We'll edit it out of relocs later. */
654 gp = symbol_create ("<GP value>", lita_sec, 0x8000, &zero_address_frag);
655
656 memset (&clear_insn, 0, sizeof (clear_insn));
657 for (i = 0; i < MAX_RELOCS; i++)
658 clear_insn.reloc[i].code = BFD_RELOC_NONE;
659 }
660
661 int optnum = 1;
662
663 static void
664 emit_insn (insn)
665 struct alpha_it *insn;
666 {
667 char *toP;
668 int j;
669
670 toP = frag_more (4);
671
672 /* put out the opcode */
673 md_number_to_chars (toP, insn->opcode, 4);
674
675 /* put out the symbol-dependent stuff */
676 for (j = 0; j < MAX_RELOCS; j++)
677 {
678 struct reloc_data *r = &insn->reloc[j];
679 fixS *f;
680
681 if (r->code != BFD_RELOC_NONE)
682 {
683 if (r->exp.X_op == O_constant)
684 {
685 r->exp.X_add_symbol = section_symbol (absolute_section);
686 r->exp.X_op = O_symbol;
687 }
688 f = fix_new_exp (frag_now, (toP - frag_now->fr_literal), 4,
689 &r->exp, r->pcrel, r->code);
690 }
691 if (r->code == BFD_RELOC_ALPHA_GPDISP_LO16)
692 {
693 static bit_fixS cookie;
694 /* @@ This'll make the range checking in write.c shut up. */
695 f->fx_bit_fixP = &cookie;
696 }
697 }
698 }
699
700 void
701 md_assemble (str)
702 char *str;
703 {
704 int i, count;
705 #define MAX_INSNS 5
706 struct alpha_it insns[MAX_INSNS];
707
708 count = alpha_ip (str, insns);
709 if (count <= 0)
710 return;
711
712 for (i = 0; i < count; i++)
713 emit_insn (&insns[i]);
714 }
715
716 static inline void
717 maybe_set_gp (sec)
718 asection *sec;
719 {
720 bfd_vma vma;
721 if (!sec)
722 return;
723 vma = bfd_get_section_vma (foo, sec);
724 if (vma && vma < alpha_gp_value)
725 alpha_gp_value = vma;
726 }
727
728 static void
729 select_gp_value ()
730 {
731 if (alpha_gp_value != 0)
732 abort ();
733
734 /* Get minus-one in whatever width... */
735 alpha_gp_value = 0; alpha_gp_value--;
736
737 /* Select the smallest VMA of these existing sections. */
738 maybe_set_gp (lita_sec);
739 /* maybe_set_gp (sdata); Was disabled before -- should we use it? */
740 #if 0
741 maybe_set_gp (lit8_sec);
742 maybe_set_gp (lit4_sec);
743 #endif
744
745 alpha_gp_value += GP_ADJUSTMENT;
746
747 S_SET_VALUE (gp, alpha_gp_value);
748
749 #ifdef DEBUG1
750 printf ("Chose GP value of %lx\n", alpha_gp_value);
751 #endif
752 }
753
754 int
755 alpha_force_relocation (f)
756 fixS *f;
757 {
758 switch (f->fx_r_type)
759 {
760 case BFD_RELOC_ALPHA_GPDISP_HI16:
761 case BFD_RELOC_ALPHA_GPDISP_LO16:
762 case BFD_RELOC_ALPHA_LITERAL:
763 case BFD_RELOC_ALPHA_LITUSE:
764 case BFD_RELOC_GPREL32:
765 return 1;
766 case BFD_RELOC_ALPHA_HINT:
767 case BFD_RELOC_64:
768 case BFD_RELOC_32:
769 case BFD_RELOC_16:
770 case BFD_RELOC_8:
771 case BFD_RELOC_23_PCREL_S2:
772 case BFD_RELOC_14:
773 case BFD_RELOC_26:
774 return 0;
775 default:
776 abort ();
777 return 0;
778 }
779 }
780
781 int
782 alpha_fix_adjustable (f)
783 fixS *f;
784 {
785 /* Are there any relocation types for which we must generate a reloc
786 but we can adjust the values contained within it? */
787 switch (f->fx_r_type)
788 {
789 case BFD_RELOC_ALPHA_GPDISP_HI16:
790 case BFD_RELOC_ALPHA_GPDISP_LO16:
791 return 0;
792 case BFD_RELOC_GPREL32:
793 return 1;
794 default:
795 return !alpha_force_relocation (f);
796 }
797 /*NOTREACHED*/
798 }
799
800 valueT
801 md_section_align (seg, size)
802 segT seg;
803 valueT size;
804 {
805 #ifdef OBJ_ECOFF
806 /* This should probably be handled within BFD, or by pulling the
807 number from BFD at least. */
808 #define MIN 15
809 size += MIN;
810 size &= ~MIN;
811 #endif
812 return size;
813 }
814
815 /* Add this thing to the .lita section and produce a LITERAL reloc referring
816 to it. */
817
818 /* Are we currently eligible to emit a LITUSE reloc for the literal
819 references just generated? */
820 static int lituse_pending;
821
822 static void
823 load_symbol_address (reg, insn)
824 int reg;
825 struct alpha_it *insn;
826 {
827 static symbolS *lita_sym;
828
829 int x;
830 valueT retval;
831
832 if (!lita_sym)
833 {
834 lita_sym = section_symbol (lita_sec);
835 S_CLEAR_EXTERNAL (lita_sym);
836 }
837
838 retval = add_to_literal_pool (insn->reloc[0].exp.X_add_symbol,
839 insn->reloc[0].exp.X_add_number,
840 lita_sec, 8);
841
842 /* Now emit a LITERAL relocation for the original section. */
843 insn->reloc[0].exp.X_op = O_symbol;
844 insn->reloc[0].exp.X_add_symbol = lita_sym;
845 insn->reloc[0].exp.X_add_number = retval;
846 insn->reloc[0].code = BFD_RELOC_ALPHA_LITERAL;
847 lituse_pending = 1;
848
849 if (retval == 0x8000)
850 /* Overflow? */
851 as_fatal ("overflow in literal (.lita) table");
852 x = retval;
853 if (addr32)
854 insn->opcode = (0xa0000000 /* ldl */
855 | (reg << SA)
856 | (base_register << SB)
857 | (x & 0xffff));
858 else
859 insn->opcode = (0xa4000000 /* ldq */
860 | (reg << SA)
861 | (base_register << SB)
862 | (x & 0xffff));
863 note_gpreg (base_register);
864 }
865
866 /* To load an address with a single instruction,
867 emit a LITERAL reloc in this section, and a REFQUAD
868 for the .lita section, so that we'll be able to access
869 it via $gp:
870 lda REG, xx -> ldq REG, -32752(gp)
871 lda REG, xx+4 -> ldq REG, -32752(gp)
872 lda REG, 4(REG)
873
874 The offsets need to start near -0x8000, and the generated LITERAL
875 relocations should negate the offset. I don't completely grok the
876 scheme yet. */
877
878 static int
879 load_expression (reg, insn)
880 int reg;
881 struct alpha_it *insn;
882 {
883 valueT addend, addendhi, addendlo;
884 int num_insns = 1;
885
886 if (insn->reloc[0].exp.X_add_symbol->bsym->flags & BSF_SECTION_SYM)
887 {
888 addend = 0;
889 }
890 else
891 {
892 addend = insn->reloc[0].exp.X_add_number;
893 insn->reloc[0].exp.X_add_number = 0;
894 }
895 load_symbol_address (reg, insn);
896 if (addend)
897 {
898 if ((addend & ~0x7fffffff) != 0
899 && (addend & ~0x7fffffff) + 0x80000000 != 0)
900 {
901 as_bad ("assembler not prepared to handle constants >32 bits yet");
902 addend = 0;
903 }
904 addendlo = addend & 0xffff;
905 addend -= addendlo;
906 addendhi = addend >> 16;
907 if (addendlo & 0x8000)
908 addendhi++;
909 /* It appears that the BASEREG LITUSE reloc should not be used on
910 an LDAH instruction. */
911 if (addendlo)
912 {
913 insn[1].opcode = (0x20000000 /* lda */
914 | (reg << SA)
915 | (reg << SB)
916 | (addendlo & 0xffff));
917 insn[1].reloc[0].code = BFD_RELOC_ALPHA_LITUSE;
918 insn[1].reloc[0].exp = lituse_basereg;
919 num_insns++;
920 }
921 if (addendhi)
922 {
923 insn[num_insns].opcode = (0x24000000
924 | (reg << SA)
925 | (reg << SB)
926 | (addendhi & 0xffff));
927 num_insns++;
928 }
929 if (num_insns == 1)
930 abort ();
931 lituse_pending = 0;
932 }
933 return num_insns;
934 }
935
936 static inline void
937 getExpression (str, this_insn)
938 char *str;
939 struct alpha_it *this_insn;
940 {
941 char *save_in;
942 segT seg;
943
944 #if 0 /* Not converted to bfd yet, and I don't think we need them
945 for ECOFF. Re-adding a.out support will probably require
946 them though. */
947 static const struct am {
948 char *name;
949 bfd_reloc_code_real_type reloc;
950 } macro[] = {
951 { "hi", RELOC_48_63 },
952 { "lo", RELOC_0_15 },
953 { "ml", RELOC_16_31 },
954 { "mh", RELOC_32_47 },
955 { "uhi", RELOC_U_48_63 },
956 { "uml", RELOC_U_16_31 },
957 { "umh", RELOC_U_32_47 },
958 { 0, }
959 };
960
961 /* Handle macros: "%macroname(expr)" */
962 if (*str == '%')
963 {
964 struct am *m;
965 char *p, *q;
966
967 str++;
968 m = &macro[0];
969 while (q = m->name)
970 {
971 p = str;
972 while (*q && *p == *q)
973 p++, q++;
974 if (*q == 0)
975 break;
976 m++;
977 }
978 if (q)
979 {
980 str = p; /* keep the '(' */
981 this_insn->reloc = m->reloc;
982 }
983 }
984 #endif
985
986 save_in = input_line_pointer;
987 input_line_pointer = str;
988
989 seg = expression (&this_insn->reloc[0].exp);
990 /* XXX validate seg and exp, make sure they're reasonable */
991 expr_end = input_line_pointer;
992 input_line_pointer = save_in;
993 }
994
995 static void
996 emit_unaligned_io (dir, addr_reg, addr_offset, reg)
997 char *dir;
998 int addr_reg, reg;
999 valueT addr_offset;
1000 {
1001 char buf[90];
1002 sprintf (buf, "%sq_u $%d,%ld($%d)", dir, reg, (long) addr_offset, addr_reg);
1003 md_assemble (buf);
1004 }
1005
1006 static void
1007 emit_load_unal (addr_reg, addr_offset, reg)
1008 int addr_reg, reg;
1009 valueT addr_offset;
1010 {
1011 emit_unaligned_io ("ld", addr_reg, addr_offset, reg);
1012 }
1013
1014 static void
1015 emit_store_unal (addr_reg, addr_offset, reg)
1016 int addr_reg, reg;
1017 valueT addr_offset;
1018 {
1019 emit_unaligned_io ("st", addr_reg, addr_offset, reg);
1020 }
1021
1022 static void
1023 emit_byte_manip_r (op, in, mask, out, mode, which)
1024 char *op;
1025 int in, mask, out, mode, which;
1026 {
1027 char buf[90];
1028 sprintf (buf, "%s%c%c $%d,$%d,$%d", op, mode, which, in, mask, out);
1029 md_assemble (buf);
1030 }
1031
1032 static void
1033 emit_extract_r (in, mask, out, mode, which)
1034 int in, mask, out, mode, which;
1035 {
1036 emit_byte_manip_r ("ext", in, mask, out, mode, which);
1037 }
1038
1039 static void
1040 emit_insert_r (in, mask, out, mode, which)
1041 int in, mask, out, mode, which;
1042 {
1043 emit_byte_manip_r ("ins", in, mask, out, mode, which);
1044 }
1045
1046 static void
1047 emit_mask_r (in, mask, out, mode, which)
1048 int in, mask, out, mode, which;
1049 {
1050 emit_byte_manip_r ("msk", in, mask, out, mode, which);
1051 }
1052
1053 static void
1054 emit_sign_extend (reg, size)
1055 int reg, size;
1056 {
1057 char buf[90];
1058 sprintf (buf, "sll $%d,0x%x,$%d", reg, 64 - size, reg);
1059 md_assemble (buf);
1060 sprintf (buf, "sra $%d,0x%x,$%d", reg, 64 - size, reg);
1061 md_assemble (buf);
1062 }
1063
1064 static void
1065 emit_bis_r (in1, in2, out)
1066 int in1, in2, out;
1067 {
1068 char buf[90];
1069 sprintf (buf, "bis $%d,$%d,$%d", in1, in2, out);
1070 md_assemble (buf);
1071 }
1072
1073 static int
1074 build_mem (opc, ra, rb, disp)
1075 int opc, ra, rb;
1076 bfd_signed_vma disp;
1077 {
1078 if ((disp >> 15) != 0
1079 && (disp >> 15) + 1 != 0)
1080 abort ();
1081 return ((opc << 26) | (ra << SA) | (rb << SB) | (disp & 0xffff));
1082 }
1083
1084 static int
1085 build_operate_n (opc, fn, ra, lit, rc)
1086 int opc, fn, ra, rc;
1087 int lit;
1088 {
1089 if (lit & ~0xff)
1090 abort ();
1091 return ((opc << 26) | (fn << 5) | (ra << SA) | (lit << SN) | (1 << 12) | (rc << SC));
1092 }
1093
1094 static void
1095 emit_sll_n (dest, disp, src)
1096 int dest, disp, src;
1097 {
1098 struct alpha_it insn = clear_insn;
1099 insn.opcode = build_operate_n (0x12, 0x39, src, disp, dest);
1100 emit_insn (&insn);
1101 }
1102
1103 static void
1104 emit_ldah_num (dest, addend, src)
1105 int dest, src;
1106 bfd_vma addend;
1107 {
1108 struct alpha_it insn = clear_insn;
1109 insn.opcode = build_mem (0x09, dest, src, addend);
1110 emit_insn (&insn);
1111 }
1112
1113 static void
1114 emit_addq_r (in1, in2, out)
1115 int in1, in2, out;
1116 {
1117 struct alpha_it insn = clear_insn;
1118 insn.opcode = 0x40000400 | (in1 << SA) | (in2 << SB) | (out << SC);
1119 emit_insn (&insn);
1120 }
1121
1122 static void
1123 emit_lda_n (dest, addend, src)
1124 int dest, src;
1125 bfd_vma addend;
1126 {
1127 struct alpha_it insn = clear_insn;
1128 insn.opcode = build_mem (0x08, dest, src, addend);
1129 emit_insn (&insn);
1130 }
1131
1132 static void
1133 emit_add64 (in, out, num)
1134 int in, out;
1135 bfd_vma num;
1136 {
1137 bfd_signed_vma snum = num;
1138
1139 if (in_range (num, 16, 0))
1140 {
1141 emit_lda_n (out, num, in);
1142 return;
1143 }
1144 if ((num & 0xffff) == 0
1145 && in == ZERO
1146 && in_range (snum >> 16, 16, 0))
1147 {
1148 emit_ldah_num (out, snum >> 16, in);
1149 return;
1150 }
1151 /* I'm not sure this one is getting invoked when it could. */
1152 if ((num & 1) == 0 && in == ZERO)
1153 {
1154 if (in_range (snum >> 1, 16, 0))
1155 {
1156 emit_lda_n (out, snum >> 1, in);
1157 emit_addq_r (out, out, out);
1158 return;
1159 }
1160 else if (num & 0x1fffe == 0
1161 && in_range (snum >> 17, 16, 0))
1162 {
1163 emit_ldah_num (out, snum >> 17, in);
1164 emit_addq_r (out, out, out);
1165 return;
1166 }
1167 }
1168 if (in_range (num, 32, 0))
1169 {
1170 bfd_vma lo = num & 0xffff;
1171 if (lo & 0x8000)
1172 lo -= 0x10000;
1173 num -= lo;
1174 emit_ldah_num (out, snum >> 16, in);
1175 if (lo)
1176 emit_lda_n (out, lo, out);
1177 return;
1178 }
1179
1180 if (in != ZERO && in != AT && out != AT && at_ok)
1181 {
1182 emit_add64 (ZERO, AT, num);
1183 emit_addq_r (AT, in, out);
1184 return;
1185 }
1186
1187 if (in != ZERO)
1188 as_bad ("load expression too complex to expand");
1189
1190 /* Could check also for loading 16- or 32-bit value and shifting by
1191 arbitrary displacement. */
1192
1193 {
1194 bfd_vma lo = snum & 0xffffffff;
1195 if (lo & 0x80000000)
1196 lo -= ((bfd_vma)0x10000000 << 4);
1197 snum -= lo;
1198 emit_add64 (ZERO, out, snum >> 32);
1199 emit_sll_n (out, 32, out);
1200 if (lo != 0)
1201 emit_add64 (out, out, lo);
1202 }
1203 }
1204
1205 /* Note that for now, this function is called recursively (by way of
1206 calling md_assemble again). Some of the macros defined as part of
1207 the assembly language are currently rewritten as sequences of
1208 strings to be assembled. See, for example, the handling of "divq".
1209
1210 For efficiency, this should be fixed someday. */
1211 static int
1212 alpha_ip (str, insns)
1213 char *str;
1214 struct alpha_it insns[];
1215 {
1216 char *s;
1217 const char *args;
1218 char c;
1219 unsigned long i;
1220 struct alpha_opcode *pattern;
1221 char *argsStart;
1222 unsigned int opcode;
1223 unsigned int mask;
1224 int match = 0, num_gen = 1;
1225 int comma = 0;
1226
1227 for (s = str;
1228 islower (*s) || *s == '_' || *s == '/' || *s == '4' || *s == '8';
1229 ++s)
1230 ;
1231 switch (*s)
1232 {
1233
1234 case '\0':
1235 break;
1236
1237 case ',':
1238 comma = 1;
1239
1240 /*FALLTHROUGH*/
1241
1242 case ' ':
1243 *s++ = '\0';
1244 break;
1245
1246 default:
1247 as_warn ("Unknown opcode: `%s'", str);
1248 exit (1);
1249 }
1250 if ((pattern = (struct alpha_opcode *) hash_find (op_hash, str)) == NULL)
1251 {
1252 as_warn ("Unknown opcode: `%s'", str);
1253 return -1;
1254 }
1255 if (comma)
1256 *--s = ',';
1257
1258 argsStart = s;
1259 for (;;)
1260 {
1261 opcode = pattern->match;
1262 num_gen = 1;
1263 for (i = 0; i < MAX_INSNS; i++)
1264 insns[i] = clear_insn;
1265
1266 /* Build the opcode, checking as we go to make sure that the
1267 operands match. */
1268 for (args = pattern->args;; ++args)
1269 {
1270 switch (*args)
1271 {
1272
1273 case '\0': /* end of args */
1274 if (*s == '\0')
1275 {
1276 match = 1;
1277 }
1278 break;
1279
1280 case '+':
1281 if (*s == '+')
1282 {
1283 ++s;
1284 continue;
1285 }
1286 if (*s == '-')
1287 {
1288 continue;
1289 }
1290 break;
1291
1292 case '(': /* these must match exactly */
1293 case ')':
1294 case ',':
1295 case ' ':
1296 case '0':
1297 if (*s++ == *args)
1298 continue;
1299 break;
1300
1301 case '1': /* next operand must be a register */
1302 case '2':
1303 case '3':
1304 case 'r':
1305 case 'R':
1306 if (*s++ == '$')
1307 {
1308 switch (c = *s++)
1309 {
1310
1311 case 'a': /* $at: as temporary */
1312 if (*s++ != 't')
1313 goto error;
1314 mask = AT;
1315 break;
1316
1317 case 'g': /* $gp: base register */
1318 if (*s++ != 'p')
1319 goto error;
1320 mask = base_register;
1321 break;
1322
1323 case 's': /* $sp: stack pointer */
1324 if (*s++ != 'p')
1325 goto error;
1326 mask = SP;
1327 break;
1328
1329
1330 case 'r': /* any register */
1331 if (!isdigit (c = *s++))
1332 {
1333 goto error;
1334 }
1335 /* FALLTHROUGH */
1336 case '0':
1337 case '1':
1338 case '2':
1339 case '3':
1340 case '4':
1341 case '5':
1342 case '6':
1343 case '7':
1344 case '8':
1345 case '9':
1346 if (isdigit (*s))
1347 {
1348 if ((c = 10 * (c - '0') + (*s++ - '0')) >= 32)
1349 {
1350 goto error;
1351 }
1352 }
1353 else
1354 {
1355 c -= '0';
1356 }
1357 if ((c == GP) && first_32bit_quadrant)
1358 c = ZERO;
1359
1360 mask = c;
1361 break;
1362
1363 default:
1364 goto error;
1365 }
1366 note_gpreg (mask);
1367 /* Got the register, now figure out where it goes in
1368 the opcode. */
1369 doregister:
1370 switch (*args)
1371 {
1372
1373 case '1':
1374 case 'e':
1375 opcode |= mask << SA;
1376 continue;
1377
1378 case '2':
1379 case 'f':
1380 opcode |= mask << SB;
1381 continue;
1382
1383 case '3':
1384 case 'g':
1385 opcode |= mask;
1386 continue;
1387
1388 case 'r':
1389 opcode |= (mask << SA) | mask;
1390 continue;
1391
1392 case 'R': /* ra and rb are the same */
1393 opcode |= (mask << SA) | (mask << SB);
1394 continue;
1395
1396 case 'E':
1397 opcode |= (mask << SA) | (mask << SB) | (mask);
1398 continue;
1399 }
1400 }
1401 break;
1402
1403 case 'e': /* next operand is a floating point register */
1404 case 'f':
1405 case 'g':
1406 case 'E':
1407 if (*s++ == '$' && *s++ == 'f' && isdigit (*s))
1408 {
1409 mask = *s++;
1410 if (isdigit (*s))
1411 {
1412 mask = 10 * (mask - '0') + (*s++ - '0');
1413 if (mask >= 32)
1414 {
1415 break;
1416 }
1417 }
1418 else
1419 {
1420 mask -= '0';
1421 }
1422 note_fpreg (mask);
1423 /* same encoding as gp registers */
1424 goto doregister;
1425 }
1426 break;
1427
1428 #if 0
1429 case 'h': /* bits 16..31 */
1430 insns[0].reloc = RELOC_16_31;
1431 goto immediate;
1432 #endif
1433
1434 case 'l': /* bits 0..15 */
1435 insns[0].reloc[0].code = BFD_RELOC_16;
1436 goto immediate;
1437
1438 case 'L': /* 21 bit PC relative immediate */
1439 insns[0].reloc[0].code = BFD_RELOC_23_PCREL_S2;
1440 insns[0].reloc[0].pcrel = 1;
1441 goto immediate;
1442
1443 case 'i': /* 14 bit immediate */
1444 if (OPCODE (opcode) != 0x1a)
1445 /* Not a jmp variant?? */
1446 abort ();
1447 else if (opcode & 0x8000)
1448 /* ret or jsr_coroutine */
1449 {
1450 insns[0].reloc[0].code = BFD_RELOC_14;
1451 insns[0].reloc[0].pcrel = 0;
1452 }
1453 else
1454 /* jmp or jsr */
1455 {
1456 insns[0].reloc[0].code = BFD_RELOC_ALPHA_HINT;
1457 insns[0].reloc[0].pcrel = 1;
1458 }
1459 goto immediate;
1460
1461 case 'b': /* 8 bit immediate */
1462 insns[0].reloc[0].code = BFD_RELOC_8;
1463 goto immediate;
1464
1465 case 'I': /* 26 bit immediate, for PALcode */
1466 insns[0].reloc[0].code = BFD_RELOC_26;
1467 goto immediate;
1468
1469 #if 0
1470 case 't': /* 12 bit 0...11 */
1471 insns[0].reloc = RELOC_0_12;
1472 goto immediate;
1473
1474 case '8': /* 8 bit 0...7 */
1475 insns[0].reloc = RELOC_0_8;
1476 goto immediate;
1477
1478 case 'I': /* 26 bit immediate */
1479 insns[0].reloc = RELOC_0_25;
1480 #else
1481 case 't':
1482 case '8':
1483 abort ();
1484 #endif
1485 /*FALLTHROUGH*/
1486
1487 immediate:
1488 if (*s == ' ')
1489 s++;
1490 getExpression (s, &insns[0]);
1491 s = expr_end;
1492 /* Handle overflow in certain instructions by converting
1493 to other instructions. */
1494 if (insns[0].reloc[0].code == BFD_RELOC_8
1495 && insns[0].reloc[0].exp.X_op == O_constant
1496 && (insns[0].reloc[0].exp.X_add_number < 0
1497 || insns[0].reloc[0].exp.X_add_number > 0xff))
1498 {
1499 if (OPCODE (opcode) == 0x10
1500 && (OP_FCN (opcode) == 0x00 /* addl */
1501 || OP_FCN (opcode) == 0x40 /* addl/v */
1502 || OP_FCN (opcode) == 0x20 /* addq */
1503 || OP_FCN (opcode) == 0x60 /* addq/v */
1504 || OP_FCN (opcode) == 0x09 /* subl */
1505 || OP_FCN (opcode) == 0x49 /* subl/v */
1506 || OP_FCN (opcode) == 0x29 /* subq */
1507 || OP_FCN (opcode) == 0x69 /* subq/v */
1508 || OP_FCN (opcode) == 0x02 /* s4addl */
1509 || OP_FCN (opcode) == 0x22 /* s4addq */
1510 || OP_FCN (opcode) == 0x0b /* s4subl */
1511 || OP_FCN (opcode) == 0x2b /* s4subq */
1512 || OP_FCN (opcode) == 0x12 /* s8addl */
1513 || OP_FCN (opcode) == 0x32 /* s8addq */
1514 || OP_FCN (opcode) == 0x1b /* s8subl */
1515 || OP_FCN (opcode) == 0x3b /* s8subq */
1516 )
1517 /* Can we make it fit by negating? */
1518 && -insns[0].reloc[0].exp.X_add_number < 0xff
1519 && -insns[0].reloc[0].exp.X_add_number > 0)
1520 {
1521 opcode ^= 0x120; /* convert add<=>sub */
1522 insns[0].reloc[0].exp.X_add_number *= -1;
1523 }
1524 else if (at_ok && macro_ok)
1525 {
1526 /* Constant value supplied, but it's too large. */
1527 emit_add64 (ZERO, AT,
1528 insns[0].reloc[0].exp.X_add_number);
1529 opcode &= ~ 0x1000;
1530 opcode |= (AT << SB);
1531 insns[0].reloc[0].code = BFD_RELOC_NONE;
1532 }
1533 else
1534 as_bad ("overflow in 8-bit literal field in `operate' format insn");
1535 }
1536 else if (insns[0].reloc[0].code == BFD_RELOC_16
1537 && insns[0].reloc[0].exp.X_op == O_constant
1538 && !in_range (insns[0].reloc[0].exp.X_add_number,
1539 16, 0))
1540 {
1541 bfd_vma val = insns[0].reloc[0].exp.X_add_number;
1542 if (OPCODE (opcode) == 0x08)
1543 {
1544 emit_add64 (ZERO, AT, val);
1545 opcode &= ~0x1000;
1546 opcode |= (AT << SB);
1547 insns[0].reloc[0].code = BFD_RELOC_NONE;
1548 }
1549 else if (OPCODE (opcode) == 0x09
1550 && in_range (val >> 16, 16, 0))
1551 {
1552 /* ldah with high operand - convert to low */
1553 insns[0].reloc[0].exp.X_add_number >>= 16;
1554 }
1555 else
1556 as_bad ("I don't know how to handle 32+ bit constants here yet, sorry.");
1557 }
1558 else if (insns[0].reloc[0].code == BFD_RELOC_32
1559 && insns[0].reloc[0].exp.X_op == O_constant)
1560 {
1561 bfd_vma val = insns[0].reloc[0].exp.X_add_number;
1562 bfd_signed_vma sval = val;
1563 if (val >> 32 != 0
1564 && sval >> 32 != 0
1565 && sval >> 32 != -1)
1566 as_bad ("I don't know how to handle 64 bit constants here yet, sorry.");
1567 }
1568 continue;
1569
1570 case 'F':
1571 {
1572 int format, length, mode, i;
1573 char temp[20 /*MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT*/];
1574 char *err;
1575 static const char formats[4] = "FGfd";
1576 bfd_vma bits, offset;
1577 char *old_input_line_pointer = input_line_pointer;
1578
1579 input_line_pointer = s;
1580 SKIP_WHITESPACE ();
1581 memset (temp, 0, sizeof (temp));
1582 mode = (opcode >> 26) & 3;
1583 format = formats[mode];
1584 err = md_atof (format, temp, &length);
1585 if (err)
1586 {
1587 as_bad ("Bad floating literal: %s", err);
1588 bits = 0;
1589 }
1590 else
1591 {
1592 /* Generate little-endian number from byte sequence. */
1593 bits = 0;
1594 for (i = length - 1; i >= 0; i--)
1595 bits += ((bfd_vma)(temp[i] & 0xff)) << (i * 8);
1596 }
1597 switch (length)
1598 {
1599 case 8:
1600 offset = get_lit8_offset (bits) - 0x8000;
1601 insns[0].reloc[0].exp.X_add_symbol = lit8_sym;
1602 insns[0].reloc[0].exp.X_add_number = 0x8000;
1603 break;
1604 case 4:
1605 offset = get_lit4_offset (bits) - 0x8000;
1606 insns[0].reloc[0].exp.X_add_symbol = lit4_sym;
1607 insns[0].reloc[0].exp.X_add_number = 0x8000;
1608 break;
1609 default:
1610 abort ();
1611 }
1612 insns[0].reloc[0].exp.X_op = O_symbol;
1613 offset &= 0xffff;
1614 num_gen = load_expression (AT, &insns[0]);
1615 if (lituse_pending)
1616 {
1617 insns[num_gen].reloc[0].code = BFD_RELOC_ALPHA_LITUSE;
1618 insns[num_gen].reloc[0].exp = lituse_basereg;
1619 lituse_pending = 0;
1620 }
1621 insns[num_gen++].opcode = opcode | (AT << SB) | offset;
1622 opcode = insns[0].opcode;
1623 s = input_line_pointer;
1624 input_line_pointer = old_input_line_pointer;
1625 }
1626 continue;
1627
1628 /* The following two.. take advantage of the fact that
1629 opcode already contains most of what we need to know.
1630 We just prepend to the instr an "ldah
1631 $r,%ml(expr)($base)" and turn this one (done later
1632 after we return) into something like "stq
1633 $r,%lo(expr)(at)" or "ldq $r,%lo(expr)($r)".
1634
1635 NOTE: This can fail later on at link time if the
1636 offset from $base actually turns out to be more than
1637 2**31 or 2**47 if use_large_offsets is set. */
1638 case 'P': /* Addressing macros: PUT */
1639 mask = AT; /* register 'at' */
1640 /* fall through */
1641
1642 case 'G': /* Addressing macros: GET */
1643 /* All it is missing is the expression, which is what we
1644 will get now */
1645
1646 if (*s == ' ')
1647 s++;
1648 getExpression (s, &insns[0]);
1649 s = expr_end;
1650
1651 /* Must check for "lda ..,number" too */
1652 if (insns[0].reloc[0].exp.X_op == O_big)
1653 {
1654 as_warn ("Sorry, not yet. Put bignums in .data section yourself.");
1655 return -1;
1656 }
1657 if (insns[0].reloc[0].exp.X_op == O_constant)
1658 {
1659 bfd_vma val = insns[0].reloc[0].exp.X_add_number;
1660 bfd_vma top, low;
1661
1662 insns[0].reloc[0].code = BFD_RELOC_NONE;
1663 insns[1].reloc[0].code = BFD_RELOC_NONE;
1664
1665 low = val & 0xffff;
1666 if (low & 0x8000)
1667 low -= 0x10000;
1668 top = val - low;
1669 if (top)
1670 {
1671 emit_add64 (ZERO, AT, top);
1672 opcode |= AT << SB;
1673 }
1674 else
1675 opcode |= ZERO << SB;
1676 opcode &= ~0x1000;
1677 opcode |= low & 0xffff;
1678 }
1679 else if (insns[0].reloc[0].exp.X_op == O_symbol)
1680 {
1681 unsigned long old_opcode = opcode;
1682 int tmp_reg;
1683
1684 if (!macro_ok)
1685 as_bad ("insn requires expansion but `nomacro' specified");
1686 else if (*args == 'G')
1687 tmp_reg = mask;
1688 else if (!at_ok)
1689 as_bad ("insn expansion requires AT use, but `noat' specified");
1690 else
1691 tmp_reg = AT;
1692 num_gen = load_expression (tmp_reg, insns);
1693 opcode = insns[0].opcode;
1694 /* lda is opcode 8, 0x20000000, and the macros that use
1695 this code have an opcode field of 0. The latter
1696 require further processing, and we don't have the
1697 true opcode here. */
1698 if (OPCODE (old_opcode) != 0
1699 && OPCODE (old_opcode) != 0x08)
1700 {
1701 struct alpha_it *i;
1702 i = &insns[num_gen++];
1703 i->opcode = old_opcode | (tmp_reg << SB);
1704
1705 if (lituse_pending)
1706 {
1707 i->reloc[0].code = BFD_RELOC_ALPHA_LITUSE;
1708 i->reloc[0].exp = lituse_basereg;
1709 lituse_pending = 0;
1710 }
1711 }
1712 }
1713 else
1714 {
1715 /* Not a number */
1716 num_gen = 2;
1717 insns[1].reloc[0].exp = insns[0].reloc[0].exp;
1718
1719 /* Generate: ldah REG,x1(GP); OP ?,x0(REG) */
1720
1721 abort (); /* relocs need fixing */
1722 #if 0
1723 insns[1].reloc = RELOC_0_15;
1724 insns[1].opcode = opcode | mask << SB;
1725
1726 insns[0].reloc = RELOC_16_31;
1727 opcode = 0x24000000 /*ldah*/ | mask << SA | (base_register << SB);
1728 #endif
1729 }
1730
1731 continue;
1732
1733 /* Same failure modes as above, actually most of the
1734 same code shared. */
1735 case 'B': /* Builtins */
1736 args++;
1737 switch (*args)
1738 {
1739
1740 case 'a': /* ldgp */
1741
1742 if (first_32bit_quadrant || no_mixed_code)
1743 return -1;
1744 switch (OUTPUT_FLAVOR)
1745 {
1746 case bfd_target_aout_flavour:
1747 /* this is cmu's a.out version */
1748 insns[0].reloc[0].code = BFD_RELOC_NONE;
1749 /* generate "zap %r,0xf,%r" to take high 32 bits */
1750 opcode |= 0x48001600 /* zap ?,#,?*/ | (0xf << SN);
1751 break;
1752 case bfd_target_ecoff_flavour:
1753 /* Given "ldgp R1,N(R2)", turn it into something
1754 like "ldah R1,###(R2) ; lda R1,###(R1)" with
1755 appropriate constants and relocations. */
1756 {
1757 unsigned long r1, r2;
1758 unsigned long addend = 0;
1759
1760 num_gen = 2;
1761 r2 = mask;
1762 r1 = opcode & 0x3f;
1763 insns[0].reloc[0].code = BFD_RELOC_ALPHA_GPDISP_HI16;
1764 insns[0].reloc[0].pcrel = 1;
1765 insns[0].reloc[0].exp.X_op = O_symbol;
1766 insns[0].reloc[0].exp.X_add_symbol = gp;
1767 insns[0].reloc[0].exp.X_add_number = 0;
1768 insns[0].opcode = (0x24000000 /* ldah */
1769 | (r1 << SA)
1770 | (r2 << SB));
1771 insns[1].reloc[0].code = BFD_RELOC_ALPHA_GPDISP_LO16;
1772 insns[1].reloc[0].exp.X_op = O_symbol;
1773 insns[1].reloc[0].exp.X_add_symbol = gp;
1774 insns[1].reloc[0].exp.X_add_number = 4;
1775 insns[1].reloc[0].pcrel = 1;
1776 insns[1].opcode = 0x20000000 | (r1 << SA) | (r1 << SB);
1777 opcode = insns[0].opcode;
1778 /* merge in addend */
1779 insns[1].opcode |= addend & 0xffff;
1780 insns[0].opcode |= ((addend >> 16)
1781 + (addend & 0x8000 ? 1 : 0));
1782 if (r2 == PV)
1783 ecoff_set_gp_prolog_size (0);
1784 }
1785 break;
1786 default:
1787 abort ();
1788 }
1789 continue;
1790
1791
1792 case 'b': /* setgp */
1793 switch (OUTPUT_FLAVOR)
1794 {
1795 case bfd_target_aout_flavour:
1796 /* generate "zap %r,0xf,$gp" to take high 32 bits */
1797 opcode |= 0x48001600 /* zap ?,#,?*/
1798 | (0xf << SN) | (base_register);
1799 break;
1800 default:
1801 abort ();
1802 }
1803 continue;
1804
1805 case 'c': /* jsr $r,foo becomes
1806 lda $27,foo
1807 jsr $r,($27),foo
1808 Register 27, t12, is used by convention
1809 here. */
1810 {
1811 struct alpha_it *jsr;
1812 expressionS etmp;
1813 struct reloc_data *r;
1814
1815 /* We still have to parse the function name */
1816 if (*s == ' ')
1817 s++;
1818 getExpression (s, &insns[0]);
1819 etmp = insns[0].reloc[0].exp;
1820 s = expr_end;
1821 num_gen = load_expression (PV, &insns[0]);
1822 note_gpreg (PV);
1823
1824 jsr = &insns[num_gen++];
1825 jsr->opcode = (0x68004000 /* jsr */
1826 | (mask << SA)
1827 | (PV << SB)
1828 | 0);
1829 if (lituse_pending)
1830 {
1831 /* LITUSE wasn't emitted yet */
1832 jsr->reloc[0].code = BFD_RELOC_ALPHA_LITUSE;
1833 jsr->reloc[0].exp = lituse_jsr;
1834 r = &jsr->reloc[1];
1835 lituse_pending = 0;
1836 }
1837 else
1838 r = &jsr->reloc[0];
1839 r->exp = etmp;
1840 r->code = BFD_RELOC_ALPHA_HINT;
1841 r->pcrel = 1;
1842 opcode = insns[0].opcode;
1843 }
1844 continue;
1845
1846 case 'd':
1847 /* Sub-word loads and stores. We load the address into
1848 $at, which might involve using the `P' parameter
1849 processing too, then emit a sequence to get the job
1850 done, using unaligned memory accesses and byte
1851 manipulation, with t9 and t10 as temporaries. */
1852 {
1853 /* Characteristics of access. */
1854 int is_load, is_unsigned = 0, is_unaligned = 0;
1855 int mode_size, mode;
1856 /* Register operand. */
1857 int reg;
1858 /* Addend for loads and stores. */
1859 valueT addend;
1860 /* Which register do we use for the address? */
1861 int addr;
1862
1863 {
1864 /* Pick apart name and set flags. */
1865 const char *s = pattern->name;
1866
1867 if (*s == 'u')
1868 {
1869 is_unaligned = 1;
1870 s++;
1871 }
1872
1873 if (s[0] == 'l' && s[1] == 'd')
1874 is_load = 1;
1875 else if (s[0] == 's' && s[1] == 't')
1876 is_load = 0;
1877 else
1878 as_fatal ("unrecognized sub-word access insn `%s'",
1879 str);
1880 s += 2;
1881
1882 mode = *s++;
1883 if (mode == 'b') mode_size = 1;
1884 else if (mode == 'w') mode_size = 2;
1885 else if (mode == 'l') mode_size = 4;
1886 else if (mode == 'q') mode_size = 8;
1887 else abort ();
1888
1889 if (*s == 'u')
1890 {
1891 is_unsigned = 1;
1892 s++;
1893 }
1894
1895 assert (*s == 0);
1896
1897 /* Longwords are always kept sign-extended. */
1898 if (mode == 'l' && is_unsigned)
1899 abort ();
1900 /* There's no special unaligned byte handling. */
1901 if (mode == 'b' && is_unaligned)
1902 abort ();
1903 /* Stores don't care about signedness. */
1904 if (!is_load && is_unsigned)
1905 abort ();
1906 }
1907
1908 if (args[-2] == 'P')
1909 {
1910 addr = AT;
1911 addend = 0;
1912 }
1913 else
1914 {
1915 /* foo r1,num(r2)
1916 r2 -> mask
1917 r1 -> (opcode >> SA) & 31
1918 num -> insns->reloc[0].*
1919
1920 We want to emit "lda at,num(r2)", since these
1921 operations require the use of a single register
1922 with the starting address of the memory operand
1923 we want to access.
1924
1925 We could probably get away without doing this
1926 (and use r2 below, with the addend for the
1927 actual reads and writes) in cases where the
1928 addend is known to be a multiple of 8. */
1929 int r2 = mask;
1930 int r1 = (opcode >> SA) & 31;
1931
1932 if (insns[0].reloc[0].code == BFD_RELOC_NONE)
1933 addend = 0;
1934 else if (insns[0].reloc[0].code == BFD_RELOC_16)
1935 {
1936 if (insns[0].reloc[0].exp.X_op != O_constant)
1937 abort ();
1938 addend = insns[0].reloc[0].exp.X_add_number;
1939 }
1940 else
1941 abort ();
1942
1943 if (addend + mode_size - 1 < 0x7fff
1944 && (addend % 8) == 0
1945 && (r2 < T9 || r2 > T12))
1946 {
1947 addr = r2;
1948 num_gen = 0;
1949 }
1950 else
1951 {
1952 /* Let later relocation processing deal
1953 with the addend field. */
1954 insns[num_gen-1].opcode = (0x20000000 /* lda */
1955 | (AT << SA)
1956 | (r2 << SB));
1957 addr = AT;
1958 addend = 0;
1959 }
1960 reg = r1;
1961 }
1962
1963 /* Because the emit_* routines append directly to
1964 the current frag, we now need to flush any
1965 pending insns. */
1966 {
1967 int i;
1968 for (i = 0; i < num_gen; i++)
1969 emit_insn (&insns[i]);
1970 num_gen = 0;
1971 }
1972
1973 if (is_load)
1974 {
1975 int reg2, reg3;
1976
1977 if (is_unaligned)
1978 reg2 = T9, reg3 = T10;
1979 else
1980 reg2 = reg;
1981
1982 emit_load_unal (addr, addend, T9);
1983 if (is_unaligned)
1984 emit_load_unal (addr, addend + mode_size - 1, T10);
1985 emit_extract_r (T9, addr, reg2, mode, 'l');
1986 if (is_unaligned)
1987 {
1988 emit_extract_r (T10, addr, reg3, mode, 'h');
1989 emit_bis_r (T9, T10, reg);
1990 }
1991 if (!is_unsigned)
1992 emit_sign_extend (reg, mode_size * 8);
1993 }
1994 else
1995 {
1996 /* The second word gets processed first
1997 because if the address does turn out to be
1998 aligned, the processing for the second word
1999 will be pushing around all-zeros, and the
2000 entire value will be handled as the `first'
2001 word. So we want to store the `first' word
2002 last. */
2003 /* Pair these up so that the memory loads get
2004 separated from each other, as well as being
2005 well in advance of the uses of the values
2006 loaded. */
2007 if (is_unaligned)
2008 {
2009 emit_load_unal (addr, addend + mode_size - 1, T11);
2010 emit_insert_r (reg, addr, T12, mode, 'h');
2011 }
2012 emit_load_unal (addr, addend, T9);
2013 emit_insert_r (reg, addr, T10, mode, 'l');
2014 if (is_unaligned)
2015 emit_mask_r (T12, addr, T12, mode, 'h');
2016 emit_mask_r (T10, addr, T10, mode, 'l');
2017 if (is_unaligned)
2018 emit_bis_r (T11, T12, T11);
2019 emit_bis_r (T9, T10, T9);
2020 if (is_unaligned)
2021 emit_store_unal (addr, addend + mode_size - 1, T11);
2022 emit_store_unal (addr, addend, T9);
2023 }
2024 }
2025 return 0;
2026
2027 /* DIVISION and MODULUS. Yech.
2028 Convert OP x,y,result
2029 to mov x,t10
2030 mov y,t11
2031 jsr t9, __OP
2032 mov t12,result
2033
2034 with appropriate optimizations if t10,t11,t12
2035 are the registers specified by the compiler.
2036 We are missing an obvious optimization
2037 opportunity here; if the ldq generated by the
2038 jsr assembly requires a cycle or two to make
2039 the value available, initiating it before one
2040 or two of the mov instructions would result in
2041 faster execution. */
2042 case '0': /* reml */
2043 case '1': /* divl */
2044 case '2': /* remq */
2045 case '3': /* divq */
2046 case '4': /* remlu */
2047 case '5': /* divlu */
2048 case '6': /* remqu */
2049 case '7': /* divqu */
2050 {
2051 static char func[8][6] = {
2052 "reml", "divl", "remq", "divq",
2053 "remlu", "divlu", "remqu", "divqu"
2054 };
2055 char expansion[64];
2056 int reg;
2057
2058 /* All regs parsed, in opcode */
2059
2060 /* Do the expansions, one instr at a time */
2061
2062 reg = (opcode >> SA) & 31;
2063 if (reg != T10)
2064 {
2065 /* x->t10 */
2066 sprintf (expansion, "mov $%d,$%d", reg, T10);
2067 md_assemble (expansion);
2068 }
2069 reg = (opcode >> SB) & 31;
2070 if (reg == T10)
2071 /* we already overwrote it! */
2072 abort ();
2073 else if (reg != T11)
2074 {
2075 /* y->t11 */
2076 sprintf (expansion, "mov $%d,$%d", reg, T11);
2077 md_assemble (expansion);
2078 }
2079 sprintf (expansion, "lda $%d,__%s", PV, func[*args - '0']);
2080 md_assemble (expansion);
2081 sprintf (expansion, "jsr $%d,($%d),__%s", T9, PV,
2082 func[*args - '0']);
2083 md_assemble (expansion);
2084 #if 0 /* huh? */
2085 if (!first_32bit_quadrant)
2086 {
2087 sprintf (expansion,
2088 "zap $%d,0xf,$%d",
2089 T9, base_register);
2090 md_assemble (expansion);
2091 }
2092 #endif
2093 sprintf (expansion, "ldgp $%d,0($%d)",
2094 base_register, T9);
2095 md_assemble (expansion);
2096
2097 /* Use insns[0] to get at the result */
2098 if ((reg = (opcode & 31)) != PV)
2099 opcode = (0x47e00400 /* or zero,zero,zero */
2100 | (PV << SB)
2101 | reg /* Rc */ ); /* pv->z */
2102 else
2103 num_gen = 0;
2104 }
2105 continue;
2106 }
2107 /* fall through */
2108
2109 default:
2110 abort ();
2111 }
2112 break;
2113 }
2114 error:
2115 if (match == 0)
2116 {
2117 /* Args don't match. */
2118 if (&pattern[1] - alpha_opcodes < NUMOPCODES
2119 && !strcmp (pattern->name, pattern[1].name))
2120 {
2121 ++pattern;
2122 s = argsStart;
2123 continue;
2124 }
2125 else
2126 {
2127 as_warn ("Illegal operands");
2128 return -1;
2129 }
2130 }
2131 else
2132 {
2133 /* Args match, see if a float instructions and -nofloats */
2134 if (nofloats && pattern->isa_float)
2135 return -1;
2136 }
2137 break;
2138 }
2139
2140 insns[0].opcode = opcode;
2141 return num_gen;
2142 }
2143
2144 /* Turn a string in input_line_pointer into a floating point constant
2145 of type type, and store the appropriate bytes in *litP. The number
2146 of LITTLENUMS emitted is stored in *sizeP. An error message is
2147 returned, or NULL on OK. */
2148
2149 /* Equal to MAX_PRECISION in atof-ieee.c */
2150 #define MAX_LITTLENUMS 6
2151
2152 char *
2153 md_atof (type, litP, sizeP)
2154 char type;
2155 char *litP;
2156 int *sizeP;
2157 {
2158 int prec;
2159 LITTLENUM_TYPE words[MAX_LITTLENUMS];
2160 LITTLENUM_TYPE *wordP;
2161 char *t;
2162 char *atof_ieee (), *vax_md_atof ();
2163
2164 switch (type)
2165 {
2166 /* VAX floats */
2167 case 'G':
2168 /* VAX md_atof doesn't like "G" for some reason. */
2169 type = 'g';
2170 case 'F':
2171 case 'D':
2172 return vax_md_atof (type, litP, sizeP);
2173
2174 /* IEEE floats */
2175 case 'f':
2176 prec = 2;
2177 break;
2178
2179 case 'd':
2180 prec = 4;
2181 break;
2182
2183 case 'x':
2184 case 'X':
2185 prec = 6;
2186 break;
2187
2188 case 'p':
2189 case 'P':
2190 prec = 6;
2191 break;
2192
2193 default:
2194 *sizeP = 0;
2195 return "Bad call to MD_ATOF()";
2196 }
2197 t = atof_ieee (input_line_pointer, type, words);
2198 if (t)
2199 input_line_pointer = t;
2200 *sizeP = prec * sizeof (LITTLENUM_TYPE);
2201
2202 for (wordP = words + prec - 1; prec--;)
2203 {
2204 md_number_to_chars (litP, (long) (*wordP--), sizeof (LITTLENUM_TYPE));
2205 litP += sizeof (LITTLENUM_TYPE);
2206 }
2207
2208 return 0;
2209 }
2210
2211 void
2212 md_bignum_to_chars (buf, bignum, nchars)
2213 char *buf;
2214 LITTLENUM_TYPE *bignum;
2215 int nchars;
2216 {
2217 while (nchars)
2218 {
2219 LITTLENUM_TYPE work = *bignum++;
2220 int nb = CHARS_PER_LITTLENUM;
2221
2222 do
2223 {
2224 *buf++ = work & ((1 << BITS_PER_CHAR) - 1);
2225 if (--nchars == 0)
2226 return;
2227 work >>= BITS_PER_CHAR;
2228 }
2229 while (--nb);
2230 }
2231 }
2232 \f
2233 CONST char *md_shortopts = "Fm:";
2234 struct option md_longopts[] = {
2235 #define OPTION_32ADDR (OPTION_MD_BASE)
2236 {"32addr", no_argument, NULL, OPTION_32ADDR},
2237 {NULL, no_argument, NULL, 0}
2238 };
2239 size_t md_longopts_size = sizeof(md_longopts);
2240
2241 int
2242 md_parse_option (c, arg)
2243 int c;
2244 char *arg;
2245 {
2246 switch (c)
2247 {
2248 case 'F':
2249 nofloats = 1;
2250 break;
2251
2252 case OPTION_32ADDR:
2253 addr32 = 1;
2254 break;
2255
2256 case 'm':
2257 {
2258 unsigned long mach;
2259
2260 if (!strcmp (arg, "21064"))
2261 mach = 21064;
2262 else if (!strcmp (arg, "21066"))
2263 mach = 21066;
2264 else if (!strcmp (arg, "21164"))
2265 mach = 21164;
2266 else
2267 {
2268 as_bad ("invalid architecture %s", arg);
2269 return 0;
2270 }
2271
2272 if (machine != 0 && machine != mach)
2273 {
2274 as_warn ("machine type %lu already chosen, overriding with %lu",
2275 machine, mach);
2276 }
2277 machine = mach;
2278 }
2279 break;
2280
2281 default:
2282 return 0;
2283 }
2284
2285 return 1;
2286 }
2287
2288 void
2289 md_show_usage (stream)
2290 FILE *stream;
2291 {
2292 fprintf(stream, "\
2293 Alpha options:\n\
2294 -32addr treat addresses as 32-bit values\n\
2295 -F lack floating point instructions support\n\
2296 -m21064 | -m21066 | -m21164\n\
2297 specify variant of Alpha architecture\n");
2298 }
2299 \f
2300 static void
2301 s_proc (is_static)
2302 int is_static;
2303 {
2304 /* XXXX Align to cache linesize XXXXX */
2305 char *name;
2306 char c;
2307 char *p;
2308 symbolS *symbolP;
2309 int temp;
2310
2311 /* Takes ".proc name,nargs" */
2312 name = input_line_pointer;
2313 c = get_symbol_end ();
2314 p = input_line_pointer;
2315 symbolP = symbol_find_or_make (name);
2316 *p = c;
2317 SKIP_WHITESPACE ();
2318 if (*input_line_pointer != ',')
2319 {
2320 *p = 0;
2321 as_warn ("Expected comma after name \"%s\"", name);
2322 *p = c;
2323 temp = 0;
2324 ignore_rest_of_line ();
2325 }
2326 else
2327 {
2328 input_line_pointer++;
2329 temp = get_absolute_expression ();
2330 }
2331 /* symbolP->sy_other = (signed char) temp; */
2332 as_warn ("unhandled: .proc %s,%d", name, temp);
2333 demand_empty_rest_of_line ();
2334 }
2335
2336 static void
2337 s_alpha_set (x)
2338 int x;
2339 {
2340 char *name = input_line_pointer, ch, *s;
2341 int yesno = 1;
2342
2343 while (!is_end_of_line[(unsigned char) *input_line_pointer])
2344 input_line_pointer++;
2345 ch = *input_line_pointer;
2346 *input_line_pointer = '\0';
2347
2348 s = name;
2349 if (s[0] == 'n' && s[1] == 'o')
2350 {
2351 yesno = 0;
2352 s += 2;
2353 }
2354 if (!strcmp ("reorder", s))
2355 /* ignore */ ;
2356 else if (!strcmp ("at", s))
2357 at_ok = yesno;
2358 else if (!strcmp ("macro", s))
2359 macro_ok = yesno;
2360 else
2361 as_warn ("Tried to set unrecognized symbol: %s", name);
2362 *input_line_pointer = ch;
2363 demand_empty_rest_of_line ();
2364 }
2365
2366 /* @@ Is this right?? */
2367 long
2368 md_pcrel_from (fixP)
2369 fixS *fixP;
2370 {
2371 valueT addr = fixP->fx_where + fixP->fx_frag->fr_address;
2372 switch (fixP->fx_r_type)
2373 {
2374 case BFD_RELOC_ALPHA_GPDISP_HI16:
2375 case BFD_RELOC_ALPHA_GPDISP_LO16:
2376 return addr;
2377 default:
2378 return fixP->fx_size + addr;
2379 }
2380 }
2381
2382 int
2383 alpha_do_align (n, fill)
2384 int n;
2385 const char *fill;
2386 {
2387 if (!fill
2388 && (now_seg == text_section
2389 || !strcmp (now_seg->name, ".init")
2390 || !strcmp (now_seg->name, ".fini")))
2391 {
2392 static const unsigned char nop_pattern[] = { 0x1f, 0x04, 0xff, 0x47 };
2393 frag_align_pattern (n, nop_pattern, sizeof (nop_pattern));
2394 return 1;
2395 }
2396 return 0;
2397 }
2398
2399 int
2400 md_apply_fix (fixP, valueP)
2401 fixS *fixP;
2402 valueT *valueP;
2403 {
2404 valueT value;
2405 int size;
2406 valueT addend;
2407 char *p = fixP->fx_frag->fr_literal + fixP->fx_where;
2408
2409 value = *valueP;
2410
2411 switch (fixP->fx_r_type)
2412 {
2413 /* The GPDISP relocations are processed internally with a symbol
2414 referring to the current function; we need to drop in a value
2415 which, when added to the address of the start of the function,
2416 gives the desired GP. */
2417 case BFD_RELOC_ALPHA_GPDISP_HI16:
2418 case BFD_RELOC_ALPHA_GPDISP_LO16:
2419 addend = value;
2420 if (fixP->fx_r_type == BFD_RELOC_ALPHA_GPDISP_HI16)
2421 {
2422 assert (fixP->fx_next->fx_r_type == BFD_RELOC_ALPHA_GPDISP_LO16);
2423 #ifdef DEBUG1
2424 printf ("hi16: ");
2425 fprintf_vma (stdout, addend);
2426 printf ("\n");
2427 #endif
2428 if (addend & 0x8000)
2429 addend += 0x10000;
2430 addend >>= 16;
2431 fixP->fx_offset = 4; /* @@ Compute this using fx_next. */
2432 }
2433 else
2434 {
2435 #ifdef DEBUG1
2436 printf ("lo16: ");
2437 fprintf_vma (stdout, addend);
2438 printf ("\n");
2439 #endif
2440 addend &= 0xffff;
2441 fixP->fx_offset = 0;
2442 }
2443 md_number_to_chars (fixP->fx_frag->fr_literal + fixP->fx_where,
2444 addend, 2);
2445 fixP->fx_addsy = section_symbol (absolute_section);
2446 fixP->fx_offset += fixP->fx_frag->fr_address + fixP->fx_where;
2447 break;
2448
2449 case BFD_RELOC_8:
2450 /* Write 8 bits, shifted left 13 bit positions. */
2451 value &= 0xff;
2452 p++;
2453 *p &= 0x1f;
2454 *p |= (value << 5) & 0xe0;
2455 value >>= 3;
2456 p++;
2457 *p &= 0xe0;
2458 *p |= value;
2459 value >>= 5;
2460 fixP->fx_done = 1;
2461 if (value != 0)
2462 as_bad_where (fixP->fx_file, fixP->fx_line,
2463 "overflow in type-%d reloc", (int) fixP->fx_r_type);
2464 return 3;
2465
2466 case BFD_RELOC_32:
2467 size = 4;
2468 goto do_it;
2469 case BFD_RELOC_64:
2470 size = 8;
2471 goto do_it;
2472 case BFD_RELOC_16:
2473 /* Don't want overflow checking. */
2474 size = 2;
2475 do_it:
2476 if (fixP->fx_pcrel == 0
2477 && fixP->fx_addsy == 0)
2478 {
2479 md_number_to_chars (p, value, size);
2480 /* @@ Overflow checks?? */
2481 goto done;
2482 }
2483 break;
2484
2485 case BFD_RELOC_26:
2486 if (fixP->fx_addsy != 0
2487 && fixP->fx_addsy->bsym->section != absolute_section)
2488 as_bad_where (fixP->fx_file, fixP->fx_line,
2489 "PALcode instructions require immediate constant function code");
2490 else if (value >> 26 != 0)
2491 as_bad_where (fixP->fx_file, fixP->fx_line,
2492 "overflow in 26-bit PALcode function field");
2493 *p++ = value & 0xff;
2494 value >>= 8;
2495 *p++ = value & 0xff;
2496 value >>= 8;
2497 *p++ = value & 0xff;
2498 value >>= 8;
2499 {
2500 char x = *p;
2501 x &= ~3;
2502 x |= (value & 3);
2503 *p++ = x;
2504 }
2505 goto done;
2506
2507 case BFD_RELOC_14:
2508 if (fixP->fx_addsy != 0
2509 && fixP->fx_addsy->bsym->section != absolute_section)
2510 as_bad_where (fixP->fx_file, fixP->fx_line,
2511 "ret/jsr_coroutine requires constant in displacement field");
2512 else if (value >> 14 != 0)
2513 as_bad_where (fixP->fx_file, fixP->fx_line,
2514 "overflow in 14-bit operand field of ret or jsr_coroutine");
2515 *p++ = value & 0xff;
2516 value >>= 8;
2517 *p = (*p & 0xc0) | (value & 0x3f);
2518 goto done;
2519
2520 case BFD_RELOC_23_PCREL_S2:
2521 /* Write 21 bits only. */
2522 value >>= 2;
2523 *p++ = value & 0xff;
2524 value >>= 8;
2525 *p++ = value & 0xff;
2526 value >>= 8;
2527 *p &= 0xe0;
2528 *p |= (value & 0x1f);
2529 goto done;
2530
2531 case BFD_RELOC_ALPHA_LITERAL:
2532 case BFD_RELOC_ALPHA_LITUSE:
2533 return 2;
2534
2535 case BFD_RELOC_GPREL32:
2536 assert (fixP->fx_subsy == gp);
2537 value = - alpha_gp_value; /* huh? this works... */
2538 fixP->fx_subsy = 0;
2539 md_number_to_chars (p, value, 4);
2540 break;
2541
2542 case BFD_RELOC_ALPHA_HINT:
2543 if (fixP->fx_addsy == 0 && fixP->fx_pcrel == 0)
2544 {
2545 size = 2;
2546 goto do_it;
2547 }
2548 return 2;
2549
2550 default:
2551 as_fatal ("unknown relocation type %d?", fixP->fx_r_type);
2552 return 9;
2553 }
2554
2555 if (fixP->fx_addsy == 0 && fixP->fx_pcrel == 0)
2556 {
2557 printf ("type %d reloc done?\n", fixP->fx_r_type);
2558 done:
2559 fixP->fx_done = 1;
2560 return 42;
2561 }
2562
2563 return 0x12345678;
2564 }
2565
2566 void
2567 alpha_frob_ecoff_data ()
2568 {
2569 select_gp_value ();
2570 /* $zero and $f31 are read-only */
2571 alpha_gprmask &= ~1;
2572 alpha_fprmask &= ~1;
2573 }
2574
2575 /* The Alpha has support for some VAX floating point types, as well as for
2576 IEEE floating point. We consider IEEE to be the primary floating point
2577 format, and sneak in the VAX floating point support here. */
2578 #define md_atof vax_md_atof
2579 #include "config/atof-vax.c"
This page took 0.087663 seconds and 4 git commands to generate.