For SPARC V9, change icc to %icc, xcc to %xcc, fccX to %fccX.
[deliverable/binutils-gdb.git] / gas / config / tc-sparc.c
1 /* tc-sparc.c -- Assemble for the SPARC
2 Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
3
4 This file is part of GAS, the GNU Assembler.
5
6 GAS is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 GAS is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GAS; see the file COPYING. If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
19
20 #define cypress 1234
21
22 #include <stdio.h>
23 #include <ctype.h>
24
25 #include "as.h"
26 #include "read.h"
27
28 /* careful, this file includes data *declarations* */
29 #include "opcode/sparc.h"
30
31 void md_begin ();
32 void md_end ();
33 void md_number_to_chars ();
34 void md_assemble ();
35 char *md_atof ();
36 void md_convert_frag ();
37 void md_create_short_jump ();
38 void md_create_long_jump ();
39 int md_estimate_size_before_relax ();
40 void md_ri_to_chars ();
41 symbolS *md_undefined_symbol ();
42 static void sparc_ip ();
43
44 static enum sparc_architecture current_architecture = v6;
45 static int architecture_requested = 0;
46 static int warn_on_bump = 0;
47
48 const relax_typeS md_relax_table[] =
49 {
50 0};
51
52 /* handle of the OPCODE hash table */
53 static struct hash_control *op_hash = NULL;
54
55 static void s_seg (), s_proc (), s_data1 (), s_reserve (), s_common ();
56 extern void s_globl (), s_long (), s_short (), s_space (), cons ();
57 extern void s_align_bytes (), s_ignore ();
58
59 const pseudo_typeS md_pseudo_table[] =
60 {
61 {"align", s_align_bytes, 0}, /* Defaulting is invalid (0) */
62 {"common", s_common, 0},
63 {"global", s_globl, 0},
64 {"half", cons, 2},
65 {"optim", s_ignore, 0},
66 {"proc", s_proc, 0},
67 {"reserve", s_reserve, 0},
68 {"seg", s_seg, 0},
69 {"skip", s_space, 0},
70 {"word", cons, 4},
71 {NULL, 0, 0},
72 };
73
74 const int md_short_jump_size = 4;
75 const int md_long_jump_size = 4;
76 const int md_reloc_size = 12; /* Size of relocation record */
77
78 /* This array holds the chars that always start a comment. If the
79 pre-processor is disabled, these aren't very useful */
80 const char comment_chars[] = "!"; /* JF removed '|' from comment_chars */
81
82 /* This array holds the chars that only start a comment at the beginning of
83 a line. If the line seems to have the form '# 123 filename'
84 .line and .file directives will appear in the pre-processed output */
85 /* Note that input_file.c hand checks for '#' at the beginning of the
86 first line of the input file. This is because the compiler outputs
87 #NO_APP at the beginning of its output. */
88 /* Also note that comments started like this one will always
89 work if '/' isn't otherwise defined. */
90 const char line_comment_chars[] = "#";
91
92 const char line_separator_chars[] = "";
93
94 /* Chars that can be used to separate mant from exp in floating point nums */
95 const char EXP_CHARS[] = "eE";
96
97 /* Chars that mean this number is a floating point constant */
98 /* As in 0f12.456 */
99 /* or 0d1.2345e12 */
100 const char FLT_CHARS[] = "rRsSfFdDxXpP";
101
102 /* Also be aware that MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT may have to be
103 changed in read.c . Ideally it shouldn't have to know about it at all,
104 but nothing is ideal around here.
105 */
106
107 static unsigned char octal[256];
108 #define isoctal(c) octal[c]
109 static unsigned char toHex[256];
110
111 struct sparc_it
112 {
113 char *error;
114 unsigned long opcode;
115 struct nlist *nlistp;
116 expressionS exp;
117 int pcrel;
118 enum reloc_type reloc;
119 } the_insn, set_insn;
120
121 #if __STDC__ == 1
122 #if 0
123 static void print_insn (struct sparc_it *insn);
124 #endif
125 static int getExpression (char *str);
126 #else /* not __STDC__ */
127 #if 0
128 static void print_insn ();
129 #endif
130 static int getExpression ();
131 #endif /* not __STDC__ */
132
133 static char *expr_end;
134 static int special_case;
135
136 /*
137 * Instructions that require wierd handling because they're longer than
138 * 4 bytes.
139 */
140 #define SPECIAL_CASE_SET 1
141 #define SPECIAL_CASE_FDIV 2
142
143 /*
144 * sort of like s_lcomm
145 *
146 */
147 static int max_alignment = 15;
148
149 static void
150 s_reserve ()
151 {
152 char *name;
153 char *p;
154 char c;
155 int align;
156 int size;
157 int temp;
158 symbolS *symbolP;
159
160 name = input_line_pointer;
161 c = get_symbol_end ();
162 p = input_line_pointer;
163 *p = c;
164 SKIP_WHITESPACE ();
165
166 if (*input_line_pointer != ',')
167 {
168 as_bad ("Expected comma after name");
169 ignore_rest_of_line ();
170 return;
171 }
172
173 ++input_line_pointer;
174
175 if ((size = get_absolute_expression ()) < 0)
176 {
177 as_bad ("BSS length (%d.) <0! Ignored.", size);
178 ignore_rest_of_line ();
179 return;
180 } /* bad length */
181
182 *p = 0;
183 symbolP = symbol_find_or_make (name);
184 *p = c;
185
186 if (strncmp (input_line_pointer, ",\"bss\"", 6) != 0)
187 {
188 as_bad ("bad .reserve segment: `%s'", input_line_pointer);
189 return;
190 } /* if not bss */
191
192 input_line_pointer += 6;
193 SKIP_WHITESPACE ();
194
195 if (*input_line_pointer == ',')
196 {
197 ++input_line_pointer;
198
199 SKIP_WHITESPACE ();
200 if (*input_line_pointer == '\n')
201 {
202 as_bad ("Missing alignment");
203 return;
204 }
205
206 align = get_absolute_expression ();
207 if (align > max_alignment)
208 {
209 align = max_alignment;
210 as_warn ("Alignment too large: %d. assumed.", align);
211 }
212 else if (align < 0)
213 {
214 align = 0;
215 as_warn ("Alignment negative. 0 assumed.");
216 }
217 #ifdef MANY_SEGMENTS
218 #define SEG_BSS SEG_E2
219 record_alignment (SEG_E2, align);
220 #else
221 record_alignment (SEG_BSS, align);
222 #endif
223
224 /* convert to a power of 2 alignment */
225 for (temp = 0; (align & 1) == 0; align >>= 1, ++temp);;
226
227 if (align != 1)
228 {
229 as_bad ("Alignment not a power of 2");
230 ignore_rest_of_line ();
231 return;
232 } /* not a power of two */
233
234 align = temp;
235
236 /* Align */
237 align = ~((~0) << align); /* Convert to a mask */
238 local_bss_counter = (local_bss_counter + align) & (~align);
239 } /* if has optional alignment */
240
241 if (S_GET_OTHER (symbolP) == 0
242 && S_GET_DESC (symbolP) == 0
243 && ((S_GET_SEGMENT (symbolP) == SEG_BSS
244 && S_GET_VALUE (symbolP) == local_bss_counter)
245 || !S_IS_DEFINED (symbolP)))
246 {
247 S_SET_VALUE (symbolP, local_bss_counter);
248 S_SET_SEGMENT (symbolP, SEG_BSS);
249 symbolP->sy_frag = &bss_address_frag;
250 local_bss_counter += size;
251 }
252 else
253 {
254 as_warn ("Ignoring attempt to re-define symbol from %d. to %d.",
255 S_GET_VALUE (symbolP), local_bss_counter);
256 } /* if not redefining */
257
258 demand_empty_rest_of_line ();
259 return;
260 } /* s_reserve() */
261
262 static void
263 s_common ()
264 {
265 register char *name;
266 register char c;
267 register char *p;
268 register int temp;
269 register symbolS *symbolP;
270
271 name = input_line_pointer;
272 c = get_symbol_end ();
273 /* just after name is now '\0' */
274 p = input_line_pointer;
275 *p = c;
276 SKIP_WHITESPACE ();
277 if (*input_line_pointer != ',')
278 {
279 as_bad ("Expected comma after symbol-name");
280 ignore_rest_of_line ();
281 return;
282 }
283 input_line_pointer++; /* skip ',' */
284 if ((temp = get_absolute_expression ()) < 0)
285 {
286 as_bad (".COMMon length (%d.) <0! Ignored.", temp);
287 ignore_rest_of_line ();
288 return;
289 }
290 *p = 0;
291 symbolP = symbol_find_or_make (name);
292 *p = c;
293 if (S_IS_DEFINED (symbolP))
294 {
295 as_bad ("Ignoring attempt to re-define symbol");
296 ignore_rest_of_line ();
297 return;
298 }
299 if (S_GET_VALUE (symbolP) != 0)
300 {
301 if (S_GET_VALUE (symbolP) != temp)
302 {
303 as_warn ("Length of .comm \"%s\" is already %d. Not changed to %d.",
304 S_GET_NAME (symbolP), S_GET_VALUE (symbolP), temp);
305 }
306 }
307 else
308 {
309 S_SET_VALUE (symbolP, temp);
310 S_SET_EXTERNAL (symbolP);
311 }
312 know (symbolP->sy_frag == &zero_address_frag);
313 if (strncmp (input_line_pointer, ",\"bss\"", 6) != 0
314 && strncmp (input_line_pointer, ",\"data\"", 7) != 0)
315 {
316 p = input_line_pointer;
317 while (*p && *p != '\n')
318 p++;
319 c = *p;
320 *p = '\0';
321 as_bad ("bad .common segment: `%s'", input_line_pointer);
322 *p = c;
323 return;
324 }
325 input_line_pointer += 6 + (input_line_pointer[2] == 'd'); /* Skip either */
326 demand_empty_rest_of_line ();
327 return;
328 } /* s_common() */
329
330 static void
331 s_seg ()
332 {
333
334 if (strncmp (input_line_pointer, "\"text\"", 6) == 0)
335 {
336 input_line_pointer += 6;
337 s_text ();
338 return;
339 }
340 if (strncmp (input_line_pointer, "\"data\"", 6) == 0)
341 {
342 input_line_pointer += 6;
343 s_data ();
344 return;
345 }
346 if (strncmp (input_line_pointer, "\"data1\"", 7) == 0)
347 {
348 input_line_pointer += 7;
349 s_data1 ();
350 return;
351 }
352 if (strncmp (input_line_pointer, "\"bss\"", 5) == 0)
353 {
354 input_line_pointer += 5;
355 /* We only support 2 segments -- text and data -- for now, so
356 things in the "bss segment" will have to go into data for now.
357 You can still allocate SEG_BSS stuff with .lcomm or .reserve. */
358 subseg_new (SEG_DATA, 255); /* FIXME-SOMEDAY */
359 return;
360 }
361 as_bad ("Unknown segment type");
362 demand_empty_rest_of_line ();
363 return;
364 } /* s_seg() */
365
366 static void
367 s_data1 ()
368 {
369 subseg_new (SEG_DATA, 1);
370 demand_empty_rest_of_line ();
371 return;
372 } /* s_data1() */
373
374 static void
375 s_proc ()
376 {
377 extern char is_end_of_line[];
378
379 while (!is_end_of_line[*input_line_pointer])
380 {
381 ++input_line_pointer;
382 }
383 ++input_line_pointer;
384 return;
385 } /* s_proc() */
386
387 /* start-sanitize-v9 */
388 #ifndef NO_V9
389 struct priv_reg_entry
390 {
391 char *name;
392 int regnum;
393 };
394 struct priv_reg_entry priv_reg_table[] =
395 {
396 {"tpc", 0},
397 {"tnpc", 1},
398 {"tstate", 2},
399 {"tt", 3},
400 {"tick", 4},
401 {"tba", 5},
402 {"pstate", 6},
403 {"tl", 7},
404 {"pil", 8},
405 {"cwp", 9},
406 {"cansave", 10},
407 {"canrestore", 11},
408 {"cleanwin", 12},
409 {"otherwin", 13},
410 {"wstate", 14},
411 {"fpq", 15},
412 {"ver", 31},
413 {"", -1}, /* end marker */
414 };
415
416 static int
417 cmp_reg_entry (p, q)
418 struct priv_reg_entry *p, *q;
419 {
420 return strcmp (q->name, p->name);
421 }
422
423 #endif
424 /* end-sanitize-v9 */
425
426 /* This function is called once, at assembler startup time. It should
427 set up all the tables, etc. that the MD part of the assembler will need. */
428 void
429 md_begin ()
430 {
431 register char *retval = NULL;
432 int lose = 0;
433 register unsigned int i = 0;
434
435 op_hash = hash_new ();
436 if (op_hash == NULL)
437 as_fatal ("Virtual memory exhausted");
438
439 while (i < NUMOPCODES)
440 {
441 const char *name = sparc_opcodes[i].name;
442 retval = hash_insert (op_hash, name, &sparc_opcodes[i]);
443 if (retval != NULL && *retval != '\0')
444 {
445 fprintf (stderr, "internal error: can't hash `%s': %s\n",
446 sparc_opcodes[i].name, retval);
447 lose = 1;
448 }
449 do
450 {
451 if (sparc_opcodes[i].match & sparc_opcodes[i].lose)
452 {
453 fprintf (stderr, "internal error: losing opcode: `%s' \"%s\"\n",
454 sparc_opcodes[i].name, sparc_opcodes[i].args);
455 lose = 1;
456 }
457 ++i;
458 }
459 while (i < NUMOPCODES
460 && !strcmp (sparc_opcodes[i].name, name));
461 }
462
463 if (lose)
464 as_fatal ("Broken assembler. No assembly attempted.");
465
466 for (i = '0'; i < '8'; ++i)
467 octal[i] = 1;
468 for (i = '0'; i <= '9'; ++i)
469 toHex[i] = i - '0';
470 for (i = 'a'; i <= 'f'; ++i)
471 toHex[i] = i + 10 - 'a';
472 for (i = 'A'; i <= 'F'; ++i)
473 toHex[i] = i + 10 - 'A';
474
475 /* start-sanitize-v9 */
476 #ifndef NO_V9
477 qsort (priv_reg_table, sizeof (priv_reg_table) / sizeof (priv_reg_table[0]),
478 sizeof (priv_reg_table[0]), cmp_reg_entry);
479 #endif
480 /* end-sanitize-v9 */
481 } /* md_begin() */
482
483 void
484 md_end ()
485 {
486 return;
487 } /* md_end() */
488
489 void
490 md_assemble (str)
491 char *str;
492 {
493 char *toP;
494 int rsd;
495
496 know (str);
497 sparc_ip (str);
498
499 /* See if "set" operand is absolute and small; skip sethi if so. */
500 if (special_case == SPECIAL_CASE_SET && the_insn.exp.X_seg == SEG_ABSOLUTE)
501 {
502 if (the_insn.exp.X_add_number >= -(1 << 12)
503 && the_insn.exp.X_add_number < (1 << 12))
504 {
505 the_insn.opcode = 0x80102000 /* or %g0,imm,... */
506 | (the_insn.opcode & 0x3E000000) /* dest reg */
507 | (the_insn.exp.X_add_number & 0x1FFF); /* imm */
508 special_case = 0; /* No longer special */
509 the_insn.reloc = NO_RELOC; /* No longer relocated */
510 }
511 }
512
513 toP = frag_more (4);
514 /* put out the opcode */
515 md_number_to_chars (toP, the_insn.opcode, 4);
516
517 /* put out the symbol-dependent stuff */
518 if (the_insn.reloc != NO_RELOC)
519 {
520 fix_new (frag_now, /* which frag */
521 (toP - frag_now->fr_literal), /* where */
522 4, /* size */
523 the_insn.exp.X_add_symbol,
524 the_insn.exp.X_subtract_symbol,
525 the_insn.exp.X_add_number,
526 the_insn.pcrel,
527 the_insn.reloc);
528 }
529 switch (special_case)
530 {
531
532 case SPECIAL_CASE_SET:
533 special_case = 0;
534 assert (the_insn.reloc == RELOC_HI22);
535 /* See if "set" operand has no low-order bits; skip OR if so. */
536 if (the_insn.exp.X_seg == SEG_ABSOLUTE
537 && ((the_insn.exp.X_add_number & 0x3FF) == 0))
538 return;
539 toP = frag_more (4);
540 rsd = (the_insn.opcode >> 25) & 0x1f;
541 the_insn.opcode = 0x80102000 | (rsd << 25) | (rsd << 14);
542 md_number_to_chars (toP, the_insn.opcode, 4);
543 fix_new (frag_now, /* which frag */
544 (toP - frag_now->fr_literal), /* where */
545 4, /* size */
546 the_insn.exp.X_add_symbol,
547 the_insn.exp.X_subtract_symbol,
548 the_insn.exp.X_add_number,
549 the_insn.pcrel,
550 RELOC_LO10);
551 return;
552
553 case SPECIAL_CASE_FDIV:
554 /* According to information leaked from Sun, the "fdiv" instructions
555 on early SPARC machines would produce incorrect results sometimes.
556 The workaround is to add an fmovs of the destination register to
557 itself just after the instruction. This was true on machines
558 with Weitek 1165 float chips, such as the Sun-4/260 and /280. */
559 special_case = 0;
560 assert (the_insn.reloc == NO_RELOC);
561 toP = frag_more (4);
562 rsd = (the_insn.opcode >> 25) & 0x1f;
563 the_insn.opcode = 0x81A00020 | (rsd << 25) | rsd; /* fmovs dest,dest */
564 md_number_to_chars (toP, the_insn.opcode, 4);
565 return;
566
567 case 0:
568 return;
569
570 default:
571 as_fatal ("failed sanity check.");
572 }
573 } /* md_assemble() */
574
575 static void
576 sparc_ip (str)
577 char *str;
578 {
579 char *error_message = "";
580 char *s;
581 const char *args;
582 char c;
583 struct sparc_opcode *insn;
584 char *argsStart;
585 unsigned long opcode;
586 unsigned int mask = 0;
587 int match = 0;
588 int comma = 0;
589 long immediate_max = 0;
590
591 for (s = str; islower (*s) || (*s >= '0' && *s <= '3'); ++s)
592 ;
593 switch (*s)
594 {
595
596 case '\0':
597 break;
598
599 case ',':
600 comma = 1;
601
602 /*FALLTHROUGH */
603
604 case ' ':
605 *s++ = '\0';
606 break;
607
608 default:
609 as_bad ("Unknown opcode: `%s'", str);
610 exit (1);
611 }
612 if ((insn = (struct sparc_opcode *) hash_find (op_hash, str)) == NULL)
613 {
614 as_bad ("Unknown opcode: `%s'", str);
615 return;
616 }
617 if (comma)
618 {
619 *--s = ',';
620 }
621 argsStart = s;
622 for (;;)
623 {
624 opcode = insn->match;
625 memset (&the_insn, '\0', sizeof (the_insn));
626 the_insn.reloc = NO_RELOC;
627
628 /*
629 * Build the opcode, checking as we go to make
630 * sure that the operands match
631 */
632 for (args = insn->args;; ++args)
633 {
634 switch (*args)
635 {
636
637 /* start-sanitize-v9 */
638 #ifndef NO_V9
639 case 'K':
640 {
641 /* Load is 0; Store is 1.
642 We compute the mask based on the values
643 we find in S. OK is set set
644 if we see something we don't like. */
645 int ok = 1;
646 int mask = 0;
647 while (ok == 1)
648 {
649 int lo = 0, hi = 0;
650 if (*s == '#')
651 {
652 s += 1;
653 if (!(lo = (s[0] == 'S')))
654 ok = (s[0] == 'L');
655 if (!(hi = (s[1] == 'S')))
656 ok = (s[1] == 'L');
657 mask |= (1 << ((hi << 1) | lo));
658 s += 2;
659 }
660 else
661 {
662 /* Parse a number, somehow. */
663 ok = 0;
664 }
665 if (s[2] != '|')
666 break;
667 }
668 if (!ok)
669 {
670 error_message = "unrecognizable mmask";
671 goto error;
672 }
673 opcode |= SIMM13 (mask);
674 continue;
675 }
676
677 case '*':
678 /* Parse a prefetch function. */
679 if (*s == '#')
680 {
681 int prefetch_fcn = 0;
682
683 s += 1;
684 if (!strncmp (s, "n_reads", 7))
685 prefetch_fcn = 0, s += 7;
686 else if (!strncmp (s, "one_read", 8))
687 prefetch_fcn = 1, s += 8;
688 else if (!strncmp (s, "n_writes", 8))
689 prefetch_fcn = 2, s += 8;
690 else if (!strncmp (s, "one_write", 9))
691 prefetch_fcn = 3, s += 9;
692 else if (!strncmp (s, "page", 4))
693 prefetch_fcn = 4, s += 4;
694 else
695 {
696 error_message = "unrecognizable prefetch fucntion";
697 goto error;
698 }
699 }
700 else
701 {
702 /* Parse a number, somehow. */
703 error_message = "unrecognizable prefetch fucntion";
704 goto error;
705 }
706 continue;
707
708 case '!':
709 case '?':
710 /* Parse a privileged register. */
711 if (*s == '%')
712 {
713 struct priv_reg_entry *p = priv_reg_table;
714 int len;
715
716 s += 1;
717 while (p->name[0] > s[0])
718 p++;
719 while (p->name[0] == s[0])
720 {
721 len = strlen (p->name);
722 if (strncmp (p->name, s, len) == 0)
723 break;
724 p++;
725 }
726 if (p->name[0] != s[0])
727 {
728 error_message = "unrecognizable privileged register";
729 goto error;
730 }
731 if (*args == '?')
732 opcode |= (p->regnum << 14);
733 else
734 opcode |= (p->regnum << 25);
735 s += len;
736 continue;
737 }
738 else
739 {
740 error_message = "unrecognizable privileged register";
741 goto error;
742 }
743 #endif
744 /* end-sanitize-v9 */
745
746 case 'M':
747 case 'm':
748 if (strncmp (s, "%asr", 4) == 0)
749 {
750 s += 4;
751
752 if (isdigit (*s))
753 {
754 long num = 0;
755
756 while (isdigit (*s))
757 {
758 num = num * 10 + *s - '0';
759 ++s;
760 }
761
762 if (num < 16 || 31 < num)
763 {
764 error_message = ": asr number must be between 15 and 31";
765 goto error;
766 } /* out of range */
767
768 opcode |= (*args == 'M' ? RS1 (num) : RD (num));
769 continue;
770 }
771 else
772 {
773 error_message = ": expecting %asrN";
774 goto error;
775 } /* if %asr followed by a number. */
776
777 } /* if %asr */
778 break;
779
780 /* start-sanitize-v9 */
781 #ifndef NO_V9
782 case 'I':
783 the_insn.reloc = RELOC_11;
784 immediate_max = 0x03FF;
785 goto immediate;
786
787 case 'j':
788 the_insn.reloc = RELOC_10;
789 immediate_max = 0x01FF;
790 goto immediate;
791
792 case 'k':
793 the_insn.reloc = RELOC_WDISP2_14;
794 the_insn.pcrel = 1;
795 goto immediate;
796
797 case 'G':
798 the_insn.reloc = RELOC_WDISP19;
799 the_insn.pcrel = 1;
800 goto immediate;
801
802 case 'N':
803 if (*s == 'p' && s[1] == 'n')
804 {
805 s += 2;
806 continue;
807 }
808 break;
809
810 case 'T':
811 if (*s == 'p' && s[1] == 't')
812 {
813 s += 2;
814 continue;
815 }
816 break;
817
818 case 'z':
819 if (*s == ' ')
820 {
821 ++s;
822 }
823 if (strncmp (s, "%icc", 4) == 0)
824 {
825 s += 4;
826 continue;
827 }
828 break;
829
830 case 'Z':
831 if (*s == ' ')
832 {
833 ++s;
834 }
835 if (strncmp (s, "%xcc", 4) == 0)
836 {
837 s += 4;
838 continue;
839 }
840 break;
841
842 case '6':
843 if (*s == ' ')
844 {
845 ++s;
846 }
847 if (strncmp (s, "%fcc0", 5) == 0)
848 {
849 s += 5;
850 continue;
851 }
852 break;
853
854 case '7':
855 if (*s == ' ')
856 {
857 ++s;
858 }
859 if (strncmp (s, "%fcc1", 5) == 0)
860 {
861 s += 5;
862 continue;
863 }
864 break;
865
866 case '8':
867 if (*s == ' ')
868 {
869 ++s;
870 }
871 if (strncmp (s, "%fcc2", 5) == 0)
872 {
873 s += 5;
874 continue;
875 }
876 break;
877
878 case '9':
879 if (*s == ' ')
880 {
881 ++s;
882 }
883 if (strncmp (s, "%fcc3", 5) == 0)
884 {
885 s += 5;
886 continue;
887 }
888 break;
889
890 case 'P':
891 if (strncmp (s, "%pc", 3) == 0)
892 {
893 s += 3;
894 continue;
895 }
896 break;
897
898 case 'W':
899 if (strncmp (s, "%tick", 5) == 0)
900 {
901 s += 5;
902 continue;
903 }
904 break;
905 #endif /* NO_V9 */
906 /* end-sanitize-v9 */
907
908 case '\0': /* end of args */
909 if (*s == '\0')
910 {
911 match = 1;
912 }
913 break;
914
915 case '+':
916 if (*s == '+')
917 {
918 ++s;
919 continue;
920 }
921 if (*s == '-')
922 {
923 continue;
924 }
925 break;
926
927 case '[': /* these must match exactly */
928 case ']':
929 case ',':
930 case ' ':
931 if (*s++ == *args)
932 continue;
933 break;
934
935 case '#': /* must be at least one digit */
936 if (isdigit (*s++))
937 {
938 while (isdigit (*s))
939 {
940 ++s;
941 }
942 continue;
943 }
944 break;
945
946 case 'C': /* coprocessor state register */
947 if (strncmp (s, "%csr", 4) == 0)
948 {
949 s += 4;
950 continue;
951 }
952 break;
953
954 case 'b': /* next operand is a coprocessor register */
955 case 'c':
956 case 'D':
957 if (*s++ == '%' && *s++ == 'c' && isdigit (*s))
958 {
959 mask = *s++;
960 if (isdigit (*s))
961 {
962 mask = 10 * (mask - '0') + (*s++ - '0');
963 if (mask >= 32)
964 {
965 break;
966 }
967 }
968 else
969 {
970 mask -= '0';
971 }
972 switch (*args)
973 {
974
975 case 'b':
976 opcode |= mask << 14;
977 continue;
978
979 case 'c':
980 opcode |= mask;
981 continue;
982
983 case 'D':
984 opcode |= mask << 25;
985 continue;
986 }
987 }
988 break;
989
990 case 'r': /* next operand must be a register */
991 case '1':
992 case '2':
993 case 'd':
994 if (*s++ == '%')
995 {
996 switch (c = *s++)
997 {
998
999 case 'f': /* frame pointer */
1000 if (*s++ == 'p')
1001 {
1002 mask = 0x1e;
1003 break;
1004 }
1005 goto error;
1006
1007 case 'g': /* global register */
1008 if (isoctal (c = *s++))
1009 {
1010 mask = c - '0';
1011 break;
1012 }
1013 goto error;
1014
1015 case 'i': /* in register */
1016 if (isoctal (c = *s++))
1017 {
1018 mask = c - '0' + 24;
1019 break;
1020 }
1021 goto error;
1022
1023 case 'l': /* local register */
1024 if (isoctal (c = *s++))
1025 {
1026 mask = (c - '0' + 16);
1027 break;
1028 }
1029 goto error;
1030
1031 case 'o': /* out register */
1032 if (isoctal (c = *s++))
1033 {
1034 mask = (c - '0' + 8);
1035 break;
1036 }
1037 goto error;
1038
1039 case 's': /* stack pointer */
1040 if (*s++ == 'p')
1041 {
1042 mask = 0xe;
1043 break;
1044 }
1045 goto error;
1046
1047 case 'r': /* any register */
1048 if (!isdigit (c = *s++))
1049 {
1050 goto error;
1051 }
1052 /* FALLTHROUGH */
1053 case '0':
1054 case '1':
1055 case '2':
1056 case '3':
1057 case '4':
1058 case '5':
1059 case '6':
1060 case '7':
1061 case '8':
1062 case '9':
1063 if (isdigit (*s))
1064 {
1065 if ((c = 10 * (c - '0') + (*s++ - '0')) >= 32)
1066 {
1067 goto error;
1068 }
1069 }
1070 else
1071 {
1072 c -= '0';
1073 }
1074 mask = c;
1075 break;
1076
1077 default:
1078 goto error;
1079 }
1080 /*
1081 * Got the register, now figure out where
1082 * it goes in the opcode.
1083 */
1084 switch (*args)
1085 {
1086
1087 case '1':
1088 opcode |= mask << 14;
1089 continue;
1090
1091 case '2':
1092 opcode |= mask;
1093 continue;
1094
1095 case 'd':
1096 opcode |= mask << 25;
1097 continue;
1098
1099 case 'r':
1100 opcode |= (mask << 25) | (mask << 14);
1101 continue;
1102 }
1103 }
1104 break;
1105
1106 case 'e': /* next operand is a floating point register */
1107 case 'v':
1108 case 'V':
1109
1110 case 'f':
1111 case 'B':
1112 case 'R':
1113
1114 case 'g':
1115 case 'H':
1116 case 'J':
1117 {
1118 char format;
1119
1120 if (*s++ == '%'
1121
1122 /* start-sanitize-v9 */
1123 #ifndef NO_V9
1124 && ((format = *s) == 'f'
1125 || *s == 'd'
1126 || *s == 'q')
1127 #else
1128 /* end-sanitize-v9 */
1129 && ((format = *s) == 'f')
1130
1131 /* start-sanitize-v9 */
1132 #endif /* NO_V9 */
1133 /* end-sanitize-v9 */
1134 && isdigit (*++s))
1135 {
1136
1137
1138
1139 for (mask = 0; isdigit (*s); ++s)
1140 {
1141 mask = 10 * mask + (*s - '0');
1142 } /* read the number */
1143
1144 if ((*args == 'v'
1145 || *args == 'B'
1146 || *args == 'H')
1147 && (mask & 1))
1148 {
1149 break;
1150 } /* register must be even numbered */
1151
1152 if ((*args == 'V'
1153 || *args == 'R'
1154 || *args == 'J')
1155 && (mask & 3))
1156 {
1157 break;
1158 } /* register must be multiple of 4 */
1159
1160 if (format == 'f')
1161 {
1162 if (mask >= 32)
1163 {
1164 error_message = ": There are only 32 f registers; [0-31]";
1165 goto error;
1166 } /* on error */
1167 /* start-sanitize-v9 */
1168 #ifndef NO_V9
1169 }
1170 else
1171 {
1172 if (format == 'd')
1173 {
1174 if (mask >= 64)
1175 {
1176 error_message = ": There are only 32 d registers [0, 2, ... 62].";
1177 goto error;
1178 }
1179 else if (mask & 1)
1180 {
1181 error_message = ": Only even numbered d registers exist.";
1182 goto error;
1183 } /* on error */
1184
1185 }
1186 else if (format == 'q')
1187 {
1188 if (mask >= 64)
1189 {
1190 error_message =
1191 ": There are only 16 q registers [0, 4, ... 60].";
1192 goto error;
1193 }
1194 else if (mask & 3)
1195 {
1196 error_message =
1197 ": Only q registers evenly divisible by four exist.";
1198 goto error;
1199 } /* on error */
1200 }
1201 else
1202 {
1203 know (0);
1204 } /* depending on format */
1205
1206 if (mask >= 32)
1207 {
1208 mask -= 31;
1209 } /* wrap high bit */
1210 #endif /* NO_V9 */
1211 /* end-sanitize-v9 */
1212 } /* if not an 'f' register. */
1213 } /* on error */
1214
1215 switch (*args)
1216 {
1217
1218 case 'v':
1219 case 'V':
1220 case 'e':
1221 opcode |= RS1 (mask);
1222 continue;
1223
1224
1225 case 'f':
1226 case 'B':
1227 case 'R':
1228 opcode |= RS2 (mask);
1229 continue;
1230
1231 case 'g':
1232 case 'H':
1233 case 'J':
1234 opcode |= RD (mask);
1235 continue;
1236 } /* pack it in. */
1237
1238 know (0);
1239 break;
1240 } /* float arg */
1241
1242 case 'F':
1243 if (strncmp (s, "%fsr", 4) == 0)
1244 {
1245 s += 4;
1246 continue;
1247 }
1248 break;
1249
1250 case 'h': /* high 22 bits */
1251 the_insn.reloc = RELOC_HI22;
1252 goto immediate;
1253
1254 case 'l': /* 22 bit PC relative immediate */
1255 the_insn.reloc = RELOC_WDISP22;
1256 the_insn.pcrel = 1;
1257 goto immediate;
1258
1259 case 'L': /* 30 bit immediate */
1260 the_insn.reloc = RELOC_WDISP30;
1261 the_insn.pcrel = 1;
1262 goto immediate;
1263
1264 case 'n': /* 22 bit immediate */
1265 the_insn.reloc = RELOC_22;
1266 goto immediate;
1267
1268 case 'i': /* 13 bit immediate */
1269 the_insn.reloc = RELOC_BASE13;
1270 immediate_max = 0x0FFF;
1271
1272 /*FALLTHROUGH */
1273
1274 immediate:
1275 if (*s == ' ')
1276 s++;
1277 if (*s == '%')
1278 {
1279 if ((c = s[1]) == 'h' && s[2] == 'i')
1280 {
1281 the_insn.reloc = RELOC_HI22;
1282 s += 3;
1283 }
1284 else if (c == 'l' && s[2] == 'o')
1285 {
1286 the_insn.reloc = RELOC_LO10;
1287 s += 3;
1288 /* start-sanitize-v9 */
1289 #ifndef NO_V9
1290 }
1291 else if (c == 'u'
1292 && s[2] == 'h'
1293 && s[3] == 'i')
1294 {
1295 the_insn.reloc = RELOC_HHI22;
1296 s += 4;
1297
1298 }
1299 else if (c == 'u'
1300 && s[2] == 'l'
1301 && s[3] == 'o')
1302 {
1303 the_insn.reloc = RELOC_HLO10;
1304 s += 4;
1305 #endif /* NO_V9 */
1306 /* end-sanitize-v9 */
1307 }
1308 else
1309 break;
1310 }
1311 /* Note that if the getExpression() fails, we
1312 will still have created U entries in the
1313 symbol table for the 'symbols' in the input
1314 string. Try not to create U symbols for
1315 registers, etc. */
1316 {
1317 /* This stuff checks to see if the
1318 expression ends in +%reg If it does,
1319 it removes the register from the
1320 expression, and re-sets 's' to point
1321 to the right place */
1322
1323 char *s1;
1324
1325 for (s1 = s; *s1 && *s1 != ',' && *s1 != ']'; s1++);;
1326
1327 if (s1 != s && isdigit (s1[-1]))
1328 {
1329 if (s1[-2] == '%' && s1[-3] == '+')
1330 {
1331 s1 -= 3;
1332 *s1 = '\0';
1333 (void) getExpression (s);
1334 *s1 = '+';
1335 s = s1;
1336 continue;
1337 }
1338 else if (strchr ("goli0123456789", s1[-2]) && s1[-3] == '%' && s1[-4] == '+')
1339 {
1340 s1 -= 4;
1341 *s1 = '\0';
1342 (void) getExpression (s);
1343 *s1 = '+';
1344 s = s1;
1345 continue;
1346 }
1347 }
1348 }
1349 (void) getExpression (s);
1350 s = expr_end;
1351
1352 /* Check for invalid constant values. Don't
1353 warn if constant was inside %hi or %lo,
1354 since these truncate the constant to
1355 fit. */
1356 if (immediate_max != 0
1357 && the_insn.reloc != RELOC_LO10
1358 && the_insn.reloc != RELOC_HI22
1359 /* start-sanitize-v9 */
1360 #ifndef NO_V9
1361 && the_insn.reloc != RELOC_HLO10
1362 && the_insn.reloc != RELOC_HHI22
1363 #endif
1364 /* end-sanitize-v9 */
1365 && the_insn.exp.X_add_symbol == 0
1366 && the_insn.exp.X_subtract_symbol == 0
1367 && the_insn.exp.X_seg == SEG_ABSOLUTE
1368 && (the_insn.exp.X_add_number > immediate_max
1369 || the_insn.exp.X_add_number < ~immediate_max))
1370 as_bad ("constant value must be between %ld and %ld",
1371 ~immediate_max, immediate_max);
1372 /* Reset to prevent extraneous range check. */
1373 immediate_max = 0;
1374
1375 continue;
1376
1377 case 'a':
1378 if (*s++ == 'a')
1379 {
1380 opcode |= ANNUL;
1381 continue;
1382 }
1383 break;
1384
1385 case 'A':
1386 {
1387 char *push = input_line_pointer;
1388 expressionS e;
1389
1390 input_line_pointer = s;
1391
1392 if (expression (&e) == SEG_ABSOLUTE)
1393 {
1394 opcode |= e.X_add_number << 5;
1395 s = input_line_pointer;
1396 input_line_pointer = push;
1397 continue;
1398 } /* if absolute */
1399
1400 break;
1401 } /* alternate space */
1402
1403 case 'p':
1404 if (strncmp (s, "%psr", 4) == 0)
1405 {
1406 s += 4;
1407 continue;
1408 }
1409 break;
1410
1411 case 'q': /* floating point queue */
1412 if (strncmp (s, "%fq", 3) == 0)
1413 {
1414 s += 3;
1415 continue;
1416 }
1417 break;
1418
1419 case 'Q': /* coprocessor queue */
1420 if (strncmp (s, "%cq", 3) == 0)
1421 {
1422 s += 3;
1423 continue;
1424 }
1425 break;
1426
1427 case 'S':
1428 if (strcmp (str, "set") == 0)
1429 {
1430 special_case = SPECIAL_CASE_SET;
1431 continue;
1432 }
1433 else if (strncmp (str, "fdiv", 4) == 0)
1434 {
1435 special_case = SPECIAL_CASE_FDIV;
1436 continue;
1437 }
1438 break;
1439
1440 /* start-sanitize-v9 */
1441 #ifndef NO_V9
1442 case 'o':
1443 if (strncmp (s, "%asi", 4) != 0)
1444 break;
1445 s += 4;
1446 continue;
1447
1448 case 's':
1449 if (strncmp (s, "%fprs", 5) != 0)
1450 break;
1451 s += 5;
1452 continue;
1453
1454 case 'E':
1455 if (strncmp (s, "%ccr", 4) != 0)
1456 break;
1457 s += 4;
1458 continue;
1459 #endif /* NO_V9 */
1460 /* end-sanitize-v9 */
1461
1462 case 't':
1463 if (strncmp (s, "%tbr", 4) != 0)
1464 break;
1465 s += 4;
1466 continue;
1467
1468 case 'w':
1469 if (strncmp (s, "%wim", 4) != 0)
1470 break;
1471 s += 4;
1472 continue;
1473
1474 case 'y':
1475 if (strncmp (s, "%y", 2) != 0)
1476 break;
1477 s += 2;
1478 continue;
1479
1480 default:
1481 as_fatal ("failed sanity check.");
1482 } /* switch on arg code */
1483 break;
1484 } /* for each arg that we expect */
1485 error:
1486 if (match == 0)
1487 {
1488 /* Args don't match. */
1489 if (((unsigned) (&insn[1] - sparc_opcodes)) < NUMOPCODES
1490 && !strcmp (insn->name, insn[1].name))
1491 {
1492 ++insn;
1493 s = argsStart;
1494 continue;
1495 }
1496 else
1497 {
1498 as_bad ("Illegal operands%s", error_message);
1499 return;
1500 }
1501 }
1502 else
1503 {
1504 if (insn->architecture > current_architecture)
1505 {
1506 if ((!architecture_requested || warn_on_bump)
1507 &&
1508 /* start-sanitize-v9 */
1509 #ifndef NO_V9
1510 !ARCHITECTURES_CONFLICT_P (current_architecture,
1511 insn->architecture)
1512 #else
1513 /* end-sanitize-v9 */
1514 1
1515 /* start-sanitize-v9 */
1516 #endif
1517 /* end-sanitize-v9 */
1518 )
1519 {
1520 if (warn_on_bump)
1521 {
1522 as_warn ("architecture bumped from \"%s\" to \"%s\" on \"%s\"",
1523 architecture_pname[current_architecture],
1524 architecture_pname[insn->architecture],
1525 str);
1526 } /* if warning */
1527
1528 current_architecture = insn->architecture;
1529 }
1530 else
1531 {
1532 as_bad ("architecture mismatch on \"%s\" (\"%s\"). current architecture is \"%s\"",
1533 str,
1534 architecture_pname[insn->architecture],
1535 architecture_pname[current_architecture]);
1536 return;
1537 } /* if bump ok else error */
1538 } /* if architecture higher */
1539 } /* if no match */
1540
1541 break;
1542 } /* forever looking for a match */
1543
1544 the_insn.opcode = opcode;
1545 return;
1546 } /* sparc_ip() */
1547
1548 static int
1549 getExpression (str)
1550 char *str;
1551 {
1552 char *save_in;
1553 segT seg;
1554
1555 save_in = input_line_pointer;
1556 input_line_pointer = str;
1557 switch (seg = expression (&the_insn.exp))
1558 {
1559
1560 case SEG_ABSOLUTE:
1561 case SEG_TEXT:
1562 case SEG_DATA:
1563 case SEG_BSS:
1564 case SEG_UNKNOWN:
1565 case SEG_DIFFERENCE:
1566 case SEG_BIG:
1567 case SEG_ABSENT:
1568 break;
1569
1570 default:
1571 the_insn.error = "bad segment";
1572 expr_end = input_line_pointer;
1573 input_line_pointer = save_in;
1574 return 1;
1575 }
1576 expr_end = input_line_pointer;
1577 input_line_pointer = save_in;
1578 return 0;
1579 } /* getExpression() */
1580
1581
1582 /*
1583 This is identical to the md_atof in m68k.c. I think this is right,
1584 but I'm not sure.
1585
1586 Turn a string in input_line_pointer into a floating point constant of type
1587 type, and store the appropriate bytes in *litP. The number of LITTLENUMS
1588 emitted is stored in *sizeP . An error message is returned, or NULL on OK.
1589 */
1590
1591 /* Equal to MAX_PRECISION in atof-ieee.c */
1592 #define MAX_LITTLENUMS 6
1593
1594 char *
1595 md_atof (type, litP, sizeP)
1596 char type;
1597 char *litP;
1598 int *sizeP;
1599 {
1600 int prec;
1601 LITTLENUM_TYPE words[MAX_LITTLENUMS];
1602 LITTLENUM_TYPE *wordP;
1603 char *t;
1604 char *atof_ieee ();
1605
1606 switch (type)
1607 {
1608
1609 case 'f':
1610 case 'F':
1611 case 's':
1612 case 'S':
1613 prec = 2;
1614 break;
1615
1616 case 'd':
1617 case 'D':
1618 case 'r':
1619 case 'R':
1620 prec = 4;
1621 break;
1622
1623 case 'x':
1624 case 'X':
1625 prec = 6;
1626 break;
1627
1628 case 'p':
1629 case 'P':
1630 prec = 6;
1631 break;
1632
1633 default:
1634 *sizeP = 0;
1635 return "Bad call to MD_ATOF()";
1636 }
1637 t = atof_ieee (input_line_pointer, type, words);
1638 if (t)
1639 input_line_pointer = t;
1640 *sizeP = prec * sizeof (LITTLENUM_TYPE);
1641 for (wordP = words; prec--;)
1642 {
1643 md_number_to_chars (litP, (long) (*wordP++), sizeof (LITTLENUM_TYPE));
1644 litP += sizeof (LITTLENUM_TYPE);
1645 }
1646 return ""; /* Someone should teach Dean about null pointers */
1647 } /* md_atof() */
1648
1649 /*
1650 * Write out big-endian.
1651 */
1652 void
1653 md_number_to_chars (buf, val, n)
1654 char *buf;
1655 long val;
1656 int n;
1657 {
1658
1659 switch (n)
1660 {
1661
1662 case 4:
1663 *buf++ = val >> 24;
1664 *buf++ = val >> 16;
1665 case 2:
1666 *buf++ = val >> 8;
1667 case 1:
1668 *buf = val;
1669 break;
1670
1671 default:
1672 as_fatal ("failed sanity check.");
1673 }
1674 return;
1675 } /* md_number_to_chars() */
1676
1677 /* Apply a fixS to the frags, now that we know the value it ought to
1678 hold. */
1679
1680 void
1681 md_apply_fix (fixP, val)
1682 fixS *fixP;
1683 long val;
1684 {
1685 char *buf = fixP->fx_where + fixP->fx_frag->fr_literal;
1686
1687 assert (fixP->fx_size == 4);
1688 assert (fixP->fx_r_type < NO_RELOC);
1689
1690 fixP->fx_addnumber = val; /* Remember value for emit_reloc */
1691
1692 /*
1693 * This is a hack. There should be a better way to
1694 * handle this.
1695 */
1696 if (fixP->fx_r_type == RELOC_WDISP30 && fixP->fx_addsy)
1697 {
1698 val += fixP->fx_where + fixP->fx_frag->fr_address;
1699 }
1700
1701 switch (fixP->fx_r_type)
1702 {
1703
1704 case RELOC_32:
1705 buf[0] = 0; /* val >> 24; */
1706 buf[1] = 0; /* val >> 16; */
1707 buf[2] = 0; /* val >> 8; */
1708 buf[3] = 0; /* val; */
1709 break;
1710
1711 #if 0
1712 case RELOC_8: /* These don't seem to ever be needed. */
1713 case RELOC_16:
1714 case RELOC_DISP8:
1715 case RELOC_DISP16:
1716 case RELOC_DISP32:
1717 #endif
1718 case RELOC_WDISP30:
1719 val = (val >>= 2) + 1;
1720 buf[0] |= (val >> 24) & 0x3f;
1721 buf[1] = (val >> 16);
1722 buf[2] = val >> 8;
1723 buf[3] = val;
1724 break;
1725
1726 /* start-sanitize-v9 */
1727 #ifndef NO_V9
1728 case RELOC_11:
1729 if (((val > 0) && (val & ~0x7ff))
1730 || ((val < 0) && (~(val - 1) & ~0x7ff)))
1731 {
1732 as_bad ("relocation overflow.");
1733 } /* on overflow */
1734
1735 buf[2] |= (val >> 8) & 0x7;
1736 buf[3] = val & 0xff;
1737 break;
1738
1739 case RELOC_10:
1740 if (((val > 0) && (val & ~0x3ff))
1741 || ((val < 0) && (~(val - 1) & ~0x3ff)))
1742 {
1743 as_bad ("relocation overflow.");
1744 } /* on overflow */
1745
1746 buf[2] |= (val >> 8) & 0x3;
1747 buf[3] = val & 0xff;
1748 break;
1749
1750 case RELOC_WDISP2_14:
1751 if (((val > 0) && (val & ~0x3fffc))
1752 || ((val < 0) && (~(val - 1) & ~0x3fffc)))
1753 {
1754 as_bad ("relocation overflow.");
1755 } /* on overflow */
1756
1757 val = (val >>= 2) + 1;
1758 buf[1] |= ((val >> 14) & 0x3) << 3;
1759 buf[2] |= (val >> 8) & 0x3f;
1760 buf[3] = val & 0xff;
1761 break;
1762
1763 case RELOC_WDISP19:
1764 if (((val > 0) && (val & ~0x1ffffc))
1765 || ((val < 0) && (~(val - 1) & ~0x1ffffc)))
1766 {
1767 as_bad ("relocation overflow.");
1768 } /* on overflow */
1769
1770 val = (val >>= 2) + 1;
1771 buf[1] |= (val >> 16) & 0x7;
1772 buf[2] = (val >> 8) & 0xff;
1773 buf[3] = val & 0xff;
1774 break;
1775
1776 case RELOC_HHI22:
1777 val >>= 32;
1778 /* intentional fallthrough */
1779 #endif /* NO_V9 */
1780 /* end-sanitize-v9 */
1781
1782 case RELOC_HI22:
1783 if (!fixP->fx_addsy)
1784 {
1785 buf[1] |= (val >> 26) & 0x3f;
1786 buf[2] = val >> 18;
1787 buf[3] = val >> 10;
1788 }
1789 else
1790 {
1791 buf[2] = 0;
1792 buf[3] = 0;
1793 }
1794 break;
1795
1796 case RELOC_22:
1797 if (val & ~0x003fffff)
1798 {
1799 as_bad ("relocation overflow");
1800 } /* on overflow */
1801 buf[1] |= (val >> 16) & 0x3f;
1802 buf[2] = val >> 8;
1803 buf[3] = val & 0xff;
1804 break;
1805
1806 case RELOC_13:
1807 if (val & ~0x00001fff)
1808 {
1809 as_bad ("relocation overflow");
1810 } /* on overflow */
1811 buf[2] |= (val >> 8) & 0x1f;
1812 buf[3] = val & 0xff;
1813 break;
1814
1815 /* start-sanitize-v9 */
1816 #ifndef NO_V9
1817 case RELOC_HLO10:
1818 val >>= 32;
1819 /* intentional fallthrough */
1820 #endif /* NO_V9 */
1821 /* end-sanitize-v9 */
1822
1823 case RELOC_LO10:
1824 if (!fixP->fx_addsy)
1825 {
1826 buf[2] |= (val >> 8) & 0x03;
1827 buf[3] = val;
1828 }
1829 else
1830 buf[3] = 0;
1831 break;
1832 #if 0
1833 case RELOC_SFA_BASE:
1834 case RELOC_SFA_OFF13:
1835 case RELOC_BASE10:
1836 #endif
1837 case RELOC_BASE13:
1838 if (((val > 0) && (val & ~0x00001fff))
1839 || ((val < 0) && (~(val - 1) & ~0x00001fff)))
1840 {
1841 as_bad ("relocation overflow");
1842 } /* on overflow */
1843 buf[2] |= (val >> 8) & 0x1f;
1844 buf[3] = val;
1845 break;
1846
1847 case RELOC_WDISP22:
1848 val = (val >>= 2) + 1;
1849 /* FALLTHROUGH */
1850 case RELOC_BASE22:
1851 buf[1] |= (val >> 16) & 0x3f;
1852 buf[2] = val >> 8;
1853 buf[3] = val;
1854 break;
1855
1856 #if 0
1857 case RELOC_PC10:
1858 case RELOC_PC22:
1859 case RELOC_JMP_TBL:
1860 case RELOC_SEGOFF16:
1861 case RELOC_GLOB_DAT:
1862 case RELOC_JMP_SLOT:
1863 case RELOC_RELATIVE:
1864 #endif
1865
1866 case NO_RELOC:
1867 default:
1868 as_bad ("bad relocation type: 0x%02x", fixP->fx_r_type);
1869 break;
1870 }
1871 } /* md_apply_fix() */
1872
1873 /* should never be called for sparc */
1874 void
1875 md_create_short_jump (ptr, from_addr, to_addr, frag, to_symbol)
1876 char *ptr;
1877 long from_addr;
1878 long to_addr;
1879 fragS *frag;
1880 symbolS *to_symbol;
1881 {
1882 as_fatal ("sparc_create_short_jmp\n");
1883 } /* md_create_short_jump() */
1884
1885 /* Translate internal representation of relocation info to target format.
1886
1887 On sparc: first 4 bytes are normal unsigned long address, next three
1888 bytes are index, most sig. byte first. Byte 7 is broken up with
1889 bit 7 as external, bits 6 & 5 unused, and the lower
1890 five bits as relocation type. Next 4 bytes are long addend. */
1891 /* Thanx and a tip of the hat to Michael Bloom, mb@ttidca.tti.com */
1892 void
1893 tc_aout_fix_to_chars (where, fixP, segment_address_in_file)
1894 char *where;
1895 fixS *fixP;
1896 relax_addressT segment_address_in_file;
1897 {
1898 long r_index;
1899 long r_extern;
1900 long r_addend = 0;
1901 long r_address;
1902
1903 know (fixP->fx_addsy);
1904
1905 if (!S_IS_DEFINED (fixP->fx_addsy))
1906 {
1907 r_extern = 1;
1908 r_index = fixP->fx_addsy->sy_number;
1909 }
1910 else
1911 {
1912 r_extern = 0;
1913 r_index = S_GET_TYPE (fixP->fx_addsy);
1914 }
1915
1916 /* this is easy */
1917 md_number_to_chars (where,
1918 r_address = fixP->fx_frag->fr_address + fixP->fx_where - segment_address_in_file,
1919 4);
1920
1921 /* now the fun stuff */
1922 where[4] = (r_index >> 16) & 0x0ff;
1923 where[5] = (r_index >> 8) & 0x0ff;
1924 where[6] = r_index & 0x0ff;
1925 where[7] = ((r_extern << 7) & 0x80) | (0 & 0x60) | (fixP->fx_r_type & 0x1F);
1926
1927 /* Also easy */
1928 if (fixP->fx_addsy->sy_frag)
1929 {
1930 r_addend = fixP->fx_addsy->sy_frag->fr_address;
1931 }
1932
1933 if (fixP->fx_pcrel)
1934 {
1935 r_addend += fixP->fx_offset - r_address;
1936 }
1937 else
1938 {
1939 r_addend = fixP->fx_addnumber;
1940 }
1941
1942 md_number_to_chars (&where[8], r_addend, 4);
1943
1944 return;
1945 } /* tc_aout_fix_to_chars() */
1946
1947 /* should never be called for sparc */
1948 void
1949 md_convert_frag (headers, fragP)
1950 object_headers *headers;
1951 register fragS *fragP;
1952 {
1953 as_fatal ("sparc_convert_frag\n");
1954 } /* md_convert_frag() */
1955
1956 /* should never be called for sparc */
1957 void
1958 md_create_long_jump (ptr, from_addr, to_addr, frag, to_symbol)
1959 char *ptr;
1960 long from_addr, to_addr;
1961 fragS *frag;
1962 symbolS *to_symbol;
1963 {
1964 as_fatal ("sparc_create_long_jump\n");
1965 } /* md_create_long_jump() */
1966
1967 /* should never be called for sparc */
1968 int
1969 md_estimate_size_before_relax (fragP, segtype)
1970 fragS *fragP;
1971 segT segtype;
1972 {
1973 as_fatal ("sparc_estimate_size_before_relax\n");
1974 return (1);
1975 } /* md_estimate_size_before_relax() */
1976
1977 #if 0
1978 /* for debugging only */
1979 static void
1980 print_insn (insn)
1981 struct sparc_it *insn;
1982 {
1983 char *Reloc[] =
1984 {
1985 "RELOC_8",
1986 "RELOC_16",
1987 "RELOC_32",
1988 "RELOC_DISP8",
1989 "RELOC_DISP16",
1990 "RELOC_DISP32",
1991 "RELOC_WDISP30",
1992 "RELOC_WDISP22",
1993 "RELOC_HI22",
1994 "RELOC_22",
1995 "RELOC_13",
1996 "RELOC_LO10",
1997 "RELOC_SFA_BASE",
1998 "RELOC_SFA_OFF13",
1999 "RELOC_BASE10",
2000 "RELOC_BASE13",
2001 "RELOC_BASE22",
2002 "RELOC_PC10",
2003 "RELOC_PC22",
2004 "RELOC_JMP_TBL",
2005 "RELOC_SEGOFF16",
2006 "RELOC_GLOB_DAT",
2007 "RELOC_JMP_SLOT",
2008 "RELOC_RELATIVE",
2009 "NO_RELOC"
2010 };
2011
2012 if (insn->error)
2013 {
2014 fprintf (stderr, "ERROR: %s\n");
2015 }
2016 fprintf (stderr, "opcode=0x%08x\n", insn->opcode);
2017 fprintf (stderr, "reloc = %s\n", Reloc[insn->reloc]);
2018 fprintf (stderr, "exp = {\n");
2019 fprintf (stderr, "\t\tX_add_symbol = %s\n",
2020 ((insn->exp.X_add_symbol != NULL)
2021 ? ((S_GET_NAME (insn->exp.X_add_symbol) != NULL)
2022 ? S_GET_NAME (insn->exp.X_add_symbol)
2023 : "???")
2024 : "0"));
2025 fprintf (stderr, "\t\tX_sub_symbol = %s\n",
2026 ((insn->exp.X_subtract_symbol != NULL)
2027 ? (S_GET_NAME (insn->exp.X_subtract_symbol)
2028 ? S_GET_NAME (insn->exp.X_subtract_symbol)
2029 : "???")
2030 : "0"));
2031 fprintf (stderr, "\t\tX_add_number = %d\n",
2032 insn->exp.X_add_number);
2033 fprintf (stderr, "}\n");
2034 return;
2035 } /* print_insn() */
2036
2037 #endif
2038
2039 /* Set the hook... */
2040
2041 /* void emit_sparc_reloc();
2042 void (*md_emit_relocations)() = emit_sparc_reloc; */
2043
2044 #ifdef comment
2045
2046 /*
2047 * Sparc/AM29K relocations are completely different, so it needs
2048 * this machine dependent routine to emit them.
2049 */
2050 #if defined(OBJ_AOUT) || defined(OBJ_BOUT)
2051 void
2052 emit_sparc_reloc (fixP, segment_address_in_file)
2053 register fixS *fixP;
2054 relax_addressT segment_address_in_file;
2055 {
2056 struct reloc_info_generic ri;
2057 register symbolS *symbolP;
2058 extern char *next_object_file_charP;
2059 /* long add_number; */
2060
2061 memset ((char *) &ri, '\0', sizeof (ri));
2062 for (; fixP; fixP = fixP->fx_next)
2063 {
2064
2065 if (fixP->fx_r_type >= NO_RELOC)
2066 {
2067 as_fatal ("fixP->fx_r_type = %d\n", fixP->fx_r_type);
2068 }
2069
2070 if ((symbolP = fixP->fx_addsy) != NULL)
2071 {
2072 ri.r_address = fixP->fx_frag->fr_address +
2073 fixP->fx_where - segment_address_in_file;
2074 if ((S_GET_TYPE (symbolP)) == N_UNDF)
2075 {
2076 ri.r_extern = 1;
2077 ri.r_index = symbolP->sy_number;
2078 }
2079 else
2080 {
2081 ri.r_extern = 0;
2082 ri.r_index = S_GET_TYPE (symbolP);
2083 }
2084 if (symbolP && symbolP->sy_frag)
2085 {
2086 ri.r_addend = symbolP->sy_frag->fr_address;
2087 }
2088 ri.r_type = fixP->fx_r_type;
2089 if (fixP->fx_pcrel)
2090 {
2091 /* ri.r_addend -= fixP->fx_where; */
2092 ri.r_addend -= ri.r_address;
2093 }
2094 else
2095 {
2096 ri.r_addend = fixP->fx_addnumber;
2097 }
2098
2099 md_ri_to_chars (next_object_file_charP, &ri);
2100 next_object_file_charP += md_reloc_size;
2101 }
2102 }
2103 return;
2104 } /* emit_sparc_reloc() */
2105
2106 #endif /* aout or bout */
2107 #endif /* comment */
2108
2109 /*
2110 * md_parse_option
2111 * Invocation line includes a switch not recognized by the base assembler.
2112 * See if it's a processor-specific option. These are:
2113 *
2114 * -bump
2115 * Warn on architecture bumps. See also -A.
2116 *
2117 * -Av6, -Av7, -Av8, -Asparclite
2118 * Select the architecture. Instructions or features not
2119 * supported by the selected architecture cause fatal errors.
2120 *
2121 * The default is to start at v6, and bump the architecture up
2122 * whenever an instruction is seen at a higher level.
2123 *
2124 * If -bump is specified, a warning is printing when bumping to
2125 * higher levels.
2126 *
2127 * If an architecture is specified, all instructions must match
2128 * that architecture. Any higher level instructions are flagged
2129 * as errors.
2130 *
2131 * if both an architecture and -bump are specified, the
2132 * architecture starts at the specified level, but bumps are
2133 * warnings.
2134 *
2135 * start-sanitize-v9
2136 * Bumping between incompatible architectures is always an
2137 * error. For example, from sparclite to v9.
2138 * end-sanitize-v9
2139 */
2140 /* start-sanitize-v9 */
2141 /* There is also a -Av9 architecture option. xoxorich. */
2142 /* end-sanitize-v9 */
2143 int
2144 md_parse_option (argP, cntP, vecP)
2145 char **argP;
2146 int *cntP;
2147 char ***vecP;
2148 {
2149 char *p;
2150 const char **arch;
2151
2152 if (!strcmp (*argP, "bump"))
2153 {
2154 warn_on_bump = 1;
2155
2156 }
2157 else if (**argP == 'A')
2158 {
2159 p = (*argP) + 1;
2160
2161 for (arch = architecture_pname; *arch != NULL; ++arch)
2162 {
2163 if (strcmp (p, *arch) == 0)
2164 {
2165 break;
2166 } /* found a match */
2167 } /* walk the pname table */
2168
2169 if (*arch == NULL)
2170 {
2171 as_bad ("unknown architecture: %s", p);
2172 }
2173 else
2174 {
2175 current_architecture = (enum sparc_architecture) (arch - architecture_pname);
2176 architecture_requested = 1;
2177 }
2178 }
2179 else
2180 {
2181 /* Unknown option */
2182 (*argP)++;
2183 return 0;
2184 }
2185 **argP = '\0'; /* Done parsing this switch */
2186 return 1;
2187 } /* md_parse_option() */
2188
2189 /* We have no need to default values of symbols. */
2190
2191 /* ARGSUSED */
2192 symbolS *
2193 md_undefined_symbol (name)
2194 char *name;
2195 {
2196 return 0;
2197 } /* md_undefined_symbol() */
2198
2199 /* Parse an operand that is machine-specific.
2200 We just return without modifying the expression if we have nothing
2201 to do. */
2202
2203 /* ARGSUSED */
2204 void
2205 md_operand (expressionP)
2206 expressionS *expressionP;
2207 {
2208 } /* md_operand() */
2209
2210 /* Round up a section size to the appropriate boundary. */
2211 long
2212 md_section_align (segment, size)
2213 segT segment;
2214 long size;
2215 {
2216 return (size + 7) & ~7; /* Round all sects to multiple of 8 */
2217 } /* md_section_align() */
2218
2219 /* Exactly what point is a PC-relative offset relative TO?
2220 On the sparc, they're relative to the address of the offset, plus
2221 its size. This gets us to the following instruction.
2222 (??? Is this right? FIXME-SOON) */
2223 long
2224 md_pcrel_from (fixP)
2225 fixS *fixP;
2226 {
2227 return fixP->fx_size + fixP->fx_where + fixP->fx_frag->fr_address;
2228 } /* md_pcrel_from() */
2229
2230 void
2231 tc_aout_pre_write_hook (headers)
2232 object_headers *headers;
2233 {
2234 H_SET_VERSION (headers, 1);
2235 return;
2236 } /* tc_aout_pre_write_hook() */
2237
2238 /*
2239 * Local Variables:
2240 * comment-column: 0
2241 * fill-column: 131
2242 * End:
2243 */
2244
2245 /* end of tc-sparc.c */
This page took 0.073069 seconds and 5 git commands to generate.