* readelf.c (display_debug_lines): Fix section length check
[deliverable/binutils-gdb.git] / gas / config / tc-hppa.c
CommitLineData
252b5132 1/* tc-hppa.c -- Assemble for the PA
ad1079af 2 Copyright (C) 1989, 93, 94, 95, 96, 97, 98, 99, 2000
49309057 3 Free Software Foundation, Inc.
252b5132
RH
4
5 This file is part of GAS, the GNU Assembler.
6
7 GAS is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 GAS is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GAS; see the file COPYING. If not, write to the Free
19 Software Foundation, 59 Temple Place - Suite 330, Boston, MA
20 02111-1307, USA. */
21
252b5132
RH
22/* HP PA-RISC support was contributed by the Center for Software Science
23 at the University of Utah. */
24
25#include <stdio.h>
26#include <ctype.h>
27
28#include "as.h"
29#include "subsegs.h"
30
31#include "bfd/libhppa.h"
252b5132
RH
32
33/* Be careful, this file includes data *declarations*. */
34#include "opcode/hppa.h"
35
49863f82
JL
36#if defined (OBJ_ELF) && defined (OBJ_SOM)
37error only one of OBJ_ELF and OBJ_SOM can be defined
38#endif
39
2d93dcc4
JL
40/* If we are using ELF, then we probably can support dwarf2 debug
41 records. Furthermore, if we are supporting dwarf2 debug records,
42 then we want to use the assembler support for compact line numbers. */
43#ifdef OBJ_ELF
44#include "dwarf2dbg.h"
2d93dcc4 45
252b5132
RH
46/* A "convient" place to put object file dependencies which do
47 not need to be seen outside of tc-hppa.c. */
ad1079af 48
252b5132 49/* Object file formats specify relocation types. */
ad1079af 50typedef enum elf_hppa_reloc_type reloc_type;
252b5132
RH
51
52/* Object file formats specify BFD symbol types. */
53typedef elf_symbol_type obj_symbol_type;
ad1079af
AM
54#define symbol_arg_reloc_info(sym)\
55 (((obj_symbol_type *) symbol_get_bfdsym (sym))->tc_data.hppa_arg_reloc)
252b5132 56
ad1079af 57#if TARGET_ARCH_SIZE == 64
252b5132 58/* How to generate a relocation. */
b388df87
JL
59#define hppa_gen_reloc_type _bfd_elf64_hppa_gen_reloc_type
60#else
61#define hppa_gen_reloc_type _bfd_elf32_hppa_gen_reloc_type
62#endif
252b5132
RH
63
64/* ELF objects can have versions, but apparently do not have anywhere
65 to store a copyright string. */
66#define obj_version obj_elf_version
67#define obj_copyright obj_elf_version
46031ca9
JL
68
69#define UNWIND_SECTION_NAME ".PARISC.unwind"
ad1079af 70#endif /* OBJ_ELF */
252b5132
RH
71
72#ifdef OBJ_SOM
73/* Names of various debugging spaces/subspaces. */
74#define GDB_DEBUG_SPACE_NAME "$GDB_DEBUG$"
75#define GDB_STRINGS_SUBSPACE_NAME "$GDB_STRINGS$"
76#define GDB_SYMBOLS_SUBSPACE_NAME "$GDB_SYMBOLS$"
77#define UNWIND_SECTION_NAME "$UNWIND$"
78
79/* Object file formats specify relocation types. */
80typedef int reloc_type;
81
82/* SOM objects can have both a version string and a copyright string. */
83#define obj_version obj_som_version
84#define obj_copyright obj_som_copyright
85
252b5132
RH
86/* How to generate a relocation. */
87#define hppa_gen_reloc_type hppa_som_gen_reloc_type
88
89/* Object file formats specify BFD symbol types. */
90typedef som_symbol_type obj_symbol_type;
ad1079af
AM
91#define symbol_arg_reloc_info(sym)\
92 (((obj_symbol_type *) symbol_get_bfdsym (sym))->tc_data.ap.hppa_arg_reloc)
252b5132
RH
93
94/* This apparently isn't in older versions of hpux reloc.h. */
95#ifndef R_DLT_REL
96#define R_DLT_REL 0x78
97#endif
252b5132
RH
98
99#ifndef R_N0SEL
100#define R_N0SEL 0xd8
101#endif
102
103#ifndef R_N1SEL
104#define R_N1SEL 0xd9
105#endif
ad1079af 106#endif /* OBJ_SOM */
252b5132
RH
107
108/* Various structures and types used internally in tc-hppa.c. */
109
110/* Unwind table and descriptor. FIXME: Sync this with GDB version. */
111
112struct unwind_desc
113 {
114 unsigned int cannot_unwind:1;
115 unsigned int millicode:1;
116 unsigned int millicode_save_rest:1;
117 unsigned int region_desc:2;
118 unsigned int save_sr:2;
119 unsigned int entry_fr:4;
120 unsigned int entry_gr:5;
121 unsigned int args_stored:1;
122 unsigned int call_fr:5;
123 unsigned int call_gr:5;
124 unsigned int save_sp:1;
125 unsigned int save_rp:1;
126 unsigned int save_rp_in_frame:1;
127 unsigned int extn_ptr_defined:1;
128 unsigned int cleanup_defined:1;
129
130 unsigned int hpe_interrupt_marker:1;
131 unsigned int hpux_interrupt_marker:1;
132 unsigned int reserved:3;
133 unsigned int frame_size:27;
134 };
135
136struct unwind_table
137 {
138 /* Starting and ending offsets of the region described by
139 descriptor. */
140 unsigned int start_offset;
141 unsigned int end_offset;
142 struct unwind_desc descriptor;
143 };
144
145/* This structure is used by the .callinfo, .enter, .leave pseudo-ops to
146 control the entry and exit code they generate. It is also used in
147 creation of the correct stack unwind descriptors.
148
149 NOTE: GAS does not support .enter and .leave for the generation of
150 prologues and epilogues. FIXME.
151
152 The fields in structure roughly correspond to the arguments available on the
153 .callinfo pseudo-op. */
154
155struct call_info
156 {
157 /* The unwind descriptor being built. */
158 struct unwind_table ci_unwind;
159
160 /* Name of this function. */
161 symbolS *start_symbol;
162
163 /* (temporary) symbol used to mark the end of this function. */
164 symbolS *end_symbol;
165
166 /* Next entry in the chain. */
167 struct call_info *ci_next;
168 };
169
170/* Operand formats for FP instructions. Note not all FP instructions
171 allow all four formats to be used (for example fmpysub only allows
172 SGL and DBL). */
173typedef enum
174 {
175 SGL, DBL, ILLEGAL_FMT, QUAD, W, UW, DW, UDW, QW, UQW
176 }
177fp_operand_format;
178
179/* This fully describes the symbol types which may be attached to
180 an EXPORT or IMPORT directive. Only SOM uses this formation
181 (ELF has no need for it). */
182typedef enum
183 {
184 SYMBOL_TYPE_UNKNOWN,
185 SYMBOL_TYPE_ABSOLUTE,
186 SYMBOL_TYPE_CODE,
187 SYMBOL_TYPE_DATA,
188 SYMBOL_TYPE_ENTRY,
189 SYMBOL_TYPE_MILLICODE,
190 SYMBOL_TYPE_PLABEL,
191 SYMBOL_TYPE_PRI_PROG,
192 SYMBOL_TYPE_SEC_PROG,
193 }
194pa_symbol_type;
195
196/* This structure contains information needed to assemble
197 individual instructions. */
198struct pa_it
199 {
200 /* Holds the opcode after parsing by pa_ip. */
201 unsigned long opcode;
202
203 /* Holds an expression associated with the current instruction. */
204 expressionS exp;
205
206 /* Does this instruction use PC-relative addressing. */
207 int pcrel;
208
209 /* Floating point formats for operand1 and operand2. */
210 fp_operand_format fpof1;
211 fp_operand_format fpof2;
212
1cf6ae67
JL
213 /* Whether or not we saw a truncation request on an fcnv insn. */
214 int trunc;
252b5132
RH
215
216 /* Holds the field selector for this instruction
217 (for example L%, LR%, etc). */
218 long field_selector;
219
220 /* Holds any argument relocation bits associated with this
221 instruction. (instruction should be some sort of call). */
ad1079af 222 unsigned int arg_reloc;
252b5132
RH
223
224 /* The format specification for this instruction. */
225 int format;
226
227 /* The relocation (if any) associated with this instruction. */
228 reloc_type reloc;
229 };
230
231/* PA-89 floating point registers are arranged like this:
232
252b5132
RH
233 +--------------+--------------+
234 | 0 or 16L | 16 or 16R |
235 +--------------+--------------+
236 | 1 or 17L | 17 or 17R |
237 +--------------+--------------+
238 | | |
239
240 . . .
241 . . .
242 . . .
243
244 | | |
245 +--------------+--------------+
246 | 14 or 30L | 30 or 30R |
247 +--------------+--------------+
248 | 15 or 31L | 31 or 31R |
ecacdc7a 249 +--------------+--------------+ */
252b5132
RH
250
251/* Additional information needed to build argument relocation stubs. */
252struct call_desc
253 {
254 /* The argument relocation specification. */
255 unsigned int arg_reloc;
256
257 /* Number of arguments. */
258 unsigned int arg_count;
259 };
260
49863f82 261#ifdef OBJ_SOM
252b5132
RH
262/* This structure defines an entry in the subspace dictionary
263 chain. */
264
265struct subspace_dictionary_chain
266 {
267 /* Nonzero if this space has been defined by the user code. */
268 unsigned int ssd_defined;
269
270 /* Name of this subspace. */
271 char *ssd_name;
272
273 /* GAS segment and subsegment associated with this subspace. */
274 asection *ssd_seg;
275 int ssd_subseg;
276
277 /* Next space in the subspace dictionary chain. */
278 struct subspace_dictionary_chain *ssd_next;
279 };
280
281typedef struct subspace_dictionary_chain ssd_chain_struct;
282
283/* This structure defines an entry in the subspace dictionary
284 chain. */
285
286struct space_dictionary_chain
287 {
288 /* Nonzero if this space has been defined by the user code or
289 as a default space. */
290 unsigned int sd_defined;
291
292 /* Nonzero if this spaces has been defined by the user code. */
293 unsigned int sd_user_defined;
294
295 /* The space number (or index). */
296 unsigned int sd_spnum;
297
298 /* The name of this subspace. */
299 char *sd_name;
300
301 /* GAS segment to which this subspace corresponds. */
302 asection *sd_seg;
303
304 /* Current subsegment number being used. */
305 int sd_last_subseg;
306
307 /* The chain of subspaces contained within this space. */
308 ssd_chain_struct *sd_subspaces;
309
310 /* The next entry in the space dictionary chain. */
311 struct space_dictionary_chain *sd_next;
312 };
313
314typedef struct space_dictionary_chain sd_chain_struct;
315
252b5132
RH
316/* This structure defines attributes of the default subspace
317 dictionary entries. */
318
319struct default_subspace_dict
320 {
321 /* Name of the subspace. */
322 char *name;
323
324 /* FIXME. Is this still needed? */
325 char defined;
326
327 /* Nonzero if this subspace is loadable. */
328 char loadable;
329
330 /* Nonzero if this subspace contains only code. */
331 char code_only;
332
333 /* Nonzero if this is a common subspace. */
334 char common;
335
336 /* Nonzero if this is a common subspace which allows symbols
337 to be multiply defined. */
338 char dup_common;
339
340 /* Nonzero if this subspace should be zero filled. */
341 char zero;
342
343 /* Sort key for this subspace. */
344 unsigned char sort;
345
346 /* Access control bits for this subspace. Can represent RWX access
347 as well as privilege level changes for gateways. */
348 int access;
349
350 /* Index of containing space. */
351 int space_index;
352
353 /* Alignment (in bytes) of this subspace. */
354 int alignment;
355
356 /* Quadrant within space where this subspace should be loaded. */
357 int quadrant;
358
359 /* An index into the default spaces array. */
360 int def_space_index;
361
252b5132
RH
362 /* Subsegment associated with this subspace. */
363 subsegT subsegment;
364 };
365
366/* This structure defines attributes of the default space
367 dictionary entries. */
368
369struct default_space_dict
370 {
371 /* Name of the space. */
372 char *name;
373
374 /* Space number. It is possible to identify spaces within
375 assembly code numerically! */
376 int spnum;
377
378 /* Nonzero if this space is loadable. */
379 char loadable;
380
381 /* Nonzero if this space is "defined". FIXME is still needed */
382 char defined;
383
384 /* Nonzero if this space can not be shared. */
385 char private;
386
387 /* Sort key for this space. */
388 unsigned char sort;
389
390 /* Segment associated with this space. */
391 asection *segment;
252b5132 392 };
49863f82
JL
393#endif
394
395/* Structure for previous label tracking. Needed so that alignments,
396 callinfo declarations, etc can be easily attached to a particular
397 label. */
398typedef struct label_symbol_struct
399 {
400 struct symbol *lss_label;
401#ifdef OBJ_SOM
402 sd_chain_struct *lss_space;
403#endif
404#ifdef OBJ_ELF
405 segT lss_segment;
406#endif
407 struct label_symbol_struct *lss_next;
408 }
409label_symbol_struct;
252b5132
RH
410
411/* Extra information needed to perform fixups (relocations) on the PA. */
412struct hppa_fix_struct
413 {
414 /* The field selector. */
415 enum hppa_reloc_field_selector_type_alt fx_r_field;
416
417 /* Type of fixup. */
418 int fx_r_type;
419
420 /* Format of fixup. */
421 int fx_r_format;
422
423 /* Argument relocation bits. */
ad1079af 424 unsigned int fx_arg_reloc;
252b5132
RH
425
426 /* The segment this fixup appears in. */
427 segT segment;
428 };
429
430/* Structure to hold information about predefined registers. */
431
432struct pd_reg
433 {
434 char *name;
435 int value;
436 };
437
438/* This structure defines the mapping from a FP condition string
439 to a condition number which can be recorded in an instruction. */
440struct fp_cond_map
441 {
442 char *string;
443 int cond;
444 };
445
446/* This structure defines a mapping from a field selector
447 string to a field selector type. */
448struct selector_entry
449 {
450 char *prefix;
451 int field_selector;
452 };
453
454/* Prototypes for functions local to tc-hppa.c. */
455
49863f82 456#ifdef OBJ_SOM
252b5132 457static void pa_check_current_space_and_subspace PARAMS ((void));
49863f82
JL
458#endif
459
ad1079af
AM
460#if !(defined (OBJ_ELF) && defined (TE_LINUX))
461static void pa_text PARAMS ((int));
462static void pa_data PARAMS ((int));
463static void pa_comm PARAMS ((int));
464#endif
252b5132
RH
465static fp_operand_format pa_parse_fp_format PARAMS ((char **s));
466static void pa_cons PARAMS ((int));
252b5132
RH
467static void pa_float_cons PARAMS ((int));
468static void pa_fill PARAMS ((int));
469static void pa_lcomm PARAMS ((int));
470static void pa_lsym PARAMS ((int));
471static void pa_stringer PARAMS ((int));
252b5132
RH
472static void pa_version PARAMS ((int));
473static int pa_parse_fp_cmp_cond PARAMS ((char **));
474static int get_expression PARAMS ((char *));
475static int pa_get_absolute_expression PARAMS ((struct pa_it *, char **));
476static int evaluate_absolute PARAMS ((struct pa_it *));
477static unsigned int pa_build_arg_reloc PARAMS ((char *));
478static unsigned int pa_align_arg_reloc PARAMS ((unsigned int, unsigned int));
479static int pa_parse_nullif PARAMS ((char **));
480static int pa_parse_nonneg_cmpsub_cmpltr PARAMS ((char **, int));
481static int pa_parse_neg_cmpsub_cmpltr PARAMS ((char **, int));
482static int pa_parse_neg_add_cmpltr PARAMS ((char **, int));
483static int pa_parse_nonneg_add_cmpltr PARAMS ((char **, int));
d53d2751
JL
484static int pa_parse_cmpb_64_cmpltr PARAMS ((char **));
485static int pa_parse_cmpib_64_cmpltr PARAMS ((char **));
486static int pa_parse_addb_64_cmpltr PARAMS ((char **));
252b5132
RH
487static void pa_block PARAMS ((int));
488static void pa_brtab PARAMS ((int));
489static void pa_try PARAMS ((int));
490static void pa_call PARAMS ((int));
491static void pa_call_args PARAMS ((struct call_desc *));
492static void pa_callinfo PARAMS ((int));
252b5132
RH
493static void pa_copyright PARAMS ((int));
494static void pa_end PARAMS ((int));
495static void pa_enter PARAMS ((int));
496static void pa_entry PARAMS ((int));
497static void pa_equ PARAMS ((int));
498static void pa_exit PARAMS ((int));
499static void pa_export PARAMS ((int));
500static void pa_type_args PARAMS ((symbolS *, int));
501static void pa_import PARAMS ((int));
502static void pa_label PARAMS ((int));
503static void pa_leave PARAMS ((int));
504static void pa_level PARAMS ((int));
505static void pa_origin PARAMS ((int));
506static void pa_proc PARAMS ((int));
507static void pa_procend PARAMS ((int));
252b5132
RH
508static void pa_param PARAMS ((int));
509static void pa_undefine_label PARAMS ((void));
ecacdc7a
AM
510static int need_pa11_opcode PARAMS ((void));
511static int pa_parse_number PARAMS ((char **, int));
252b5132 512static label_symbol_struct *pa_get_label PARAMS ((void));
49863f82 513#ifdef OBJ_SOM
3f9b03b5 514static int log2 PARAMS ((int));
49863f82
JL
515static void pa_compiler PARAMS ((int));
516static void pa_align PARAMS ((int));
517static void pa_space PARAMS ((int));
518static void pa_spnum PARAMS ((int));
519static void pa_subspace PARAMS ((int));
252b5132
RH
520static sd_chain_struct *create_new_space PARAMS ((char *, int, int,
521 int, int, int,
522 asection *, int));
523static ssd_chain_struct *create_new_subspace PARAMS ((sd_chain_struct *,
524 char *, int, int,
525 int, int, int,
526 int, int, int, int,
527 int, asection *));
528static ssd_chain_struct *update_subspace PARAMS ((sd_chain_struct *,
529 char *, int, int, int,
530 int, int, int, int,
531 int, int, int,
532 asection *));
533static sd_chain_struct *is_defined_space PARAMS ((char *));
534static ssd_chain_struct *is_defined_subspace PARAMS ((char *));
535static sd_chain_struct *pa_segment_to_space PARAMS ((asection *));
536static ssd_chain_struct *pa_subsegment_to_subspace PARAMS ((asection *,
537 subsegT));
538static sd_chain_struct *pa_find_space_by_number PARAMS ((int));
539static unsigned int pa_subspace_start PARAMS ((sd_chain_struct *, int));
49863f82
JL
540static sd_chain_struct *pa_parse_space_stmt PARAMS ((char *, int));
541static int pa_next_subseg PARAMS ((sd_chain_struct *));
542static void pa_spaces_begin PARAMS ((void));
543#endif
252b5132
RH
544static void pa_ip PARAMS ((char *));
545static void fix_new_hppa PARAMS ((fragS *, int, int, symbolS *,
ad1079af 546 offsetT, expressionS *, int,
252b5132
RH
547 bfd_reloc_code_real_type,
548 enum hppa_reloc_field_selector_type_alt,
ad1079af 549 int, unsigned int, int *));
252b5132
RH
550static int is_end_of_statement PARAMS ((void));
551static int reg_name_search PARAMS ((char *));
552static int pa_chk_field_selector PARAMS ((char **));
553static int is_same_frag PARAMS ((fragS *, fragS *));
554static void process_exit PARAMS ((void));
252b5132 555static unsigned int pa_stringer_aux PARAMS ((char *));
1cf6ae67
JL
556static fp_operand_format pa_parse_fp_cnv_format PARAMS ((char **s));
557static int pa_parse_ftest_gfx_completer PARAMS ((char **));
252b5132
RH
558
559#ifdef OBJ_ELF
560static void hppa_elf_mark_end_of_function PARAMS ((void));
561static void pa_build_unwind_subspace PARAMS ((struct call_info *));
904a31bf
AM
562static void pa_vtable_entry PARAMS ((int));
563static void pa_vtable_inherit PARAMS ((int));
252b5132
RH
564#endif
565
566/* File and gloally scoped variable declarations. */
567
49863f82 568#ifdef OBJ_SOM
252b5132
RH
569/* Root and final entry in the space chain. */
570static sd_chain_struct *space_dict_root;
571static sd_chain_struct *space_dict_last;
572
573/* The current space and subspace. */
574static sd_chain_struct *current_space;
575static ssd_chain_struct *current_subspace;
49863f82 576#endif
252b5132
RH
577
578/* Root of the call_info chain. */
579static struct call_info *call_info_root;
580
581/* The last call_info (for functions) structure
582 seen so it can be associated with fixups and
583 function labels. */
584static struct call_info *last_call_info;
585
586/* The last call description (for actual calls). */
587static struct call_desc last_call_desc;
588
589/* handle of the OPCODE hash table */
590static struct hash_control *op_hash = NULL;
591
252b5132
RH
592/* Table of pseudo ops for the PA. FIXME -- how many of these
593 are now redundant with the overall GAS and the object file
594 dependent tables? */
595const pseudo_typeS md_pseudo_table[] =
596{
597 /* align pseudo-ops on the PA specify the actual alignment requested,
598 not the log2 of the requested alignment. */
49863f82 599#ifdef OBJ_SOM
252b5132 600 {"align", pa_align, 8},
49863f82
JL
601#endif
602#ifdef OBJ_ELF
603 {"align", s_align_bytes, 8},
604#endif
252b5132
RH
605 {"begin_brtab", pa_brtab, 1},
606 {"begin_try", pa_try, 1},
607 {"block", pa_block, 1},
608 {"blockz", pa_block, 0},
609 {"byte", pa_cons, 1},
610 {"call", pa_call, 0},
611 {"callinfo", pa_callinfo, 0},
ad1079af
AM
612#if defined (OBJ_ELF) && defined (TE_LINUX)
613 {"code", obj_elf_text, 0},
614#else
615 {"code", pa_text, 0},
252b5132 616 {"comm", pa_comm, 0},
ad1079af 617#endif
252b5132
RH
618#ifdef OBJ_SOM
619 {"compiler", pa_compiler, 0},
620#endif
621 {"copyright", pa_copyright, 0},
ad1079af 622#if !(defined (OBJ_ELF) && defined (TE_LINUX))
252b5132 623 {"data", pa_data, 0},
ad1079af 624#endif
252b5132 625 {"double", pa_float_cons, 'd'},
077db52a 626 {"dword", pa_cons, 8},
252b5132
RH
627 {"end", pa_end, 0},
628 {"end_brtab", pa_brtab, 0},
ad1079af 629#if !(defined (OBJ_ELF) && defined (TE_LINUX))
252b5132 630 {"end_try", pa_try, 0},
ad1079af 631#endif
252b5132
RH
632 {"enter", pa_enter, 0},
633 {"entry", pa_entry, 0},
634 {"equ", pa_equ, 0},
635 {"exit", pa_exit, 0},
636 {"export", pa_export, 0},
2d93dcc4 637#ifdef OBJ_ELF
ad1079af 638 {"file", dwarf2_directive_file, 0 },
2d93dcc4 639#endif
252b5132
RH
640 {"fill", pa_fill, 0},
641 {"float", pa_float_cons, 'f'},
642 {"half", pa_cons, 2},
643 {"import", pa_import, 0},
644 {"int", pa_cons, 4},
645 {"label", pa_label, 0},
646 {"lcomm", pa_lcomm, 0},
647 {"leave", pa_leave, 0},
648 {"level", pa_level, 0},
2d93dcc4 649#ifdef OBJ_ELF
ad1079af 650 {"loc", dwarf2_directive_loc, 0 },
2d93dcc4 651#endif
252b5132
RH
652 {"long", pa_cons, 4},
653 {"lsym", pa_lsym, 0},
49863f82 654#ifdef OBJ_SOM
252b5132 655 {"nsubspa", pa_subspace, 1},
49863f82 656#endif
252b5132
RH
657 {"octa", pa_cons, 16},
658 {"org", pa_origin, 0},
659 {"origin", pa_origin, 0},
660 {"param", pa_param, 0},
661 {"proc", pa_proc, 0},
662 {"procend", pa_procend, 0},
663 {"quad", pa_cons, 8},
664 {"reg", pa_equ, 1},
665 {"short", pa_cons, 2},
666 {"single", pa_float_cons, 'f'},
49863f82 667#ifdef OBJ_SOM
252b5132
RH
668 {"space", pa_space, 0},
669 {"spnum", pa_spnum, 0},
49863f82 670#endif
252b5132
RH
671 {"string", pa_stringer, 0},
672 {"stringz", pa_stringer, 1},
49863f82 673#ifdef OBJ_SOM
252b5132 674 {"subspa", pa_subspace, 0},
49863f82 675#endif
ad1079af 676#if !(defined (OBJ_ELF) && defined (TE_LINUX))
252b5132 677 {"text", pa_text, 0},
ad1079af 678#endif
252b5132 679 {"version", pa_version, 0},
904a31bf
AM
680#ifdef OBJ_ELF
681 {"vtable_entry", pa_vtable_entry, 0},
682 {"vtable_inherit", pa_vtable_inherit, 0},
683#endif
252b5132
RH
684 {"word", pa_cons, 4},
685 {NULL, 0, 0}
686};
687
688/* This array holds the chars that only start a comment at the beginning of
689 a line. If the line seems to have the form '# 123 filename'
690 .line and .file directives will appear in the pre-processed output.
691
692 Note that input_file.c hand checks for '#' at the beginning of the
693 first line of the input file. This is because the compiler outputs
694 #NO_APP at the beginning of its output.
695
a28a3ccf 696 Also note that C style comments will always work. */
252b5132
RH
697const char line_comment_chars[] = "#";
698
ad1079af
AM
699/* This array holds the chars that always start a comment. If the
700 pre-processor is disabled, these aren't very useful. */
701const char comment_chars[] = ";";
702
252b5132
RH
703/* This array holds the characters which act as line separators. */
704const char line_separator_chars[] = "!";
705
706/* Chars that can be used to separate mant from exp in floating point nums. */
707const char EXP_CHARS[] = "eE";
708
709/* Chars that mean this number is a floating point constant.
710 As in 0f12.456 or 0d1.2345e12.
711
712 Be aware that MAXIMUM_NUMBER_OF_CHARS_FOR_FLOAT may have to be
713 changed in read.c. Ideally it shouldn't hae to know abou it at
714 all, but nothing is ideal around here. */
715const char FLT_CHARS[] = "rRsSfFdDxXpP";
716
717static struct pa_it the_insn;
718
719/* Points to the end of an expression just parsed by get_expressoin
720 and friends. FIXME. This shouldn't be handled with a file-global
721 variable. */
722static char *expr_end;
723
724/* Nonzero if a .callinfo appeared within the current procedure. */
725static int callinfo_found;
726
727/* Nonzero if the assembler is currently within a .entry/.exit pair. */
728static int within_entry_exit;
729
730/* Nonzero if the assembler is currently within a procedure definition. */
731static int within_procedure;
732
ad1079af 733/* Handle on structure which keep track of the last symbol
252b5132
RH
734 seen in each subspace. */
735static label_symbol_struct *label_symbols_rootp = NULL;
736
737/* Holds the last field selector. */
738static int hppa_field_selector;
739
0f4f8b56
JL
740/* Nonzero when strict syntax checking is enabled. Zero otherwise.
741
742 Each opcode in the table has a flag which indicates whether or not
743 strict syntax checking should be enabled for that instruction. */
744static int strict = 0;
745
ecacdc7a
AM
746/* pa_parse_number returns values in `pa_number'. Mostly
747 pa_parse_number is used to return a register number, with floating
748 point registers being numbered from FP_REG_BASE upwards.
749 The bit specified with FP_REG_RSEL is set if the floating point
750 register has a `r' suffix. */
751#define FP_REG_BASE 64
752#define FP_REG_RSEL 128
753static int pa_number;
754
993142d5 755#ifdef OBJ_SOM
252b5132
RH
756/* A dummy bfd symbol so that all relocations have symbols of some kind. */
757static symbolS *dummy_symbol;
993142d5 758#endif
252b5132
RH
759
760/* Nonzero if errors are to be printed. */
761static int print_errors = 1;
762
763/* List of registers that are pre-defined:
764
765 Each general register has one predefined name of the form
766 %r<REGNUM> which has the value <REGNUM>.
767
768 Space and control registers are handled in a similar manner,
769 but use %sr<REGNUM> and %cr<REGNUM> as their predefined names.
770
771 Likewise for the floating point registers, but of the form
772 %fr<REGNUM>. Floating point registers have additional predefined
773 names with 'L' and 'R' suffixes (e.g. %fr19L, %fr19R) which
774 again have the value <REGNUM>.
775
776 Many registers also have synonyms:
777
778 %r26 - %r23 have %arg0 - %arg3 as synonyms
779 %r28 - %r29 have %ret0 - %ret1 as synonyms
780 %r30 has %sp as a synonym
781 %r27 has %dp as a synonym
782 %r2 has %rp as a synonym
783
784 Almost every control register has a synonym; they are not listed
785 here for brevity.
786
a28a3ccf 787 The table is sorted. Suitable for searching by a binary search. */
252b5132
RH
788
789static const struct pd_reg pre_defined_registers[] =
790{
ecacdc7a
AM
791 {"%arg0", 26},
792 {"%arg1", 25},
793 {"%arg2", 24},
794 {"%arg3", 23},
795 {"%cr0", 0},
796 {"%cr10", 10},
797 {"%cr11", 11},
798 {"%cr12", 12},
799 {"%cr13", 13},
800 {"%cr14", 14},
801 {"%cr15", 15},
802 {"%cr16", 16},
803 {"%cr17", 17},
804 {"%cr18", 18},
805 {"%cr19", 19},
806 {"%cr20", 20},
807 {"%cr21", 21},
808 {"%cr22", 22},
809 {"%cr23", 23},
810 {"%cr24", 24},
811 {"%cr25", 25},
812 {"%cr26", 26},
813 {"%cr27", 27},
814 {"%cr28", 28},
815 {"%cr29", 29},
816 {"%cr30", 30},
817 {"%cr31", 31},
818 {"%cr8", 8},
819 {"%cr9", 9},
820 {"%dp", 27},
821 {"%eiem", 15},
822 {"%eirr", 23},
823 {"%fr0", 0 + FP_REG_BASE},
824 {"%fr0l", 0 + FP_REG_BASE},
825 {"%fr0r", 0 + FP_REG_BASE + FP_REG_RSEL},
826 {"%fr1", 1 + FP_REG_BASE},
827 {"%fr10", 10 + FP_REG_BASE},
828 {"%fr10l", 10 + FP_REG_BASE},
829 {"%fr10r", 10 + FP_REG_BASE + FP_REG_RSEL},
830 {"%fr11", 11 + FP_REG_BASE},
831 {"%fr11l", 11 + FP_REG_BASE},
832 {"%fr11r", 11 + FP_REG_BASE + FP_REG_RSEL},
833 {"%fr12", 12 + FP_REG_BASE},
834 {"%fr12l", 12 + FP_REG_BASE},
835 {"%fr12r", 12 + FP_REG_BASE + FP_REG_RSEL},
836 {"%fr13", 13 + FP_REG_BASE},
837 {"%fr13l", 13 + FP_REG_BASE},
838 {"%fr13r", 13 + FP_REG_BASE + FP_REG_RSEL},
839 {"%fr14", 14 + FP_REG_BASE},
840 {"%fr14l", 14 + FP_REG_BASE},
841 {"%fr14r", 14 + FP_REG_BASE + FP_REG_RSEL},
842 {"%fr15", 15 + FP_REG_BASE},
843 {"%fr15l", 15 + FP_REG_BASE},
844 {"%fr15r", 15 + FP_REG_BASE + FP_REG_RSEL},
845 {"%fr16", 16 + FP_REG_BASE},
846 {"%fr16l", 16 + FP_REG_BASE},
847 {"%fr16r", 16 + FP_REG_BASE + FP_REG_RSEL},
848 {"%fr17", 17 + FP_REG_BASE},
849 {"%fr17l", 17 + FP_REG_BASE},
850 {"%fr17r", 17 + FP_REG_BASE + FP_REG_RSEL},
851 {"%fr18", 18 + FP_REG_BASE},
852 {"%fr18l", 18 + FP_REG_BASE},
853 {"%fr18r", 18 + FP_REG_BASE + FP_REG_RSEL},
854 {"%fr19", 19 + FP_REG_BASE},
855 {"%fr19l", 19 + FP_REG_BASE},
856 {"%fr19r", 19 + FP_REG_BASE + FP_REG_RSEL},
857 {"%fr1l", 1 + FP_REG_BASE},
858 {"%fr1r", 1 + FP_REG_BASE + FP_REG_RSEL},
859 {"%fr2", 2 + FP_REG_BASE},
860 {"%fr20", 20 + FP_REG_BASE},
861 {"%fr20l", 20 + FP_REG_BASE},
862 {"%fr20r", 20 + FP_REG_BASE + FP_REG_RSEL},
863 {"%fr21", 21 + FP_REG_BASE},
864 {"%fr21l", 21 + FP_REG_BASE},
865 {"%fr21r", 21 + FP_REG_BASE + FP_REG_RSEL},
866 {"%fr22", 22 + FP_REG_BASE},
867 {"%fr22l", 22 + FP_REG_BASE},
868 {"%fr22r", 22 + FP_REG_BASE + FP_REG_RSEL},
869 {"%fr23", 23 + FP_REG_BASE},
870 {"%fr23l", 23 + FP_REG_BASE},
871 {"%fr23r", 23 + FP_REG_BASE + FP_REG_RSEL},
872 {"%fr24", 24 + FP_REG_BASE},
873 {"%fr24l", 24 + FP_REG_BASE},
874 {"%fr24r", 24 + FP_REG_BASE + FP_REG_RSEL},
875 {"%fr25", 25 + FP_REG_BASE},
876 {"%fr25l", 25 + FP_REG_BASE},
877 {"%fr25r", 25 + FP_REG_BASE + FP_REG_RSEL},
878 {"%fr26", 26 + FP_REG_BASE},
879 {"%fr26l", 26 + FP_REG_BASE},
880 {"%fr26r", 26 + FP_REG_BASE + FP_REG_RSEL},
881 {"%fr27", 27 + FP_REG_BASE},
882 {"%fr27l", 27 + FP_REG_BASE},
883 {"%fr27r", 27 + FP_REG_BASE + FP_REG_RSEL},
884 {"%fr28", 28 + FP_REG_BASE},
885 {"%fr28l", 28 + FP_REG_BASE},
886 {"%fr28r", 28 + FP_REG_BASE + FP_REG_RSEL},
887 {"%fr29", 29 + FP_REG_BASE},
888 {"%fr29l", 29 + FP_REG_BASE},
889 {"%fr29r", 29 + FP_REG_BASE + FP_REG_RSEL},
890 {"%fr2l", 2 + FP_REG_BASE},
891 {"%fr2r", 2 + FP_REG_BASE + FP_REG_RSEL},
892 {"%fr3", 3 + FP_REG_BASE},
893 {"%fr30", 30 + FP_REG_BASE},
894 {"%fr30l", 30 + FP_REG_BASE},
895 {"%fr30r", 30 + FP_REG_BASE + FP_REG_RSEL},
896 {"%fr31", 31 + FP_REG_BASE},
897 {"%fr31l", 31 + FP_REG_BASE},
898 {"%fr31r", 31 + FP_REG_BASE + FP_REG_RSEL},
899 {"%fr3l", 3 + FP_REG_BASE},
900 {"%fr3r", 3 + FP_REG_BASE + FP_REG_RSEL},
901 {"%fr4", 4 + FP_REG_BASE},
902 {"%fr4l", 4 + FP_REG_BASE},
903 {"%fr4r", 4 + FP_REG_BASE + FP_REG_RSEL},
904 {"%fr5", 5 + FP_REG_BASE},
905 {"%fr5l", 5 + FP_REG_BASE},
906 {"%fr5r", 5 + FP_REG_BASE + FP_REG_RSEL},
907 {"%fr6", 6 + FP_REG_BASE},
908 {"%fr6l", 6 + FP_REG_BASE},
909 {"%fr6r", 6 + FP_REG_BASE + FP_REG_RSEL},
910 {"%fr7", 7 + FP_REG_BASE},
911 {"%fr7l", 7 + FP_REG_BASE},
912 {"%fr7r", 7 + FP_REG_BASE + FP_REG_RSEL},
913 {"%fr8", 8 + FP_REG_BASE},
914 {"%fr8l", 8 + FP_REG_BASE},
915 {"%fr8r", 8 + FP_REG_BASE + FP_REG_RSEL},
916 {"%fr9", 9 + FP_REG_BASE},
917 {"%fr9l", 9 + FP_REG_BASE},
918 {"%fr9r", 9 + FP_REG_BASE + FP_REG_RSEL},
919 {"%hta", 25},
920 {"%iir", 19},
921 {"%ior", 21},
922 {"%ipsw", 22},
923 {"%isr", 20},
924 {"%itmr", 16},
925 {"%iva", 14},
926 {"%pcoq", 18},
927 {"%pcsq", 17},
928 {"%pidr1", 8},
929 {"%pidr2", 9},
252b5132
RH
930 {"%pidr3", 12},
931 {"%pidr4", 13},
ecacdc7a
AM
932 {"%ppda", 24},
933 {"%r0", 0},
934 {"%r1", 1},
935 {"%r10", 10},
936 {"%r11", 11},
937 {"%r12", 12},
938 {"%r13", 13},
939 {"%r14", 14},
940 {"%r15", 15},
941 {"%r16", 16},
942 {"%r17", 17},
943 {"%r18", 18},
944 {"%r19", 19},
945 {"%r2", 2},
946 {"%r20", 20},
947 {"%r21", 21},
948 {"%r22", 22},
949 {"%r23", 23},
950 {"%r24", 24},
951 {"%r25", 25},
952 {"%r26", 26},
953 {"%r27", 27},
954 {"%r28", 28},
955 {"%r29", 29},
956 {"%r3", 3},
957 {"%r30", 30},
958 {"%r31", 31},
959 {"%r4", 4},
960 {"%r5", 5},
961 {"%r6", 6},
962 {"%r7", 7},
963 {"%r8", 8},
964 {"%r9", 9},
965 {"%rctr", 0},
966 {"%ret0", 28},
967 {"%ret1", 29},
968 {"%rp", 2},
969 {"%sar", 11},
970 {"%sp", 30},
971 {"%sr0", 0},
972 {"%sr1", 1},
973 {"%sr2", 2},
974 {"%sr3", 3},
975 {"%sr4", 4},
976 {"%sr5", 5},
977 {"%sr6", 6},
978 {"%sr7", 7},
979 {"%tr0", 24},
980 {"%tr1", 25},
981 {"%tr2", 26},
982 {"%tr3", 27},
983 {"%tr4", 28},
984 {"%tr5", 29},
985 {"%tr6", 30},
986 {"%tr7", 31}
252b5132
RH
987};
988
989/* This table is sorted by order of the length of the string. This is
990 so we check for <> before we check for <. If we had a <> and checked
991 for < first, we would get a false match. */
992static const struct fp_cond_map fp_cond_map[] =
993{
994 {"false?", 0},
995 {"false", 1},
996 {"true?", 30},
997 {"true", 31},
998 {"!<=>", 3},
999 {"!?>=", 8},
1000 {"!?<=", 16},
1001 {"!<>", 7},
1002 {"!>=", 11},
1003 {"!?>", 12},
1004 {"?<=", 14},
1005 {"!<=", 19},
1006 {"!?<", 20},
1007 {"?>=", 22},
1008 {"!?=", 24},
1009 {"!=t", 27},
1010 {"<=>", 29},
1011 {"=t", 5},
1012 {"?=", 6},
1013 {"?<", 10},
1014 {"<=", 13},
1015 {"!>", 15},
1016 {"?>", 18},
1017 {">=", 21},
1018 {"!<", 23},
1019 {"<>", 25},
1020 {"!=", 26},
1021 {"!?", 28},
1022 {"?", 2},
1023 {"=", 4},
1024 {"<", 9},
1025 {">", 17}
1026};
1027
1028static const struct selector_entry selector_table[] =
1029{
1030 {"f", e_fsel},
1031 {"l", e_lsel},
1032 {"ld", e_ldsel},
1033 {"lp", e_lpsel},
1034 {"lr", e_lrsel},
1035 {"ls", e_lssel},
1036 {"lt", e_ltsel},
39ba5561 1037 {"ltp", e_ltpsel},
252b5132
RH
1038 {"n", e_nsel},
1039 {"nl", e_nlsel},
1040 {"nlr", e_nlrsel},
1041 {"p", e_psel},
1042 {"r", e_rsel},
1043 {"rd", e_rdsel},
1044 {"rp", e_rpsel},
1045 {"rr", e_rrsel},
1046 {"rs", e_rssel},
1047 {"rt", e_rtsel},
39ba5561 1048 {"rtp", e_rtpsel},
252b5132
RH
1049 {"t", e_tsel},
1050};
1051
49863f82 1052#ifdef OBJ_SOM
252b5132
RH
1053/* default space and subspace dictionaries */
1054
1055#define GDB_SYMBOLS GDB_SYMBOLS_SUBSPACE_NAME
1056#define GDB_STRINGS GDB_STRINGS_SUBSPACE_NAME
1057
1058/* pre-defined subsegments (subspaces) for the HPPA. */
1059#define SUBSEG_CODE 0
1060#define SUBSEG_LIT 1
1061#define SUBSEG_MILLI 2
1062#define SUBSEG_DATA 0
1063#define SUBSEG_BSS 2
1064#define SUBSEG_UNWIND 3
1065#define SUBSEG_GDB_STRINGS 0
1066#define SUBSEG_GDB_SYMBOLS 1
1067
1068static struct default_subspace_dict pa_def_subspaces[] =
1069{
49863f82
JL
1070 {"$CODE$", 1, 1, 1, 0, 0, 0, 24, 0x2c, 0, 8, 0, 0, SUBSEG_CODE},
1071 {"$DATA$", 1, 1, 0, 0, 0, 0, 24, 0x1f, 1, 8, 1, 1, SUBSEG_DATA},
1072 {"$LIT$", 1, 1, 0, 0, 0, 0, 16, 0x2c, 0, 8, 0, 0, SUBSEG_LIT},
1073 {"$MILLICODE$", 1, 1, 0, 0, 0, 0, 8, 0x2c, 0, 8, 0, 0, SUBSEG_MILLI},
1074 {"$BSS$", 1, 1, 0, 0, 0, 1, 80, 0x1f, 1, 8, 1, 1, SUBSEG_BSS},
252b5132
RH
1075 {NULL, 0, 1, 0, 0, 0, 0, 255, 0x1f, 0, 4, 0, 0, 0}
1076};
1077
1078static struct default_space_dict pa_def_spaces[] =
1079{
49863f82
JL
1080 {"$TEXT$", 0, 1, 1, 0, 8, ASEC_NULL},
1081 {"$PRIVATE$", 1, 1, 1, 1, 16, ASEC_NULL},
1082 {NULL, 0, 0, 0, 0, 0, ASEC_NULL}
252b5132
RH
1083};
1084
1085/* Misc local definitions used by the assembler. */
1086
252b5132
RH
1087/* These macros are used to maintain spaces/subspaces. */
1088#define SPACE_DEFINED(space_chain) (space_chain)->sd_defined
1089#define SPACE_USER_DEFINED(space_chain) (space_chain)->sd_user_defined
1090#define SPACE_SPNUM(space_chain) (space_chain)->sd_spnum
1091#define SPACE_NAME(space_chain) (space_chain)->sd_name
1092
1093#define SUBSPACE_DEFINED(ss_chain) (ss_chain)->ssd_defined
1094#define SUBSPACE_NAME(ss_chain) (ss_chain)->ssd_name
49863f82
JL
1095#endif
1096
1097/* Return nonzero if the string pointed to by S potentially represents
1098 a right or left half of a FP register */
1099#define IS_R_SELECT(S) (*(S) == 'R' || *(S) == 'r')
1100#define IS_L_SELECT(S) (*(S) == 'L' || *(S) == 'l')
252b5132
RH
1101
1102/* Insert FIELD into OPCODE starting at bit START. Continue pa_ip
1103 main loop after insertion. */
1104
1105#define INSERT_FIELD_AND_CONTINUE(OPCODE, FIELD, START) \
1106 { \
1107 ((OPCODE) |= (FIELD) << (START)); \
1108 continue; \
1109 }
1110
1111/* Simple range checking for FIELD againt HIGH and LOW bounds.
1112 IGNORE is used to suppress the error message. */
1113
1114#define CHECK_FIELD(FIELD, HIGH, LOW, IGNORE) \
1115 { \
1116 if ((FIELD) > (HIGH) || (FIELD) < (LOW)) \
1117 { \
1118 if (! IGNORE) \
1119 as_bad (_("Field out of range [%d..%d] (%d)."), (LOW), (HIGH), \
1120 (int) (FIELD));\
1121 break; \
1122 } \
1123 }
1124
a02fab7e
JL
1125/* Simple alignment checking for FIELD againt ALIGN (a power of two).
1126 IGNORE is used to suppress the error message. */
1127
1128#define CHECK_ALIGN(FIELD, ALIGN, IGNORE) \
1129 { \
1130 if ((FIELD) & ((ALIGN) - 1)) \
1131 { \
1132 if (! IGNORE) \
1133 as_bad (_("Field not properly aligned [%d] (%d)."), (ALIGN), \
1134 (int) (FIELD));\
1135 break; \
1136 } \
1137 }
1138
252b5132
RH
1139#define is_DP_relative(exp) \
1140 ((exp).X_op == O_subtract \
a0f75b47 1141 && strcmp (S_GET_NAME ((exp).X_op_symbol), "$global$") == 0)
252b5132
RH
1142
1143#define is_PC_relative(exp) \
1144 ((exp).X_op == O_subtract \
a0f75b47 1145 && strcmp (S_GET_NAME ((exp).X_op_symbol), "$PIC_pcrel$0") == 0)
252b5132
RH
1146
1147/* We need some complex handling for stabs (sym1 - sym2). Luckily, we'll
1148 always be able to reduce the expression to a constant, so we don't
1149 need real complex handling yet. */
1150#define is_complex(exp) \
1151 ((exp).X_op != O_constant && (exp).X_op != O_symbol)
1152
1153/* Actual functions to implement the PA specific code for the assembler. */
1154
1155/* Called before writing the object file. Make sure entry/exit and
1156 proc/procend pairs match. */
1157
1158void
1159pa_check_eof ()
1160{
1161 if (within_entry_exit)
1162 as_fatal (_("Missing .exit\n"));
1163
1164 if (within_procedure)
1165 as_fatal (_("Missing .procend\n"));
1166}
1167
252b5132
RH
1168/* Returns a pointer to the label_symbol_struct for the current space.
1169 or NULL if no label_symbol_struct exists for the current space. */
1170
1171static label_symbol_struct *
1172pa_get_label ()
1173{
1174 label_symbol_struct *label_chain;
252b5132
RH
1175
1176 for (label_chain = label_symbols_rootp;
1177 label_chain;
1178 label_chain = label_chain->lss_next)
49863f82
JL
1179 {
1180#ifdef OBJ_SOM
1181 if (current_space == label_chain->lss_space && label_chain->lss_label)
1182 return label_chain;
1183#endif
1184#ifdef OBJ_ELF
1185 if (now_seg == label_chain->lss_segment && label_chain->lss_label)
252b5132 1186 return label_chain;
49863f82
JL
1187#endif
1188 }
252b5132
RH
1189
1190 return NULL;
1191}
1192
1193/* Defines a label for the current space. If one is already defined,
1194 this function will replace it with the new label. */
1195
1196void
1197pa_define_label (symbol)
1198 symbolS *symbol;
1199{
1200 label_symbol_struct *label_chain = pa_get_label ();
252b5132
RH
1201
1202 if (label_chain)
1203 label_chain->lss_label = symbol;
1204 else
1205 {
1206 /* Create a new label entry and add it to the head of the chain. */
1207 label_chain
1208 = (label_symbol_struct *) xmalloc (sizeof (label_symbol_struct));
1209 label_chain->lss_label = symbol;
49863f82
JL
1210#ifdef OBJ_SOM
1211 label_chain->lss_space = current_space;
1212#endif
1213#ifdef OBJ_ELF
1214 label_chain->lss_segment = now_seg;
1215#endif
252b5132
RH
1216 label_chain->lss_next = NULL;
1217
1218 if (label_symbols_rootp)
1219 label_chain->lss_next = label_symbols_rootp;
1220
1221 label_symbols_rootp = label_chain;
1222 }
1223}
1224
1225/* Removes a label definition for the current space.
1226 If there is no label_symbol_struct entry, then no action is taken. */
1227
1228static void
1229pa_undefine_label ()
1230{
1231 label_symbol_struct *label_chain;
1232 label_symbol_struct *prev_label_chain = NULL;
252b5132
RH
1233
1234 for (label_chain = label_symbols_rootp;
1235 label_chain;
1236 label_chain = label_chain->lss_next)
1237 {
49863f82
JL
1238 if (1
1239#ifdef OBJ_SOM
1240 && current_space == label_chain->lss_space && label_chain->lss_label
1241#endif
1242#ifdef OBJ_ELF
1243 && now_seg == label_chain->lss_segment && label_chain->lss_label
1244#endif
1245 )
252b5132
RH
1246 {
1247 /* Remove the label from the chain and free its memory. */
1248 if (prev_label_chain)
1249 prev_label_chain->lss_next = label_chain->lss_next;
1250 else
1251 label_symbols_rootp = label_chain->lss_next;
1252
1253 free (label_chain);
1254 break;
1255 }
1256 prev_label_chain = label_chain;
1257 }
1258}
1259
252b5132
RH
1260/* An HPPA-specific version of fix_new. This is required because the HPPA
1261 code needs to keep track of some extra stuff. Each call to fix_new_hppa
1262 results in the creation of an instance of an hppa_fix_struct. An
1263 hppa_fix_struct stores the extra information along with a pointer to the
1264 original fixS. This is attached to the original fixup via the
1265 tc_fix_data field. */
1266
1267static void
1268fix_new_hppa (frag, where, size, add_symbol, offset, exp, pcrel,
1269 r_type, r_field, r_format, arg_reloc, unwind_bits)
1270 fragS *frag;
1271 int where;
1272 int size;
1273 symbolS *add_symbol;
ad1079af 1274 offsetT offset;
252b5132
RH
1275 expressionS *exp;
1276 int pcrel;
1277 bfd_reloc_code_real_type r_type;
1278 enum hppa_reloc_field_selector_type_alt r_field;
1279 int r_format;
ad1079af 1280 unsigned int arg_reloc;
3f9b03b5 1281 int* unwind_bits ATTRIBUTE_UNUSED;
252b5132
RH
1282{
1283 fixS *new_fix;
1284
1285 struct hppa_fix_struct *hppa_fix = (struct hppa_fix_struct *)
1286 obstack_alloc (&notes, sizeof (struct hppa_fix_struct));
1287
1288 if (exp != NULL)
1289 new_fix = fix_new_exp (frag, where, size, exp, pcrel, r_type);
1290 else
1291 new_fix = fix_new (frag, where, size, add_symbol, offset, pcrel, r_type);
1292 new_fix->tc_fix_data = (void *) hppa_fix;
1293 hppa_fix->fx_r_type = r_type;
1294 hppa_fix->fx_r_field = r_field;
1295 hppa_fix->fx_r_format = r_format;
1296 hppa_fix->fx_arg_reloc = arg_reloc;
1297 hppa_fix->segment = now_seg;
1298#ifdef OBJ_SOM
1299 if (r_type == R_ENTRY || r_type == R_EXIT)
1300 new_fix->fx_offset = *unwind_bits;
1301#endif
1302
1303 /* foo-$global$ is used to access non-automatic storage. $global$
1304 is really just a marker and has served its purpose, so eliminate
904a31bf 1305 it now so as not to confuse write.c. Ditto for $PIC_pcrel$0. */
252b5132 1306 if (new_fix->fx_subsy
904a31bf
AM
1307 && (strcmp (S_GET_NAME (new_fix->fx_subsy), "$global$") == 0
1308 || strcmp (S_GET_NAME (new_fix->fx_subsy), "$PIC_pcrel$0") == 0))
252b5132
RH
1309 new_fix->fx_subsy = NULL;
1310}
1311
1312/* Parse a .byte, .word, .long expression for the HPPA. Called by
1313 cons via the TC_PARSE_CONS_EXPRESSION macro. */
1314
1315void
1316parse_cons_expression_hppa (exp)
1317 expressionS *exp;
1318{
1319 hppa_field_selector = pa_chk_field_selector (&input_line_pointer);
1320 expression (exp);
1321}
1322
1323/* This fix_new is called by cons via TC_CONS_FIX_NEW.
1324 hppa_field_selector is set by the parse_cons_expression_hppa. */
1325
1326void
1327cons_fix_new_hppa (frag, where, size, exp)
1328 fragS *frag;
1329 int where;
1330 int size;
1331 expressionS *exp;
1332{
1333 unsigned int rel_type;
1334
1335 /* Get a base relocation type. */
1336 if (is_DP_relative (*exp))
1337 rel_type = R_HPPA_GOTOFF;
1338 else if (is_complex (*exp))
1339 rel_type = R_HPPA_COMPLEX;
1340 else
1341 rel_type = R_HPPA;
1342
1343 if (hppa_field_selector != e_psel && hppa_field_selector != e_fsel)
ad1079af
AM
1344 {
1345 as_warn (_("Invalid field selector. Assuming F%%."));
1346 hppa_field_selector = e_fsel;
1347 }
252b5132
RH
1348
1349 fix_new_hppa (frag, where, size,
1350 (symbolS *) NULL, (offsetT) 0, exp, 0, rel_type,
077db52a 1351 hppa_field_selector, size * 8, 0, NULL);
252b5132
RH
1352
1353 /* Reset field selector to its default state. */
1354 hppa_field_selector = 0;
1355}
1356
1357/* This function is called once, at assembler startup time. It should
1358 set up all the tables, etc. that the MD part of the assembler will need. */
1359
1360void
1361md_begin ()
1362{
1363 const char *retval = NULL;
1364 int lose = 0;
1365 unsigned int i = 0;
1366
1367 last_call_info = NULL;
1368 call_info_root = NULL;
1369
1370 /* Set the default machine type. */
1371 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, 10))
1372 as_warn (_("could not set architecture and machine"));
1373
1374 /* Folding of text and data segments fails miserably on the PA.
1375 Warn user and disable "-R" option. */
1376 if (flag_readonly_data_in_text)
1377 {
1378 as_warn (_("-R option not supported on this target."));
1379 flag_readonly_data_in_text = 0;
1380 }
1381
49863f82 1382#ifdef OBJ_SOM
252b5132 1383 pa_spaces_begin ();
49863f82 1384#endif
252b5132
RH
1385
1386 op_hash = hash_new ();
1387
1388 while (i < NUMOPCODES)
1389 {
1390 const char *name = pa_opcodes[i].name;
1391 retval = hash_insert (op_hash, name, (struct pa_opcode *) &pa_opcodes[i]);
1392 if (retval != NULL && *retval != '\0')
1393 {
1394 as_fatal (_("Internal error: can't hash `%s': %s\n"), name, retval);
1395 lose = 1;
1396 }
1397 do
1398 {
1399 if ((pa_opcodes[i].match & pa_opcodes[i].mask)
1400 != pa_opcodes[i].match)
1401 {
1402 fprintf (stderr, _("internal error: losing opcode: `%s' \"%s\"\n"),
1403 pa_opcodes[i].name, pa_opcodes[i].args);
1404 lose = 1;
1405 }
1406 ++i;
1407 }
1408 while (i < NUMOPCODES && !strcmp (pa_opcodes[i].name, name));
1409 }
1410
1411 if (lose)
1412 as_fatal (_("Broken assembler. No assembly attempted."));
1413
49863f82 1414#ifdef OBJ_SOM
252b5132
RH
1415 /* SOM will change text_section. To make sure we never put
1416 anything into the old one switch to the new one now. */
1417 subseg_set (text_section, 0);
49863f82 1418#endif
252b5132 1419
993142d5 1420#ifdef OBJ_SOM
252b5132
RH
1421 dummy_symbol = symbol_find_or_make ("L$dummy");
1422 S_SET_SEGMENT (dummy_symbol, text_section);
a28a3ccf 1423 /* Force the symbol to be converted to a real symbol. */
d53d2751 1424 (void) symbol_get_bfdsym (dummy_symbol);
993142d5 1425#endif
252b5132
RH
1426}
1427
1428/* Assemble a single instruction storing it into a frag. */
1429void
1430md_assemble (str)
1431 char *str;
1432{
1433 char *to;
1434
1435 /* The had better be something to assemble. */
1436 assert (str);
1437
1438 /* If we are within a procedure definition, make sure we've
1439 defined a label for the procedure; handle case where the
1440 label was defined after the .PROC directive.
1441
1442 Note there's not need to diddle with the segment or fragment
1443 for the label symbol in this case. We have already switched
1444 into the new $CODE$ subspace at this point. */
1445 if (within_procedure && last_call_info->start_symbol == NULL)
1446 {
1447 label_symbol_struct *label_symbol = pa_get_label ();
1448
1449 if (label_symbol)
1450 {
1451 if (label_symbol->lss_label)
1452 {
1453 last_call_info->start_symbol = label_symbol->lss_label;
a0f75b47
ILT
1454 symbol_get_bfdsym (label_symbol->lss_label)->flags
1455 |= BSF_FUNCTION;
252b5132
RH
1456#ifdef OBJ_SOM
1457 /* Also handle allocation of a fixup to hold the unwind
1458 information when the label appears after the proc/procend. */
1459 if (within_entry_exit)
1460 {
1461 char *where = frag_more (0);
1462
1463 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
1464 NULL, (offsetT) 0, NULL,
1465 0, R_HPPA_ENTRY, e_fsel, 0, 0,
1466 (int *)&last_call_info->ci_unwind.descriptor);
1467 }
1468#endif
1469 }
1470 else
1471 as_bad (_("Missing function name for .PROC (corrupted label chain)"));
1472 }
1473 else
1474 as_bad (_("Missing function name for .PROC"));
1475 }
1476
1477 /* Assemble the instruction. Results are saved into "the_insn". */
1478 pa_ip (str);
1479
1480 /* Get somewhere to put the assembled instrution. */
1481 to = frag_more (4);
1482
a28a3ccf 1483 /* Output the opcode. */
252b5132
RH
1484 md_number_to_chars (to, the_insn.opcode, 4);
1485
1486 /* If necessary output more stuff. */
1487 if (the_insn.reloc != R_HPPA_NONE)
1488 fix_new_hppa (frag_now, (to - frag_now->fr_literal), 4, NULL,
1489 (offsetT) 0, &the_insn.exp, the_insn.pcrel,
1490 the_insn.reloc, the_insn.field_selector,
1491 the_insn.format, the_insn.arg_reloc, NULL);
2d93dcc4
JL
1492
1493#ifdef OBJ_ELF
1494 if (debug_type == DEBUG_DWARF2)
85a39694 1495 dwarf2_generate_asm_lineno (4);
b52c78b8 1496#endif
252b5132
RH
1497}
1498
1499/* Do the real work for assembling a single instruction. Store results
1500 into the global "the_insn" variable. */
1501
1502static void
1503pa_ip (str)
1504 char *str;
1505{
1506 char *error_message = "";
1507 char *s, c, *argstart, *name, *save_s;
1508 const char *args;
1509 int match = FALSE;
1510 int comma = 0;
1511 int cmpltr, nullif, flag, cond, num;
1512 unsigned long opcode;
1513 struct pa_opcode *insn;
1514
49863f82 1515#ifdef OBJ_SOM
252b5132
RH
1516 /* We must have a valid space and subspace. */
1517 pa_check_current_space_and_subspace ();
49863f82 1518#endif
252b5132 1519
b1c5e0ee
JL
1520 /* Convert everything up to the first whitespace character into lower
1521 case. */
1522 for (s = str; *s != ' ' && *s != '\t' && *s != '\n' && *s != '\0'; s++)
1523 if (isupper (*s))
1524 *s = tolower (*s);
1525
252b5132
RH
1526 /* Skip to something interesting. */
1527 for (s = str; isupper (*s) || islower (*s) || (*s >= '0' && *s <= '3'); ++s)
1528 ;
1529
1530 switch (*s)
1531 {
1532
1533 case '\0':
1534 break;
1535
1536 case ',':
1537 comma = 1;
1538
1539 /*FALLTHROUGH */
1540
1541 case ' ':
1542 *s++ = '\0';
1543 break;
1544
1545 default:
1546 as_fatal (_("Unknown opcode: `%s'"), str);
1547 }
1548
1549 save_s = str;
1550
252b5132
RH
1551 /* Look up the opcode in the has table. */
1552 if ((insn = (struct pa_opcode *) hash_find (op_hash, str)) == NULL)
1553 {
1554 as_bad ("Unknown opcode: `%s'", str);
1555 return;
1556 }
1557
1558 if (comma)
1559 {
1560 *--s = ',';
1561 }
1562
1563 /* Mark the location where arguments for the instruction start, then
1564 start processing them. */
1565 argstart = s;
1566 for (;;)
1567 {
1568 /* Do some initialization. */
1569 opcode = insn->match;
0f4f8b56 1570 strict = (insn->flags & FLAG_STRICT);
252b5132
RH
1571 memset (&the_insn, 0, sizeof (the_insn));
1572
1573 the_insn.reloc = R_HPPA_NONE;
1574
1575 /* If this instruction is specific to a particular architecture,
1576 then set a new architecture. */
1577 /* But do not automatically promote to pa2.0. The automatic promotion
1578 crud is for compatability with HP's old assemblers only. */
1579 if (insn->arch < 20
1580 && bfd_get_mach (stdoutput) < insn->arch)
1581 {
1582 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, insn->arch))
1583 as_warn (_("could not update architecture and machine"));
1584 }
1585 else if (bfd_get_mach (stdoutput) < insn->arch)
1586 {
1587 match = FALSE;
1588 goto failed;
1589 }
1590
1591 /* Build the opcode, checking as we go to make
1592 sure that the operands match. */
1593 for (args = insn->args;; ++args)
1594 {
680ef6de
JL
1595 /* Absorb white space in instruction. */
1596 while (*s == ' ' || *s == '\t')
1597 s++;
1598
252b5132
RH
1599 switch (*args)
1600 {
1601
1602 /* End of arguments. */
1603 case '\0':
1604 if (*s == '\0')
1605 match = TRUE;
1606 break;
1607
1608 case '+':
1609 if (*s == '+')
1610 {
1611 ++s;
1612 continue;
1613 }
1614 if (*s == '-')
1615 continue;
1616 break;
1617
1618 /* These must match exactly. */
1619 case '(':
1620 case ')':
1621 case ',':
1622 case ' ':
1623 if (*s++ == *args)
1624 continue;
1625 break;
1626
1627 /* Handle a 5 bit register or control register field at 10. */
1628 case 'b':
1629 case '^':
ecacdc7a 1630 if (!pa_parse_number (&s, 0))
0f4f8b56 1631 break;
ecacdc7a 1632 num = pa_number;
252b5132
RH
1633 CHECK_FIELD (num, 31, 0, 0);
1634 INSERT_FIELD_AND_CONTINUE (opcode, num, 21);
1635
a97685e9
JL
1636 /* Handle %sar or %cr11. No bits get set, we just verify that it
1637 is there. */
1638 case '!':
1639 /* Skip whitespace before register. */
1640 while (*s == ' ' || *s == '\t')
1641 s = s + 1;
1642
1643 if (!strncasecmp(s, "%sar", 4))
1644 {
1645 s += 4;
1646 continue;
1647 }
1648 else if (!strncasecmp(s, "%cr11", 5))
1649 {
1650 s += 5;
1651 continue;
1652 }
1653 break;
1654
252b5132
RH
1655 /* Handle a 5 bit register field at 15. */
1656 case 'x':
ecacdc7a 1657 if (!pa_parse_number (&s, 0))
0f4f8b56 1658 break;
ecacdc7a 1659 num = pa_number;
252b5132
RH
1660 CHECK_FIELD (num, 31, 0, 0);
1661 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
1662
1663 /* Handle a 5 bit register field at 31. */
252b5132 1664 case 't':
ecacdc7a 1665 if (!pa_parse_number (&s, 0))
0f4f8b56 1666 break;
ecacdc7a 1667 num = pa_number;
252b5132
RH
1668 CHECK_FIELD (num, 31, 0, 0);
1669 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
1670
413c94ba
JL
1671 /* Handle a 5 bit register field at 10 and 15. */
1672 case 'a':
ecacdc7a 1673 if (!pa_parse_number (&s, 0))
0f4f8b56 1674 break;
ecacdc7a 1675 num = pa_number;
413c94ba
JL
1676 CHECK_FIELD (num, 31, 0, 0);
1677 opcode |= num << 16;
1678 INSERT_FIELD_AND_CONTINUE (opcode, num, 21);
1679
252b5132
RH
1680 /* Handle a 5 bit field length at 31. */
1681 case 'T':
1682 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1683 if (strict && the_insn.exp.X_op != O_constant)
1684 break;
252b5132
RH
1685 s = expr_end;
1686 CHECK_FIELD (num, 32, 1, 0);
1687 INSERT_FIELD_AND_CONTINUE (opcode, 32 - num, 0);
1688
1689 /* Handle a 5 bit immediate at 15. */
1690 case '5':
1691 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1692 if (strict && the_insn.exp.X_op != O_constant)
1693 break;
252b5132 1694 s = expr_end;
0f4f8b56
JL
1695 /* When in strict mode, we want to just reject this
1696 match instead of giving an out of range error. */
1697 CHECK_FIELD (num, 15, -16, strict);
3f9b03b5 1698 num = low_sign_unext (num, 5);
252b5132
RH
1699 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
1700
1701 /* Handle a 5 bit immediate at 31. */
1702 case 'V':
1703 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1704 if (strict && the_insn.exp.X_op != O_constant)
1705 break;
252b5132 1706 s = expr_end;
0f4f8b56
JL
1707 /* When in strict mode, we want to just reject this
1708 match instead of giving an out of range error. */
ad1079af 1709 CHECK_FIELD (num, 15, -16, strict);
3f9b03b5 1710 num = low_sign_unext (num, 5);
252b5132
RH
1711 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
1712
1713 /* Handle an unsigned 5 bit immediate at 31. */
1714 case 'r':
1715 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1716 if (strict && the_insn.exp.X_op != O_constant)
1717 break;
252b5132 1718 s = expr_end;
ad1079af
AM
1719 CHECK_FIELD (num, 31, 0, strict);
1720 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
252b5132
RH
1721
1722 /* Handle an unsigned 5 bit immediate at 15. */
1723 case 'R':
1724 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1725 if (strict && the_insn.exp.X_op != O_constant)
1726 break;
252b5132 1727 s = expr_end;
0f4f8b56 1728 CHECK_FIELD (num, 31, 0, strict);
252b5132
RH
1729 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
1730
680ef6de
JL
1731 /* Handle an unsigned 10 bit immediate at 15. */
1732 case 'U':
1733 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
1734 if (strict && the_insn.exp.X_op != O_constant)
1735 break;
680ef6de 1736 s = expr_end;
0f4f8b56 1737 CHECK_FIELD (num, 1023, 0, strict);
680ef6de
JL
1738 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
1739
252b5132
RH
1740 /* Handle a 2 bit space identifier at 17. */
1741 case 's':
ecacdc7a 1742 if (!pa_parse_number (&s, 0))
0f4f8b56 1743 break;
ecacdc7a 1744 num = pa_number;
252b5132
RH
1745 CHECK_FIELD (num, 3, 0, 1);
1746 INSERT_FIELD_AND_CONTINUE (opcode, num, 14);
1747
1748 /* Handle a 3 bit space identifier at 18. */
1749 case 'S':
ecacdc7a 1750 if (!pa_parse_number (&s, 0))
0f4f8b56 1751 break;
ecacdc7a 1752 num = pa_number;
252b5132 1753 CHECK_FIELD (num, 7, 0, 1);
ad1079af 1754 opcode |= re_assemble_3 (num);
3f9b03b5 1755 continue;
252b5132 1756
28252e61 1757 /* Handle all completers. */
252b5132 1758 case 'c':
28252e61
JL
1759 switch (*++args)
1760 {
1761
1762 /* Handle a completer for an indexing load or store. */
1763 case 'x':
252b5132 1764 {
28252e61
JL
1765 int uu = 0;
1766 int m = 0;
1767 int i = 0;
1768 while (*s == ',' && i < 2)
252b5132 1769 {
28252e61
JL
1770 s++;
1771 if (strncasecmp (s, "sm", 2) == 0)
1772 {
1773 uu = 1;
1774 m = 1;
1775 s++;
1776 i++;
1777 }
1778 else if (strncasecmp (s, "m", 1) == 0)
1779 m = 1;
d53d2751
JL
1780 else if ((strncasecmp (s, "s ", 2) == 0)
1781 || (strncasecmp (s, "s,", 2) == 0))
28252e61 1782 uu = 1;
0f4f8b56
JL
1783 /* When in strict mode this is a match failure. */
1784 else if (strict)
d53d2751
JL
1785 {
1786 s--;
1787 break;
1788 }
28252e61
JL
1789 else
1790 as_bad (_("Invalid Indexed Load Completer."));
252b5132
RH
1791 s++;
1792 i++;
1793 }
28252e61
JL
1794 if (i > 2)
1795 as_bad (_("Invalid Indexed Load Completer Syntax."));
1796 opcode |= m << 5;
1797 INSERT_FIELD_AND_CONTINUE (opcode, uu, 13);
252b5132 1798 }
252b5132 1799
28252e61
JL
1800 /* Handle a short load/store completer. */
1801 case 'm':
61dd1d31 1802 case 'q':
71823da4 1803 case 'J':
d53d2751 1804 case 'e':
252b5132 1805 {
28252e61
JL
1806 int a = 0;
1807 int m = 0;
1808 if (*s == ',')
252b5132 1809 {
d53d2751 1810 int found = 0;
28252e61
JL
1811 s++;
1812 if (strncasecmp (s, "ma", 2) == 0)
1813 {
1814 a = 0;
1815 m = 1;
d53d2751 1816 found = 1;
28252e61
JL
1817 }
1818 else if (strncasecmp (s, "mb", 2) == 0)
1819 {
1820 a = 1;
1821 m = 1;
d53d2751 1822 found = 1;
28252e61 1823 }
d53d2751
JL
1824
1825 /* When in strict mode, pass through for cache op. */
1826 if (!found && strict)
1827 s--;
28252e61 1828 else
d53d2751
JL
1829 {
1830 if (!found)
1831 as_bad (_("Invalid Short Load/Store Completer."));
1832 s += 2;
1833 }
252b5132 1834 }
65fab780 1835 /* If we did not get a ma/mb completer, then we do not
d53d2751
JL
1836 consider this a positive match for 'ce'. */
1837 else if (*args == 'e')
65fab780 1838 break;
252b5132 1839
71823da4
JL
1840 /* 'J', 'm' and 'q' are the same, except for where they
1841 encode the before/after field. */
61dd1d31
JL
1842 if (*args == 'm')
1843 {
1844 opcode |= m << 5;
1845 INSERT_FIELD_AND_CONTINUE (opcode, a, 13);
1846 }
1847 else if (*args == 'q')
1848 {
1849 opcode |= m << 3;
1850 INSERT_FIELD_AND_CONTINUE (opcode, a, 2);
1851 }
71823da4
JL
1852 else if (*args == 'J')
1853 {
1854 /* M bit is explicit in the major opcode. */
1855 INSERT_FIELD_AND_CONTINUE (opcode, a, 2);
1856 }
d53d2751 1857 else if (*args == 'e')
65fab780
JL
1858 {
1859 /* Gross! Hide these values in the immediate field
1860 of the instruction, then pull them out later. */
1861 opcode |= m << 8;
1862 opcode |= a << 9;
1863 continue;
1864 }
252b5132 1865 }
252b5132 1866
28252e61
JL
1867 /* Handle a stbys completer. */
1868 case 's':
252b5132 1869 {
28252e61
JL
1870 int a = 0;
1871 int m = 0;
1872 int i = 0;
1873 while (*s == ',' && i < 2)
1874 {
1875 s++;
1876 if (strncasecmp (s, "m", 1) == 0)
1877 m = 1;
d53d2751
JL
1878 else if ((strncasecmp (s, "b ", 2) == 0)
1879 || (strncasecmp (s, "b,", 2) == 0))
28252e61
JL
1880 a = 0;
1881 else if (strncasecmp (s, "e", 1) == 0)
1882 a = 1;
0f4f8b56
JL
1883 /* When in strict mode this is a match failure. */
1884 else if (strict)
d53d2751
JL
1885 {
1886 s--;
1887 break;
1888 }
28252e61
JL
1889 else
1890 as_bad (_("Invalid Store Bytes Short Completer"));
1891 s++;
1892 i++;
1893 }
1894 if (i > 2)
252b5132 1895 as_bad (_("Invalid Store Bytes Short Completer"));
28252e61
JL
1896 opcode |= m << 5;
1897 INSERT_FIELD_AND_CONTINUE (opcode, a, 13);
252b5132 1898 }
28252e61 1899
d53d2751
JL
1900 /* Handle load cache hint completer. */
1901 case 'c':
1902 cmpltr = 0;
1903 if (!strncmp(s, ",sl", 3))
1904 {
1905 s += 3;
1906 cmpltr = 2;
1907 }
1908 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 10);
1909
1910 /* Handle store cache hint completer. */
1911 case 'C':
1912 cmpltr = 0;
1913 if (!strncmp(s, ",sl", 3))
1914 {
1915 s += 3;
1916 cmpltr = 2;
1917 }
1918 else if (!strncmp(s, ",bc", 3))
1919 {
1920 s += 3;
1921 cmpltr = 1;
1922 }
1923 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 10);
1924
1925 /* Handle load and clear cache hint completer. */
1926 case 'd':
1927 cmpltr = 0;
1928 if (!strncmp(s, ",co", 3))
1929 {
1930 s += 3;
1931 cmpltr = 1;
1932 }
1933 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 10);
1934
a28a3ccf 1935 /* Handle load ordering completer. */
d53d2751
JL
1936 case 'o':
1937 if (strncmp(s, ",o", 2) != 0)
1938 break;
1939 s += 2;
1940 continue;
1941
ce674324
JL
1942 /* Handle a branch gate completer. */
1943 case 'g':
1944 if (strncasecmp (s, ",gate", 5) != 0)
1945 break;
1946 s += 5;
1947 continue;
1948
1949 /* Handle a branch link and push completer. */
1950 case 'p':
1951 if (strncasecmp (s, ",l,push", 7) != 0)
1952 break;
1953 s += 7;
1954 continue;
1955
1956 /* Handle a branch link completer. */
1957 case 'l':
1958 if (strncasecmp (s, ",l", 2) != 0)
1959 break;
1960 s += 2;
1961 continue;
1962
1963 /* Handle a branch pop completer. */
1964 case 'P':
1965 if (strncasecmp (s, ",pop", 4) != 0)
1966 break;
1967 s += 4;
1968 continue;
1969
680ef6de
JL
1970 /* Handle a local processor completer. */
1971 case 'L':
1972 if (strncasecmp (s, ",l", 2) != 0)
1973 break;
1974 s += 2;
1975 continue;
1976
1977 /* Handle a PROBE read/write completer. */
1978 case 'w':
1979 flag = 0;
1980 if (!strncasecmp (s, ",w", 2))
1981 {
1982 flag = 1;
1983 s += 2;
1984 }
1985 else if (!strncasecmp (s, ",r", 2))
1986 {
1987 flag = 0;
1988 s += 2;
1989 }
1990
1991 INSERT_FIELD_AND_CONTINUE (opcode, flag, 6);
1992
1993 /* Handle MFCTL wide completer. */
d53d2751 1994 case 'W':
680ef6de
JL
1995 if (strncasecmp (s, ",w", 2) != 0)
1996 break;
1997 s += 2;
1998 continue;
1999
2000 /* Handle an RFI restore completer. */
2001 case 'r':
2002 flag = 0;
2003 if (!strncasecmp (s, ",r", 2))
2004 {
2005 flag = 5;
2006 s += 2;
2007 }
2008
2009 INSERT_FIELD_AND_CONTINUE (opcode, flag, 5);
2010
28252e61
JL
2011 /* Handle a system control completer. */
2012 case 'Z':
2013 if (*s == ',' && (*(s + 1) == 'm' || *(s + 1) == 'M'))
2014 {
2015 flag = 1;
2016 s += 2;
2017 }
2018 else
2019 flag = 0;
2020
2021 INSERT_FIELD_AND_CONTINUE (opcode, flag, 5);
2022
680ef6de
JL
2023 /* Handle intermediate/final completer for DCOR. */
2024 case 'i':
2025 flag = 0;
2026 if (!strncasecmp (s, ",i", 2))
2027 {
2028 flag = 1;
2029 s += 2;
2030 }
2031
2032 INSERT_FIELD_AND_CONTINUE (opcode, flag, 6);
2033
9e4f2d3a
JL
2034 /* Handle zero/sign extension completer. */
2035 case 'z':
2036 flag = 1;
2037 if (!strncasecmp (s, ",z", 2))
2038 {
2039 flag = 0;
2040 s += 2;
2041 }
2042
2043 INSERT_FIELD_AND_CONTINUE (opcode, flag, 10);
2044
680ef6de
JL
2045 /* Handle add completer. */
2046 case 'a':
2047 flag = 1;
2048 if (!strncasecmp (s, ",l", 2))
2049 {
2050 flag = 2;
2051 s += 2;
2052 }
2053 else if (!strncasecmp (s, ",tsv", 4))
2054 {
2055 flag = 3;
2056 s += 4;
2057 }
d53d2751 2058
680ef6de
JL
2059 INSERT_FIELD_AND_CONTINUE (opcode, flag, 10);
2060
2061 /* Handle 64 bit carry for ADD. */
2062 case 'Y':
2063 flag = 0;
2064 if (!strncasecmp (s, ",dc,tsv", 7) ||
2065 !strncasecmp (s, ",tsv,dc", 7))
2066 {
2067 flag = 1;
2068 s += 7;
2069 }
2070 else if (!strncasecmp (s, ",dc", 3))
2071 {
2072 flag = 0;
2073 s += 3;
2074 }
2075 else
2076 break;
2077
2078 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2079
2080 /* Handle 32 bit carry for ADD. */
2081 case 'y':
2082 flag = 0;
2083 if (!strncasecmp (s, ",c,tsv", 6) ||
2084 !strncasecmp (s, ",tsv,c", 6))
2085 {
2086 flag = 1;
2087 s += 6;
2088 }
2089 else if (!strncasecmp (s, ",c", 2))
2090 {
2091 flag = 0;
2092 s += 2;
2093 }
2094 else
2095 break;
2096
2097 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2098
2099 /* Handle trap on signed overflow. */
2100 case 'v':
2101 flag = 0;
2102 if (!strncasecmp (s, ",tsv", 4))
2103 {
2104 flag = 1;
2105 s += 4;
2106 }
2107
2108 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2109
2110 /* Handle trap on condition and overflow. */
2111 case 't':
2112 flag = 0;
2113 if (!strncasecmp (s, ",tc,tsv", 7) ||
2114 !strncasecmp (s, ",tsv,tc", 7))
2115 {
2116 flag = 1;
2117 s += 7;
2118 }
2119 else if (!strncasecmp (s, ",tc", 3))
2120 {
2121 flag = 0;
2122 s += 3;
2123 }
2124 else
2125 break;
2126
2127 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2128
2129 /* Handle 64 bit borrow for SUB. */
2130 case 'B':
2131 flag = 0;
2132 if (!strncasecmp (s, ",db,tsv", 7) ||
2133 !strncasecmp (s, ",tsv,db", 7))
2134 {
2135 flag = 1;
2136 s += 7;
2137 }
2138 else if (!strncasecmp (s, ",db", 3))
2139 {
2140 flag = 0;
2141 s += 3;
2142 }
2143 else
2144 break;
2145
2146 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2147
2148 /* Handle 32 bit borrow for SUB. */
2149 case 'b':
2150 flag = 0;
2151 if (!strncasecmp (s, ",b,tsv", 6) ||
2152 !strncasecmp (s, ",tsv,b", 6))
2153 {
2154 flag = 1;
2155 s += 6;
2156 }
2157 else if (!strncasecmp (s, ",b", 2))
2158 {
2159 flag = 0;
2160 s += 2;
2161 }
2162 else
2163 break;
2164
2165 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
2166
2167 /* Handle trap condition completer for UADDCM. */
2168 case 'T':
2169 flag = 0;
2170 if (!strncasecmp (s, ",tc", 3))
2171 {
2172 flag = 1;
2173 s += 3;
2174 }
2175
2176 INSERT_FIELD_AND_CONTINUE (opcode, flag, 6);
2177
413c94ba
JL
2178 /* Handle signed/unsigned at 21. */
2179 case 'S':
2180 {
2181 int sign = 1;
2182 if (strncasecmp (s, ",s", 2) == 0)
2183 {
2184 sign = 1;
2185 s += 2;
2186 }
2187 else if (strncasecmp (s, ",u", 2) == 0)
2188 {
2189 sign = 0;
2190 s += 2;
2191 }
2192
2193 INSERT_FIELD_AND_CONTINUE (opcode, sign, 10);
2194 }
2195
2196 /* Handle left/right combination at 17:18. */
2197 case 'h':
2198 if (*s++ == ',')
2199 {
2200 int lr = 0;
2201 if (*s == 'r')
2202 lr = 2;
2203 else if (*s == 'l')
2204 lr = 0;
2205 else
2206 as_bad(_("Invalid left/right combination completer"));
2207
2208 s++;
2209 INSERT_FIELD_AND_CONTINUE (opcode, lr, 13);
2210 }
2211 else
2212 as_bad(_("Invalid left/right combination completer"));
2213 break;
2214
2215 /* Handle saturation at 24:25. */
2216 case 'H':
2217 {
2218 int sat = 3;
2219 if (strncasecmp (s, ",ss", 3) == 0)
2220 {
2221 sat = 1;
2222 s += 3;
2223 }
2224 else if (strncasecmp (s, ",us", 3) == 0)
2225 {
2226 sat = 0;
2227 s += 3;
2228 }
2229
2230 INSERT_FIELD_AND_CONTINUE (opcode, sat, 6);
2231 }
2232
2233 /* Handle permutation completer. */
2234 case '*':
2235 if (*s++ == ',')
2236 {
b1039fc4 2237 int permloc[4];
413c94ba
JL
2238 int perm = 0;
2239 int i = 0;
b1039fc4
JL
2240 permloc[0] = 13;
2241 permloc[1] = 10;
2242 permloc[2] = 8;
2243 permloc[3] = 6;
413c94ba
JL
2244 for (; i < 4; i++)
2245 {
2246 switch (*s++)
2247 {
2248 case '0':
2249 perm = 0;
2250 break;
2251 case '1':
2252 perm = 1;
2253 break;
2254 case '2':
2255 perm = 2;
2256 break;
2257 case '3':
2258 perm = 3;
2259 break;
2260 default:
2261 as_bad(_("Invalid permutation completer"));
2262 }
2263 opcode |= perm << permloc[i];
2264 }
2265 continue;
2266 }
2267 else
2268 as_bad(_("Invalid permutation completer"));
2269 break;
2270
28252e61
JL
2271 default:
2272 abort ();
2273 }
2274 break;
252b5132 2275
55a914bc 2276 /* Handle all conditions. */
252b5132 2277 case '?':
55a914bc
JL
2278 {
2279 args++;
2280 switch (*args)
2281 {
2282 /* Handle FP compare conditions. */
2283 case 'f':
2284 cond = pa_parse_fp_cmp_cond (&s);
2285 INSERT_FIELD_AND_CONTINUE (opcode, cond, 0);
2286
2287 /* Handle an add condition. */
9a913dfb 2288 case 'A':
55a914bc
JL
2289 case 'a':
2290 cmpltr = 0;
2291 flag = 0;
2292 if (*s == ',')
2293 {
2294 s++;
9a913dfb
JL
2295
2296 /* 64 bit conditions. */
2297 if (*args == 'A')
2298 {
2299 if (*s == '*')
2300 s++;
2301 else
2302 break;
2303 }
17d9105c
JL
2304 else if (*s == '*')
2305 break;
55a914bc 2306 name = s;
9a913dfb 2307
680ef6de 2308 name = s;
55a914bc
JL
2309 while (*s != ',' && *s != ' ' && *s != '\t')
2310 s += 1;
2311 c = *s;
2312 *s = 0x00;
2313 if (strcmp (name, "=") == 0)
2314 cmpltr = 1;
2315 else if (strcmp (name, "<") == 0)
2316 cmpltr = 2;
2317 else if (strcmp (name, "<=") == 0)
2318 cmpltr = 3;
2319 else if (strcasecmp (name, "nuv") == 0)
2320 cmpltr = 4;
2321 else if (strcasecmp (name, "znv") == 0)
2322 cmpltr = 5;
2323 else if (strcasecmp (name, "sv") == 0)
2324 cmpltr = 6;
2325 else if (strcasecmp (name, "od") == 0)
2326 cmpltr = 7;
2327 else if (strcasecmp (name, "tr") == 0)
2328 {
2329 cmpltr = 0;
2330 flag = 1;
2331 }
2332 else if (strcmp (name, "<>") == 0)
2333 {
2334 cmpltr = 1;
2335 flag = 1;
2336 }
2337 else if (strcmp (name, ">=") == 0)
2338 {
2339 cmpltr = 2;
2340 flag = 1;
2341 }
2342 else if (strcmp (name, ">") == 0)
2343 {
2344 cmpltr = 3;
2345 flag = 1;
2346 }
2347 else if (strcasecmp (name, "uv") == 0)
2348 {
2349 cmpltr = 4;
2350 flag = 1;
2351 }
2352 else if (strcasecmp (name, "vnz") == 0)
2353 {
2354 cmpltr = 5;
2355 flag = 1;
2356 }
2357 else if (strcasecmp (name, "nsv") == 0)
2358 {
2359 cmpltr = 6;
2360 flag = 1;
2361 }
2362 else if (strcasecmp (name, "ev") == 0)
2363 {
2364 cmpltr = 7;
2365 flag = 1;
2366 }
9a913dfb
JL
2367 /* ",*" is a valid condition. */
2368 else if (*args == 'a')
55a914bc
JL
2369 as_bad (_("Invalid Add Condition: %s"), name);
2370 *s = c;
2371 }
2372 opcode |= cmpltr << 13;
2373 INSERT_FIELD_AND_CONTINUE (opcode, flag, 12);
252b5132 2374
55a914bc
JL
2375 /* Handle non-negated add and branch condition. */
2376 case 'd':
2377 cmpltr = pa_parse_nonneg_add_cmpltr (&s, 1);
2378 if (cmpltr < 0)
2379 {
d53d2751 2380 as_bad (_("Invalid Add and Branch Condition: %c"), *s);
55a914bc
JL
2381 cmpltr = 0;
2382 }
2383 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
2384
d53d2751 2385 /* Handle 64 bit wide-mode add and branch condition. */
9a913dfb 2386 case 'W':
d53d2751
JL
2387 cmpltr = pa_parse_addb_64_cmpltr (&s);
2388 if (cmpltr < 0)
2389 {
2390 as_bad (_("Invalid Add and Branch Condition: %c"), *s);
2391 cmpltr = 0;
2392 }
2393 else
2394 {
a28a3ccf 2395 /* Negated condition requires an opcode change. */
d53d2751
JL
2396 opcode |= (cmpltr & 8) << 24;
2397 }
2398 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr & 7, 13);
9a913dfb 2399
d53d2751 2400 /* Handle a negated or non-negated add and branch
55a914bc
JL
2401 condition. */
2402 case '@':
2403 save_s = s;
2404 cmpltr = pa_parse_nonneg_add_cmpltr (&s, 1);
2405 if (cmpltr < 0)
2406 {
2407 s = save_s;
2408 cmpltr = pa_parse_neg_add_cmpltr (&s, 1);
2409 if (cmpltr < 0)
2410 {
2411 as_bad (_("Invalid Compare/Subtract Condition"));
2412 cmpltr = 0;
2413 }
2414 else
2415 {
a28a3ccf 2416 /* Negated condition requires an opcode change. */
55a914bc
JL
2417 opcode |= 1 << 27;
2418 }
2419 }
2420 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
252b5132 2421
55a914bc 2422 /* Handle branch on bit conditions. */
9a913dfb 2423 case 'B':
55a914bc
JL
2424 case 'b':
2425 cmpltr = 0;
2426 if (*s == ',')
2427 {
2428 s++;
9a913dfb
JL
2429
2430 if (*args == 'B')
2431 {
2432 if (*s == '*')
2433 s++;
2434 else
2435 break;
2436 }
17d9105c
JL
2437 else if (*s == '*')
2438 break;
9a913dfb 2439
55a914bc
JL
2440 if (strncmp (s, "<", 1) == 0)
2441 {
2442 cmpltr = 0;
2443 s++;
2444 }
2445 else if (strncmp (s, ">=", 2) == 0)
2446 {
2447 cmpltr = 1;
2448 s += 2;
2449 }
2450 else
2451 as_bad (_("Invalid Bit Branch Condition: %c"), *s);
2452 }
2453 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 15);
252b5132 2454
55a914bc 2455 /* Handle a compare/subtract condition. */
9a913dfb 2456 case 'S':
55a914bc
JL
2457 case 's':
2458 cmpltr = 0;
2459 flag = 0;
2460 if (*s == ',')
2461 {
2462 s++;
9a913dfb
JL
2463
2464 /* 64 bit conditions. */
2465 if (*args == 'S')
d53d2751 2466 {
9a913dfb
JL
2467 if (*s == '*')
2468 s++;
2469 else
2470 break;
d53d2751 2471 }
17d9105c
JL
2472 else if (*s == '*')
2473 break;
55a914bc 2474 name = s;
d53d2751 2475
680ef6de 2476 name = s;
55a914bc
JL
2477 while (*s != ',' && *s != ' ' && *s != '\t')
2478 s += 1;
2479 c = *s;
2480 *s = 0x00;
2481 if (strcmp (name, "=") == 0)
2482 cmpltr = 1;
2483 else if (strcmp (name, "<") == 0)
2484 cmpltr = 2;
2485 else if (strcmp (name, "<=") == 0)
2486 cmpltr = 3;
2487 else if (strcasecmp (name, "<<") == 0)
2488 cmpltr = 4;
2489 else if (strcasecmp (name, "<<=") == 0)
2490 cmpltr = 5;
2491 else if (strcasecmp (name, "sv") == 0)
2492 cmpltr = 6;
2493 else if (strcasecmp (name, "od") == 0)
2494 cmpltr = 7;
2495 else if (strcasecmp (name, "tr") == 0)
2496 {
2497 cmpltr = 0;
2498 flag = 1;
2499 }
2500 else if (strcmp (name, "<>") == 0)
2501 {
2502 cmpltr = 1;
2503 flag = 1;
2504 }
2505 else if (strcmp (name, ">=") == 0)
2506 {
2507 cmpltr = 2;
2508 flag = 1;
2509 }
2510 else if (strcmp (name, ">") == 0)
2511 {
2512 cmpltr = 3;
2513 flag = 1;
2514 }
2515 else if (strcasecmp (name, ">>=") == 0)
2516 {
2517 cmpltr = 4;
2518 flag = 1;
2519 }
2520 else if (strcasecmp (name, ">>") == 0)
2521 {
2522 cmpltr = 5;
2523 flag = 1;
2524 }
2525 else if (strcasecmp (name, "nsv") == 0)
2526 {
2527 cmpltr = 6;
2528 flag = 1;
2529 }
2530 else if (strcasecmp (name, "ev") == 0)
2531 {
2532 cmpltr = 7;
2533 flag = 1;
2534 }
9a913dfb
JL
2535 /* ",*" is a valid condition. */
2536 else if (*args != 'S')
55a914bc
JL
2537 as_bad (_("Invalid Compare/Subtract Condition: %s"),
2538 name);
2539 *s = c;
2540 }
2541 opcode |= cmpltr << 13;
2542 INSERT_FIELD_AND_CONTINUE (opcode, flag, 12);
252b5132 2543
55a914bc
JL
2544 /* Handle a non-negated compare condition. */
2545 case 't':
2546 cmpltr = pa_parse_nonneg_cmpsub_cmpltr (&s, 1);
2547 if (cmpltr < 0)
2548 {
2549 as_bad (_("Invalid Compare/Subtract Condition: %c"), *s);
2550 cmpltr = 0;
2551 }
2552 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
9a913dfb 2553
d53d2751 2554 /* Handle a 32 bit compare and branch condition. */
55a914bc
JL
2555 case 'n':
2556 save_s = s;
2557 cmpltr = pa_parse_nonneg_cmpsub_cmpltr (&s, 1);
2558 if (cmpltr < 0)
2559 {
2560 s = save_s;
2561 cmpltr = pa_parse_neg_cmpsub_cmpltr (&s, 1);
2562 if (cmpltr < 0)
2563 {
d53d2751 2564 as_bad (_("Invalid Compare and Branch Condition."));
55a914bc
JL
2565 cmpltr = 0;
2566 }
2567 else
2568 {
a28a3ccf 2569 /* Negated condition requires an opcode change. */
55a914bc
JL
2570 opcode |= 1 << 27;
2571 }
2572 }
d53d2751
JL
2573
2574 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
2575
2576 /* Handle a 64 bit compare and branch condition. */
2577 case 'N':
2578 cmpltr = pa_parse_cmpb_64_cmpltr (&s);
2579 if (cmpltr >= 0)
2580 {
a28a3ccf 2581 /* Negated condition requires an opcode change. */
d53d2751
JL
2582 opcode |= (cmpltr & 8) << 26;
2583 }
2584 else
a28a3ccf 2585 /* Not a 64 bit cond. Give 32 bit a chance. */
d53d2751
JL
2586 break;
2587
2588 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr & 7, 13);
2589
2590 /* Handle a 64 bit cmpib condition. */
2591 case 'Q':
2592 cmpltr = pa_parse_cmpib_64_cmpltr (&s);
2593 if (cmpltr < 0)
a28a3ccf 2594 /* Not a 64 bit cond. Give 32 bit a chance. */
d53d2751
JL
2595 break;
2596
55a914bc
JL
2597 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
2598
2599 /* Handle a logical instruction condition. */
9a913dfb 2600 case 'L':
55a914bc
JL
2601 case 'l':
2602 cmpltr = 0;
2603 flag = 0;
2604 if (*s == ',')
2605 {
2606 s++;
9a913dfb
JL
2607
2608 /* 64 bit conditions. */
2609 if (*args == 'L')
2610 {
2611 if (*s == '*')
2612 s++;
2613 else
2614 break;
2615 }
17d9105c
JL
2616 else if (*s == '*')
2617 break;
d53d2751 2618
680ef6de 2619 name = s;
55a914bc
JL
2620 while (*s != ',' && *s != ' ' && *s != '\t')
2621 s += 1;
2622 c = *s;
2623 *s = 0x00;
d53d2751 2624
55a914bc
JL
2625 if (strcmp (name, "=") == 0)
2626 cmpltr = 1;
2627 else if (strcmp (name, "<") == 0)
2628 cmpltr = 2;
2629 else if (strcmp (name, "<=") == 0)
2630 cmpltr = 3;
2631 else if (strcasecmp (name, "od") == 0)
2632 cmpltr = 7;
2633 else if (strcasecmp (name, "tr") == 0)
2634 {
2635 cmpltr = 0;
2636 flag = 1;
2637 }
2638 else if (strcmp (name, "<>") == 0)
2639 {
2640 cmpltr = 1;
2641 flag = 1;
2642 }
2643 else if (strcmp (name, ">=") == 0)
2644 {
2645 cmpltr = 2;
2646 flag = 1;
2647 }
2648 else if (strcmp (name, ">") == 0)
2649 {
2650 cmpltr = 3;
2651 flag = 1;
2652 }
2653 else if (strcasecmp (name, "ev") == 0)
2654 {
2655 cmpltr = 7;
2656 flag = 1;
2657 }
9a913dfb
JL
2658 /* ",*" is a valid condition. */
2659 else if (*args != 'L')
55a914bc
JL
2660 as_bad (_("Invalid Logical Instruction Condition."));
2661 *s = c;
2662 }
2663 opcode |= cmpltr << 13;
2664 INSERT_FIELD_AND_CONTINUE (opcode, flag, 12);
2665
2666 /* Handle a shift/extract/deposit condition. */
9a913dfb 2667 case 'X':
55a914bc
JL
2668 case 'x':
2669 case 'y':
2670 cmpltr = 0;
2671 if (*s == ',')
2672 {
2673 save_s = s++;
2674
9a913dfb
JL
2675 /* 64 bit conditions. */
2676 if (*args == 'X')
2677 {
2678 if (*s == '*')
2679 s++;
2680 else
2681 break;
2682 }
17d9105c
JL
2683 else if (*s == '*')
2684 break;
d53d2751 2685
680ef6de 2686 name = s;
55a914bc
JL
2687 while (*s != ',' && *s != ' ' && *s != '\t')
2688 s += 1;
2689 c = *s;
2690 *s = 0x00;
2691 if (strcmp (name, "=") == 0)
2692 cmpltr = 1;
2693 else if (strcmp (name, "<") == 0)
2694 cmpltr = 2;
2695 else if (strcasecmp (name, "od") == 0)
2696 cmpltr = 3;
2697 else if (strcasecmp (name, "tr") == 0)
2698 cmpltr = 4;
2699 else if (strcmp (name, "<>") == 0)
2700 cmpltr = 5;
2701 else if (strcmp (name, ">=") == 0)
2702 cmpltr = 6;
2703 else if (strcasecmp (name, "ev") == 0)
2704 cmpltr = 7;
2705 /* Handle movb,n. Put things back the way they were.
2706 This includes moving s back to where it started. */
2707 else if (strcasecmp (name, "n") == 0 && *args == 'y')
2708 {
2709 *s = c;
2710 s = save_s;
2711 continue;
2712 }
9a913dfb
JL
2713 /* ",*" is a valid condition. */
2714 else if (*args != 'X')
55a914bc
JL
2715 as_bad (_("Invalid Shift/Extract/Deposit Condition."));
2716 *s = c;
2717 }
2718 INSERT_FIELD_AND_CONTINUE (opcode, cmpltr, 13);
252b5132 2719
55a914bc 2720 /* Handle a unit instruction condition. */
9a913dfb
JL
2721 case 'U':
2722 case 'u':
55a914bc
JL
2723 cmpltr = 0;
2724 flag = 0;
2725 if (*s == ',')
2726 {
2727 s++;
d53d2751 2728
9a913dfb
JL
2729 /* 64 bit conditions. */
2730 if (*args == 'U')
2731 {
2732 if (*s == '*')
2733 s++;
2734 else
2735 break;
2736 }
17d9105c
JL
2737 else if (*s == '*')
2738 break;
d53d2751 2739
55a914bc
JL
2740 if (strncasecmp (s, "sbz", 3) == 0)
2741 {
2742 cmpltr = 2;
2743 s += 3;
2744 }
2745 else if (strncasecmp (s, "shz", 3) == 0)
2746 {
2747 cmpltr = 3;
2748 s += 3;
2749 }
2750 else if (strncasecmp (s, "sdc", 3) == 0)
2751 {
2752 cmpltr = 4;
2753 s += 3;
2754 }
2755 else if (strncasecmp (s, "sbc", 3) == 0)
2756 {
2757 cmpltr = 6;
2758 s += 3;
2759 }
2760 else if (strncasecmp (s, "shc", 3) == 0)
2761 {
2762 cmpltr = 7;
2763 s += 3;
2764 }
2765 else if (strncasecmp (s, "tr", 2) == 0)
2766 {
2767 cmpltr = 0;
2768 flag = 1;
2769 s += 2;
2770 }
2771 else if (strncasecmp (s, "nbz", 3) == 0)
2772 {
2773 cmpltr = 2;
2774 flag = 1;
2775 s += 3;
2776 }
2777 else if (strncasecmp (s, "nhz", 3) == 0)
2778 {
2779 cmpltr = 3;
2780 flag = 1;
2781 s += 3;
2782 }
2783 else if (strncasecmp (s, "ndc", 3) == 0)
2784 {
2785 cmpltr = 4;
2786 flag = 1;
2787 s += 3;
2788 }
2789 else if (strncasecmp (s, "nbc", 3) == 0)
2790 {
2791 cmpltr = 6;
2792 flag = 1;
2793 s += 3;
2794 }
2795 else if (strncasecmp (s, "nhc", 3) == 0)
2796 {
2797 cmpltr = 7;
2798 flag = 1;
2799 s += 3;
2800 }
afbf211f
JL
2801 else if (strncasecmp (s, "swz", 3) == 0)
2802 {
2803 cmpltr = 1;
2804 flag = 0;
2805 s += 3;
2806 }
2807 else if (strncasecmp (s, "swc", 3) == 0)
2808 {
2809 cmpltr = 5;
2810 flag = 0;
2811 s += 3;
2812 }
2813 else if (strncasecmp (s, "nwz", 3) == 0)
2814 {
2815 cmpltr = 1;
2816 flag = 1;
2817 s += 3;
2818 }
2819 else if (strncasecmp (s, "nwc", 3) == 0)
2820 {
2821 cmpltr = 5;
2822 flag = 1;
2823 s += 3;
2824 }
9a913dfb
JL
2825 /* ",*" is a valid condition. */
2826 else if (*args != 'U')
55a914bc
JL
2827 as_bad (_("Invalid Unit Instruction Condition."));
2828 }
2829 opcode |= cmpltr << 13;
2830 INSERT_FIELD_AND_CONTINUE (opcode, flag, 12);
252b5132 2831
55a914bc
JL
2832 default:
2833 abort ();
2834 }
0741736b 2835 break;
55a914bc 2836 }
252b5132 2837
252b5132
RH
2838 /* Handle a nullification completer for branch instructions. */
2839 case 'n':
2840 nullif = pa_parse_nullif (&s);
2841 INSERT_FIELD_AND_CONTINUE (opcode, nullif, 1);
2842
2843 /* Handle a nullification completer for copr and spop insns. */
2844 case 'N':
2845 nullif = pa_parse_nullif (&s);
2846 INSERT_FIELD_AND_CONTINUE (opcode, nullif, 5);
2847
dbe2f9ee
JL
2848 /* Handle ,%r2 completer for new syntax branches. */
2849 case 'L':
54af6ff6 2850 if (*s == ',' && strncasecmp (s + 1, "%r2", 3) == 0)
dbe2f9ee 2851 s += 4;
54af6ff6 2852 else if (*s == ',' && strncasecmp (s + 1, "%rp", 3) == 0)
dbe2f9ee
JL
2853 s += 4;
2854 else
2855 break;
2856 continue;
2857
1cf6ae67
JL
2858 /* Handle 3 bit entry into the fp compare array. Valid values
2859 are 0..6 inclusive. */
2860 case 'h':
2861 get_expression (s);
2862 s = expr_end;
2863 if (the_insn.exp.X_op == O_constant)
2864 {
2865 num = evaluate_absolute (&the_insn);
2866 CHECK_FIELD (num, 6, 0, 0);
2867 num++;
2868 INSERT_FIELD_AND_CONTINUE (opcode, num, 13);
2869 }
2870 else
2871 break;
2872
2873 /* Handle 3 bit entry into the fp compare array. Valid values
2874 are 0..6 inclusive. */
2875 case 'm':
2876 get_expression (s);
1cf6ae67
JL
2877 if (the_insn.exp.X_op == O_constant)
2878 {
b1039fc4 2879 s = expr_end;
1cf6ae67
JL
2880 num = evaluate_absolute (&the_insn);
2881 CHECK_FIELD (num, 6, 0, 0);
2882 num = (num + 1) ^ 1;
2883 INSERT_FIELD_AND_CONTINUE (opcode, num, 13);
2884 }
2885 else
b1039fc4 2886 break;
1cf6ae67
JL
2887
2888 /* Handle graphics test completers for ftest */
2889 case '=':
2890 {
2891 num = pa_parse_ftest_gfx_completer (&s);
2892 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
2893 }
2894
252b5132
RH
2895 /* Handle a 11 bit immediate at 31. */
2896 case 'i':
2897 the_insn.field_selector = pa_chk_field_selector (&s);
2898 get_expression (s);
2899 s = expr_end;
2900 if (the_insn.exp.X_op == O_constant)
2901 {
2902 num = evaluate_absolute (&the_insn);
2903 CHECK_FIELD (num, 1023, -1024, 0);
3f9b03b5 2904 num = low_sign_unext (num, 11);
252b5132
RH
2905 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
2906 }
2907 else
2908 {
2909 if (is_DP_relative (the_insn.exp))
2910 the_insn.reloc = R_HPPA_GOTOFF;
2911 else if (is_PC_relative (the_insn.exp))
2912 the_insn.reloc = R_HPPA_PCREL_CALL;
2913 else
2914 the_insn.reloc = R_HPPA;
2915 the_insn.format = 11;
2916 continue;
2917 }
2918
65fab780
JL
2919 /* Handle a 14 bit immediate at 31. */
2920 case 'J':
2921 the_insn.field_selector = pa_chk_field_selector (&s);
2922 get_expression (s);
2923 s = expr_end;
2924 if (the_insn.exp.X_op == O_constant)
2925 {
2926 int a, m;
2927
2928 /* XXX the completer stored away tibits of information
2929 for us to extract. We need a cleaner way to do this.
2930 Now that we have lots of letters again, it would be
2931 good to rethink this. */
2932 m = (opcode & (1 << 8)) != 0;
2933 a = (opcode & (1 << 9)) != 0;
2934 opcode &= ~ (3 << 8);
2935 num = evaluate_absolute (&the_insn);
fd232ac8 2936 if ((a == 1 && num >= 0) || (a == 0 && num < 0))
65fab780
JL
2937 break;
2938 CHECK_FIELD (num, 8191, -8192, 0);
3f9b03b5 2939 num = low_sign_unext (num, 14);
65fab780
JL
2940 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
2941 }
2942 else
2943 {
2944 break;
2945 }
2946
2947 /* Handle a 14 bit immediate at 31. */
2948 case 'K':
2949 the_insn.field_selector = pa_chk_field_selector (&s);
2950 get_expression (s);
2951 s = expr_end;
2952 if (the_insn.exp.X_op == O_constant)
2953 {
2954 int a, m;
2955
2956 /* XXX the completer stored away tibits of information
2957 for us to extract. We need a cleaner way to do this.
2958 Now that we have lots of letters again, it would be
2959 good to rethink this. */
2960 m = (opcode & (1 << 8)) != 0;
2961 a = (opcode & (1 << 9)) != 0;
2962 opcode &= ~ (3 << 8);
2963 num = evaluate_absolute (&the_insn);
fd232ac8 2964 if ((a == 1 && num < 0) || (a == 0 && num > 0))
65fab780
JL
2965 break;
2966 if (num % 4)
2967 break;
2968 CHECK_FIELD (num, 8191, -8192, 0);
2969 if (num < 0)
2970 opcode |= 1;
2971 num &= 0x1fff;
2972 num >>= 2;
2973 INSERT_FIELD_AND_CONTINUE (opcode, num, 3);
2974 }
2975 else
2976 {
2977 break;
2978 }
2979
ad1079af 2980 /* Handle 14 bit immediate, shifted left three times. */
61dd1d31
JL
2981 case '#':
2982 the_insn.field_selector = pa_chk_field_selector (&s);
2983 get_expression (s);
2984 s = expr_end;
2985 if (the_insn.exp.X_op == O_constant)
2986 {
2987 num = evaluate_absolute (&the_insn);
2988 if (num & 0x7)
2989 break;
2990 CHECK_FIELD (num, 8191, -8192, 0);
2991 if (num < 0)
2992 opcode |= 1;
2993 num &= 0x1fff;
2994 num >>= 3;
2995 INSERT_FIELD_AND_CONTINUE (opcode, num, 4);
2996 }
2997 else
2998 {
2999 if (is_DP_relative (the_insn.exp))
3000 the_insn.reloc = R_HPPA_GOTOFF;
3001 else if (is_PC_relative (the_insn.exp))
3002 the_insn.reloc = R_HPPA_PCREL_CALL;
3003 else
3004 the_insn.reloc = R_HPPA;
3005 the_insn.format = 14;
3006 continue;
3007 }
3008 break;
3009
3010 /* Handle 14 bit immediate, shifted left twice. */
3011 case 'd':
3012 the_insn.field_selector = pa_chk_field_selector (&s);
3013 get_expression (s);
3014 s = expr_end;
3015 if (the_insn.exp.X_op == O_constant)
3016 {
3017 num = evaluate_absolute (&the_insn);
3018 if (num & 0x3)
3019 break;
3020 CHECK_FIELD (num, 8191, -8192, 0);
3021 if (num < 0)
3022 opcode |= 1;
3023 num &= 0x1fff;
3024 num >>= 2;
3025 INSERT_FIELD_AND_CONTINUE (opcode, num, 3);
3026 }
3027 else
3028 {
3029 if (is_DP_relative (the_insn.exp))
3030 the_insn.reloc = R_HPPA_GOTOFF;
3031 else if (is_PC_relative (the_insn.exp))
3032 the_insn.reloc = R_HPPA_PCREL_CALL;
3033 else
3034 the_insn.reloc = R_HPPA;
3035 the_insn.format = 14;
3036 continue;
3037 }
252b5132
RH
3038
3039 /* Handle a 14 bit immediate at 31. */
3040 case 'j':
3041 the_insn.field_selector = pa_chk_field_selector (&s);
3042 get_expression (s);
3043 s = expr_end;
3044 if (the_insn.exp.X_op == O_constant)
3045 {
3046 num = evaluate_absolute (&the_insn);
3047 CHECK_FIELD (num, 8191, -8192, 0);
3f9b03b5 3048 num = low_sign_unext (num, 14);
252b5132
RH
3049 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3050 }
3051 else
3052 {
3053 if (is_DP_relative (the_insn.exp))
3054 the_insn.reloc = R_HPPA_GOTOFF;
3055 else if (is_PC_relative (the_insn.exp))
3056 the_insn.reloc = R_HPPA_PCREL_CALL;
3057 else
3058 the_insn.reloc = R_HPPA;
3059 the_insn.format = 14;
3060 continue;
3061 }
3062
3063 /* Handle a 21 bit immediate at 31. */
3064 case 'k':
3065 the_insn.field_selector = pa_chk_field_selector (&s);
3066 get_expression (s);
3067 s = expr_end;
3068 if (the_insn.exp.X_op == O_constant)
3069 {
3070 num = evaluate_absolute (&the_insn);
3071 CHECK_FIELD (num >> 11, 1048575, -1048576, 0);
ad1079af 3072 opcode |= re_assemble_21 (num);
3f9b03b5 3073 continue;
252b5132
RH
3074 }
3075 else
3076 {
3077 if (is_DP_relative (the_insn.exp))
3078 the_insn.reloc = R_HPPA_GOTOFF;
3079 else if (is_PC_relative (the_insn.exp))
3080 the_insn.reloc = R_HPPA_PCREL_CALL;
3081 else
3082 the_insn.reloc = R_HPPA;
3083 the_insn.format = 21;
3084 continue;
3085 }
3086
a02fab7e
JL
3087 /* Handle a 16 bit immediate at 31 (PA 2.0 wide mode only). */
3088 case 'l':
3089 the_insn.field_selector = pa_chk_field_selector (&s);
3090 get_expression (s);
3091 s = expr_end;
3092 if (the_insn.exp.X_op == O_constant)
3093 {
a02fab7e
JL
3094 num = evaluate_absolute (&the_insn);
3095 CHECK_FIELD (num, 32767, -32768, 0);
ad1079af 3096 opcode |= re_assemble_16 (num);
3f9b03b5 3097 continue;
a02fab7e
JL
3098 }
3099 else
3100 {
3101 /* ??? Is this valid for wide mode? */
3102 if (is_DP_relative (the_insn.exp))
3103 the_insn.reloc = R_HPPA_GOTOFF;
3104 else if (is_PC_relative (the_insn.exp))
3105 the_insn.reloc = R_HPPA_PCREL_CALL;
3106 else
3107 the_insn.reloc = R_HPPA;
3108 the_insn.format = 14;
3109 continue;
3110 }
3111
3112 /* Handle a word-aligned 16-bit imm. at 31 (PA2.0 wide). */
3113 case 'y':
3114 the_insn.field_selector = pa_chk_field_selector (&s);
3115 get_expression (s);
3116 s = expr_end;
3117 if (the_insn.exp.X_op == O_constant)
3118 {
a02fab7e
JL
3119 num = evaluate_absolute (&the_insn);
3120 CHECK_FIELD (num, 32767, -32768, 0);
3121 CHECK_ALIGN (num, 4, 0);
ad1079af 3122 opcode |= re_assemble_16 (num);
3f9b03b5 3123 continue;
a02fab7e
JL
3124 }
3125 else
3126 {
3127 /* ??? Is this valid for wide mode? */
3128 if (is_DP_relative (the_insn.exp))
3129 the_insn.reloc = R_HPPA_GOTOFF;
3130 else if (is_PC_relative (the_insn.exp))
3131 the_insn.reloc = R_HPPA_PCREL_CALL;
3132 else
3133 the_insn.reloc = R_HPPA;
3134 the_insn.format = 14;
3135 continue;
3136 }
3137
3138 /* Handle a dword-aligned 16-bit imm. at 31 (PA2.0 wide). */
3139 case '&':
3140 the_insn.field_selector = pa_chk_field_selector (&s);
3141 get_expression (s);
3142 s = expr_end;
3143 if (the_insn.exp.X_op == O_constant)
3144 {
a02fab7e
JL
3145 num = evaluate_absolute (&the_insn);
3146 CHECK_FIELD (num, 32767, -32768, 0);
3147 CHECK_ALIGN (num, 8, 0);
ad1079af 3148 opcode |= re_assemble_16 (num);
3f9b03b5 3149 continue;
a02fab7e
JL
3150 }
3151 else
3152 {
3153 /* ??? Is this valid for wide mode? */
3154 if (is_DP_relative (the_insn.exp))
3155 the_insn.reloc = R_HPPA_GOTOFF;
3156 else if (is_PC_relative (the_insn.exp))
3157 the_insn.reloc = R_HPPA_PCREL_CALL;
3158 else
3159 the_insn.reloc = R_HPPA;
3160 the_insn.format = 14;
3161 continue;
3162 }
3163
252b5132
RH
3164 /* Handle a 12 bit branch displacement. */
3165 case 'w':
3166 the_insn.field_selector = pa_chk_field_selector (&s);
3167 get_expression (s);
3168 s = expr_end;
3169 the_insn.pcrel = 1;
3170 if (!strcmp (S_GET_NAME (the_insn.exp.X_add_symbol), "L$0\001"))
3171 {
252b5132
RH
3172 num = evaluate_absolute (&the_insn);
3173 if (num % 4)
3174 {
3175 as_bad (_("Branch to unaligned address"));
3176 break;
3177 }
3178 CHECK_FIELD (num, 8199, -8184, 0);
a28a3ccf 3179
ad1079af 3180 opcode |= re_assemble_12 ((num - 8) >> 2);
3f9b03b5 3181 continue;
252b5132
RH
3182 }
3183 else
3184 {
3185 the_insn.reloc = R_HPPA_PCREL_CALL;
3186 the_insn.format = 12;
3187 the_insn.arg_reloc = last_call_desc.arg_reloc;
3188 memset (&last_call_desc, 0, sizeof (struct call_desc));
3189 s = expr_end;
3190 continue;
3191 }
3192
3193 /* Handle a 17 bit branch displacement. */
3194 case 'W':
3195 the_insn.field_selector = pa_chk_field_selector (&s);
3196 get_expression (s);
3197 s = expr_end;
3198 the_insn.pcrel = 1;
3199 if (!the_insn.exp.X_add_symbol
3200 || !strcmp (S_GET_NAME (the_insn.exp.X_add_symbol),
3201 "L$0\001"))
3202 {
252b5132
RH
3203 num = evaluate_absolute (&the_insn);
3204 if (num % 4)
3205 {
3206 as_bad (_("Branch to unaligned address"));
3207 break;
3208 }
3209 CHECK_FIELD (num, 262143, -262144, 0);
3210
3211 if (the_insn.exp.X_add_symbol)
3212 num -= 8;
3213
ad1079af 3214 opcode |= re_assemble_17 (num >> 2);
3f9b03b5 3215 continue;
252b5132
RH
3216 }
3217 else
3218 {
3219 the_insn.reloc = R_HPPA_PCREL_CALL;
3220 the_insn.format = 17;
3221 the_insn.arg_reloc = last_call_desc.arg_reloc;
3222 memset (&last_call_desc, 0, sizeof (struct call_desc));
3223 continue;
3224 }
3225
77c02e18
JL
3226 /* Handle a 22 bit branch displacement. */
3227 case 'X':
3228 the_insn.field_selector = pa_chk_field_selector (&s);
3229 get_expression (s);
3230 s = expr_end;
3231 the_insn.pcrel = 1;
3232 if (!the_insn.exp.X_add_symbol
3233 || !strcmp (S_GET_NAME (the_insn.exp.X_add_symbol),
3234 "L$0\001"))
3235 {
77c02e18
JL
3236 num = evaluate_absolute (&the_insn);
3237 if (num % 4)
3238 {
3239 as_bad (_("Branch to unaligned address"));
3240 break;
3241 }
3242 CHECK_FIELD (num, 8388607, -8388608, 0);
3243
3244 if (the_insn.exp.X_add_symbol)
3245 num -= 8;
3246
ad1079af 3247 opcode |= re_assemble_22 (num >> 2);
77c02e18
JL
3248 }
3249 else
3250 {
3251 the_insn.reloc = R_HPPA_PCREL_CALL;
3252 the_insn.format = 22;
3253 the_insn.arg_reloc = last_call_desc.arg_reloc;
3254 memset (&last_call_desc, 0, sizeof (struct call_desc));
3255 continue;
3256 }
3257
252b5132
RH
3258 /* Handle an absolute 17 bit branch target. */
3259 case 'z':
3260 the_insn.field_selector = pa_chk_field_selector (&s);
3261 get_expression (s);
3262 s = expr_end;
3263 the_insn.pcrel = 0;
3264 if (!the_insn.exp.X_add_symbol
3265 || !strcmp (S_GET_NAME (the_insn.exp.X_add_symbol),
3266 "L$0\001"))
3267 {
252b5132
RH
3268 num = evaluate_absolute (&the_insn);
3269 if (num % 4)
3270 {
3271 as_bad (_("Branch to unaligned address"));
3272 break;
3273 }
3274 CHECK_FIELD (num, 262143, -262144, 0);
3275
3276 if (the_insn.exp.X_add_symbol)
3277 num -= 8;
3278
ad1079af 3279 opcode |= re_assemble_17 (num >> 2);
3f9b03b5 3280 continue;
252b5132
RH
3281 }
3282 else
3283 {
3284 the_insn.reloc = R_HPPA_ABS_CALL;
3285 the_insn.format = 17;
3286 the_insn.arg_reloc = last_call_desc.arg_reloc;
3287 memset (&last_call_desc, 0, sizeof (struct call_desc));
3288 continue;
3289 }
3290
4964086a
JL
3291 /* Handle '%r1' implicit operand of addil instruction. */
3292 case 'Z':
3293 if (*s == ',' && *(s + 1) == '%' && *(s + 3) == '1'
3294 && (*(s + 2) == 'r' || *(s + 2) == 'R'))
3295 {
3296 s += 4;
3297 continue;
3298 }
3299 else
3300 break;
3301
ce674324
JL
3302 /* Handle '%sr0,%r31' implicit operand of be,l instruction. */
3303 case 'Y':
3304 if (strncasecmp (s, "%sr0,%r31", 9) != 0)
3305 break;
3306 s += 9;
3307 continue;
3308
d53d2751
JL
3309 /* Handle immediate value of 0 for ordered load/store instructions. */
3310 case '@':
3311 if (*s != '0')
3312 break;
3313 s++;
3314 continue;
3315
a97685e9
JL
3316 /* Handle a 2 bit shift count at 25. */
3317 case '.':
3318 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3319 if (strict && the_insn.exp.X_op != O_constant)
3320 break;
a97685e9 3321 s = expr_end;
0f4f8b56 3322 CHECK_FIELD (num, 3, 1, strict);
a97685e9
JL
3323 INSERT_FIELD_AND_CONTINUE (opcode, num, 6);
3324
413c94ba
JL
3325 /* Handle a 4 bit shift count at 25. */
3326 case '*':
3327 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3328 if (strict && the_insn.exp.X_op != O_constant)
3329 break;
413c94ba 3330 s = expr_end;
0f4f8b56 3331 CHECK_FIELD (num, 15, 0, strict);
413c94ba
JL
3332 INSERT_FIELD_AND_CONTINUE (opcode, num, 6);
3333
252b5132
RH
3334 /* Handle a 5 bit shift count at 26. */
3335 case 'p':
3336 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3337 if (strict && the_insn.exp.X_op != O_constant)
3338 break;
252b5132 3339 s = expr_end;
0f4f8b56 3340 CHECK_FIELD (num, 31, 0, strict);
252b5132
RH
3341 INSERT_FIELD_AND_CONTINUE (opcode, 31 - num, 5);
3342
a97685e9
JL
3343 /* Handle a 6 bit shift count at 20,22:26. */
3344 case '~':
3345 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3346 if (strict && the_insn.exp.X_op != O_constant)
3347 break;
a97685e9 3348 s = expr_end;
0f4f8b56 3349 CHECK_FIELD (num, 63, 0, strict);
a97685e9
JL
3350 num = 63 - num;
3351 opcode |= (num & 0x20) << 6;
3352 INSERT_FIELD_AND_CONTINUE (opcode, num & 0x1f, 5);
3353
9e4f2d3a
JL
3354 /* Handle a 6 bit field length at 23,27:31. */
3355 case '%':
3356 flag = 0;
3357 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3358 if (strict && the_insn.exp.X_op != O_constant)
3359 break;
9e4f2d3a 3360 s = expr_end;
0f4f8b56 3361 CHECK_FIELD (num, 64, 1, strict);
9e4f2d3a
JL
3362 num--;
3363 opcode |= (num & 0x20) << 3;
3364 num = 31 - (num & 0x1f);
3365 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3366
3367 /* Handle a 6 bit field length at 19,27:31. */
3368 case '|':
3369 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3370 if (strict && the_insn.exp.X_op != O_constant)
3371 break;
9e4f2d3a 3372 s = expr_end;
0f4f8b56 3373 CHECK_FIELD (num, 64, 1, strict);
9e4f2d3a
JL
3374 num--;
3375 opcode |= (num & 0x20) << 7;
3376 num = 31 - (num & 0x1f);
3377 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3378
252b5132
RH
3379 /* Handle a 5 bit bit position at 26. */
3380 case 'P':
3381 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3382 if (strict && the_insn.exp.X_op != O_constant)
3383 break;
252b5132 3384 s = expr_end;
0f4f8b56 3385 CHECK_FIELD (num, 31, 0, strict);
252b5132
RH
3386 INSERT_FIELD_AND_CONTINUE (opcode, num, 5);
3387
9e4f2d3a
JL
3388 /* Handle a 6 bit bit position at 20,22:26. */
3389 case 'q':
3390 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3391 if (strict && the_insn.exp.X_op != O_constant)
3392 break;
9e4f2d3a 3393 s = expr_end;
0f4f8b56 3394 CHECK_FIELD (num, 63, 0, strict);
9e4f2d3a
JL
3395 opcode |= (num & 0x20) << 6;
3396 INSERT_FIELD_AND_CONTINUE (opcode, num & 0x1f, 5);
3397
afbf211f
JL
3398 /* Handle a 5 bit immediate at 10 with 'd' as the complement
3399 of the high bit of the immediate. */
3400 case 'B':
3401 num = pa_get_absolute_expression (&the_insn, &s);
3402 if (strict && the_insn.exp.X_op != O_constant)
3403 break;
3404 s = expr_end;
3405 CHECK_FIELD (num, 63, 0, strict);
3406 if (num & 0x20)
3407 ;
3408 else
3409 opcode |= (1 << 13);
3410 INSERT_FIELD_AND_CONTINUE (opcode, num & 0x1f, 21);
3411
252b5132
RH
3412 /* Handle a 5 bit immediate at 10. */
3413 case 'Q':
252b5132 3414 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3415 if (strict && the_insn.exp.X_op != O_constant)
3416 break;
252b5132 3417 s = expr_end;
0f4f8b56 3418 CHECK_FIELD (num, 31, 0, strict);
252b5132
RH
3419 INSERT_FIELD_AND_CONTINUE (opcode, num, 21);
3420
a97685e9
JL
3421 /* Handle a 9 bit immediate at 28. */
3422 case '$':
3423 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3424 if (strict && the_insn.exp.X_op != O_constant)
3425 break;
a97685e9 3426 s = expr_end;
0f4f8b56 3427 CHECK_FIELD (num, 511, 1, strict);
a97685e9 3428 INSERT_FIELD_AND_CONTINUE (opcode, num, 3);
d53d2751 3429
252b5132
RH
3430 /* Handle a 13 bit immediate at 18. */
3431 case 'A':
3432 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3433 if (strict && the_insn.exp.X_op != O_constant)
3434 break;
252b5132 3435 s = expr_end;
0f4f8b56 3436 CHECK_FIELD (num, 8191, 0, strict);
252b5132
RH
3437 INSERT_FIELD_AND_CONTINUE (opcode, num, 13);
3438
3439 /* Handle a 26 bit immediate at 31. */
3440 case 'D':
3441 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3442 if (strict && the_insn.exp.X_op != O_constant)
3443 break;
252b5132 3444 s = expr_end;
0f4f8b56 3445 CHECK_FIELD (num, 671108864, 0, strict);
252b5132
RH
3446 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3447
3448 /* Handle a 3 bit SFU identifier at 25. */
97e1581b 3449 case 'v':
252b5132
RH
3450 if (*s++ != ',')
3451 as_bad (_("Invalid SFU identifier"));
3452 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3453 if (strict && the_insn.exp.X_op != O_constant)
3454 break;
252b5132 3455 s = expr_end;
0f4f8b56 3456 CHECK_FIELD (num, 7, 0, strict);
252b5132
RH
3457 INSERT_FIELD_AND_CONTINUE (opcode, num, 6);
3458
3459 /* Handle a 20 bit SOP field for spop0. */
3460 case 'O':
3461 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3462 if (strict && the_insn.exp.X_op != O_constant)
3463 break;
252b5132 3464 s = expr_end;
0f4f8b56 3465 CHECK_FIELD (num, 1048575, 0, strict);
252b5132
RH
3466 num = (num & 0x1f) | ((num & 0x000fffe0) << 6);
3467 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3468
3469 /* Handle a 15bit SOP field for spop1. */
3470 case 'o':
3471 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3472 if (strict && the_insn.exp.X_op != O_constant)
3473 break;
252b5132 3474 s = expr_end;
0f4f8b56 3475 CHECK_FIELD (num, 32767, 0, strict);
252b5132
RH
3476 INSERT_FIELD_AND_CONTINUE (opcode, num, 11);
3477
3478 /* Handle a 10bit SOP field for spop3. */
3479 case '0':
3480 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3481 if (strict && the_insn.exp.X_op != O_constant)
3482 break;
252b5132 3483 s = expr_end;
0f4f8b56 3484 CHECK_FIELD (num, 1023, 0, strict);
252b5132
RH
3485 num = (num & 0x1f) | ((num & 0x000003e0) << 6);
3486 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3487
3488 /* Handle a 15 bit SOP field for spop2. */
3489 case '1':
3490 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3491 if (strict && the_insn.exp.X_op != O_constant)
3492 break;
252b5132 3493 s = expr_end;
0f4f8b56 3494 CHECK_FIELD (num, 32767, 0, strict);
252b5132
RH
3495 num = (num & 0x1f) | ((num & 0x00007fe0) << 6);
3496 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3497
3498 /* Handle a 3-bit co-processor ID field. */
3499 case 'u':
3500 if (*s++ != ',')
3501 as_bad (_("Invalid COPR identifier"));
3502 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3503 if (strict && the_insn.exp.X_op != O_constant)
3504 break;
252b5132 3505 s = expr_end;
0f4f8b56 3506 CHECK_FIELD (num, 7, 0, strict);
252b5132
RH
3507 INSERT_FIELD_AND_CONTINUE (opcode, num, 6);
3508
3509 /* Handle a 22bit SOP field for copr. */
3510 case '2':
3511 num = pa_get_absolute_expression (&the_insn, &s);
0f4f8b56
JL
3512 if (strict && the_insn.exp.X_op != O_constant)
3513 break;
252b5132 3514 s = expr_end;
0f4f8b56 3515 CHECK_FIELD (num, 4194303, 0, strict);
252b5132
RH
3516 num = (num & 0x1f) | ((num & 0x003fffe0) << 4);
3517 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
3518
1cf6ae67
JL
3519 /* Handle a source FP operand format completer. */
3520 case '{':
3521 if (*s == ',' && *(s+1) == 't')
3522 {
3523 the_insn.trunc = 1;
3524 s += 2;
3525 }
3526 else
3527 the_insn.trunc = 0;
3528 flag = pa_parse_fp_cnv_format (&s);
3529 the_insn.fpof1 = flag;
3530 if (flag == W || flag == UW)
3531 flag = SGL;
3532 if (flag == DW || flag == UDW)
3533 flag = DBL;
3534 if (flag == QW || flag == UQW)
3535 flag = QUAD;
3536 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
3537
3538 /* Handle a destination FP operand format completer. */
3539 case '_':
3540 /* pa_parse_format needs the ',' prefix. */
3541 s--;
3542 flag = pa_parse_fp_cnv_format (&s);
3543 the_insn.fpof2 = flag;
3544 if (flag == W || flag == UW)
3545 flag = SGL;
3546 if (flag == DW || flag == UDW)
3547 flag = DBL;
3548 if (flag == QW || flag == UQW)
3549 flag = QUAD;
3550 opcode |= flag << 13;
3551 if (the_insn.fpof1 == SGL
d53d2751 3552 || the_insn.fpof1 == DBL
1cf6ae67
JL
3553 || the_insn.fpof1 == QUAD)
3554 {
3555 if (the_insn.fpof2 == SGL
3556 || the_insn.fpof2 == DBL
3557 || the_insn.fpof2 == QUAD)
3558 flag = 0;
3559 else if (the_insn.fpof2 == W
3560 || the_insn.fpof2 == DW
3561 || the_insn.fpof2 == QW)
3562 flag = 2;
3563 else if (the_insn.fpof2 == UW
3564 || the_insn.fpof2 == UDW
3565 || the_insn.fpof2 == UQW)
3566 flag = 6;
3567 else
3568 abort ();
3569 }
3570 else if (the_insn.fpof1 == W
d53d2751 3571 || the_insn.fpof1 == DW
1cf6ae67
JL
3572 || the_insn.fpof1 == QW)
3573 {
3574 if (the_insn.fpof2 == SGL
3575 || the_insn.fpof2 == DBL
3576 || the_insn.fpof2 == QUAD)
3577 flag = 1;
3578 else
3579 abort ();
3580 }
3581 else if (the_insn.fpof1 == UW
d53d2751 3582 || the_insn.fpof1 == UDW
1cf6ae67
JL
3583 || the_insn.fpof1 == UQW)
3584 {
3585 if (the_insn.fpof2 == SGL
3586 || the_insn.fpof2 == DBL
3587 || the_insn.fpof2 == QUAD)
3588 flag = 5;
3589 else
3590 abort ();
3591 }
3592 flag |= the_insn.trunc;
3593 INSERT_FIELD_AND_CONTINUE (opcode, flag, 15);
252b5132
RH
3594
3595 /* Handle a source FP operand format completer. */
3596 case 'F':
3597 flag = pa_parse_fp_format (&s);
3598 the_insn.fpof1 = flag;
3599 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
3600
3601 /* Handle a destination FP operand format completer. */
3602 case 'G':
3603 /* pa_parse_format needs the ',' prefix. */
3604 s--;
3605 flag = pa_parse_fp_format (&s);
3606 the_insn.fpof2 = flag;
3607 INSERT_FIELD_AND_CONTINUE (opcode, flag, 13);
3608
9ecc05f0
JL
3609 /* Handle a source FP operand format completer at 20. */
3610 case 'I':
3611 flag = pa_parse_fp_format (&s);
3612 the_insn.fpof1 = flag;
3613 INSERT_FIELD_AND_CONTINUE (opcode, flag, 11);
3614
97e1581b
JL
3615 /* Handle a floating point operand format at 26.
3616 Only allows single and double precision. */
3617 case 'H':
3618 flag = pa_parse_fp_format (&s);
3619 switch (flag)
3620 {
3621 case SGL:
3622 opcode |= 0x20;
3623 case DBL:
3624 the_insn.fpof1 = flag;
3625 continue;
252b5132 3626
97e1581b
JL
3627 case QUAD:
3628 case ILLEGAL_FMT:
3629 default:
3630 as_bad (_("Invalid Floating Point Operand Format."));
3631 }
3632 break;
252b5132 3633
97e1581b
JL
3634 /* Handle all floating point registers. */
3635 case 'f':
3636 switch (*++args)
3637 {
3638 /* Float target register. */
3639 case 't':
ecacdc7a 3640 if (!pa_parse_number (&s, 3))
0f4f8b56 3641 break;
ecacdc7a 3642 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
97e1581b
JL
3643 CHECK_FIELD (num, 31, 0, 0);
3644 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
252b5132 3645
97e1581b
JL
3646 /* Float target register with L/R selection. */
3647 case 'T':
252b5132 3648 {
ecacdc7a 3649 if (!pa_parse_number (&s, 1))
0f4f8b56 3650 break;
ecacdc7a
AM
3651 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3652 CHECK_FIELD (num, 31, 0, 0);
3653 opcode |= num;
b53fcc20 3654
97e1581b
JL
3655 /* 0x30 opcodes are FP arithmetic operation opcodes
3656 and need to be turned into 0x38 opcodes. This
3657 is not necessary for loads/stores. */
ecacdc7a 3658 if (need_pa11_opcode ()
97e1581b
JL
3659 && ((opcode & 0xfc000000) == 0x30000000))
3660 opcode |= 1 << 27;
b53fcc20 3661
ecacdc7a
AM
3662 opcode |= (pa_number & FP_REG_RSEL ? 1 << 6 : 0);
3663 continue;
97e1581b 3664 }
252b5132 3665
97e1581b
JL
3666 /* Float operand 1. */
3667 case 'a':
3668 {
ecacdc7a 3669 if (!pa_parse_number (&s, 1))
0f4f8b56 3670 break;
ecacdc7a
AM
3671 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3672 CHECK_FIELD (num, 31, 0, 0);
3673 opcode |= num << 21;
3674 if (need_pa11_opcode ())
97e1581b 3675 {
ecacdc7a 3676 opcode |= (pa_number & FP_REG_RSEL ? 1 << 7 : 0);
97e1581b
JL
3677 opcode |= 1 << 27;
3678 }
3679 continue;
3680 }
252b5132 3681
97e1581b 3682 /* Float operand 1 with L/R selection. */
e061d86f 3683 case 'X':
97e1581b 3684 case 'A':
252b5132 3685 {
ecacdc7a 3686 if (!pa_parse_number (&s, 1))
0f4f8b56 3687 break;
ecacdc7a
AM
3688 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3689 CHECK_FIELD (num, 31, 0, 0);
3690 opcode |= num << 21;
3691 opcode |= (pa_number & FP_REG_RSEL ? 1 << 7 : 0);
97e1581b 3692 continue;
252b5132 3693 }
252b5132 3694
97e1581b
JL
3695 /* Float operand 2. */
3696 case 'b':
3697 {
ecacdc7a 3698 if (!pa_parse_number (&s, 1))
0f4f8b56 3699 break;
ecacdc7a
AM
3700 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3701 CHECK_FIELD (num, 31, 0, 0);
3702 opcode |= num << 16;
3703 if (need_pa11_opcode ())
97e1581b 3704 {
ecacdc7a 3705 opcode |= (pa_number & FP_REG_RSEL ? 1 << 12 : 0);
97e1581b
JL
3706 opcode |= 1 << 27;
3707 }
3708 continue;
3709 }
3710
3711 /* Float operand 2 with L/R selection. */
3712 case 'B':
252b5132 3713 {
ecacdc7a 3714 if (!pa_parse_number (&s, 1))
0f4f8b56 3715 break;
ecacdc7a
AM
3716 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3717 CHECK_FIELD (num, 31, 0, 0);
3718 opcode |= num << 16;
3719 opcode |= (pa_number & FP_REG_RSEL ? 1 << 12 : 0);
97e1581b 3720 continue;
252b5132 3721 }
252b5132 3722
97e1581b
JL
3723 /* Float operand 3 for fmpyfadd, fmpynfadd. */
3724 case 'C':
3725 {
ecacdc7a 3726 if (!pa_parse_number (&s, 1))
0f4f8b56 3727 break;
ecacdc7a
AM
3728 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3729 CHECK_FIELD (num, 31, 0, 0);
3730 opcode |= (num & 0x1c) << 11;
3731 opcode |= (num & 0x03) << 9;
3732 opcode |= (pa_number & FP_REG_RSEL ? 1 << 8 : 0);
97e1581b
JL
3733 continue;
3734 }
b53fcc20 3735
97e1581b
JL
3736 /* Float mult operand 1 for fmpyadd, fmpysub */
3737 case 'i':
3738 {
ecacdc7a 3739 if (!pa_parse_number (&s, 1))
0f4f8b56 3740 break;
ecacdc7a
AM
3741 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3742 CHECK_FIELD (num, 31, 0, 0);
97e1581b
JL
3743 if (the_insn.fpof1 == SGL)
3744 {
ecacdc7a 3745 if (num < 16)
97e1581b
JL
3746 {
3747 as_bad (_("Invalid register for single precision fmpyadd or fmpysub"));
3748 break;
3749 }
ecacdc7a
AM
3750 num &= 0xF;
3751 num |= (pa_number & FP_REG_RSEL ? 1 << 4 : 0);
97e1581b 3752 }
ecacdc7a 3753 INSERT_FIELD_AND_CONTINUE (opcode, num, 21);
97e1581b
JL
3754 }
3755
3756 /* Float mult operand 2 for fmpyadd, fmpysub */
3757 case 'j':
252b5132 3758 {
ecacdc7a 3759 if (!pa_parse_number (&s, 1))
0f4f8b56 3760 break;
ecacdc7a
AM
3761 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3762 CHECK_FIELD (num, 31, 0, 0);
97e1581b 3763 if (the_insn.fpof1 == SGL)
252b5132 3764 {
ecacdc7a 3765 if (num < 16)
97e1581b 3766 {
ecacdc7a
AM
3767 as_bad (_("Invalid register for single precision fmpyadd or fmpysub"));
3768 break;
97e1581b 3769 }
ecacdc7a
AM
3770 num &= 0xF;
3771 num |= (pa_number & FP_REG_RSEL ? 1 << 4 : 0);
252b5132 3772 }
ecacdc7a 3773 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
252b5132 3774 }
252b5132 3775
97e1581b
JL
3776 /* Float mult target for fmpyadd, fmpysub */
3777 case 'k':
252b5132 3778 {
ecacdc7a 3779 if (!pa_parse_number (&s, 1))
0f4f8b56 3780 break;
ecacdc7a
AM
3781 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3782 CHECK_FIELD (num, 31, 0, 0);
97e1581b 3783 if (the_insn.fpof1 == SGL)
252b5132 3784 {
ecacdc7a 3785 if (num < 16)
97e1581b 3786 {
ecacdc7a
AM
3787 as_bad (_("Invalid register for single precision fmpyadd or fmpysub"));
3788 break;
97e1581b 3789 }
ecacdc7a
AM
3790 num &= 0xF;
3791 num |= (pa_number & FP_REG_RSEL ? 1 << 4 : 0);
252b5132 3792 }
ecacdc7a 3793 INSERT_FIELD_AND_CONTINUE (opcode, num, 0);
252b5132 3794 }
252b5132 3795
97e1581b
JL
3796 /* Float add operand 1 for fmpyadd, fmpysub */
3797 case 'l':
252b5132 3798 {
ecacdc7a 3799 if (!pa_parse_number (&s, 1))
0f4f8b56 3800 break;
ecacdc7a
AM
3801 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3802 CHECK_FIELD (num, 31, 0, 0);
97e1581b 3803 if (the_insn.fpof1 == SGL)
252b5132 3804 {
ecacdc7a 3805 if (num < 16)
97e1581b 3806 {
ecacdc7a
AM
3807 as_bad (_("Invalid register for single precision fmpyadd or fmpysub"));
3808 break;
97e1581b 3809 }
ecacdc7a
AM
3810 num &= 0xF;
3811 num |= (pa_number & FP_REG_RSEL ? 1 << 4 : 0);
252b5132 3812 }
ecacdc7a 3813 INSERT_FIELD_AND_CONTINUE (opcode, num, 6);
252b5132 3814 }
252b5132 3815
97e1581b
JL
3816 /* Float add target for fmpyadd, fmpysub */
3817 case 'm':
252b5132 3818 {
ecacdc7a 3819 if (!pa_parse_number (&s, 1))
0f4f8b56 3820 break;
ecacdc7a
AM
3821 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3822 CHECK_FIELD (num, 31, 0, 0);
97e1581b 3823 if (the_insn.fpof1 == SGL)
252b5132 3824 {
ecacdc7a 3825 if (num < 16)
97e1581b 3826 {
ecacdc7a
AM
3827 as_bad (_("Invalid register for single precision fmpyadd or fmpysub"));
3828 break;
97e1581b 3829 }
ecacdc7a
AM
3830 num &= 0xF;
3831 num |= (pa_number & FP_REG_RSEL ? 1 << 4 : 0);
252b5132 3832 }
ecacdc7a 3833 INSERT_FIELD_AND_CONTINUE (opcode, num, 11);
252b5132 3834 }
252b5132 3835
71823da4 3836 /* Handle L/R register halves like 'x'. */
a02fab7e 3837 case 'E':
71823da4
JL
3838 case 'e':
3839 {
ecacdc7a 3840 if (!pa_parse_number (&s, 1))
71823da4 3841 break;
ecacdc7a
AM
3842 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
3843 CHECK_FIELD (num, 31, 0, 0);
3844 opcode |= num << 16;
3845 if (need_pa11_opcode ())
71823da4 3846 {
ecacdc7a 3847 opcode |= (pa_number & FP_REG_RSEL ? 1 << 1 : 0);
71823da4
JL
3848 }
3849 continue;
d3426803 3850 }
a02fab7e
JL
3851
3852 /* Float target register (PA 2.0 wide). */
3853 case 'x':
ecacdc7a 3854 if (!pa_parse_number (&s, 3))
a02fab7e 3855 break;
ecacdc7a 3856 num = (pa_number & ~FP_REG_RSEL) - FP_REG_BASE;
a02fab7e
JL
3857 CHECK_FIELD (num, 31, 0, 0);
3858 INSERT_FIELD_AND_CONTINUE (opcode, num, 16);
3859
97e1581b
JL
3860 default:
3861 abort ();
3862 }
3863 break;
3864
252b5132
RH
3865 default:
3866 abort ();
3867 }
3868 break;
3869 }
3870
3871 failed:
3872 /* Check if the args matched. */
3873 if (match == FALSE)
3874 {
3875 if (&insn[1] - pa_opcodes < (int) NUMOPCODES
3876 && !strcmp (insn->name, insn[1].name))
3877 {
3878 ++insn;
3879 s = argstart;
3880 continue;
3881 }
3882 else
3883 {
3884 as_bad (_("Invalid operands %s"), error_message);
3885 return;
3886 }
3887 }
3888 break;
3889 }
3890
3891 the_insn.opcode = opcode;
3892}
3893
3894/* Turn a string in input_line_pointer into a floating point constant of type
3895 type, and store the appropriate bytes in *litP. The number of LITTLENUMS
3896 emitted is stored in *sizeP . An error message or NULL is returned. */
3897
3898#define MAX_LITTLENUMS 6
3899
3900char *
3901md_atof (type, litP, sizeP)
3902 char type;
3903 char *litP;
3904 int *sizeP;
3905{
3906 int prec;
3907 LITTLENUM_TYPE words[MAX_LITTLENUMS];
3908 LITTLENUM_TYPE *wordP;
3909 char *t;
3910
3911 switch (type)
3912 {
3913
3914 case 'f':
3915 case 'F':
3916 case 's':
3917 case 'S':
3918 prec = 2;
3919 break;
3920
3921 case 'd':
3922 case 'D':
3923 case 'r':
3924 case 'R':
3925 prec = 4;
3926 break;
3927
3928 case 'x':
3929 case 'X':
3930 prec = 6;
3931 break;
3932
3933 case 'p':
3934 case 'P':
3935 prec = 6;
3936 break;
3937
3938 default:
3939 *sizeP = 0;
3940 return _("Bad call to MD_ATOF()");
3941 }
3942 t = atof_ieee (input_line_pointer, type, words);
3943 if (t)
3944 input_line_pointer = t;
3945 *sizeP = prec * sizeof (LITTLENUM_TYPE);
3946 for (wordP = words; prec--;)
3947 {
3948 md_number_to_chars (litP, (valueT) (*wordP++), sizeof (LITTLENUM_TYPE));
3949 litP += sizeof (LITTLENUM_TYPE);
3950 }
3951 return NULL;
3952}
3953
3954/* Write out big-endian. */
3955
3956void
3957md_number_to_chars (buf, val, n)
3958 char *buf;
3959 valueT val;
3960 int n;
3961{
3962 number_to_chars_bigendian (buf, val, n);
3963}
3964
3965/* Translate internal representation of relocation info to BFD target
3966 format. */
3967
3968arelent **
3969tc_gen_reloc (section, fixp)
3970 asection *section;
3971 fixS *fixp;
3972{
3973 arelent *reloc;
3974 struct hppa_fix_struct *hppa_fixp;
252b5132
RH
3975 static arelent *no_relocs = NULL;
3976 arelent **relocs;
ad1079af
AM
3977 reloc_type **codes;
3978 reloc_type code;
252b5132
RH
3979 int n_relocs;
3980 int i;
3981
3982 hppa_fixp = (struct hppa_fix_struct *) fixp->tc_fix_data;
3983 if (fixp->fx_addsy == 0)
3984 return &no_relocs;
ad1079af 3985
252b5132
RH
3986 assert (hppa_fixp != 0);
3987 assert (section != 0);
3988
3989 reloc = (arelent *) xmalloc (sizeof (arelent));
3990
a0f75b47
ILT
3991 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
3992 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
ad1079af 3993 codes = hppa_gen_reloc_type (stdoutput,
252b5132
RH
3994 fixp->fx_r_type,
3995 hppa_fixp->fx_r_format,
3996 hppa_fixp->fx_r_field,
3997 fixp->fx_subsy != NULL,
a0f75b47 3998 symbol_get_bfdsym (fixp->fx_addsy));
252b5132
RH
3999
4000 if (codes == NULL)
5506e1a5
AM
4001 {
4002 as_bad (_("Cannot handle fixup at %s:%d"), fixp->fx_file, fixp->fx_line);
4003 abort ();
4004 }
252b5132
RH
4005
4006 for (n_relocs = 0; codes[n_relocs]; n_relocs++)
4007 ;
4008
4009 relocs = (arelent **) xmalloc (sizeof (arelent *) * n_relocs + 1);
4010 reloc = (arelent *) xmalloc (sizeof (arelent) * n_relocs);
4011 for (i = 0; i < n_relocs; i++)
4012 relocs[i] = &reloc[i];
4013
4014 relocs[n_relocs] = NULL;
4015
4016#ifdef OBJ_ELF
4017 switch (fixp->fx_r_type)
4018 {
4019 default:
4020 assert (n_relocs == 1);
4021
4022 code = *codes[0];
4023
a0f75b47
ILT
4024 reloc->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4025 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
ad1079af
AM
4026 reloc->howto = bfd_reloc_type_lookup (stdoutput,
4027 (bfd_reloc_code_real_type) code);
252b5132 4028 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
252b5132 4029
ad1079af 4030 assert (reloc->howto && (unsigned int) code == reloc->howto->type);
252b5132
RH
4031
4032 /* Now, do any processing that is dependent on the relocation type. */
4033 switch (code)
4034 {
4035 case R_PARISC_DLTREL21L:
4036 case R_PARISC_DLTREL14R:
4037 case R_PARISC_DLTREL14F:
4038 case R_PARISC_PLABEL32:
4039 case R_PARISC_PLABEL21L:
4040 case R_PARISC_PLABEL14R:
4041 /* For plabel relocations, the addend of the
4042 relocation should be either 0 (no static link) or 2
904a31bf
AM
4043 (static link required). This adjustment is done in
4044 bfd/elf32-hppa.c:elf32_hppa_relocate_section.
252b5132
RH
4045
4046 We also slam a zero addend into the DLT relative relocs;
4047 it doesn't make a lot of sense to use any addend since
4048 it gets you a different (eg unknown) DLT entry. */
4049 reloc->addend = 0;
4050 break;
4051
ad1079af 4052#ifdef ELF_ARG_RELOC
252b5132
RH
4053 case R_PARISC_PCREL17R:
4054 case R_PARISC_PCREL17F:
4055 case R_PARISC_PCREL17C:
ad1079af
AM
4056 case R_PARISC_DIR17R:
4057 case R_PARISC_DIR17F:
ad1079af
AM
4058 case R_PARISC_PCREL21L:
4059 case R_PARISC_DIR21L:
904a31bf
AM
4060 reloc->addend = HPPA_R_ADDEND (hppa_fixp->fx_arg_reloc,
4061 fixp->fx_offset);
ad1079af
AM
4062 break;
4063#endif
4064
252b5132
RH
4065 default:
4066 reloc->addend = fixp->fx_offset;
4067 break;
4068 }
4069 break;
4070 }
4071#else /* OBJ_SOM */
4072
4073 /* Walk over reach relocation returned by the BFD backend. */
4074 for (i = 0; i < n_relocs; i++)
4075 {
4076 code = *codes[i];
4077
398e8c25
ILT
4078 relocs[i]->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4079 *relocs[i]->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
ad1079af
AM
4080 relocs[i]->howto =
4081 bfd_reloc_type_lookup (stdoutput,
4082 (bfd_reloc_code_real_type) code);
252b5132
RH
4083 relocs[i]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4084
4085 switch (code)
4086 {
4087 case R_COMP2:
4088 /* The only time we ever use a R_COMP2 fixup is for the difference
4089 of two symbols. With that in mind we fill in all four
4090 relocs now and break out of the loop. */
4091 assert (i == 1);
993142d5 4092 relocs[0]->sym_ptr_ptr = (asymbol **) &(bfd_abs_symbol);
ad1079af
AM
4093 relocs[0]->howto =
4094 bfd_reloc_type_lookup (stdoutput,
4095 (bfd_reloc_code_real_type) *codes[0]);
252b5132
RH
4096 relocs[0]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4097 relocs[0]->addend = 0;
993142d5
ILT
4098 relocs[1]->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4099 *relocs[1]->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
ad1079af
AM
4100 relocs[1]->howto =
4101 bfd_reloc_type_lookup (stdoutput,
4102 (bfd_reloc_code_real_type) *codes[1]);
252b5132
RH
4103 relocs[1]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4104 relocs[1]->addend = 0;
993142d5
ILT
4105 relocs[2]->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4106 *relocs[2]->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_subsy);
ad1079af
AM
4107 relocs[2]->howto =
4108 bfd_reloc_type_lookup (stdoutput,
4109 (bfd_reloc_code_real_type) *codes[2]);
252b5132
RH
4110 relocs[2]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4111 relocs[2]->addend = 0;
993142d5 4112 relocs[3]->sym_ptr_ptr = (asymbol **) &(bfd_abs_symbol);
ad1079af
AM
4113 relocs[3]->howto =
4114 bfd_reloc_type_lookup (stdoutput,
4115 (bfd_reloc_code_real_type) *codes[3]);
252b5132
RH
4116 relocs[3]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4117 relocs[3]->addend = 0;
993142d5 4118 relocs[4]->sym_ptr_ptr = (asymbol **) &(bfd_abs_symbol);
ad1079af
AM
4119 relocs[4]->howto =
4120 bfd_reloc_type_lookup (stdoutput,
4121 (bfd_reloc_code_real_type) *codes[4]);
252b5132
RH
4122 relocs[4]->address = fixp->fx_frag->fr_address + fixp->fx_where;
4123 relocs[4]->addend = 0;
4124 goto done;
4125 case R_PCREL_CALL:
4126 case R_ABS_CALL:
4127 relocs[i]->addend = HPPA_R_ADDEND (hppa_fixp->fx_arg_reloc, 0);
4128 break;
4129
4130 case R_DLT_REL:
4131 case R_DATA_PLABEL:
4132 case R_CODE_PLABEL:
4133 /* For plabel relocations, the addend of the
4134 relocation should be either 0 (no static link) or 2
4135 (static link required).
4136
4137 FIXME: We always assume no static link!
4138
4139 We also slam a zero addend into the DLT relative relocs;
4140 it doesn't make a lot of sense to use any addend since
4141 it gets you a different (eg unknown) DLT entry. */
4142 relocs[i]->addend = 0;
4143 break;
4144
4145 case R_N_MODE:
4146 case R_S_MODE:
4147 case R_D_MODE:
4148 case R_R_MODE:
4149 case R_FSEL:
4150 case R_LSEL:
4151 case R_RSEL:
4152 case R_BEGIN_BRTAB:
4153 case R_END_BRTAB:
4154 case R_BEGIN_TRY:
4155 case R_N0SEL:
4156 case R_N1SEL:
4157 /* There is no symbol or addend associated with these fixups. */
993142d5
ILT
4158 relocs[i]->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4159 *relocs[i]->sym_ptr_ptr = symbol_get_bfdsym (dummy_symbol);
252b5132
RH
4160 relocs[i]->addend = 0;
4161 break;
4162
4163 case R_END_TRY:
4164 case R_ENTRY:
4165 case R_EXIT:
4166 /* There is no symbol associated with these fixups. */
993142d5
ILT
4167 relocs[i]->sym_ptr_ptr = (asymbol **) xmalloc (sizeof (asymbol *));
4168 *relocs[i]->sym_ptr_ptr = symbol_get_bfdsym (dummy_symbol);
252b5132
RH
4169 relocs[i]->addend = fixp->fx_offset;
4170 break;
4171
4172 default:
4173 relocs[i]->addend = fixp->fx_offset;
4174 }
4175 }
4176
4177 done:
4178#endif
4179
4180 return relocs;
4181}
4182
4183/* Process any machine dependent frag types. */
4184
4185void
4186md_convert_frag (abfd, sec, fragP)
3f9b03b5
AM
4187 register bfd *abfd ATTRIBUTE_UNUSED;
4188 register asection *sec ATTRIBUTE_UNUSED;
252b5132
RH
4189 register fragS *fragP;
4190{
4191 unsigned int address;
4192
4193 if (fragP->fr_type == rs_machine_dependent)
4194 {
4195 switch ((int) fragP->fr_subtype)
4196 {
4197 case 0:
4198 fragP->fr_type = rs_fill;
4199 know (fragP->fr_var == 1);
4200 know (fragP->fr_next);
4201 address = fragP->fr_address + fragP->fr_fix;
4202 if (address % fragP->fr_offset)
4203 {
4204 fragP->fr_offset =
4205 fragP->fr_next->fr_address
4206 - fragP->fr_address
4207 - fragP->fr_fix;
4208 }
4209 else
4210 fragP->fr_offset = 0;
4211 break;
4212 }
4213 }
4214}
4215
a28a3ccf 4216/* Round up a section size to the appropriate boundary. */
252b5132
RH
4217
4218valueT
4219md_section_align (segment, size)
4220 asection *segment;
4221 valueT size;
4222{
4223 int align = bfd_get_section_alignment (stdoutput, segment);
4224 int align2 = (1 << align) - 1;
4225
4226 return (size + align2) & ~align2;
4227}
4228
4229/* Return the approximate size of a frag before relaxation has occurred. */
4230int
4231md_estimate_size_before_relax (fragP, segment)
4232 register fragS *fragP;
3f9b03b5 4233 asection *segment ATTRIBUTE_UNUSED;
252b5132
RH
4234{
4235 int size;
4236
4237 size = 0;
4238
4239 while ((fragP->fr_fix + size) % fragP->fr_offset)
4240 size++;
4241
4242 return size;
4243}
4244\f
ad1079af 4245#ifdef OBJ_ELF
4c400d5e
AM
4246# ifdef WARN_COMMENTS
4247const char *md_shortopts = "Vc";
4248# else
ad1079af 4249const char *md_shortopts = "V";
4c400d5e 4250# endif
ad1079af 4251#else
4c400d5e
AM
4252# ifdef WARN_COMMENTS
4253const char *md_shortopts = "c";
4254# else
ad1079af 4255const char *md_shortopts = "";
4c400d5e 4256# endif
ad1079af
AM
4257#endif
4258
252b5132 4259struct option md_longopts[] = {
4c400d5e
AM
4260#ifdef WARN_COMMENTS
4261 {"warn-comment", no_argument, NULL, 'c'},
4262#endif
252b5132
RH
4263 {NULL, no_argument, NULL, 0}
4264};
4265size_t md_longopts_size = sizeof(md_longopts);
4266
4267int
4268md_parse_option (c, arg)
3f9b03b5
AM
4269 int c ATTRIBUTE_UNUSED;
4270 char *arg ATTRIBUTE_UNUSED;
252b5132 4271{
ad1079af
AM
4272 switch (c)
4273 {
4274 default:
4275 return 0;
4276
4277#ifdef OBJ_ELF
4278 case 'V':
4279 print_version_id ();
4280 break;
4c400d5e
AM
4281#endif
4282#ifdef WARN_COMMENTS
4283 case 'c':
4284 warn_comment = 1;
4285 break;
ad1079af
AM
4286#endif
4287 }
4288
4289 return 1;
252b5132
RH
4290}
4291
4292void
4293md_show_usage (stream)
3f9b03b5 4294 FILE *stream ATTRIBUTE_UNUSED;
252b5132 4295{
4c400d5e
AM
4296#ifdef OBJ_ELF
4297 fprintf (stream, _("\
4298 -Q ignored\n"));
4299#endif
4300#ifdef WARN_COMMENTS
4301 fprintf (stream, _("\
4302 -c print a warning if a comment is found\n"));
4303#endif
252b5132
RH
4304}
4305\f
4306/* We have no need to default values of symbols. */
4307
4308symbolS *
4309md_undefined_symbol (name)
3f9b03b5 4310 char *name ATTRIBUTE_UNUSED;
252b5132
RH
4311{
4312 return 0;
4313}
4314
25a8b250 4315#if defined (OBJ_SOM) || defined (ELF_ARG_RELOC)
5506e1a5
AM
4316#define nonzero_dibits(x) \
4317 ((x) | (((x) & 0x55555555) << 1) | (((x) & 0xAAAAAAAA) >> 1))
ad1079af 4318#define arg_reloc_stub_needed(CALLER, CALLEE) \
5506e1a5 4319 (((CALLER) ^ (CALLEE)) & nonzero_dibits (CALLER) & nonzero_dibits (CALLEE))
ad1079af
AM
4320#else
4321#define arg_reloc_stub_needed(CALLER, CALLEE) 0
4322#endif
4323
252b5132
RH
4324/* Apply a fixup to an instruction. */
4325
4326int
4327md_apply_fix (fixP, valp)
4328 fixS *fixP;
4329 valueT *valp;
4330{
dc1fc56b 4331 unsigned char *buf;
252b5132 4332 struct hppa_fix_struct *hppa_fixP;
3f9b03b5 4333 offsetT new_val;
dc1fc56b 4334 int insn, val, fmt;
252b5132 4335
252b5132
RH
4336 /* SOM uses R_HPPA_ENTRY and R_HPPA_EXIT relocations which can
4337 never be "applied" (they are just markers). Likewise for
4338 R_HPPA_BEGIN_BRTAB and R_HPPA_END_BRTAB. */
4339#ifdef OBJ_SOM
4340 if (fixP->fx_r_type == R_HPPA_ENTRY
4341 || fixP->fx_r_type == R_HPPA_EXIT
4342 || fixP->fx_r_type == R_HPPA_BEGIN_BRTAB
4343 || fixP->fx_r_type == R_HPPA_END_BRTAB
4344 || fixP->fx_r_type == R_HPPA_BEGIN_TRY)
4345 return 1;
4346
4347 /* Disgusting. We must set fx_offset ourselves -- R_HPPA_END_TRY
4348 fixups are considered not adjustable, which in turn causes
4349 adjust_reloc_syms to not set fx_offset. Ugh. */
4350 if (fixP->fx_r_type == R_HPPA_END_TRY)
4351 {
4352 fixP->fx_offset = *valp;
4353 return 1;
4354 }
4355#endif
904a31bf
AM
4356#ifdef OBJ_ELF
4357 if (fixP->fx_r_type == (int) R_PARISC_GNU_VTENTRY
4358 || fixP->fx_r_type == (int) R_PARISC_GNU_VTINHERIT)
4359 return 1;
4360#endif
252b5132
RH
4361
4362 /* There should have been an HPPA specific fixup associated
4363 with the GAS fixup. */
dc1fc56b
AM
4364 hppa_fixP = (struct hppa_fix_struct *) fixP->tc_fix_data;
4365 if (hppa_fixP == NULL)
252b5132 4366 {
dc1fc56b
AM
4367 printf (_("no hppa_fixup entry for fixup type 0x%x at %s:%d"),
4368 fixP->fx_r_type, fixP->fx_file, fixP->fx_line);
4369 return 0;
4370 }
252b5132 4371
dc1fc56b
AM
4372 buf = fixP->fx_frag->fr_literal + fixP->fx_where;
4373 insn = bfd_get_32 (stdoutput, buf);
4374 fmt = bfd_hppa_insn2fmt (stdoutput, insn);
5506e1a5 4375
dc1fc56b
AM
4376 /* If there is a symbol associated with this fixup, then it's something
4377 which will need a SOM relocation (except for some PC-relative relocs).
4378 In such cases we should treat the "val" or "addend" as zero since it
4379 will be added in as needed from fx_offset in tc_gen_reloc. */
4380 if ((fixP->fx_addsy != NULL
4381 || fixP->fx_r_type == (int) R_HPPA_NONE)
252b5132 4382#ifdef OBJ_SOM
dc1fc56b 4383 && fmt != 32
252b5132 4384#endif
dc1fc56b
AM
4385 )
4386 new_val = ((fmt == 12 || fmt == 17 || fmt == 22) ? 8 : 0);
252b5132 4387#ifdef OBJ_SOM
dc1fc56b
AM
4388 /* These field selectors imply that we do not want an addend. */
4389 else if (hppa_fixP->fx_r_field == e_psel
4390 || hppa_fixP->fx_r_field == e_rpsel
4391 || hppa_fixP->fx_r_field == e_lpsel
4392 || hppa_fixP->fx_r_field == e_tsel
4393 || hppa_fixP->fx_r_field == e_rtsel
4394 || hppa_fixP->fx_r_field == e_ltsel)
4395 new_val = ((fmt == 12 || fmt == 17 || fmt == 22) ? 8 : 0);
4396 /* This is truly disgusting. The machine independent code blindly
4397 adds in the value of the symbol being relocated against. Damn! */
4398 else if (fmt == 32
4399 && fixP->fx_addsy != NULL
4400 && S_GET_SEGMENT (fixP->fx_addsy) != bfd_com_section_ptr)
4401 new_val = hppa_field_adjust (*valp - S_GET_VALUE (fixP->fx_addsy),
4402 0, hppa_fixP->fx_r_field);
252b5132 4403#endif
dc1fc56b
AM
4404 else
4405 new_val = hppa_field_adjust (*valp, 0, hppa_fixP->fx_r_field);
4406
4407 /* Handle pc-relative exceptions from above. */
4408 if ((fmt == 12 || fmt == 17 || fmt == 22)
4409 && fixP->fx_addsy
4410 && fixP->fx_pcrel
4411 && !arg_reloc_stub_needed (symbol_arg_reloc_info (fixP->fx_addsy),
4412 hppa_fixP->fx_arg_reloc)
27df9f40 4413#ifdef OBJ_ELF
dc1fc56b
AM
4414 && (*valp - 8 + 8192 < 16384
4415 || (fmt == 17 && *valp - 8 + 262144 < 524288)
4416 || (fmt == 22 && *valp - 8 + 8388608 < 16777216))
27df9f40
AM
4417#endif
4418#ifdef OBJ_SOM
dc1fc56b
AM
4419 && (*valp - 8 + 262144 < 524288
4420 || (fmt == 22 && *valp - 8 + 8388608 < 16777216))
27df9f40 4421#endif
dc1fc56b
AM
4422 && !S_IS_EXTERNAL (fixP->fx_addsy)
4423 && !S_IS_WEAK (fixP->fx_addsy)
4424 && S_GET_SEGMENT (fixP->fx_addsy) == hppa_fixP->segment
4425 && !(fixP->fx_subsy
4426 && S_GET_SEGMENT (fixP->fx_subsy) != hppa_fixP->segment))
4427 {
4428 new_val = hppa_field_adjust (*valp, 0, hppa_fixP->fx_r_field);
4429 }
3f9b03b5 4430
dc1fc56b
AM
4431 switch (fmt)
4432 {
4433 case 10:
4434 CHECK_FIELD (new_val, 8191, -8192, 0);
4435 val = new_val;
a02fab7e 4436
dc1fc56b
AM
4437 insn = (insn & ~ 0x3ff1) | (((val & 0x1ff8) << 1)
4438 | ((val & 0x2000) >> 13));
4439 break;
4440 case -11:
4441 CHECK_FIELD (new_val, 8191, -8192, 0);
4442 val = new_val;
a02fab7e 4443
dc1fc56b
AM
4444 insn = (insn & ~ 0x3ff9) | (((val & 0x1ffc) << 1)
4445 | ((val & 0x2000) >> 13));
4446 break;
4447 /* Handle all opcodes with the 'j' operand type. */
4448 case 14:
4449 CHECK_FIELD (new_val, 8191, -8192, 0);
4450 val = new_val;
252b5132 4451
dc1fc56b
AM
4452 insn = ((insn & ~ 0x3fff) | low_sign_unext (val, 14));
4453 break;
252b5132 4454
dc1fc56b
AM
4455 /* Handle all opcodes with the 'k' operand type. */
4456 case 21:
4457 CHECK_FIELD (new_val, 1048575, -1048576, 0);
4458 val = new_val;
3f9b03b5 4459
dc1fc56b
AM
4460 insn = (insn & ~ 0x1fffff) | re_assemble_21 (val);
4461 break;
252b5132 4462
dc1fc56b
AM
4463 /* Handle all the opcodes with the 'i' operand type. */
4464 case 11:
4465 CHECK_FIELD (new_val, 1023, -1023, 0);
4466 val = new_val;
252b5132 4467
dc1fc56b
AM
4468 insn = (insn & ~ 0x7ff) | low_sign_unext (val, 11);
4469 break;
252b5132 4470
dc1fc56b
AM
4471 /* Handle all the opcodes with the 'w' operand type. */
4472 case 12:
4473 CHECK_FIELD (new_val - 8, 8191, -8192, 0);
4474 val = new_val - 8;
252b5132 4475
dc1fc56b
AM
4476 insn = (insn & ~ 0x1ffd) | re_assemble_12 (val >> 2);
4477 break;
252b5132 4478
dc1fc56b
AM
4479 /* Handle some of the opcodes with the 'W' operand type. */
4480 case 17:
4481 {
4482 offsetT distance = *valp;
252b5132 4483
dc1fc56b
AM
4484 /* If this is an absolute branch (ie no link) with an out of
4485 range target, then we want to complain. */
4486 if (fixP->fx_r_type == (int) R_HPPA_PCREL_CALL
4487 && (insn & 0xffe00000) == 0xe8000000)
4488 CHECK_FIELD (distance - 8, 262143, -262144, 0);
3f9b03b5 4489
dc1fc56b
AM
4490 CHECK_FIELD (new_val - 8, 262143, -262144, 0);
4491 val = new_val - 8;
252b5132 4492
dc1fc56b
AM
4493 insn = (insn & ~ 0x1f1ffd) | re_assemble_17 (val >> 2);
4494 break;
4495 }
77c02e18 4496
dc1fc56b
AM
4497 case 22:
4498 {
4499 offsetT distance = *valp;
77c02e18 4500
dc1fc56b
AM
4501 /* If this is an absolute branch (ie no link) with an out of
4502 range target, then we want to complain. */
4503 if (fixP->fx_r_type == (int) R_HPPA_PCREL_CALL
4504 && (insn & 0xffe00000) == 0xe8000000)
4505 CHECK_FIELD (distance - 8, 8388607, -8388608, 0);
3f9b03b5 4506
dc1fc56b
AM
4507 CHECK_FIELD (new_val - 8, 8388607, -8388608, 0);
4508 val = new_val - 8;
77c02e18 4509
dc1fc56b
AM
4510 insn = (insn & ~ 0x3ff1ffd) | re_assemble_22 (val >> 2);
4511 break;
4512 }
ad1079af 4513
dc1fc56b
AM
4514 case -10:
4515 val = new_val;
4516 insn = (insn & ~ 0xfff1) | re_assemble_16 (val & -8);
4517 break;
ad1079af 4518
dc1fc56b
AM
4519 case -16:
4520 val = new_val;
4521 insn = (insn & ~ 0xfff9) | re_assemble_16 (val & -4);
4522 break;
ad1079af 4523
dc1fc56b
AM
4524 case 16:
4525 val = new_val;
4526 insn = (insn & ~ 0xffff) | re_assemble_16 (val);
4527 break;
252b5132 4528
dc1fc56b
AM
4529 case 32:
4530 insn = new_val;
4531 break;
252b5132 4532
dc1fc56b
AM
4533 default:
4534 as_bad (_("Unknown relocation encountered in md_apply_fix."));
252b5132
RH
4535 return 0;
4536 }
dc1fc56b
AM
4537
4538 /* Insert the relocation. */
4539 bfd_put_32 (stdoutput, insn, buf);
4540 return 1;
252b5132
RH
4541}
4542
4543/* Exactly what point is a PC-relative offset relative TO?
4544 On the PA, they're relative to the address of the offset. */
4545
4546long
4547md_pcrel_from (fixP)
4548 fixS *fixP;
4549{
4550 return fixP->fx_where + fixP->fx_frag->fr_address;
4551}
4552
4553/* Return nonzero if the input line pointer is at the end of
4554 a statement. */
4555
4556static int
4557is_end_of_statement ()
4558{
4559 return ((*input_line_pointer == '\n')
4560 || (*input_line_pointer == ';')
4561 || (*input_line_pointer == '!'));
4562}
4563
4564/* Read a number from S. The number might come in one of many forms,
4565 the most common will be a hex or decimal constant, but it could be
4566 a pre-defined register (Yuk!), or an absolute symbol.
4567
ecacdc7a
AM
4568 Return 1 on success or 0 on failure. If STRICT, then a missing
4569 register prefix will cause a failure. The number itself is
4570 returned in `pa_number'.
252b5132 4571
ecacdc7a
AM
4572 IS_FLOAT indicates that a PA-89 FP register number should be
4573 parsed; A `l' or `r' suffix is checked for if but 2 of IS_FLOAT is
4574 not set.
252b5132
RH
4575
4576 pa_parse_number can not handle negative constants and will fail
4577 horribly if it is passed such a constant. */
4578
4579static int
ecacdc7a 4580pa_parse_number (s, is_float)
252b5132 4581 char **s;
ecacdc7a 4582 int is_float;
252b5132
RH
4583{
4584 int num;
4585 char *name;
4586 char c;
4587 symbolS *sym;
4588 int status;
4589 char *p = *s;
ecacdc7a 4590 boolean have_prefix;
252b5132
RH
4591
4592 /* Skip whitespace before the number. */
4593 while (*p == ' ' || *p == '\t')
4594 p = p + 1;
4595
ecacdc7a
AM
4596 pa_number = -1;
4597 have_prefix = 0;
4598 num = 0;
4599 if (!strict && isdigit (*p))
252b5132
RH
4600 {
4601 /* Looks like a number. */
252b5132
RH
4602
4603 if (*p == '0' && (*(p + 1) == 'x' || *(p + 1) == 'X'))
4604 {
4605 /* The number is specified in hex. */
4606 p += 2;
4607 while (isdigit (*p) || ((*p >= 'a') && (*p <= 'f'))
4608 || ((*p >= 'A') && (*p <= 'F')))
4609 {
4610 if (isdigit (*p))
4611 num = num * 16 + *p - '0';
4612 else if (*p >= 'a' && *p <= 'f')
4613 num = num * 16 + *p - 'a' + 10;
4614 else
4615 num = num * 16 + *p - 'A' + 10;
4616 ++p;
4617 }
4618 }
4619 else
4620 {
4621 /* The number is specified in decimal. */
4622 while (isdigit (*p))
4623 {
4624 num = num * 10 + *p - '0';
4625 ++p;
4626 }
4627 }
4628
ecacdc7a 4629 pa_number = num;
252b5132 4630
ecacdc7a
AM
4631 /* Check for a `l' or `r' suffix. */
4632 if (is_float)
4633 {
4634 pa_number += FP_REG_BASE;
4635 if (! (is_float & 2))
252b5132 4636 {
ecacdc7a
AM
4637 if (IS_R_SELECT (p))
4638 {
4639 pa_number += FP_REG_RSEL;
4640 ++p;
4641 }
4642 else if (IS_L_SELECT (p))
4643 {
4644 ++p;
4645 }
252b5132 4646 }
252b5132
RH
4647 }
4648 }
4649 else if (*p == '%')
4650 {
4651 /* The number might be a predefined register. */
ecacdc7a 4652 have_prefix = 1;
252b5132
RH
4653 name = p;
4654 p++;
4655 c = *p;
4656 /* Tege hack: Special case for general registers as the general
4657 code makes a binary search with case translation, and is VERY
a28a3ccf 4658 slow. */
252b5132
RH
4659 if (c == 'r')
4660 {
4661 p++;
4662 if (*p == 'e' && *(p + 1) == 't'
4663 && (*(p + 2) == '0' || *(p + 2) == '1'))
4664 {
4665 p += 2;
4666 num = *p - '0' + 28;
4667 p++;
4668 }
4669 else if (*p == 'p')
4670 {
4671 num = 2;
4672 p++;
4673 }
4674 else if (!isdigit (*p))
4675 {
4676 if (print_errors)
4677 as_bad (_("Undefined register: '%s'."), name);
4678 num = -1;
4679 }
4680 else
4681 {
4682 do
4683 num = num * 10 + *p++ - '0';
4684 while (isdigit (*p));
4685 }
4686 }
4687 else
4688 {
4689 /* Do a normal register search. */
4690 while (is_part_of_name (c))
4691 {
4692 p = p + 1;
4693 c = *p;
4694 }
4695 *p = 0;
4696 status = reg_name_search (name);
4697 if (status >= 0)
4698 num = status;
4699 else
4700 {
4701 if (print_errors)
4702 as_bad (_("Undefined register: '%s'."), name);
4703 num = -1;
4704 }
4705 *p = c;
4706 }
4707
ecacdc7a 4708 pa_number = num;
252b5132
RH
4709 }
4710 else
4711 {
4712 /* And finally, it could be a symbol in the absolute section which
ecacdc7a 4713 is effectively a constant, or a register alias symbol. */
252b5132
RH
4714 name = p;
4715 c = *p;
4716 while (is_part_of_name (c))
4717 {
4718 p = p + 1;
4719 c = *p;
4720 }
4721 *p = 0;
4722 if ((sym = symbol_find (name)) != NULL)
4723 {
ecacdc7a
AM
4724 if (S_GET_SEGMENT (sym) == reg_section)
4725 {
4726 num = S_GET_VALUE (sym);
4727 /* Well, we don't really have one, but we do have a
4728 register, so... */
4729 have_prefix = true;
4730 }
4731 else if (S_GET_SEGMENT (sym) == &bfd_abs_section)
252b5132 4732 num = S_GET_VALUE (sym);
ecacdc7a 4733 else if (!strict)
252b5132
RH
4734 {
4735 if (print_errors)
4736 as_bad (_("Non-absolute symbol: '%s'."), name);
4737 num = -1;
4738 }
4739 }
ecacdc7a 4740 else if (!strict)
252b5132
RH
4741 {
4742 /* There is where we'd come for an undefined symbol
4743 or for an empty string. For an empty string we
4744 will return zero. That's a concession made for
4745 compatability with the braindamaged HP assemblers. */
4746 if (*name == 0)
4747 num = 0;
4748 else
4749 {
4750 if (print_errors)
4751 as_bad (_("Undefined absolute constant: '%s'."), name);
4752 num = -1;
4753 }
4754 }
4755 *p = c;
4756
ecacdc7a 4757 pa_number = num;
252b5132
RH
4758 }
4759
ecacdc7a
AM
4760 if (!strict || have_prefix)
4761 {
4762 *s = p;
4763 return 1;
4764 }
4765 return 0;
252b5132
RH
4766}
4767
4768#define REG_NAME_CNT (sizeof(pre_defined_registers) / sizeof(struct pd_reg))
4769
4770/* Given NAME, find the register number associated with that name, return
4771 the integer value associated with the given name or -1 on failure. */
4772
4773static int
4774reg_name_search (name)
4775 char *name;
4776{
4777 int middle, low, high;
4778 int cmp;
4779
4780 low = 0;
4781 high = REG_NAME_CNT - 1;
4782
4783 do
4784 {
4785 middle = (low + high) / 2;
4786 cmp = strcasecmp (name, pre_defined_registers[middle].name);
4787 if (cmp < 0)
4788 high = middle - 1;
4789 else if (cmp > 0)
4790 low = middle + 1;
4791 else
4792 return pre_defined_registers[middle].value;
4793 }
4794 while (low <= high);
4795
4796 return -1;
4797}
4798
252b5132
RH
4799/* Return nonzero if the given INSN and L/R information will require
4800 a new PA-1.1 opcode. */
4801
4802static int
ecacdc7a 4803need_pa11_opcode ()
252b5132 4804{
ecacdc7a
AM
4805 if ((pa_number & FP_REG_RSEL) != 0
4806 && !(the_insn.fpof1 == DBL && the_insn.fpof2 == DBL))
252b5132
RH
4807 {
4808 /* If this instruction is specific to a particular architecture,
4809 then set a new architecture. */
4810 if (bfd_get_mach (stdoutput) < pa11)
4811 {
4812 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, pa11))
4813 as_warn (_("could not update architecture and machine"));
4814 }
4815 return TRUE;
4816 }
4817 else
4818 return FALSE;
4819}
4820
4821/* Parse a condition for a fcmp instruction. Return the numerical
4822 code associated with the condition. */
4823
4824static int
4825pa_parse_fp_cmp_cond (s)
4826 char **s;
4827{
4828 int cond, i;
4829
4830 cond = 0;
4831
4832 for (i = 0; i < 32; i++)
4833 {
4834 if (strncasecmp (*s, fp_cond_map[i].string,
4835 strlen (fp_cond_map[i].string)) == 0)
4836 {
4837 cond = fp_cond_map[i].cond;
4838 *s += strlen (fp_cond_map[i].string);
4839 /* If not a complete match, back up the input string and
4840 report an error. */
4841 if (**s != ' ' && **s != '\t')
4842 {
4843 *s -= strlen (fp_cond_map[i].string);
4844 break;
4845 }
4846 while (**s == ' ' || **s == '\t')
4847 *s = *s + 1;
4848 return cond;
4849 }
4850 }
4851
4852 as_bad (_("Invalid FP Compare Condition: %s"), *s);
4853
4854 /* Advance over the bogus completer. */
4855 while (**s != ',' && **s != ' ' && **s != '\t')
4856 *s += 1;
4857
4858 return 0;
4859}
4860
1cf6ae67
JL
4861/* Parse a graphics test complete for ftest. */
4862
4863static int
4864pa_parse_ftest_gfx_completer (s)
4865 char **s;
4866{
4867 int value;
4868
4869 value = 0;
4870 if (strncasecmp (*s, "acc8", 4) == 0)
4871 {
4872 value = 5;
4873 *s += 4;
4874 }
4875 else if (strncasecmp (*s, "acc6", 4) == 0)
4876 {
4877 value = 9;
4878 *s += 4;
4879 }
4880 else if (strncasecmp (*s, "acc4", 4) == 0)
4881 {
4882 value = 13;
4883 *s += 4;
4884 }
4885 else if (strncasecmp (*s, "acc2", 4) == 0)
4886 {
4887 value = 17;
4888 *s += 4;
4889 }
4890 else if (strncasecmp (*s, "acc", 3) == 0)
4891 {
4892 value = 1;
4893 *s += 3;
4894 }
4895 else if (strncasecmp (*s, "rej8", 4) == 0)
4896 {
4897 value = 6;
4898 *s += 4;
4899 }
4900 else if (strncasecmp (*s, "rej", 3) == 0)
4901 {
4902 value = 2;
4903 *s += 3;
4904 }
4905 else
4906 {
4907 value = 0;
4908 as_bad (_("Invalid FTEST completer: %s"), *s);
4909 }
4910
4911 return value;
4912}
4913
4914/* Parse an FP operand format completer returning the completer
4915 type. */
4916
4917static fp_operand_format
4918pa_parse_fp_cnv_format (s)
4919 char **s;
4920{
4921 int format;
4922
4923 format = SGL;
4924 if (**s == ',')
4925 {
4926 *s += 1;
4927 if (strncasecmp (*s, "sgl", 3) == 0)
4928 {
4929 format = SGL;
4930 *s += 4;
4931 }
4932 else if (strncasecmp (*s, "dbl", 3) == 0)
4933 {
4934 format = DBL;
4935 *s += 4;
4936 }
4937 else if (strncasecmp (*s, "quad", 4) == 0)
4938 {
4939 format = QUAD;
4940 *s += 5;
4941 }
4942 else if (strncasecmp (*s, "w", 1) == 0)
4943 {
4944 format = W;
4945 *s += 2;
4946 }
4947 else if (strncasecmp (*s, "uw", 2) == 0)
4948 {
4949 format = UW;
4950 *s += 3;
4951 }
4952 else if (strncasecmp (*s, "dw", 2) == 0)
4953 {
4954 format = DW;
4955 *s += 3;
4956 }
4957 else if (strncasecmp (*s, "udw", 3) == 0)
4958 {
4959 format = UDW;
4960 *s += 4;
4961 }
4962 else if (strncasecmp (*s, "qw", 2) == 0)
4963 {
4964 format = QW;
4965 *s += 3;
4966 }
4967 else if (strncasecmp (*s, "uqw", 3) == 0)
4968 {
4969 format = UQW;
4970 *s += 4;
4971 }
4972 else
4973 {
4974 format = ILLEGAL_FMT;
4975 as_bad (_("Invalid FP Operand Format: %3s"), *s);
4976 }
4977 }
4978
4979 return format;
4980}
252b5132
RH
4981
4982/* Parse an FP operand format completer returning the completer
4983 type. */
4984
4985static fp_operand_format
4986pa_parse_fp_format (s)
4987 char **s;
4988{
4989 int format;
4990
4991 format = SGL;
4992 if (**s == ',')
4993 {
4994 *s += 1;
4995 if (strncasecmp (*s, "sgl", 3) == 0)
4996 {
4997 format = SGL;
4998 *s += 4;
4999 }
5000 else if (strncasecmp (*s, "dbl", 3) == 0)
5001 {
5002 format = DBL;
5003 *s += 4;
5004 }
5005 else if (strncasecmp (*s, "quad", 4) == 0)
5006 {
5007 format = QUAD;
5008 *s += 5;
5009 }
5010 else
5011 {
5012 format = ILLEGAL_FMT;
5013 as_bad (_("Invalid FP Operand Format: %3s"), *s);
5014 }
5015 }
5016
5017 return format;
5018}
5019
5020/* Convert from a selector string into a selector type. */
5021
5022static int
5023pa_chk_field_selector (str)
5024 char **str;
5025{
5026 int middle, low, high;
5027 int cmp;
5028 char name[4];
5029
5030 /* Read past any whitespace. */
5031 /* FIXME: should we read past newlines and formfeeds??? */
5032 while (**str == ' ' || **str == '\t' || **str == '\n' || **str == '\f')
5033 *str = *str + 1;
5034
5035 if ((*str)[1] == '\'' || (*str)[1] == '%')
5036 name[0] = tolower ((*str)[0]),
5037 name[1] = 0;
5038 else if ((*str)[2] == '\'' || (*str)[2] == '%')
5039 name[0] = tolower ((*str)[0]),
5040 name[1] = tolower ((*str)[1]),
5041 name[2] = 0;
252b5132
RH
5042 else if ((*str)[3] == '\'' || (*str)[3] == '%')
5043 name[0] = tolower ((*str)[0]),
5044 name[1] = tolower ((*str)[1]),
5045 name[2] = tolower ((*str)[2]),
5046 name[3] = 0;
252b5132
RH
5047 else
5048 return e_fsel;
5049
5050 low = 0;
5051 high = sizeof (selector_table) / sizeof (struct selector_entry) - 1;
5052
5053 do
5054 {
5055 middle = (low + high) / 2;
5056 cmp = strcmp (name, selector_table[middle].prefix);
5057 if (cmp < 0)
5058 high = middle - 1;
5059 else if (cmp > 0)
5060 low = middle + 1;
5061 else
5062 {
5063 *str += strlen (name) + 1;
5064#ifndef OBJ_SOM
5065 if (selector_table[middle].field_selector == e_nsel)
5066 return e_fsel;
5067#endif
5068 return selector_table[middle].field_selector;
5069 }
5070 }
5071 while (low <= high);
5072
5073 return e_fsel;
5074}
5075
5076/* Mark (via expr_end) the end of an expression (I think). FIXME. */
5077
5078static int
5079get_expression (str)
5080 char *str;
5081{
5082 char *save_in;
5083 asection *seg;
5084
5085 save_in = input_line_pointer;
5086 input_line_pointer = str;
5087 seg = expression (&the_insn.exp);
5088 if (!(seg == absolute_section
5089 || seg == undefined_section
5090 || SEG_NORMAL (seg)))
5091 {
5092 as_warn (_("Bad segment in expression."));
5093 expr_end = input_line_pointer;
5094 input_line_pointer = save_in;
5095 return 1;
5096 }
5097 expr_end = input_line_pointer;
5098 input_line_pointer = save_in;
5099 return 0;
5100}
5101
a28a3ccf 5102/* Mark (via expr_end) the end of an absolute expression. FIXME. */
252b5132
RH
5103static int
5104pa_get_absolute_expression (insn, strp)
5105 struct pa_it *insn;
5106 char **strp;
5107{
5108 char *save_in;
5109
5110 insn->field_selector = pa_chk_field_selector (strp);
5111 save_in = input_line_pointer;
5112 input_line_pointer = *strp;
5113 expression (&insn->exp);
5114 /* This is not perfect, but is a huge improvement over doing nothing.
5115
5116 The PA assembly syntax is ambigious in a variety of ways. Consider
5117 this string "4 %r5" Is that the number 4 followed by the register
ecacdc7a 5118 r5, or is that 4 MOD r5?
252b5132
RH
5119
5120 If we get a modulo expresion When looking for an absolute, we try
5121 again cutting off the input string at the first whitespace character. */
5122 if (insn->exp.X_op == O_modulus)
5123 {
5124 char *s, c;
5125 int retval;
5126
5127 input_line_pointer = *strp;
5128 s = *strp;
5129 while (*s != ',' && *s != ' ' && *s != '\t')
5130 s++;
5131
5132 c = *s;
5133 *s = 0;
5134
5135 retval = pa_get_absolute_expression (insn, strp);
5136
5137 input_line_pointer = save_in;
5138 *s = c;
5139 return evaluate_absolute (insn);
5140 }
0f4f8b56
JL
5141 /* When in strict mode we have a non-match, fix up the pointers
5142 and return to our caller. */
5143 if (insn->exp.X_op != O_constant && strict)
5144 {
5145 expr_end = input_line_pointer;
5146 input_line_pointer = save_in;
5147 return 0;
5148 }
252b5132
RH
5149 if (insn->exp.X_op != O_constant)
5150 {
5151 as_bad (_("Bad segment (should be absolute)."));
5152 expr_end = input_line_pointer;
5153 input_line_pointer = save_in;
5154 return 0;
5155 }
5156 expr_end = input_line_pointer;
5157 input_line_pointer = save_in;
5158 return evaluate_absolute (insn);
5159}
5160
5161/* Evaluate an absolute expression EXP which may be modified by
5162 the selector FIELD_SELECTOR. Return the value of the expression. */
5163static int
5164evaluate_absolute (insn)
5165 struct pa_it *insn;
5166{
3f9b03b5 5167 offsetT value;
252b5132
RH
5168 expressionS exp;
5169 int field_selector = insn->field_selector;
5170
5171 exp = insn->exp;
5172 value = exp.X_add_number;
5173
3f9b03b5 5174 return hppa_field_adjust (0, value, field_selector);
252b5132
RH
5175}
5176
5177/* Given an argument location specification return the associated
5178 argument location number. */
5179
5180static unsigned int
5181pa_build_arg_reloc (type_name)
5182 char *type_name;
5183{
5184
5185 if (strncasecmp (type_name, "no", 2) == 0)
5186 return 0;
5187 if (strncasecmp (type_name, "gr", 2) == 0)
5188 return 1;
5189 else if (strncasecmp (type_name, "fr", 2) == 0)
5190 return 2;
5191 else if (strncasecmp (type_name, "fu", 2) == 0)
5192 return 3;
5193 else
5194 as_bad (_("Invalid argument location: %s\n"), type_name);
5195
5196 return 0;
5197}
5198
5199/* Encode and return an argument relocation specification for
5200 the given register in the location specified by arg_reloc. */
5201
5202static unsigned int
5203pa_align_arg_reloc (reg, arg_reloc)
5204 unsigned int reg;
5205 unsigned int arg_reloc;
5206{
5207 unsigned int new_reloc;
5208
5209 new_reloc = arg_reloc;
5210 switch (reg)
5211 {
5212 case 0:
5213 new_reloc <<= 8;
5214 break;
5215 case 1:
5216 new_reloc <<= 6;
5217 break;
5218 case 2:
5219 new_reloc <<= 4;
5220 break;
5221 case 3:
5222 new_reloc <<= 2;
5223 break;
5224 default:
5225 as_bad (_("Invalid argument description: %d"), reg);
5226 }
5227
5228 return new_reloc;
5229}
5230
5231/* Parse a PA nullification completer (,n). Return nonzero if the
5232 completer was found; return zero if no completer was found. */
5233
5234static int
5235pa_parse_nullif (s)
5236 char **s;
5237{
5238 int nullif;
5239
5240 nullif = 0;
5241 if (**s == ',')
5242 {
5243 *s = *s + 1;
5244 if (strncasecmp (*s, "n", 1) == 0)
5245 nullif = 1;
5246 else
5247 {
5248 as_bad (_("Invalid Nullification: (%c)"), **s);
5249 nullif = 0;
5250 }
5251 *s = *s + 1;
5252 }
5253
5254 return nullif;
5255}
5256
5257/* Parse a non-negated compare/subtract completer returning the
5258 number (for encoding in instrutions) of the given completer.
5259
5260 ISBRANCH specifies whether or not this is parsing a condition
5261 completer for a branch (vs a nullification completer for a
5262 computational instruction. */
5263
5264static int
5265pa_parse_nonneg_cmpsub_cmpltr (s, isbranch)
5266 char **s;
5267 int isbranch;
5268{
5269 int cmpltr;
5270 char *name = *s + 1;
5271 char c;
5272 char *save_s = *s;
5273 int nullify = 0;
5274
5275 cmpltr = 0;
5276 if (**s == ',')
5277 {
5278 *s += 1;
5279 while (**s != ',' && **s != ' ' && **s != '\t')
5280 *s += 1;
5281 c = **s;
5282 **s = 0x00;
5283
252b5132
RH
5284 if (strcmp (name, "=") == 0)
5285 {
5286 cmpltr = 1;
5287 }
5288 else if (strcmp (name, "<") == 0)
5289 {
5290 cmpltr = 2;
5291 }
5292 else if (strcmp (name, "<=") == 0)
5293 {
5294 cmpltr = 3;
5295 }
5296 else if (strcmp (name, "<<") == 0)
5297 {
5298 cmpltr = 4;
5299 }
5300 else if (strcmp (name, "<<=") == 0)
5301 {
5302 cmpltr = 5;
5303 }
5304 else if (strcasecmp (name, "sv") == 0)
5305 {
5306 cmpltr = 6;
5307 }
5308 else if (strcasecmp (name, "od") == 0)
5309 {
5310 cmpltr = 7;
5311 }
5312 /* If we have something like addb,n then there is no condition
5313 completer. */
5314 else if (strcasecmp (name, "n") == 0 && isbranch)
5315 {
5316 cmpltr = 0;
5317 nullify = 1;
5318 }
5319 else
5320 {
5321 cmpltr = -1;
5322 }
5323 **s = c;
5324 }
5325
5326 /* Reset pointers if this was really a ,n for a branch instruction. */
5327 if (nullify)
5328 *s = save_s;
5329
252b5132
RH
5330 return cmpltr;
5331}
5332
5333/* Parse a negated compare/subtract completer returning the
5334 number (for encoding in instrutions) of the given completer.
5335
5336 ISBRANCH specifies whether or not this is parsing a condition
5337 completer for a branch (vs a nullification completer for a
5338 computational instruction. */
5339
5340static int
5341pa_parse_neg_cmpsub_cmpltr (s, isbranch)
5342 char **s;
5343 int isbranch;
5344{
5345 int cmpltr;
5346 char *name = *s + 1;
5347 char c;
5348 char *save_s = *s;
5349 int nullify = 0;
5350
5351 cmpltr = 0;
5352 if (**s == ',')
5353 {
5354 *s += 1;
5355 while (**s != ',' && **s != ' ' && **s != '\t')
5356 *s += 1;
5357 c = **s;
5358 **s = 0x00;
5359
252b5132
RH
5360 if (strcasecmp (name, "tr") == 0)
5361 {
5362 cmpltr = 0;
5363 }
5364 else if (strcmp (name, "<>") == 0)
5365 {
5366 cmpltr = 1;
5367 }
5368 else if (strcmp (name, ">=") == 0)
5369 {
5370 cmpltr = 2;
5371 }
5372 else if (strcmp (name, ">") == 0)
5373 {
5374 cmpltr = 3;
5375 }
5376 else if (strcmp (name, ">>=") == 0)
5377 {
5378 cmpltr = 4;
5379 }
5380 else if (strcmp (name, ">>") == 0)
5381 {
5382 cmpltr = 5;
5383 }
5384 else if (strcasecmp (name, "nsv") == 0)
5385 {
5386 cmpltr = 6;
5387 }
5388 else if (strcasecmp (name, "ev") == 0)
5389 {
5390 cmpltr = 7;
5391 }
5392 /* If we have something like addb,n then there is no condition
5393 completer. */
5394 else if (strcasecmp (name, "n") == 0 && isbranch)
5395 {
5396 cmpltr = 0;
5397 nullify = 1;
5398 }
5399 else
5400 {
5401 cmpltr = -1;
5402 }
5403 **s = c;
5404 }
5405
5406 /* Reset pointers if this was really a ,n for a branch instruction. */
5407 if (nullify)
5408 *s = save_s;
5409
252b5132
RH
5410 return cmpltr;
5411}
5412
d53d2751
JL
5413/* Parse a 64 bit compare and branch completer returning the number (for
5414 encoding in instrutions) of the given completer.
5415
5416 Nonnegated comparisons are returned as 0-7, negated comparisons are
5417 returned as 8-15. */
5418
5419static int
5420pa_parse_cmpb_64_cmpltr (s)
5421 char **s;
5422{
5423 int cmpltr;
5424 char *name = *s + 1;
5425 char c;
d53d2751
JL
5426
5427 cmpltr = -1;
5428 if (**s == ',')
5429 {
5430 *s += 1;
5431 while (**s != ',' && **s != ' ' && **s != '\t')
5432 *s += 1;
5433 c = **s;
5434 **s = 0x00;
5435
5436 if (strcmp (name, "*") == 0)
5437 {
5438 cmpltr = 0;
5439 }
5440 else if (strcmp (name, "*=") == 0)
5441 {
5442 cmpltr = 1;
5443 }
5444 else if (strcmp (name, "*<") == 0)
5445 {
5446 cmpltr = 2;
5447 }
5448 else if (strcmp (name, "*<=") == 0)
5449 {
5450 cmpltr = 3;
5451 }
5452 else if (strcmp (name, "*<<") == 0)
5453 {
5454 cmpltr = 4;
5455 }
5456 else if (strcmp (name, "*<<=") == 0)
5457 {
5458 cmpltr = 5;
5459 }
5460 else if (strcasecmp (name, "*sv") == 0)
5461 {
5462 cmpltr = 6;
5463 }
5464 else if (strcasecmp (name, "*od") == 0)
5465 {
5466 cmpltr = 7;
5467 }
5468 else if (strcasecmp (name, "*tr") == 0)
5469 {
5470 cmpltr = 8;
5471 }
5472 else if (strcmp (name, "*<>") == 0)
5473 {
5474 cmpltr = 9;
5475 }
5476 else if (strcmp (name, "*>=") == 0)
5477 {
5478 cmpltr = 10;
5479 }
5480 else if (strcmp (name, "*>") == 0)
5481 {
5482 cmpltr = 11;
5483 }
5484 else if (strcmp (name, "*>>=") == 0)
5485 {
5486 cmpltr = 12;
5487 }
5488 else if (strcmp (name, "*>>") == 0)
5489 {
5490 cmpltr = 13;
5491 }
5492 else if (strcasecmp (name, "*nsv") == 0)
5493 {
5494 cmpltr = 14;
5495 }
5496 else if (strcasecmp (name, "*ev") == 0)
5497 {
5498 cmpltr = 15;
5499 }
5500 else
5501 {
5502 cmpltr = -1;
5503 }
5504 **s = c;
5505 }
5506
d53d2751
JL
5507 return cmpltr;
5508}
5509
5510/* Parse a 64 bit compare immediate and branch completer returning the number
5511 (for encoding in instrutions) of the given completer. */
5512
5513static int
5514pa_parse_cmpib_64_cmpltr (s)
5515 char **s;
5516{
5517 int cmpltr;
5518 char *name = *s + 1;
5519 char c;
d53d2751
JL
5520
5521 cmpltr = -1;
5522 if (**s == ',')
5523 {
5524 *s += 1;
5525 while (**s != ',' && **s != ' ' && **s != '\t')
5526 *s += 1;
5527 c = **s;
5528 **s = 0x00;
5529
5530 if (strcmp (name, "*<<") == 0)
5531 {
5532 cmpltr = 0;
5533 }
5534 else if (strcmp (name, "*=") == 0)
5535 {
5536 cmpltr = 1;
5537 }
5538 else if (strcmp (name, "*<") == 0)
5539 {
5540 cmpltr = 2;
5541 }
5542 else if (strcmp (name, "*<=") == 0)
5543 {
5544 cmpltr = 3;
5545 }
5546 else if (strcmp (name, "*>>=") == 0)
5547 {
5548 cmpltr = 4;
5549 }
5550 else if (strcmp (name, "*<>") == 0)
5551 {
5552 cmpltr = 5;
5553 }
5554 else if (strcasecmp (name, "*>=") == 0)
5555 {
5556 cmpltr = 6;
5557 }
5558 else if (strcasecmp (name, "*>") == 0)
5559 {
5560 cmpltr = 7;
5561 }
5562 else
5563 {
5564 cmpltr = -1;
5565 }
5566 **s = c;
5567 }
5568
d53d2751
JL
5569 return cmpltr;
5570}
5571
252b5132
RH
5572/* Parse a non-negated addition completer returning the number
5573 (for encoding in instrutions) of the given completer.
5574
5575 ISBRANCH specifies whether or not this is parsing a condition
5576 completer for a branch (vs a nullification completer for a
5577 computational instruction. */
5578
5579static int
5580pa_parse_nonneg_add_cmpltr (s, isbranch)
5581 char **s;
5582 int isbranch;
5583{
5584 int cmpltr;
5585 char *name = *s + 1;
5586 char c;
5587 char *save_s = *s;
5588
5589 cmpltr = 0;
5590 if (**s == ',')
5591 {
5592 *s += 1;
5593 while (**s != ',' && **s != ' ' && **s != '\t')
5594 *s += 1;
5595 c = **s;
5596 **s = 0x00;
5597 if (strcmp (name, "=") == 0)
5598 {
5599 cmpltr = 1;
5600 }
5601 else if (strcmp (name, "<") == 0)
5602 {
5603 cmpltr = 2;
5604 }
5605 else if (strcmp (name, "<=") == 0)
5606 {
5607 cmpltr = 3;
5608 }
5609 else if (strcasecmp (name, "nuv") == 0)
5610 {
5611 cmpltr = 4;
5612 }
5613 else if (strcasecmp (name, "znv") == 0)
5614 {
5615 cmpltr = 5;
5616 }
5617 else if (strcasecmp (name, "sv") == 0)
5618 {
5619 cmpltr = 6;
5620 }
5621 else if (strcasecmp (name, "od") == 0)
5622 {
5623 cmpltr = 7;
5624 }
5625 /* If we have something like addb,n then there is no condition
5626 completer. */
5627 else if (strcasecmp (name, "n") == 0 && isbranch)
5628 {
5629 cmpltr = 0;
5630 }
5631 else
5632 {
5633 cmpltr = -1;
5634 }
5635 **s = c;
5636 }
5637
5638 /* Reset pointers if this was really a ,n for a branch instruction. */
5639 if (cmpltr == 0 && *name == 'n' && isbranch)
5640 *s = save_s;
5641
5642 return cmpltr;
5643}
5644
5645/* Parse a negated addition completer returning the number
5646 (for encoding in instrutions) of the given completer.
5647
5648 ISBRANCH specifies whether or not this is parsing a condition
5649 completer for a branch (vs a nullification completer for a
5650 computational instruction). */
5651
5652static int
5653pa_parse_neg_add_cmpltr (s, isbranch)
5654 char **s;
5655 int isbranch;
5656{
5657 int cmpltr;
5658 char *name = *s + 1;
5659 char c;
5660 char *save_s = *s;
5661
5662 cmpltr = 0;
5663 if (**s == ',')
5664 {
5665 *s += 1;
5666 while (**s != ',' && **s != ' ' && **s != '\t')
5667 *s += 1;
5668 c = **s;
5669 **s = 0x00;
5670 if (strcasecmp (name, "tr") == 0)
5671 {
5672 cmpltr = 0;
5673 }
5674 else if (strcmp (name, "<>") == 0)
5675 {
5676 cmpltr = 1;
5677 }
5678 else if (strcmp (name, ">=") == 0)
5679 {
5680 cmpltr = 2;
5681 }
5682 else if (strcmp (name, ">") == 0)
5683 {
5684 cmpltr = 3;
5685 }
5686 else if (strcasecmp (name, "uv") == 0)
5687 {
5688 cmpltr = 4;
5689 }
5690 else if (strcasecmp (name, "vnz") == 0)
5691 {
5692 cmpltr = 5;
5693 }
5694 else if (strcasecmp (name, "nsv") == 0)
5695 {
5696 cmpltr = 6;
5697 }
5698 else if (strcasecmp (name, "ev") == 0)
5699 {
5700 cmpltr = 7;
5701 }
5702 /* If we have something like addb,n then there is no condition
5703 completer. */
5704 else if (strcasecmp (name, "n") == 0 && isbranch)
5705 {
5706 cmpltr = 0;
5707 }
5708 else
5709 {
5710 cmpltr = -1;
5711 }
5712 **s = c;
5713 }
5714
5715 /* Reset pointers if this was really a ,n for a branch instruction. */
5716 if (cmpltr == 0 && *name == 'n' && isbranch)
5717 *s = save_s;
5718
5719 return cmpltr;
5720}
5721
d53d2751
JL
5722/* Parse a 64 bit wide mode add and branch completer returning the number (for
5723 encoding in instrutions) of the given completer. */
5724
5725static int
5726pa_parse_addb_64_cmpltr (s)
5727 char **s;
5728{
5729 int cmpltr;
5730 char *name = *s + 1;
5731 char c;
5732 char *save_s = *s;
5733 int nullify = 0;
5734
5735 cmpltr = 0;
5736 if (**s == ',')
5737 {
5738 *s += 1;
5739 while (**s != ',' && **s != ' ' && **s != '\t')
5740 *s += 1;
5741 c = **s;
5742 **s = 0x00;
5743 if (strcmp (name, "=") == 0)
5744 {
5745 cmpltr = 1;
5746 }
5747 else if (strcmp (name, "<") == 0)
5748 {
5749 cmpltr = 2;
5750 }
5751 else if (strcmp (name, "<=") == 0)
5752 {
5753 cmpltr = 3;
5754 }
5755 else if (strcasecmp (name, "nuv") == 0)
5756 {
5757 cmpltr = 4;
5758 }
5759 else if (strcasecmp (name, "*=") == 0)
5760 {
5761 cmpltr = 5;
5762 }
5763 else if (strcasecmp (name, "*<") == 0)
5764 {
5765 cmpltr = 6;
5766 }
5767 else if (strcasecmp (name, "*<=") == 0)
5768 {
5769 cmpltr = 7;
5770 }
5771 else if (strcmp (name, "tr") == 0)
5772 {
5773 cmpltr = 8;
5774 }
5775 else if (strcmp (name, "<>") == 0)
5776 {
5777 cmpltr = 9;
5778 }
5779 else if (strcmp (name, ">=") == 0)
5780 {
5781 cmpltr = 10;
5782 }
5783 else if (strcmp (name, ">") == 0)
5784 {
5785 cmpltr = 11;
5786 }
5787 else if (strcasecmp (name, "uv") == 0)
5788 {
5789 cmpltr = 12;
5790 }
5791 else if (strcasecmp (name, "*<>") == 0)
5792 {
5793 cmpltr = 13;
5794 }
5795 else if (strcasecmp (name, "*>=") == 0)
5796 {
5797 cmpltr = 14;
5798 }
5799 else if (strcasecmp (name, "*>") == 0)
5800 {
5801 cmpltr = 15;
5802 }
5803 /* If we have something like addb,n then there is no condition
5804 completer. */
5805 else if (strcasecmp (name, "n") == 0)
5806 {
5807 cmpltr = 0;
5808 nullify = 1;
5809 }
5810 else
5811 {
5812 cmpltr = -1;
5813 }
5814 **s = c;
5815 }
5816
5817 /* Reset pointers if this was really a ,n for a branch instruction. */
5818 if (nullify)
5819 *s = save_s;
5820
5821 return cmpltr;
5822}
5823
49863f82 5824#ifdef OBJ_SOM
252b5132
RH
5825/* Handle an alignment directive. Special so that we can update the
5826 alignment of the subspace if necessary. */
5827static void
5828pa_align (bytes)
5506e1a5 5829 int bytes;
252b5132
RH
5830{
5831 /* We must have a valid space and subspace. */
5832 pa_check_current_space_and_subspace ();
5833
5834 /* Let the generic gas code do most of the work. */
5835 s_align_bytes (bytes);
5836
5837 /* If bytes is a power of 2, then update the current subspace's
5838 alignment if necessary. */
5839 if (log2 (bytes) != -1)
5840 record_alignment (current_subspace->ssd_seg, log2 (bytes));
5841}
49863f82 5842#endif
252b5132
RH
5843
5844/* Handle a .BLOCK type pseudo-op. */
5845
5846static void
5847pa_block (z)
3f9b03b5 5848 int z ATTRIBUTE_UNUSED;
252b5132
RH
5849{
5850 char *p;
5851 long int temp_fill;
5852 unsigned int temp_size;
5853 unsigned int i;
5854
49863f82 5855#ifdef OBJ_SOM
252b5132
RH
5856 /* We must have a valid space and subspace. */
5857 pa_check_current_space_and_subspace ();
49863f82 5858#endif
252b5132
RH
5859
5860 temp_size = get_absolute_expression ();
5861
5862 /* Always fill with zeros, that's what the HP assembler does. */
5863 temp_fill = 0;
5864
5865 p = frag_var (rs_fill, (int) temp_size, (int) temp_size,
5866 (relax_substateT) 0, (symbolS *) 0, (offsetT) 1, NULL);
5867 memset (p, 0, temp_size);
5868
5869 /* Convert 2 bytes at a time. */
5870
5871 for (i = 0; i < temp_size; i += 2)
5872 {
5873 md_number_to_chars (p + i,
5874 (valueT) temp_fill,
5875 (int) ((temp_size - i) > 2 ? 2 : (temp_size - i)));
5876 }
5877
5878 pa_undefine_label ();
5879 demand_empty_rest_of_line ();
5880}
5881
5882/* Handle a .begin_brtab and .end_brtab pseudo-op. */
5883
5884static void
5885pa_brtab (begin)
3f9b03b5 5886 int begin ATTRIBUTE_UNUSED;
252b5132
RH
5887{
5888
5889#ifdef OBJ_SOM
5890 /* The BRTAB relocations are only availble in SOM (to denote
5891 the beginning and end of branch tables). */
5892 char *where = frag_more (0);
5893
5894 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
5895 NULL, (offsetT) 0, NULL,
5896 0, begin ? R_HPPA_BEGIN_BRTAB : R_HPPA_END_BRTAB,
5897 e_fsel, 0, 0, NULL);
5898#endif
5899
5900 demand_empty_rest_of_line ();
5901}
5902
5903/* Handle a .begin_try and .end_try pseudo-op. */
5904
5905static void
5906pa_try (begin)
3f9b03b5 5907 int begin ATTRIBUTE_UNUSED;
252b5132
RH
5908{
5909#ifdef OBJ_SOM
5910 expressionS exp;
5911 char *where = frag_more (0);
5912
5913 if (! begin)
5914 expression (&exp);
5915
5916 /* The TRY relocations are only availble in SOM (to denote
5917 the beginning and end of exception handling regions). */
5918
5919 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
5920 NULL, (offsetT) 0, begin ? NULL : &exp,
5921 0, begin ? R_HPPA_BEGIN_TRY : R_HPPA_END_TRY,
5922 e_fsel, 0, 0, NULL);
5923#endif
5924
5925 demand_empty_rest_of_line ();
5926}
5927
5928/* Handle a .CALL pseudo-op. This involves storing away information
5929 about where arguments are to be found so the linker can detect
5930 (and correct) argument location mismatches between caller and callee. */
5931
5932static void
5933pa_call (unused)
3f9b03b5 5934 int unused ATTRIBUTE_UNUSED;
252b5132 5935{
49863f82 5936#ifdef OBJ_SOM
252b5132
RH
5937 /* We must have a valid space and subspace. */
5938 pa_check_current_space_and_subspace ();
49863f82 5939#endif
252b5132
RH
5940
5941 pa_call_args (&last_call_desc);
5942 demand_empty_rest_of_line ();
5943}
5944
5945/* Do the dirty work of building a call descriptor which describes
5946 where the caller placed arguments to a function call. */
5947
5948static void
5949pa_call_args (call_desc)
5950 struct call_desc *call_desc;
5951{
5952 char *name, c, *p;
5953 unsigned int temp, arg_reloc;
5954
5955 while (!is_end_of_statement ())
5956 {
5957 name = input_line_pointer;
5958 c = get_symbol_end ();
5959 /* Process a source argument. */
5960 if ((strncasecmp (name, "argw", 4) == 0))
5961 {
5962 temp = atoi (name + 4);
5963 p = input_line_pointer;
5964 *p = c;
5965 input_line_pointer++;
5966 name = input_line_pointer;
5967 c = get_symbol_end ();
5968 arg_reloc = pa_build_arg_reloc (name);
5969 call_desc->arg_reloc |= pa_align_arg_reloc (temp, arg_reloc);
5970 }
5971 /* Process a return value. */
5972 else if ((strncasecmp (name, "rtnval", 6) == 0))
5973 {
5974 p = input_line_pointer;
5975 *p = c;
5976 input_line_pointer++;
5977 name = input_line_pointer;
5978 c = get_symbol_end ();
5979 arg_reloc = pa_build_arg_reloc (name);
5980 call_desc->arg_reloc |= (arg_reloc & 0x3);
5981 }
5982 else
5983 {
5984 as_bad (_("Invalid .CALL argument: %s"), name);
5985 }
5986 p = input_line_pointer;
5987 *p = c;
5988 if (!is_end_of_statement ())
5989 input_line_pointer++;
5990 }
5991}
5992
5993/* Return TRUE if FRAG1 and FRAG2 are the same. */
5994
5995static int
5996is_same_frag (frag1, frag2)
5997 fragS *frag1;
5998 fragS *frag2;
5999{
6000
6001 if (frag1 == NULL)
6002 return (FALSE);
6003 else if (frag2 == NULL)
6004 return (FALSE);
6005 else if (frag1 == frag2)
6006 return (TRUE);
6007 else if (frag2->fr_type == rs_fill && frag2->fr_fix == 0)
6008 return (is_same_frag (frag1, frag2->fr_next));
6009 else
6010 return (FALSE);
6011}
6012
6013#ifdef OBJ_ELF
6014/* Build an entry in the UNWIND subspace from the given function
6015 attributes in CALL_INFO. This is not needed for SOM as using
6016 R_ENTRY and R_EXIT relocations allow the linker to handle building
6017 of the unwind spaces. */
6018
6019static void
6020pa_build_unwind_subspace (call_info)
6021 struct call_info *call_info;
6022{
6023 char *unwind;
6024 asection *seg, *save_seg;
3f9b03b5
AM
6025 subsegT save_subseg;
6026 unsigned int i;
6027 int reloc;
252b5132
RH
6028 char c, *p;
6029
f1a1312b 6030 if (now_seg != text_section)
7acbfc6b
JL
6031 return;
6032
9100134c
JL
6033 if (bfd_get_arch_info (stdoutput)->bits_per_address == 32)
6034 reloc = R_PARISC_DIR32;
46031ca9 6035 else
9100134c 6036 reloc = R_PARISC_SEGREL32;
d53d2751 6037
c97305a1
JL
6038 save_seg = now_seg;
6039 save_subseg = now_subseg;
252b5132
RH
6040 /* Get into the right seg/subseg. This may involve creating
6041 the seg the first time through. Make sure to have the
6042 old seg/subseg so that we can reset things when we are done. */
252b5132
RH
6043 seg = bfd_get_section_by_name (stdoutput, UNWIND_SECTION_NAME);
6044 if (seg == ASEC_NULL)
6045 {
c97305a1 6046 seg = subseg_new (UNWIND_SECTION_NAME, 0);
252b5132
RH
6047 bfd_set_section_flags (stdoutput, seg,
6048 SEC_READONLY | SEC_HAS_CONTENTS
b100be66
JL
6049 | SEC_LOAD | SEC_RELOC | SEC_ALLOC | SEC_DATA);
6050 bfd_set_section_alignment (stdoutput, seg, 2);
252b5132
RH
6051 }
6052
46031ca9 6053 subseg_set (seg, 0);
252b5132 6054
252b5132
RH
6055 /* Get some space to hold relocation information for the unwind
6056 descriptor. */
6057 p = frag_more (4);
6058 md_number_to_chars (p, 0, 4);
6059
6060 /* Relocation info. for start offset of the function. */
6061 fix_new_hppa (frag_now, p - frag_now->fr_literal, 4,
6062 call_info->start_symbol, (offsetT) 0,
46031ca9
JL
6063 (expressionS *) NULL, 0, reloc,
6064 e_fsel, 32, 0, NULL);
252b5132
RH
6065
6066 p = frag_more (4);
6067 md_number_to_chars (p, 0, 4);
6068
6069 /* Relocation info. for end offset of the function.
6070
6071 Because we allow reductions of 32bit relocations for ELF, this will be
6072 reduced to section_sym + offset which avoids putting the temporary
6073 symbol into the symbol table. It (should) end up giving the same
6074 value as call_info->start_symbol + function size once the linker is
6075 finished with its work. */
6076
6077 fix_new_hppa (frag_now, p - frag_now->fr_literal, 4,
6078 call_info->end_symbol, (offsetT) 0,
46031ca9
JL
6079 (expressionS *) NULL, 0, reloc,
6080 e_fsel, 32, 0, NULL);
252b5132 6081
a28a3ccf 6082 /* Dump it. */
252b5132
RH
6083 unwind = (char *) &call_info->ci_unwind;
6084 for (i = 8; i < sizeof (struct unwind_table); i++)
6085 {
6086 c = *(unwind + i);
6087 {
6088 FRAG_APPEND_1_CHAR (c);
6089 }
6090 }
6091
6092 /* Return back to the original segment/subsegment. */
6093 subseg_set (save_seg, save_subseg);
6094}
6095#endif
6096
6097/* Process a .CALLINFO pseudo-op. This information is used later
6098 to build unwind descriptors and maybe one day to support
6099 .ENTER and .LEAVE. */
6100
6101static void
6102pa_callinfo (unused)
3f9b03b5 6103 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6104{
6105 char *name, c, *p;
6106 int temp;
6107
49863f82 6108#ifdef OBJ_SOM
252b5132
RH
6109 /* We must have a valid space and subspace. */
6110 pa_check_current_space_and_subspace ();
49863f82 6111#endif
252b5132
RH
6112
6113 /* .CALLINFO must appear within a procedure definition. */
6114 if (!within_procedure)
6115 as_bad (_(".callinfo is not within a procedure definition"));
6116
6117 /* Mark the fact that we found the .CALLINFO for the
6118 current procedure. */
6119 callinfo_found = TRUE;
6120
6121 /* Iterate over the .CALLINFO arguments. */
6122 while (!is_end_of_statement ())
6123 {
6124 name = input_line_pointer;
6125 c = get_symbol_end ();
6126 /* Frame size specification. */
6127 if ((strncasecmp (name, "frame", 5) == 0))
6128 {
6129 p = input_line_pointer;
6130 *p = c;
6131 input_line_pointer++;
6132 temp = get_absolute_expression ();
6133 if ((temp & 0x3) != 0)
6134 {
6135 as_bad (_("FRAME parameter must be a multiple of 8: %d\n"), temp);
6136 temp = 0;
6137 }
6138
6139 /* callinfo is in bytes and unwind_desc is in 8 byte units. */
6140 last_call_info->ci_unwind.descriptor.frame_size = temp / 8;
6141
6142 }
6143 /* Entry register (GR, GR and SR) specifications. */
6144 else if ((strncasecmp (name, "entry_gr", 8) == 0))
6145 {
6146 p = input_line_pointer;
6147 *p = c;
6148 input_line_pointer++;
6149 temp = get_absolute_expression ();
6150 /* The HP assembler accepts 19 as the high bound for ENTRY_GR
6151 even though %r19 is caller saved. I think this is a bug in
6152 the HP assembler, and we are not going to emulate it. */
6153 if (temp < 3 || temp > 18)
6154 as_bad (_("Value for ENTRY_GR must be in the range 3..18\n"));
6155 last_call_info->ci_unwind.descriptor.entry_gr = temp - 2;
6156 }
6157 else if ((strncasecmp (name, "entry_fr", 8) == 0))
6158 {
6159 p = input_line_pointer;
6160 *p = c;
6161 input_line_pointer++;
6162 temp = get_absolute_expression ();
6163 /* Similarly the HP assembler takes 31 as the high bound even
6164 though %fr21 is the last callee saved floating point register. */
6165 if (temp < 12 || temp > 21)
6166 as_bad (_("Value for ENTRY_FR must be in the range 12..21\n"));
6167 last_call_info->ci_unwind.descriptor.entry_fr = temp - 11;
6168 }
6169 else if ((strncasecmp (name, "entry_sr", 8) == 0))
6170 {
6171 p = input_line_pointer;
6172 *p = c;
6173 input_line_pointer++;
6174 temp = get_absolute_expression ();
6175 if (temp != 3)
6176 as_bad (_("Value for ENTRY_SR must be 3\n"));
6177 }
6178 /* Note whether or not this function performs any calls. */
6179 else if ((strncasecmp (name, "calls", 5) == 0) ||
6180 (strncasecmp (name, "caller", 6) == 0))
6181 {
6182 p = input_line_pointer;
6183 *p = c;
6184 }
6185 else if ((strncasecmp (name, "no_calls", 8) == 0))
6186 {
6187 p = input_line_pointer;
6188 *p = c;
6189 }
6190 /* Should RP be saved into the stack. */
6191 else if ((strncasecmp (name, "save_rp", 7) == 0))
6192 {
6193 p = input_line_pointer;
6194 *p = c;
6195 last_call_info->ci_unwind.descriptor.save_rp = 1;
6196 }
6197 /* Likewise for SP. */
6198 else if ((strncasecmp (name, "save_sp", 7) == 0))
6199 {
6200 p = input_line_pointer;
6201 *p = c;
6202 last_call_info->ci_unwind.descriptor.save_sp = 1;
6203 }
6204 /* Is this an unwindable procedure. If so mark it so
6205 in the unwind descriptor. */
6206 else if ((strncasecmp (name, "no_unwind", 9) == 0))
6207 {
6208 p = input_line_pointer;
6209 *p = c;
6210 last_call_info->ci_unwind.descriptor.cannot_unwind = 1;
6211 }
6212 /* Is this an interrupt routine. If so mark it in the
6213 unwind descriptor. */
6214 else if ((strncasecmp (name, "hpux_int", 7) == 0))
6215 {
6216 p = input_line_pointer;
6217 *p = c;
6218 last_call_info->ci_unwind.descriptor.hpux_interrupt_marker = 1;
6219 }
6220 /* Is this a millicode routine. "millicode" isn't in my
6221 assembler manual, but my copy is old. The HP assembler
6222 accepts it, and there's a place in the unwind descriptor
6223 to drop the information, so we'll accept it too. */
6224 else if ((strncasecmp (name, "millicode", 9) == 0))
6225 {
6226 p = input_line_pointer;
6227 *p = c;
6228 last_call_info->ci_unwind.descriptor.millicode = 1;
6229 }
6230 else
6231 {
6232 as_bad (_("Invalid .CALLINFO argument: %s"), name);
6233 *input_line_pointer = c;
6234 }
6235 if (!is_end_of_statement ())
6236 input_line_pointer++;
6237 }
6238
6239 demand_empty_rest_of_line ();
6240}
6241
ad1079af
AM
6242#if !(defined (OBJ_ELF) && defined (TE_LINUX))
6243/* Switch to the text space. Like s_text, but delete our
6244 label when finished. */
252b5132 6245static void
ad1079af 6246pa_text (unused)
3f9b03b5 6247 int unused ATTRIBUTE_UNUSED;
252b5132 6248{
49863f82 6249#ifdef OBJ_SOM
252b5132
RH
6250 current_space = is_defined_space ("$TEXT$");
6251 current_subspace
6252 = pa_subsegment_to_subspace (current_space->sd_seg, 0);
49863f82 6253#endif
ad1079af 6254
252b5132
RH
6255 s_text (0);
6256 pa_undefine_label ();
6257}
6258
ad1079af
AM
6259/* Switch to the data space. As usual delete our label. */
6260static void
6261pa_data (unused)
6262 int unused ATTRIBUTE_UNUSED;
6263{
6264#ifdef OBJ_SOM
6265 current_space = is_defined_space ("$PRIVATE$");
6266 current_subspace
6267 = pa_subsegment_to_subspace (current_space->sd_seg, 0);
6268#endif
6269 s_data (0);
6270 pa_undefine_label ();
6271}
6272
252b5132
RH
6273/* This is different than the standard GAS s_comm(). On HP9000/800 machines,
6274 the .comm pseudo-op has the following symtax:
6275
6276 <label> .comm <length>
6277
6278 where <label> is optional and is a symbol whose address will be the start of
6279 a block of memory <length> bytes long. <length> must be an absolute
6280 expression. <length> bytes will be allocated in the current space
6281 and subspace.
6282
6283 Also note the label may not even be on the same line as the .comm.
6284
6285 This difference in syntax means the colon function will be called
6286 on the symbol before we arrive in pa_comm. colon will set a number
6287 of attributes of the symbol that need to be fixed here. In particular
6288 the value, section pointer, fragment pointer, flags, etc. What
6289 a pain.
6290
6291 This also makes error detection all but impossible. */
6292
6293static void
6294pa_comm (unused)
3f9b03b5 6295 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6296{
6297 unsigned int size;
6298 symbolS *symbol;
6299 label_symbol_struct *label_symbol = pa_get_label ();
6300
6301 if (label_symbol)
6302 symbol = label_symbol->lss_label;
6303 else
6304 symbol = NULL;
6305
6306 SKIP_WHITESPACE ();
6307 size = get_absolute_expression ();
6308
6309 if (symbol)
6310 {
6311 S_SET_VALUE (symbol, size);
6312 S_SET_SEGMENT (symbol, bfd_und_section_ptr);
6313 S_SET_EXTERNAL (symbol);
6314
6315 /* colon() has already set the frag to the current location in the
6316 current subspace; we need to reset the fragment to the zero address
6317 fragment. We also need to reset the segment pointer. */
a0f75b47 6318 symbol_set_frag (symbol, &zero_address_frag);
252b5132
RH
6319 }
6320 demand_empty_rest_of_line ();
6321}
ad1079af 6322#endif /* !(defined (OBJ_ELF) && defined (TE_LINUX)) */
252b5132
RH
6323
6324/* Process a .END pseudo-op. */
6325
6326static void
6327pa_end (unused)
3f9b03b5 6328 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6329{
6330 demand_empty_rest_of_line ();
6331}
6332
6333/* Process a .ENTER pseudo-op. This is not supported. */
6334static void
6335pa_enter (unused)
3f9b03b5 6336 int unused ATTRIBUTE_UNUSED;
252b5132 6337{
49863f82 6338#ifdef OBJ_SOM
252b5132
RH
6339 /* We must have a valid space and subspace. */
6340 pa_check_current_space_and_subspace ();
49863f82 6341#endif
252b5132
RH
6342
6343 as_bad (_("The .ENTER pseudo-op is not supported"));
6344 demand_empty_rest_of_line ();
6345}
6346
6347/* Process a .ENTRY pseudo-op. .ENTRY marks the beginning of the
6348 procesure. */
6349static void
6350pa_entry (unused)
3f9b03b5 6351 int unused ATTRIBUTE_UNUSED;
252b5132 6352{
49863f82 6353#ifdef OBJ_SOM
252b5132
RH
6354 /* We must have a valid space and subspace. */
6355 pa_check_current_space_and_subspace ();
49863f82 6356#endif
252b5132
RH
6357
6358 if (!within_procedure)
6359 as_bad (_("Misplaced .entry. Ignored."));
6360 else
6361 {
6362 if (!callinfo_found)
6363 as_bad (_("Missing .callinfo."));
6364 }
6365 demand_empty_rest_of_line ();
6366 within_entry_exit = TRUE;
6367
6368#ifdef OBJ_SOM
6369 /* SOM defers building of unwind descriptors until the link phase.
6370 The assembler is responsible for creating an R_ENTRY relocation
6371 to mark the beginning of a region and hold the unwind bits, and
6372 for creating an R_EXIT relocation to mark the end of the region.
6373
6374 FIXME. ELF should be using the same conventions! The problem
6375 is an unwind requires too much relocation space. Hmmm. Maybe
6376 if we split the unwind bits up between the relocations which
6377 denote the entry and exit points. */
6378 if (last_call_info->start_symbol != NULL)
6379 {
6380 char *where = frag_more (0);
6381
6382 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
6383 NULL, (offsetT) 0, NULL,
6384 0, R_HPPA_ENTRY, e_fsel, 0, 0,
6385 (int *) &last_call_info->ci_unwind.descriptor);
6386 }
6387#endif
6388}
6389
ecacdc7a
AM
6390/* Silly nonsense for pa_equ. The only half-sensible use for this is
6391 being able to subtract two register symbols that specify a range of
6392 registers, to get the size of the range. */
6393static int fudge_reg_expressions;
6394
6395int
6396hppa_force_reg_syms_absolute (resultP, op, rightP)
6397 expressionS *resultP;
6398 operatorT op ATTRIBUTE_UNUSED;
6399 expressionS *rightP;
6400{
6401 if (fudge_reg_expressions
6402 && rightP->X_op == O_register
6403 && resultP->X_op == O_register)
6404 {
6405 rightP->X_op = O_constant;
6406 resultP->X_op = O_constant;
6407 }
6408 return 0; /* Continue normal expr handling. */
6409}
6410
252b5132
RH
6411/* Handle a .EQU pseudo-op. */
6412
6413static void
6414pa_equ (reg)
6415 int reg;
6416{
6417 label_symbol_struct *label_symbol = pa_get_label ();
6418 symbolS *symbol;
6419
6420 if (label_symbol)
6421 {
6422 symbol = label_symbol->lss_label;
6423 if (reg)
ecacdc7a
AM
6424 {
6425 strict = 1;
6426 if (!pa_parse_number (&input_line_pointer, 0))
6427 as_bad (_(".REG expression must be a register"));
6428 S_SET_VALUE (symbol, pa_number);
6429 S_SET_SEGMENT (symbol, reg_section);
6430 }
252b5132 6431 else
ecacdc7a
AM
6432 {
6433 expressionS exp;
6434 segT seg;
6435
6436 fudge_reg_expressions = 1;
6437 seg = expression (&exp);
6438 fudge_reg_expressions = 0;
6439 if (exp.X_op != O_constant
6440 && exp.X_op != O_register)
6441 {
6442 if (exp.X_op != O_absent)
6443 as_bad (_("bad or irreducible absolute expression; zero assumed"));
6444 exp.X_add_number = 0;
6445 seg = absolute_section;
6446 }
6447 S_SET_VALUE (symbol, (unsigned int) exp.X_add_number);
6448 S_SET_SEGMENT (symbol, seg);
6449 }
252b5132
RH
6450 }
6451 else
6452 {
6453 if (reg)
6454 as_bad (_(".REG must use a label"));
6455 else
6456 as_bad (_(".EQU must use a label"));
6457 }
6458
6459 pa_undefine_label ();
6460 demand_empty_rest_of_line ();
6461}
6462
6463/* Helper function. Does processing for the end of a function. This
6464 usually involves creating some relocations or building special
6465 symbols to mark the end of the function. */
6466
6467static void
6468process_exit ()
6469{
6470 char *where;
6471
6472 where = frag_more (0);
6473
6474#ifdef OBJ_ELF
6475 /* Mark the end of the function, stuff away the location of the frag
6476 for the end of the function, and finally call pa_build_unwind_subspace
6477 to add an entry in the unwind table. */
6478 hppa_elf_mark_end_of_function ();
6479 pa_build_unwind_subspace (last_call_info);
6480#else
6481 /* SOM defers building of unwind descriptors until the link phase.
6482 The assembler is responsible for creating an R_ENTRY relocation
6483 to mark the beginning of a region and hold the unwind bits, and
6484 for creating an R_EXIT relocation to mark the end of the region.
6485
6486 FIXME. ELF should be using the same conventions! The problem
6487 is an unwind requires too much relocation space. Hmmm. Maybe
6488 if we split the unwind bits up between the relocations which
6489 denote the entry and exit points. */
6490 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
6491 NULL, (offsetT) 0,
6492 NULL, 0, R_HPPA_EXIT, e_fsel, 0, 0,
6493 (int *) &last_call_info->ci_unwind.descriptor + 1);
6494#endif
6495}
6496
6497/* Process a .EXIT pseudo-op. */
6498
6499static void
6500pa_exit (unused)
3f9b03b5 6501 int unused ATTRIBUTE_UNUSED;
252b5132 6502{
49863f82 6503#ifdef OBJ_SOM
252b5132
RH
6504 /* We must have a valid space and subspace. */
6505 pa_check_current_space_and_subspace ();
49863f82 6506#endif
252b5132
RH
6507
6508 if (!within_procedure)
6509 as_bad (_(".EXIT must appear within a procedure"));
6510 else
6511 {
6512 if (!callinfo_found)
6513 as_bad (_("Missing .callinfo"));
6514 else
6515 {
6516 if (!within_entry_exit)
6517 as_bad (_("No .ENTRY for this .EXIT"));
6518 else
6519 {
6520 within_entry_exit = FALSE;
6521 process_exit ();
6522 }
6523 }
6524 }
6525 demand_empty_rest_of_line ();
6526}
6527
6528/* Process a .EXPORT directive. This makes functions external
6529 and provides information such as argument relocation entries
6530 to callers. */
6531
6532static void
6533pa_export (unused)
3f9b03b5 6534 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6535{
6536 char *name, c, *p;
6537 symbolS *symbol;
6538
6539 name = input_line_pointer;
6540 c = get_symbol_end ();
6541 /* Make sure the given symbol exists. */
6542 if ((symbol = symbol_find_or_make (name)) == NULL)
6543 {
6544 as_bad (_("Cannot define export symbol: %s\n"), name);
6545 p = input_line_pointer;
6546 *p = c;
6547 input_line_pointer++;
6548 }
6549 else
6550 {
20348649 6551 /* OK. Set the external bits and process argument relocations.
a28a3ccf 6552 For the HP, weak and global are not mutually exclusive.
20348649
JL
6553 S_SET_EXTERNAL will not set BSF_GLOBAL if WEAK is set.
6554 Call S_SET_EXTERNAL to get the other processing. Manually
6555 set BSF_GLOBAL when we get back. */
252b5132 6556 S_SET_EXTERNAL (symbol);
20348649 6557 symbol_get_bfdsym (symbol)->flags |= BSF_GLOBAL;
252b5132
RH
6558 p = input_line_pointer;
6559 *p = c;
6560 if (!is_end_of_statement ())
6561 {
6562 input_line_pointer++;
6563 pa_type_args (symbol, 1);
6564 }
6565 }
6566
6567 demand_empty_rest_of_line ();
6568}
6569
6570/* Helper function to process arguments to a .EXPORT pseudo-op. */
6571
6572static void
6573pa_type_args (symbolP, is_export)
6574 symbolS *symbolP;
6575 int is_export;
6576{
6577 char *name, c, *p;
6578 unsigned int temp, arg_reloc;
6579 pa_symbol_type type = SYMBOL_TYPE_UNKNOWN;
904a31bf 6580 asymbol *bfdsym = symbol_get_bfdsym (symbolP);
252b5132
RH
6581
6582 if (strncasecmp (input_line_pointer, "absolute", 8) == 0)
6583
6584 {
6585 input_line_pointer += 8;
904a31bf 6586 bfdsym->flags &= ~BSF_FUNCTION;
252b5132
RH
6587 S_SET_SEGMENT (symbolP, bfd_abs_section_ptr);
6588 type = SYMBOL_TYPE_ABSOLUTE;
6589 }
6590 else if (strncasecmp (input_line_pointer, "code", 4) == 0)
6591 {
6592 input_line_pointer += 4;
6593 /* IMPORTing/EXPORTing CODE types for functions is meaningless for SOM,
6594 instead one should be IMPORTing/EXPORTing ENTRY types.
6595
6596 Complain if one tries to EXPORT a CODE type since that's never
6597 done. Both GCC and HP C still try to IMPORT CODE types, so
6598 silently fix them to be ENTRY types. */
a0f75b47 6599 if (S_IS_FUNCTION (symbolP))
252b5132
RH
6600 {
6601 if (is_export)
a0f75b47
ILT
6602 as_tsktsk (_("Using ENTRY rather than CODE in export directive for %s"),
6603 S_GET_NAME (symbolP));
252b5132 6604
904a31bf 6605 bfdsym->flags |= BSF_FUNCTION;
252b5132
RH
6606 type = SYMBOL_TYPE_ENTRY;
6607 }
6608 else
6609 {
904a31bf 6610 bfdsym->flags &= ~BSF_FUNCTION;
252b5132
RH
6611 type = SYMBOL_TYPE_CODE;
6612 }
6613 }
6614 else if (strncasecmp (input_line_pointer, "data", 4) == 0)
6615 {
6616 input_line_pointer += 4;
904a31bf
AM
6617 bfdsym->flags &= ~BSF_FUNCTION;
6618 bfdsym->flags |= BSF_OBJECT;
252b5132
RH
6619 type = SYMBOL_TYPE_DATA;
6620 }
6621 else if ((strncasecmp (input_line_pointer, "entry", 5) == 0))
6622 {
6623 input_line_pointer += 5;
904a31bf 6624 bfdsym->flags |= BSF_FUNCTION;
252b5132
RH
6625 type = SYMBOL_TYPE_ENTRY;
6626 }
6627 else if (strncasecmp (input_line_pointer, "millicode", 9) == 0)
6628 {
6629 input_line_pointer += 9;
904a31bf
AM
6630 bfdsym->flags |= BSF_FUNCTION;
6631#ifdef OBJ_ELF
6632 {
6633 elf_symbol_type *elfsym = (elf_symbol_type *) bfdsym;
6634 elfsym->internal_elf_sym.st_info =
6635 ELF_ST_INFO (ELF_ST_BIND (elfsym->internal_elf_sym.st_info),
6636 STT_PARISC_MILLI);
6637 }
6638#endif
252b5132
RH
6639 type = SYMBOL_TYPE_MILLICODE;
6640 }
6641 else if (strncasecmp (input_line_pointer, "plabel", 6) == 0)
6642 {
6643 input_line_pointer += 6;
904a31bf 6644 bfdsym->flags &= ~BSF_FUNCTION;
252b5132
RH
6645 type = SYMBOL_TYPE_PLABEL;
6646 }
6647 else if (strncasecmp (input_line_pointer, "pri_prog", 8) == 0)
6648 {
6649 input_line_pointer += 8;
904a31bf 6650 bfdsym->flags |= BSF_FUNCTION;
252b5132
RH
6651 type = SYMBOL_TYPE_PRI_PROG;
6652 }
6653 else if (strncasecmp (input_line_pointer, "sec_prog", 8) == 0)
6654 {
6655 input_line_pointer += 8;
904a31bf 6656 bfdsym->flags |= BSF_FUNCTION;
252b5132
RH
6657 type = SYMBOL_TYPE_SEC_PROG;
6658 }
6659
6660 /* SOM requires much more information about symbol types
6661 than BFD understands. This is how we get this information
6662 to the SOM BFD backend. */
6663#ifdef obj_set_symbol_type
904a31bf 6664 obj_set_symbol_type (bfdsym, (int) type);
252b5132
RH
6665#endif
6666
6667 /* Now that the type of the exported symbol has been handled,
6668 handle any argument relocation information. */
6669 while (!is_end_of_statement ())
6670 {
6671 if (*input_line_pointer == ',')
6672 input_line_pointer++;
6673 name = input_line_pointer;
6674 c = get_symbol_end ();
6675 /* Argument sources. */
6676 if ((strncasecmp (name, "argw", 4) == 0))
6677 {
6678 p = input_line_pointer;
6679 *p = c;
6680 input_line_pointer++;
6681 temp = atoi (name + 4);
6682 name = input_line_pointer;
6683 c = get_symbol_end ();
6684 arg_reloc = pa_align_arg_reloc (temp, pa_build_arg_reloc (name));
25a8b250 6685#if defined (OBJ_SOM) || defined (ELF_ARG_RELOC)
ad1079af 6686 symbol_arg_reloc_info (symbolP) |= arg_reloc;
49863f82 6687#endif
252b5132
RH
6688 *input_line_pointer = c;
6689 }
6690 /* The return value. */
6691 else if ((strncasecmp (name, "rtnval", 6)) == 0)
6692 {
6693 p = input_line_pointer;
6694 *p = c;
6695 input_line_pointer++;
6696 name = input_line_pointer;
6697 c = get_symbol_end ();
6698 arg_reloc = pa_build_arg_reloc (name);
25a8b250 6699#if defined (OBJ_SOM) || defined (ELF_ARG_RELOC)
ad1079af 6700 symbol_arg_reloc_info (symbolP) |= arg_reloc;
49863f82 6701#endif
252b5132
RH
6702 *input_line_pointer = c;
6703 }
6704 /* Privelege level. */
6705 else if ((strncasecmp (name, "priv_lev", 8)) == 0)
6706 {
6707 p = input_line_pointer;
6708 *p = c;
6709 input_line_pointer++;
6710 temp = atoi (input_line_pointer);
49863f82 6711#ifdef OBJ_SOM
904a31bf 6712 ((obj_symbol_type *) bfdsym)->tc_data.ap.hppa_priv_level = temp;
49863f82 6713#endif
252b5132
RH
6714 c = get_symbol_end ();
6715 *input_line_pointer = c;
6716 }
6717 else
6718 {
6719 as_bad (_("Undefined .EXPORT/.IMPORT argument (ignored): %s"), name);
6720 p = input_line_pointer;
6721 *p = c;
6722 }
6723 if (!is_end_of_statement ())
6724 input_line_pointer++;
6725 }
6726}
6727
6728/* Handle an .IMPORT pseudo-op. Any symbol referenced in a given
6729 assembly file must either be defined in the assembly file, or
6730 explicitly IMPORTED from another. */
6731
6732static void
6733pa_import (unused)
3f9b03b5 6734 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6735{
6736 char *name, c, *p;
6737 symbolS *symbol;
6738
6739 name = input_line_pointer;
6740 c = get_symbol_end ();
6741
6742 symbol = symbol_find (name);
6743 /* Ugh. We might be importing a symbol defined earlier in the file,
6744 in which case all the code below will really screw things up
6745 (set the wrong segment, symbol flags & type, etc). */
6746 if (symbol == NULL || !S_IS_DEFINED (symbol))
6747 {
6748 symbol = symbol_find_or_make (name);
6749 p = input_line_pointer;
6750 *p = c;
6751
6752 if (!is_end_of_statement ())
6753 {
6754 input_line_pointer++;
6755 pa_type_args (symbol, 0);
6756 }
6757 else
6758 {
6759 /* Sigh. To be compatable with the HP assembler and to help
6760 poorly written assembly code, we assign a type based on
6761 the the current segment. Note only BSF_FUNCTION really
6762 matters, we do not need to set the full SYMBOL_TYPE_* info. */
6763 if (now_seg == text_section)
a0f75b47 6764 symbol_get_bfdsym (symbol)->flags |= BSF_FUNCTION;
252b5132
RH
6765
6766 /* If the section is undefined, then the symbol is undefined
6767 Since this is an import, leave the section undefined. */
6768 S_SET_SEGMENT (symbol, bfd_und_section_ptr);
6769 }
6770 }
6771 else
6772 {
6773 /* The symbol was already defined. Just eat everything up to
6774 the end of the current statement. */
6775 while (!is_end_of_statement ())
6776 input_line_pointer++;
6777 }
6778
6779 demand_empty_rest_of_line ();
6780}
6781
6782/* Handle a .LABEL pseudo-op. */
6783
6784static void
6785pa_label (unused)
3f9b03b5 6786 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6787{
6788 char *name, c, *p;
6789
6790 name = input_line_pointer;
6791 c = get_symbol_end ();
6792
6793 if (strlen (name) > 0)
6794 {
6795 colon (name);
6796 p = input_line_pointer;
6797 *p = c;
6798 }
6799 else
6800 {
6801 as_warn (_("Missing label name on .LABEL"));
6802 }
6803
6804 if (!is_end_of_statement ())
6805 {
6806 as_warn (_("extra .LABEL arguments ignored."));
6807 ignore_rest_of_line ();
6808 }
6809 demand_empty_rest_of_line ();
6810}
6811
6812/* Handle a .LEAVE pseudo-op. This is not supported yet. */
6813
6814static void
6815pa_leave (unused)
3f9b03b5 6816 int unused ATTRIBUTE_UNUSED;
252b5132 6817{
49863f82 6818#ifdef OBJ_SOM
252b5132
RH
6819 /* We must have a valid space and subspace. */
6820 pa_check_current_space_and_subspace ();
49863f82 6821#endif
252b5132
RH
6822
6823 as_bad (_("The .LEAVE pseudo-op is not supported"));
6824 demand_empty_rest_of_line ();
6825}
6826
6827/* Handle a .LEVEL pseudo-op. */
6828
6829static void
6830pa_level (unused)
3f9b03b5 6831 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6832{
6833 char *level;
6834
6835 level = input_line_pointer;
6836 if (strncmp (level, "1.0", 3) == 0)
6837 {
6838 input_line_pointer += 3;
6839 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, 10))
6840 as_warn (_("could not set architecture and machine"));
6841 }
6842 else if (strncmp (level, "1.1", 3) == 0)
6843 {
6844 input_line_pointer += 3;
6845 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, 11))
6846 as_warn (_("could not set architecture and machine"));
6847 }
46031ca9
JL
6848 else if (strncmp (level, "2.0w", 4) == 0)
6849 {
6850 input_line_pointer += 4;
6851 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, 25))
6852 as_warn (_("could not set architecture and machine"));
6853 }
252b5132
RH
6854 else if (strncmp (level, "2.0", 3) == 0)
6855 {
6856 input_line_pointer += 3;
6857 if (!bfd_set_arch_mach (stdoutput, bfd_arch_hppa, 20))
6858 as_warn (_("could not set architecture and machine"));
6859 }
6860 else
6861 {
6862 as_bad (_("Unrecognized .LEVEL argument\n"));
6863 ignore_rest_of_line ();
6864 }
6865 demand_empty_rest_of_line ();
6866}
6867
6868/* Handle a .ORIGIN pseudo-op. */
6869
6870static void
6871pa_origin (unused)
3f9b03b5 6872 int unused ATTRIBUTE_UNUSED;
252b5132 6873{
49863f82 6874#ifdef OBJ_SOM
252b5132
RH
6875 /* We must have a valid space and subspace. */
6876 pa_check_current_space_and_subspace ();
49863f82 6877#endif
252b5132
RH
6878
6879 s_org (0);
6880 pa_undefine_label ();
6881}
6882
6883/* Handle a .PARAM pseudo-op. This is much like a .EXPORT, except it
6884 is for static functions. FIXME. Should share more code with .EXPORT. */
6885
6886static void
6887pa_param (unused)
3f9b03b5 6888 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6889{
6890 char *name, c, *p;
6891 symbolS *symbol;
6892
6893 name = input_line_pointer;
6894 c = get_symbol_end ();
6895
6896 if ((symbol = symbol_find_or_make (name)) == NULL)
6897 {
6898 as_bad (_("Cannot define static symbol: %s\n"), name);
6899 p = input_line_pointer;
6900 *p = c;
6901 input_line_pointer++;
6902 }
6903 else
6904 {
6905 S_CLEAR_EXTERNAL (symbol);
6906 p = input_line_pointer;
6907 *p = c;
6908 if (!is_end_of_statement ())
6909 {
6910 input_line_pointer++;
6911 pa_type_args (symbol, 0);
6912 }
6913 }
6914
6915 demand_empty_rest_of_line ();
6916}
6917
6918/* Handle a .PROC pseudo-op. It is used to mark the beginning
ad1079af 6919 of a procedure from a syntactical point of view. */
252b5132
RH
6920
6921static void
6922pa_proc (unused)
3f9b03b5 6923 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6924{
6925 struct call_info *call_info;
6926
49863f82 6927#ifdef OBJ_SOM
252b5132
RH
6928 /* We must have a valid space and subspace. */
6929 pa_check_current_space_and_subspace ();
49863f82 6930#endif
252b5132
RH
6931
6932 if (within_procedure)
6933 as_fatal (_("Nested procedures"));
6934
6935 /* Reset global variables for new procedure. */
6936 callinfo_found = FALSE;
6937 within_procedure = TRUE;
6938
6939 /* Create another call_info structure. */
6940 call_info = (struct call_info *) xmalloc (sizeof (struct call_info));
6941
6942 if (!call_info)
6943 as_fatal (_("Cannot allocate unwind descriptor\n"));
6944
6945 memset (call_info, 0, sizeof (struct call_info));
6946
6947 call_info->ci_next = NULL;
6948
6949 if (call_info_root == NULL)
6950 {
6951 call_info_root = call_info;
6952 last_call_info = call_info;
6953 }
6954 else
6955 {
6956 last_call_info->ci_next = call_info;
6957 last_call_info = call_info;
6958 }
6959
6960 /* set up defaults on call_info structure */
6961
6962 call_info->ci_unwind.descriptor.cannot_unwind = 0;
6963 call_info->ci_unwind.descriptor.region_desc = 1;
6964 call_info->ci_unwind.descriptor.hpux_interrupt_marker = 0;
6965
6966 /* If we got a .PROC pseudo-op, we know that the function is defined
6967 locally. Make sure it gets into the symbol table. */
6968 {
6969 label_symbol_struct *label_symbol = pa_get_label ();
6970
6971 if (label_symbol)
6972 {
6973 if (label_symbol->lss_label)
6974 {
6975 last_call_info->start_symbol = label_symbol->lss_label;
a0f75b47 6976 symbol_get_bfdsym (label_symbol->lss_label)->flags |= BSF_FUNCTION;
252b5132
RH
6977 }
6978 else
6979 as_bad (_("Missing function name for .PROC (corrupted label chain)"));
6980 }
6981 else
6982 last_call_info->start_symbol = NULL;
6983 }
6984
6985 demand_empty_rest_of_line ();
6986}
6987
6988/* Process the syntatical end of a procedure. Make sure all the
6989 appropriate pseudo-ops were found within the procedure. */
6990
6991static void
6992pa_procend (unused)
3f9b03b5 6993 int unused ATTRIBUTE_UNUSED;
252b5132
RH
6994{
6995
49863f82 6996#ifdef OBJ_SOM
252b5132
RH
6997 /* We must have a valid space and subspace. */
6998 pa_check_current_space_and_subspace ();
49863f82 6999#endif
252b5132
RH
7000
7001 /* If we are within a procedure definition, make sure we've
7002 defined a label for the procedure; handle case where the
7003 label was defined after the .PROC directive.
7004
7005 Note there's not need to diddle with the segment or fragment
7006 for the label symbol in this case. We have already switched
7007 into the new $CODE$ subspace at this point. */
7008 if (within_procedure && last_call_info->start_symbol == NULL)
7009 {
7010 label_symbol_struct *label_symbol = pa_get_label ();
7011
7012 if (label_symbol)
7013 {
7014 if (label_symbol->lss_label)
7015 {
7016 last_call_info->start_symbol = label_symbol->lss_label;
a0f75b47
ILT
7017 symbol_get_bfdsym (label_symbol->lss_label)->flags
7018 |= BSF_FUNCTION;
252b5132
RH
7019#ifdef OBJ_SOM
7020 /* Also handle allocation of a fixup to hold the unwind
7021 information when the label appears after the proc/procend. */
7022 if (within_entry_exit)
7023 {
7024 char *where = frag_more (0);
7025
7026 fix_new_hppa (frag_now, where - frag_now->fr_literal, 0,
7027 NULL, (offsetT) 0, NULL,
7028 0, R_HPPA_ENTRY, e_fsel, 0, 0,
7029 (int *) &last_call_info->ci_unwind.descriptor);
7030 }
7031#endif
7032 }
7033 else
7034 as_bad (_("Missing function name for .PROC (corrupted label chain)"));
7035 }
7036 else
7037 as_bad (_("Missing function name for .PROC"));
7038 }
7039
7040 if (!within_procedure)
7041 as_bad (_("misplaced .procend"));
7042
7043 if (!callinfo_found)
7044 as_bad (_("Missing .callinfo for this procedure"));
7045
7046 if (within_entry_exit)
7047 as_bad (_("Missing .EXIT for a .ENTRY"));
7048
7049#ifdef OBJ_ELF
7050 /* ELF needs to mark the end of each function so that it can compute
7051 the size of the function (apparently its needed in the symbol table). */
7052 hppa_elf_mark_end_of_function ();
7053#endif
7054
7055 within_procedure = FALSE;
7056 demand_empty_rest_of_line ();
7057 pa_undefine_label ();
7058}
7059
3f9b03b5 7060#ifdef OBJ_SOM
49863f82
JL
7061/* If VALUE is an exact power of two between zero and 2^31, then
7062 return log2 (VALUE). Else return -1. */
7063
7064static int
7065log2 (value)
7066 int value;
7067{
7068 int shift = 0;
7069
7070 while ((1 << shift) != value && shift < 32)
7071 shift++;
7072
7073 if (shift >= 32)
7074 return -1;
7075 else
7076 return shift;
7077}
7078
49863f82
JL
7079/* Check to make sure we have a valid space and subspace. */
7080
7081static void
7082pa_check_current_space_and_subspace ()
7083{
7084 if (current_space == NULL)
7085 as_fatal (_("Not in a space.\n"));
7086
7087 if (current_subspace == NULL)
7088 as_fatal (_("Not in a subspace.\n"));
7089}
7090
252b5132
RH
7091/* Parse the parameters to a .SPACE directive; if CREATE_FLAG is nonzero,
7092 then create a new space entry to hold the information specified
7093 by the parameters to the .SPACE directive. */
7094
7095static sd_chain_struct *
7096pa_parse_space_stmt (space_name, create_flag)
7097 char *space_name;
7098 int create_flag;
7099{
7100 char *name, *ptemp, c;
7101 char loadable, defined, private, sort;
ecacdc7a 7102 int spnum;
252b5132
RH
7103 asection *seg = NULL;
7104 sd_chain_struct *space;
7105
7106 /* load default values */
7107 spnum = 0;
7108 sort = 0;
7109 loadable = TRUE;
7110 defined = TRUE;
7111 private = FALSE;
7112 if (strcmp (space_name, "$TEXT$") == 0)
7113 {
7114 seg = pa_def_spaces[0].segment;
7115 defined = pa_def_spaces[0].defined;
7116 private = pa_def_spaces[0].private;
7117 sort = pa_def_spaces[0].sort;
7118 spnum = pa_def_spaces[0].spnum;
7119 }
7120 else if (strcmp (space_name, "$PRIVATE$") == 0)
7121 {
7122 seg = pa_def_spaces[1].segment;
7123 defined = pa_def_spaces[1].defined;
7124 private = pa_def_spaces[1].private;
7125 sort = pa_def_spaces[1].sort;
7126 spnum = pa_def_spaces[1].spnum;
7127 }
7128
7129 if (!is_end_of_statement ())
7130 {
7131 print_errors = FALSE;
7132 ptemp = input_line_pointer + 1;
7133 /* First see if the space was specified as a number rather than
7134 as a name. According to the PA assembly manual the rest of
7135 the line should be ignored. */
ecacdc7a
AM
7136 strict = 0;
7137 pa_parse_number (&ptemp, 0);
7138 if (pa_number >= 0)
252b5132 7139 {
ecacdc7a 7140 spnum = pa_number;
252b5132
RH
7141 input_line_pointer = ptemp;
7142 }
7143 else
7144 {
7145 while (!is_end_of_statement ())
7146 {
7147 input_line_pointer++;
7148 name = input_line_pointer;
7149 c = get_symbol_end ();
7150 if ((strncasecmp (name, "spnum", 5) == 0))
7151 {
7152 *input_line_pointer = c;
7153 input_line_pointer++;
7154 spnum = get_absolute_expression ();
7155 }
7156 else if ((strncasecmp (name, "sort", 4) == 0))
7157 {
7158 *input_line_pointer = c;
7159 input_line_pointer++;
7160 sort = get_absolute_expression ();
7161 }
7162 else if ((strncasecmp (name, "unloadable", 10) == 0))
7163 {
7164 *input_line_pointer = c;
7165 loadable = FALSE;
7166 }
7167 else if ((strncasecmp (name, "notdefined", 10) == 0))
7168 {
7169 *input_line_pointer = c;
7170 defined = FALSE;
7171 }
7172 else if ((strncasecmp (name, "private", 7) == 0))
7173 {
7174 *input_line_pointer = c;
7175 private = TRUE;
7176 }
7177 else
7178 {
7179 as_bad (_("Invalid .SPACE argument"));
7180 *input_line_pointer = c;
7181 if (!is_end_of_statement ())
7182 input_line_pointer++;
7183 }
7184 }
7185 }
7186 print_errors = TRUE;
7187 }
7188
7189 if (create_flag && seg == NULL)
7190 seg = subseg_new (space_name, 0);
7191
7192 /* If create_flag is nonzero, then create the new space with
7193 the attributes computed above. Else set the values in
7194 an already existing space -- this can only happen for
7195 the first occurence of a built-in space. */
7196 if (create_flag)
7197 space = create_new_space (space_name, spnum, loadable, defined,
7198 private, sort, seg, 1);
7199 else
7200 {
7201 space = is_defined_space (space_name);
7202 SPACE_SPNUM (space) = spnum;
7203 SPACE_DEFINED (space) = defined & 1;
7204 SPACE_USER_DEFINED (space) = 1;
7205 }
7206
7207#ifdef obj_set_section_attributes
7208 obj_set_section_attributes (seg, defined, private, sort, spnum);
7209#endif
7210
7211 return space;
7212}
7213
7214/* Handle a .SPACE pseudo-op; this switches the current space to the
7215 given space, creating the new space if necessary. */
7216
7217static void
7218pa_space (unused)
3f9b03b5 7219 int unused ATTRIBUTE_UNUSED;
252b5132
RH
7220{
7221 char *name, c, *space_name, *save_s;
252b5132
RH
7222 sd_chain_struct *sd_chain;
7223
7224 if (within_procedure)
7225 {
7226 as_bad (_("Can\'t change spaces within a procedure definition. Ignored"));
7227 ignore_rest_of_line ();
7228 }
7229 else
7230 {
7231 /* Check for some of the predefined spaces. FIXME: most of the code
7232 below is repeated several times, can we extract the common parts
7233 and place them into a subroutine or something similar? */
7234 /* FIXME Is this (and the next IF stmt) really right?
7235 What if INPUT_LINE_POINTER points to "$TEXT$FOO"? */
7236 if (strncmp (input_line_pointer, "$TEXT$", 6) == 0)
7237 {
7238 input_line_pointer += 6;
7239 sd_chain = is_defined_space ("$TEXT$");
7240 if (sd_chain == NULL)
7241 sd_chain = pa_parse_space_stmt ("$TEXT$", 1);
7242 else if (SPACE_USER_DEFINED (sd_chain) == 0)
7243 sd_chain = pa_parse_space_stmt ("$TEXT$", 0);
7244
7245 current_space = sd_chain;
7246 subseg_set (text_section, sd_chain->sd_last_subseg);
7247 current_subspace
7248 = pa_subsegment_to_subspace (text_section,
7249 sd_chain->sd_last_subseg);
7250 demand_empty_rest_of_line ();
7251 return;
7252 }
7253 if (strncmp (input_line_pointer, "$PRIVATE$", 9) == 0)
7254 {
7255 input_line_pointer += 9;
7256 sd_chain = is_defined_space ("$PRIVATE$");
7257 if (sd_chain == NULL)
7258 sd_chain = pa_parse_space_stmt ("$PRIVATE$", 1);
7259 else if (SPACE_USER_DEFINED (sd_chain) == 0)
7260 sd_chain = pa_parse_space_stmt ("$PRIVATE$", 0);
7261
7262 current_space = sd_chain;
7263 subseg_set (data_section, sd_chain->sd_last_subseg);
7264 current_subspace
7265 = pa_subsegment_to_subspace (data_section,
7266 sd_chain->sd_last_subseg);
7267 demand_empty_rest_of_line ();
7268 return;
7269 }
7270 if (!strncasecmp (input_line_pointer,
7271 GDB_DEBUG_SPACE_NAME,
7272 strlen (GDB_DEBUG_SPACE_NAME)))
7273 {
7274 input_line_pointer += strlen (GDB_DEBUG_SPACE_NAME);
7275 sd_chain = is_defined_space (GDB_DEBUG_SPACE_NAME);
7276 if (sd_chain == NULL)
7277 sd_chain = pa_parse_space_stmt (GDB_DEBUG_SPACE_NAME, 1);
7278 else if (SPACE_USER_DEFINED (sd_chain) == 0)
7279 sd_chain = pa_parse_space_stmt (GDB_DEBUG_SPACE_NAME, 0);
7280
7281 current_space = sd_chain;
7282
7283 {
7284 asection *gdb_section
7285 = bfd_make_section_old_way (stdoutput, GDB_DEBUG_SPACE_NAME);
7286
7287 subseg_set (gdb_section, sd_chain->sd_last_subseg);
7288 current_subspace
7289 = pa_subsegment_to_subspace (gdb_section,
7290 sd_chain->sd_last_subseg);
7291 }
7292 demand_empty_rest_of_line ();
7293 return;
7294 }
7295
7296 /* It could be a space specified by number. */
7297 print_errors = 0;
7298 save_s = input_line_pointer;
ecacdc7a
AM
7299 strict = 0;
7300 pa_parse_number (&input_line_pointer, 0);
7301 if (pa_number >= 0)
252b5132 7302 {
ecacdc7a 7303 if ((sd_chain = pa_find_space_by_number (pa_number)))
252b5132
RH
7304 {
7305 current_space = sd_chain;
7306
7307 subseg_set (sd_chain->sd_seg, sd_chain->sd_last_subseg);
7308 current_subspace
7309 = pa_subsegment_to_subspace (sd_chain->sd_seg,
7310 sd_chain->sd_last_subseg);
7311 demand_empty_rest_of_line ();
7312 return;
7313 }
7314 }
7315
7316 /* Not a number, attempt to create a new space. */
7317 print_errors = 1;
7318 input_line_pointer = save_s;
7319 name = input_line_pointer;
7320 c = get_symbol_end ();
7321 space_name = xmalloc (strlen (name) + 1);
7322 strcpy (space_name, name);
7323 *input_line_pointer = c;
7324
7325 sd_chain = pa_parse_space_stmt (space_name, 1);
7326 current_space = sd_chain;
7327
7328 subseg_set (sd_chain->sd_seg, sd_chain->sd_last_subseg);
7329 current_subspace = pa_subsegment_to_subspace (sd_chain->sd_seg,
7330 sd_chain->sd_last_subseg);
7331 demand_empty_rest_of_line ();
7332 }
7333}
7334
7335/* Switch to a new space. (I think). FIXME. */
7336
7337static void
7338pa_spnum (unused)
3f9b03b5 7339 int unused ATTRIBUTE_UNUSED;
252b5132
RH
7340{
7341 char *name;
7342 char c;
7343 char *p;
7344 sd_chain_struct *space;
7345
7346 name = input_line_pointer;
7347 c = get_symbol_end ();
7348 space = is_defined_space (name);
7349 if (space)
7350 {
7351 p = frag_more (4);
7352 md_number_to_chars (p, SPACE_SPNUM (space), 4);
7353 }
7354 else
7355 as_warn (_("Undefined space: '%s' Assuming space number = 0."), name);
7356
7357 *input_line_pointer = c;
7358 demand_empty_rest_of_line ();
7359}
7360
252b5132
RH
7361/* Handle a .SUBSPACE pseudo-op; this switches the current subspace to the
7362 given subspace, creating the new subspace if necessary.
7363
7364 FIXME. Should mirror pa_space more closely, in particular how
7365 they're broken up into subroutines. */
7366
7367static void
7368pa_subspace (create_new)
7369 int create_new;
7370{
49863f82 7371 char *name, *ss_name, c;
252b5132
RH
7372 char loadable, code_only, common, dup_common, zero, sort;
7373 int i, access, space_index, alignment, quadrant, applicable, flags;
7374 sd_chain_struct *space;
7375 ssd_chain_struct *ssd;
7376 asection *section;
7377
7378 if (current_space == NULL)
7379 as_fatal (_("Must be in a space before changing or declaring subspaces.\n"));
7380
7381 if (within_procedure)
7382 {
7383 as_bad (_("Can\'t change subspaces within a procedure definition. Ignored"));
7384 ignore_rest_of_line ();
7385 }
7386 else
7387 {
7388 name = input_line_pointer;
7389 c = get_symbol_end ();
7390 ss_name = xmalloc (strlen (name) + 1);
7391 strcpy (ss_name, name);
7392 *input_line_pointer = c;
7393
7394 /* Load default values. */
7395 sort = 0;
7396 access = 0x7f;
7397 loadable = 1;
7398 common = 0;
7399 dup_common = 0;
7400 code_only = 0;
7401 zero = 0;
7402 space_index = ~0;
7403 alignment = 1;
7404 quadrant = 0;
252b5132
RH
7405
7406 space = current_space;
7407 if (create_new)
7408 ssd = NULL;
7409 else
7410 ssd = is_defined_subspace (ss_name);
7411 /* Allow user to override the builtin attributes of subspaces. But
7412 only allow the attributes to be changed once! */
7413 if (ssd && SUBSPACE_DEFINED (ssd))
7414 {
7415 subseg_set (ssd->ssd_seg, ssd->ssd_subseg);
7416 current_subspace = ssd;
7417 if (!is_end_of_statement ())
7418 as_warn (_("Parameters of an existing subspace can\'t be modified"));
7419 demand_empty_rest_of_line ();
7420 return;
7421 }
7422 else
7423 {
7424 /* A new subspace. Load default values if it matches one of
7425 the builtin subspaces. */
7426 i = 0;
7427 while (pa_def_subspaces[i].name)
7428 {
7429 if (strcasecmp (pa_def_subspaces[i].name, ss_name) == 0)
7430 {
7431 loadable = pa_def_subspaces[i].loadable;
7432 common = pa_def_subspaces[i].common;
7433 dup_common = pa_def_subspaces[i].dup_common;
7434 code_only = pa_def_subspaces[i].code_only;
7435 zero = pa_def_subspaces[i].zero;
7436 space_index = pa_def_subspaces[i].space_index;
7437 alignment = pa_def_subspaces[i].alignment;
7438 quadrant = pa_def_subspaces[i].quadrant;
7439 access = pa_def_subspaces[i].access;
7440 sort = pa_def_subspaces[i].sort;
252b5132
RH
7441 break;
7442 }
7443 i++;
7444 }
7445 }
7446
7447 /* We should be working with a new subspace now. Fill in
7448 any information as specified by the user. */
7449 if (!is_end_of_statement ())
7450 {
7451 input_line_pointer++;
7452 while (!is_end_of_statement ())
7453 {
7454 name = input_line_pointer;
7455 c = get_symbol_end ();
7456 if ((strncasecmp (name, "quad", 4) == 0))
7457 {
7458 *input_line_pointer = c;
7459 input_line_pointer++;
7460 quadrant = get_absolute_expression ();
7461 }
7462 else if ((strncasecmp (name, "align", 5) == 0))
7463 {
7464 *input_line_pointer = c;
7465 input_line_pointer++;
7466 alignment = get_absolute_expression ();
7467 if (log2 (alignment) == -1)
7468 {
7469 as_bad (_("Alignment must be a power of 2"));
7470 alignment = 1;
7471 }
7472 }
7473 else if ((strncasecmp (name, "access", 6) == 0))
7474 {
7475 *input_line_pointer = c;
7476 input_line_pointer++;
7477 access = get_absolute_expression ();
7478 }
7479 else if ((strncasecmp (name, "sort", 4) == 0))
7480 {
7481 *input_line_pointer = c;
7482 input_line_pointer++;
7483 sort = get_absolute_expression ();
7484 }
7485 else if ((strncasecmp (name, "code_only", 9) == 0))
7486 {
7487 *input_line_pointer = c;
7488 code_only = 1;
7489 }
7490 else if ((strncasecmp (name, "unloadable", 10) == 0))
7491 {
7492 *input_line_pointer = c;
7493 loadable = 0;
7494 }
7495 else if ((strncasecmp (name, "common", 6) == 0))
7496 {
7497 *input_line_pointer = c;
7498 common = 1;
7499 }
7500 else if ((strncasecmp (name, "dup_comm", 8) == 0))
7501 {
7502 *input_line_pointer = c;
7503 dup_common = 1;
7504 }
7505 else if ((strncasecmp (name, "zero", 4) == 0))
7506 {
7507 *input_line_pointer = c;
7508 zero = 1;
7509 }
7510 else if ((strncasecmp (name, "first", 5) == 0))
7511 as_bad (_("FIRST not supported as a .SUBSPACE argument"));
7512 else
7513 as_bad (_("Invalid .SUBSPACE argument"));
7514 if (!is_end_of_statement ())
7515 input_line_pointer++;
7516 }
7517 }
7518
7519 /* Compute a reasonable set of BFD flags based on the information
7520 in the .subspace directive. */
7521 applicable = bfd_applicable_section_flags (stdoutput);
7522 flags = 0;
7523 if (loadable)
7524 flags |= (SEC_ALLOC | SEC_LOAD);
7525 if (code_only)
7526 flags |= SEC_CODE;
7527 if (common || dup_common)
7528 flags |= SEC_IS_COMMON;
7529
7530 flags |= SEC_RELOC | SEC_HAS_CONTENTS;
7531
7532 /* This is a zero-filled subspace (eg BSS). */
7533 if (zero)
7534 flags &= ~(SEC_LOAD | SEC_HAS_CONTENTS);
7535
7536 applicable &= flags;
7537
7538 /* If this is an existing subspace, then we want to use the
7539 segment already associated with the subspace.
7540
7541 FIXME NOW! ELF BFD doesn't appear to be ready to deal with
7542 lots of sections. It might be a problem in the PA ELF
7543 code, I do not know yet. For now avoid creating anything
7544 but the "standard" sections for ELF. */
7545 if (create_new)
7546 section = subseg_force_new (ss_name, 0);
7547 else if (ssd)
7548 section = ssd->ssd_seg;
252b5132
RH
7549 else
7550 section = subseg_new (ss_name, 0);
7551
7552 if (zero)
7553 seg_info (section)->bss = 1;
7554
7555 /* Now set the flags. */
7556 bfd_set_section_flags (stdoutput, section, applicable);
7557
7558 /* Record any alignment request for this section. */
7559 record_alignment (section, log2 (alignment));
7560
7561 /* Set the starting offset for this section. */
7562 bfd_set_section_vma (stdoutput, section,
7563 pa_subspace_start (space, quadrant));
7564
7565 /* Now that all the flags are set, update an existing subspace,
7566 or create a new one. */
7567 if (ssd)
7568
7569 current_subspace = update_subspace (space, ss_name, loadable,
7570 code_only, common, dup_common,
7571 sort, zero, access, space_index,
7572 alignment, quadrant,
7573 section);
7574 else
7575 current_subspace = create_new_subspace (space, ss_name, loadable,
7576 code_only, common,
7577 dup_common, zero, sort,
7578 access, space_index,
7579 alignment, quadrant, section);
7580
7581 demand_empty_rest_of_line ();
7582 current_subspace->ssd_seg = section;
7583 subseg_set (current_subspace->ssd_seg, current_subspace->ssd_subseg);
7584 }
7585 SUBSPACE_DEFINED (current_subspace) = 1;
7586}
7587
252b5132
RH
7588/* Create default space and subspace dictionaries. */
7589
7590static void
7591pa_spaces_begin ()
7592{
7593 int i;
7594
7595 space_dict_root = NULL;
7596 space_dict_last = NULL;
7597
7598 i = 0;
7599 while (pa_def_spaces[i].name)
7600 {
7601 char *name;
7602
7603 /* Pick the right name to use for the new section. */
49863f82 7604 name = pa_def_spaces[i].name;
252b5132
RH
7605
7606 pa_def_spaces[i].segment = subseg_new (name, 0);
7607 create_new_space (pa_def_spaces[i].name, pa_def_spaces[i].spnum,
7608 pa_def_spaces[i].loadable, pa_def_spaces[i].defined,
7609 pa_def_spaces[i].private, pa_def_spaces[i].sort,
7610 pa_def_spaces[i].segment, 0);
7611 i++;
7612 }
7613
7614 i = 0;
7615 while (pa_def_subspaces[i].name)
7616 {
7617 char *name;
7618 int applicable, subsegment;
7619 asection *segment = NULL;
7620 sd_chain_struct *space;
7621
7622 /* Pick the right name for the new section and pick the right
7623 subsegment number. */
49863f82
JL
7624 name = pa_def_subspaces[i].name;
7625 subsegment = 0;
252b5132
RH
7626
7627 /* Create the new section. */
7628 segment = subseg_new (name, subsegment);
7629
252b5132
RH
7630 /* For SOM we want to replace the standard .text, .data, and .bss
7631 sections with our own. We also want to set BFD flags for
7632 all the built-in subspaces. */
49863f82 7633 if (!strcmp (pa_def_subspaces[i].name, "$CODE$"))
252b5132
RH
7634 {
7635 text_section = segment;
7636 applicable = bfd_applicable_section_flags (stdoutput);
7637 bfd_set_section_flags (stdoutput, segment,
7638 applicable & (SEC_ALLOC | SEC_LOAD
7639 | SEC_RELOC | SEC_CODE
7640 | SEC_READONLY
7641 | SEC_HAS_CONTENTS));
7642 }
49863f82 7643 else if (!strcmp (pa_def_subspaces[i].name, "$DATA$"))
252b5132
RH
7644 {
7645 data_section = segment;
7646 applicable = bfd_applicable_section_flags (stdoutput);
7647 bfd_set_section_flags (stdoutput, segment,
7648 applicable & (SEC_ALLOC | SEC_LOAD
7649 | SEC_RELOC
7650 | SEC_HAS_CONTENTS));
7651
252b5132 7652 }
49863f82 7653 else if (!strcmp (pa_def_subspaces[i].name, "$BSS$"))
252b5132
RH
7654 {
7655 bss_section = segment;
7656 applicable = bfd_applicable_section_flags (stdoutput);
7657 bfd_set_section_flags (stdoutput, segment,
7658 applicable & SEC_ALLOC);
7659 }
49863f82 7660 else if (!strcmp (pa_def_subspaces[i].name, "$LIT$"))
252b5132
RH
7661 {
7662 applicable = bfd_applicable_section_flags (stdoutput);
7663 bfd_set_section_flags (stdoutput, segment,
7664 applicable & (SEC_ALLOC | SEC_LOAD
7665 | SEC_RELOC
7666 | SEC_READONLY
7667 | SEC_HAS_CONTENTS));
7668 }
49863f82 7669 else if (!strcmp (pa_def_subspaces[i].name, "$MILLICODE$"))
252b5132
RH
7670 {
7671 applicable = bfd_applicable_section_flags (stdoutput);
7672 bfd_set_section_flags (stdoutput, segment,
7673 applicable & (SEC_ALLOC | SEC_LOAD
7674 | SEC_RELOC
7675 | SEC_READONLY
7676 | SEC_HAS_CONTENTS));
7677 }
49863f82 7678 else if (!strcmp (pa_def_subspaces[i].name, "$UNWIND$"))
252b5132
RH
7679 {
7680 applicable = bfd_applicable_section_flags (stdoutput);
7681 bfd_set_section_flags (stdoutput, segment,
7682 applicable & (SEC_ALLOC | SEC_LOAD
7683 | SEC_RELOC
7684 | SEC_READONLY
7685 | SEC_HAS_CONTENTS));
7686 }
7687
7688 /* Find the space associated with this subspace. */
7689 space = pa_segment_to_space (pa_def_spaces[pa_def_subspaces[i].
7690 def_space_index].segment);
7691 if (space == NULL)
7692 {
7693 as_fatal (_("Internal error: Unable to find containing space for %s."),
7694 pa_def_subspaces[i].name);
7695 }
7696
7697 create_new_subspace (space, name,
7698 pa_def_subspaces[i].loadable,
7699 pa_def_subspaces[i].code_only,
7700 pa_def_subspaces[i].common,
7701 pa_def_subspaces[i].dup_common,
7702 pa_def_subspaces[i].zero,
7703 pa_def_subspaces[i].sort,
7704 pa_def_subspaces[i].access,
7705 pa_def_subspaces[i].space_index,
7706 pa_def_subspaces[i].alignment,
7707 pa_def_subspaces[i].quadrant,
7708 segment);
7709 i++;
7710 }
7711}
7712
252b5132
RH
7713/* Create a new space NAME, with the appropriate flags as defined
7714 by the given parameters. */
7715
7716static sd_chain_struct *
7717create_new_space (name, spnum, loadable, defined, private,
7718 sort, seg, user_defined)
7719 char *name;
7720 int spnum;
7721 int loadable;
7722 int defined;
7723 int private;
7724 int sort;
7725 asection *seg;
7726 int user_defined;
7727{
7728 sd_chain_struct *chain_entry;
7729
7730 chain_entry = (sd_chain_struct *) xmalloc (sizeof (sd_chain_struct));
7731 if (!chain_entry)
7732 as_fatal (_("Out of memory: could not allocate new space chain entry: %s\n"),
7733 name);
7734
7735 SPACE_NAME (chain_entry) = (char *) xmalloc (strlen (name) + 1);
7736 strcpy (SPACE_NAME (chain_entry), name);
7737 SPACE_DEFINED (chain_entry) = defined;
7738 SPACE_USER_DEFINED (chain_entry) = user_defined;
7739 SPACE_SPNUM (chain_entry) = spnum;
7740
7741 chain_entry->sd_seg = seg;
7742 chain_entry->sd_last_subseg = -1;
7743 chain_entry->sd_subspaces = NULL;
7744 chain_entry->sd_next = NULL;
7745
7746 /* Find spot for the new space based on its sort key. */
7747 if (!space_dict_last)
7748 space_dict_last = chain_entry;
7749
7750 if (space_dict_root == NULL)
7751 space_dict_root = chain_entry;
7752 else
7753 {
7754 sd_chain_struct *chain_pointer;
7755 sd_chain_struct *prev_chain_pointer;
7756
7757 chain_pointer = space_dict_root;
7758 prev_chain_pointer = NULL;
7759
7760 while (chain_pointer)
7761 {
7762 prev_chain_pointer = chain_pointer;
7763 chain_pointer = chain_pointer->sd_next;
7764 }
7765
7766 /* At this point we've found the correct place to add the new
7767 entry. So add it and update the linked lists as appropriate. */
7768 if (prev_chain_pointer)
7769 {
7770 chain_entry->sd_next = chain_pointer;
7771 prev_chain_pointer->sd_next = chain_entry;
7772 }
7773 else
7774 {
7775 space_dict_root = chain_entry;
7776 chain_entry->sd_next = chain_pointer;
7777 }
7778
7779 if (chain_entry->sd_next == NULL)
7780 space_dict_last = chain_entry;
7781 }
7782
7783 /* This is here to catch predefined spaces which do not get
7784 modified by the user's input. Another call is found at
7785 the bottom of pa_parse_space_stmt to handle cases where
7786 the user modifies a predefined space. */
7787#ifdef obj_set_section_attributes
7788 obj_set_section_attributes (seg, defined, private, sort, spnum);
7789#endif
7790
7791 return chain_entry;
7792}
7793
7794/* Create a new subspace NAME, with the appropriate flags as defined
7795 by the given parameters.
7796
7797 Add the new subspace to the subspace dictionary chain in numerical
7798 order as defined by the SORT entries. */
7799
7800static ssd_chain_struct *
7801create_new_subspace (space, name, loadable, code_only, common,
7802 dup_common, is_zero, sort, access, space_index,
7803 alignment, quadrant, seg)
7804 sd_chain_struct *space;
7805 char *name;
7806 int loadable, code_only, common, dup_common, is_zero;
7807 int sort;
7808 int access;
7809 int space_index;
7810 int alignment;
7811 int quadrant;
7812 asection *seg;
7813{
7814 ssd_chain_struct *chain_entry;
7815
7816 chain_entry = (ssd_chain_struct *) xmalloc (sizeof (ssd_chain_struct));
7817 if (!chain_entry)
7818 as_fatal (_("Out of memory: could not allocate new subspace chain entry: %s\n"), name);
7819
7820 SUBSPACE_NAME (chain_entry) = (char *) xmalloc (strlen (name) + 1);
7821 strcpy (SUBSPACE_NAME (chain_entry), name);
7822
7823 /* Initialize subspace_defined. When we hit a .subspace directive
7824 we'll set it to 1 which "locks-in" the subspace attributes. */
7825 SUBSPACE_DEFINED (chain_entry) = 0;
7826
49863f82 7827 chain_entry->ssd_subseg = 0;
252b5132
RH
7828 chain_entry->ssd_seg = seg;
7829 chain_entry->ssd_next = NULL;
7830
7831 /* Find spot for the new subspace based on its sort key. */
7832 if (space->sd_subspaces == NULL)
7833 space->sd_subspaces = chain_entry;
7834 else
7835 {
7836 ssd_chain_struct *chain_pointer;
7837 ssd_chain_struct *prev_chain_pointer;
7838
7839 chain_pointer = space->sd_subspaces;
7840 prev_chain_pointer = NULL;
7841
7842 while (chain_pointer)
7843 {
7844 prev_chain_pointer = chain_pointer;
7845 chain_pointer = chain_pointer->ssd_next;
7846 }
7847
7848 /* Now we have somewhere to put the new entry. Insert it and update
7849 the links. */
7850 if (prev_chain_pointer)
7851 {
7852 chain_entry->ssd_next = chain_pointer;
7853 prev_chain_pointer->ssd_next = chain_entry;
7854 }
7855 else
7856 {
7857 space->sd_subspaces = chain_entry;
7858 chain_entry->ssd_next = chain_pointer;
7859 }
7860 }
7861
7862#ifdef obj_set_subsection_attributes
7863 obj_set_subsection_attributes (seg, space->sd_seg, access,
7864 sort, quadrant);
7865#endif
7866
7867 return chain_entry;
7868}
7869
7870/* Update the information for the given subspace based upon the
7871 various arguments. Return the modified subspace chain entry. */
7872
7873static ssd_chain_struct *
7874update_subspace (space, name, loadable, code_only, common, dup_common, sort,
7875 zero, access, space_index, alignment, quadrant, section)
7876 sd_chain_struct *space;
7877 char *name;
7878 int loadable;
7879 int code_only;
7880 int common;
7881 int dup_common;
7882 int zero;
7883 int sort;
7884 int access;
7885 int space_index;
7886 int alignment;
7887 int quadrant;
7888 asection *section;
7889{
7890 ssd_chain_struct *chain_entry;
7891
7892 chain_entry = is_defined_subspace (name);
7893
7894#ifdef obj_set_subsection_attributes
7895 obj_set_subsection_attributes (section, space->sd_seg, access,
7896 sort, quadrant);
7897#endif
7898
7899 return chain_entry;
7900}
7901
7902/* Return the space chain entry for the space with the name NAME or
7903 NULL if no such space exists. */
7904
7905static sd_chain_struct *
7906is_defined_space (name)
7907 char *name;
7908{
7909 sd_chain_struct *chain_pointer;
7910
7911 for (chain_pointer = space_dict_root;
7912 chain_pointer;
7913 chain_pointer = chain_pointer->sd_next)
7914 {
7915 if (strcmp (SPACE_NAME (chain_pointer), name) == 0)
7916 return chain_pointer;
7917 }
7918
7919 /* No mapping from segment to space was found. Return NULL. */
7920 return NULL;
7921}
7922
7923/* Find and return the space associated with the given seg. If no mapping
7924 from the given seg to a space is found, then return NULL.
7925
7926 Unlike subspaces, the number of spaces is not expected to grow much,
7927 so a linear exhaustive search is OK here. */
7928
7929static sd_chain_struct *
7930pa_segment_to_space (seg)
7931 asection *seg;
7932{
7933 sd_chain_struct *space_chain;
7934
7935 /* Walk through each space looking for the correct mapping. */
7936 for (space_chain = space_dict_root;
7937 space_chain;
7938 space_chain = space_chain->sd_next)
7939 {
7940 if (space_chain->sd_seg == seg)
7941 return space_chain;
7942 }
7943
7944 /* Mapping was not found. Return NULL. */
7945 return NULL;
7946}
7947
7948/* Return the space chain entry for the subspace with the name NAME or
7949 NULL if no such subspace exists.
7950
7951 Uses a linear search through all the spaces and subspaces, this may
7952 not be appropriate if we ever being placing each function in its
7953 own subspace. */
7954
7955static ssd_chain_struct *
7956is_defined_subspace (name)
7957 char *name;
7958{
7959 sd_chain_struct *space_chain;
7960 ssd_chain_struct *subspace_chain;
7961
7962 /* Walk through each space. */
7963 for (space_chain = space_dict_root;
7964 space_chain;
7965 space_chain = space_chain->sd_next)
7966 {
7967 /* Walk through each subspace looking for a name which matches. */
7968 for (subspace_chain = space_chain->sd_subspaces;
7969 subspace_chain;
7970 subspace_chain = subspace_chain->ssd_next)
7971 if (strcmp (SUBSPACE_NAME (subspace_chain), name) == 0)
7972 return subspace_chain;
7973 }
7974
7975 /* Subspace wasn't found. Return NULL. */
7976 return NULL;
7977}
7978
7979/* Find and return the subspace associated with the given seg. If no
7980 mapping from the given seg to a subspace is found, then return NULL.
7981
7982 If we ever put each procedure/function within its own subspace
7983 (to make life easier on the compiler and linker), then this will have
7984 to become more efficient. */
7985
7986static ssd_chain_struct *
7987pa_subsegment_to_subspace (seg, subseg)
7988 asection *seg;
7989 subsegT subseg;
7990{
7991 sd_chain_struct *space_chain;
7992 ssd_chain_struct *subspace_chain;
7993
7994 /* Walk through each space. */
7995 for (space_chain = space_dict_root;
7996 space_chain;
7997 space_chain = space_chain->sd_next)
7998 {
7999 if (space_chain->sd_seg == seg)
8000 {
8001 /* Walk through each subspace within each space looking for
8002 the correct mapping. */
8003 for (subspace_chain = space_chain->sd_subspaces;
8004 subspace_chain;
8005 subspace_chain = subspace_chain->ssd_next)
8006 if (subspace_chain->ssd_subseg == (int) subseg)
8007 return subspace_chain;
8008 }
8009 }
8010
8011 /* No mapping from subsegment to subspace found. Return NULL. */
8012 return NULL;
8013}
8014
8015/* Given a number, try and find a space with the name number.
8016
8017 Return a pointer to a space dictionary chain entry for the space
8018 that was found or NULL on failure. */
8019
8020static sd_chain_struct *
8021pa_find_space_by_number (number)
8022 int number;
8023{
8024 sd_chain_struct *space_chain;
8025
8026 for (space_chain = space_dict_root;
8027 space_chain;
8028 space_chain = space_chain->sd_next)
8029 {
8030 if (SPACE_SPNUM (space_chain) == (unsigned int) number)
8031 return space_chain;
8032 }
8033
8034 /* No appropriate space found. Return NULL. */
8035 return NULL;
8036}
8037
8038/* Return the starting address for the given subspace. If the starting
8039 address is unknown then return zero. */
8040
8041static unsigned int
8042pa_subspace_start (space, quadrant)
8043 sd_chain_struct *space;
8044 int quadrant;
8045{
252b5132
RH
8046 /* FIXME. Assumes everyone puts read/write data at 0x4000000, this
8047 is not correct for the PA OSF1 port. */
8048 if ((strcmp (SPACE_NAME (space), "$PRIVATE$") == 0) && quadrant == 1)
8049 return 0x40000000;
8050 else if (space->sd_seg == data_section && quadrant == 1)
8051 return 0x40000000;
8052 else
8053 return 0;
252b5132
RH
8054 return 0;
8055}
8056
8057/* FIXME. Needs documentation. */
8058static int
8059pa_next_subseg (space)
8060 sd_chain_struct *space;
8061{
8062
8063 space->sd_last_subseg++;
8064 return space->sd_last_subseg;
8065}
49863f82 8066#endif
252b5132
RH
8067
8068/* Helper function for pa_stringer. Used to find the end of
8069 a string. */
8070
8071static unsigned int
8072pa_stringer_aux (s)
8073 char *s;
8074{
8075 unsigned int c = *s & CHAR_MASK;
8076
252b5132
RH
8077 switch (c)
8078 {
8079 case '\"':
8080 c = NOT_A_CHAR;
8081 break;
8082 default:
8083 break;
8084 }
8085 return c;
8086}
8087
8088/* Handle a .STRING type pseudo-op. */
8089
8090static void
8091pa_stringer (append_zero)
8092 int append_zero;
8093{
8094 char *s, num_buf[4];
8095 unsigned int c;
8096 int i;
8097
8098 /* Preprocess the string to handle PA-specific escape sequences.
ad1079af 8099 For example, \xDD where DD is a hexadecimal number should be
252b5132
RH
8100 changed to \OOO where OOO is an octal number. */
8101
ad1079af
AM
8102#ifdef OBJ_SOM
8103 /* We must have a valid space and subspace. */
8104 pa_check_current_space_and_subspace ();
8105#endif
8106
252b5132
RH
8107 /* Skip the opening quote. */
8108 s = input_line_pointer + 1;
8109
8110 while (is_a_char (c = pa_stringer_aux (s++)))
8111 {
8112 if (c == '\\')
8113 {
8114 c = *s;
8115 switch (c)
8116 {
8117 /* Handle \x<num>. */
8118 case 'x':
8119 {
8120 unsigned int number;
8121 int num_digit;
8122 char dg;
8123 char *s_start = s;
8124
ad1079af 8125 /* Get past the 'x'. */
252b5132
RH
8126 s++;
8127 for (num_digit = 0, number = 0, dg = *s;
8128 num_digit < 2
8129 && (isdigit (dg) || (dg >= 'a' && dg <= 'f')
8130 || (dg >= 'A' && dg <= 'F'));
8131 num_digit++)
8132 {
8133 if (isdigit (dg))
8134 number = number * 16 + dg - '0';
8135 else if (dg >= 'a' && dg <= 'f')
8136 number = number * 16 + dg - 'a' + 10;
8137 else
8138 number = number * 16 + dg - 'A' + 10;
8139
8140 s++;
8141 dg = *s;
8142 }
8143 if (num_digit > 0)
8144 {
8145 switch (num_digit)
8146 {
8147 case 1:
8148 sprintf (num_buf, "%02o", number);
8149 break;
8150 case 2:
8151 sprintf (num_buf, "%03o", number);
8152 break;
8153 }
8154 for (i = 0; i <= num_digit; i++)
8155 s_start[i] = num_buf[i];
8156 }
8157 break;
8158 }
8159 /* This might be a "\"", skip over the escaped char. */
8160 default:
8161 s++;
8162 break;
8163 }
8164 }
8165 }
8166 stringer (append_zero);
8167 pa_undefine_label ();
8168}
8169
8170/* Handle a .VERSION pseudo-op. */
8171
8172static void
8173pa_version (unused)
3f9b03b5 8174 int unused ATTRIBUTE_UNUSED;
252b5132
RH
8175{
8176 obj_version (0);
8177 pa_undefine_label ();
8178}
8179
8180#ifdef OBJ_SOM
8181
8182/* Handle a .COMPILER pseudo-op. */
8183
8184static void
8185pa_compiler (unused)
3f9b03b5 8186 int unused ATTRIBUTE_UNUSED;
252b5132
RH
8187{
8188 obj_som_compiler (0);
8189 pa_undefine_label ();
8190}
8191
8192#endif
8193
8194/* Handle a .COPYRIGHT pseudo-op. */
8195
8196static void
8197pa_copyright (unused)
3f9b03b5 8198 int unused ATTRIBUTE_UNUSED;
252b5132
RH
8199{
8200 obj_copyright (0);
8201 pa_undefine_label ();
8202}
8203
8204/* Just like a normal cons, but when finished we have to undefine
8205 the latest space label. */
8206
8207static void
8208pa_cons (nbytes)
8209 int nbytes;
8210{
8211 cons (nbytes);
8212 pa_undefine_label ();
8213}
8214
252b5132
RH
8215/* Like float_cons, but we need to undefine our label. */
8216
8217static void
8218pa_float_cons (float_type)
8219 int float_type;
8220{
8221 float_cons (float_type);
8222 pa_undefine_label ();
8223}
8224
8225/* Like s_fill, but delete our label when finished. */
8226
8227static void
8228pa_fill (unused)
3f9b03b5 8229 int unused ATTRIBUTE_UNUSED;
252b5132 8230{
49863f82 8231#ifdef OBJ_SOM
252b5132
RH
8232 /* We must have a valid space and subspace. */
8233 pa_check_current_space_and_subspace ();
49863f82 8234#endif
252b5132
RH
8235
8236 s_fill (0);
8237 pa_undefine_label ();
8238}
8239
8240/* Like lcomm, but delete our label when finished. */
8241
8242static void
8243pa_lcomm (needs_align)
8244 int needs_align;
8245{
49863f82 8246#ifdef OBJ_SOM
252b5132
RH
8247 /* We must have a valid space and subspace. */
8248 pa_check_current_space_and_subspace ();
49863f82 8249#endif
252b5132
RH
8250
8251 s_lcomm (needs_align);
8252 pa_undefine_label ();
8253}
8254
8255/* Like lsym, but delete our label when finished. */
8256
8257static void
8258pa_lsym (unused)
3f9b03b5 8259 int unused ATTRIBUTE_UNUSED;
252b5132 8260{
49863f82 8261#ifdef OBJ_SOM
252b5132
RH
8262 /* We must have a valid space and subspace. */
8263 pa_check_current_space_and_subspace ();
49863f82 8264#endif
252b5132
RH
8265
8266 s_lsym (0);
8267 pa_undefine_label ();
8268}
8269
252b5132
RH
8270/* On the PA relocations which involve function symbols must not be
8271 adjusted. This so that the linker can know when/how to create argument
8272 relocation stubs for indirect calls and calls to static functions.
8273
8274 "T" field selectors create DLT relative fixups for accessing
8275 globals and statics in PIC code; each DLT relative fixup creates
8276 an entry in the DLT table. The entries contain the address of
8277 the final target (eg accessing "foo" would create a DLT entry
8278 with the address of "foo").
8279
8280 Unfortunately, the HP linker doesn't take into account any addend
8281 when generating the DLT; so accessing $LIT$+8 puts the address of
8282 $LIT$ into the DLT rather than the address of $LIT$+8.
8283
8284 The end result is we can't perform relocation symbol reductions for
8285 any fixup which creates entries in the DLT (eg they use "T" field
8286 selectors).
8287
8288 Reject reductions involving symbols with external scope; such
d53d2751 8289 reductions make life a living hell for object file editors.
252b5132
RH
8290
8291 FIXME. Also reject R_HPPA relocations which are 32bits wide in
8292 the code space. The SOM BFD backend doesn't know how to pull the
8293 right bits out of an instruction. */
8294
8295int
8296hppa_fix_adjustable (fixp)
8297 fixS *fixp;
8298{
8299 struct hppa_fix_struct *hppa_fix;
8300
8301 hppa_fix = (struct hppa_fix_struct *) fixp->tc_fix_data;
8302
8303#ifdef OBJ_SOM
8304 /* Reject reductions of symbols in 32bit relocs. */
8305 if (fixp->fx_r_type == R_HPPA && hppa_fix->fx_r_format == 32)
8306 return 0;
1cd1c99b 8307#endif
252b5132 8308
904a31bf
AM
8309#ifdef OBJ_ELF
8310 if (fixp->fx_r_type == (int) R_PARISC_GNU_VTINHERIT
8311 || fixp->fx_r_type == (int) R_PARISC_GNU_VTENTRY)
8312 return 0;
5506e1a5 8313#endif
959ee541
AM
8314
8315 if (fixp->fx_addsy && (S_IS_EXTERNAL (fixp->fx_addsy)
8316 || S_IS_WEAK (fixp->fx_addsy)))
8317 return 0;
904a31bf 8318
252b5132 8319 /* Reject reductions of symbols in sym1-sym2 expressions when
d53d2751 8320 the fixup will occur in a CODE subspace.
252b5132
RH
8321
8322 XXX FIXME: Long term we probably want to reject all of these;
8323 for example reducing in the debug section would lose if we ever
8324 supported using the optimizing hp linker. */
8325 if (fixp->fx_addsy
8326 && fixp->fx_subsy
8327 && (hppa_fix->segment->flags & SEC_CODE))
8328 {
8329 /* Apparently sy_used_in_reloc never gets set for sub symbols. */
398e8c25 8330 symbol_mark_used_in_reloc (fixp->fx_subsy);
252b5132
RH
8331 return 0;
8332 }
8333
8334 /* We can't adjust any relocs that use LR% and RR% field selectors.
1cd1c99b
AM
8335
8336 If a symbol is reduced to a section symbol, the assembler will
8337 adjust the addend unless the symbol happens to reside right at
8338 the start of the section. Additionally, the linker has no choice
8339 but to manipulate the addends when coalescing input sections for
8340 "ld -r". Since an LR% field selector is defined to round the
8341 addend, we can't change the addend without risking that a LR% and
8342 it's corresponding (possible multiple) RR% field will no longer
8343 sum to the right value.
8344
8345 eg. Suppose we have
8346 . ldil LR%foo+0,%r21
8347 . ldw RR%foo+0(%r21),%r26
25a8b250
AM
8348 . ldw RR%foo+4(%r21),%r25
8349
8350 If foo is at address 4092 (decimal) in section `sect', then after
8351 reducing to the section symbol we get
8352 . LR%sect+4092 == (L%sect)+0
8353 . RR%sect+4092 == (R%sect)+4092
8354 . RR%sect+4096 == (R%sect)-4096
8355 and the last address loses because rounding the addend to 8k
8356 mutiples takes us up to 8192 with an offset of -4096.
8357
8358 In cases where the LR% expression is identical to the RR% one we
8359 will never have a problem, but is so happens that gcc rounds
8360 addends involved in LR% field selectors to work around a HP
8361 linker bug. ie. We often have addresses like the last case
1cd1c99b
AM
8362 above where the LR% expression is offset from the RR% one. */
8363
252b5132
RH
8364 if (hppa_fix->fx_r_field == e_lrsel
8365 || hppa_fix->fx_r_field == e_rrsel
8366 || hppa_fix->fx_r_field == e_nlrsel)
8367 return 0;
252b5132
RH
8368
8369 /* Reject reductions of symbols in DLT relative relocs,
8370 relocations with plabels. */
8371 if (hppa_fix->fx_r_field == e_tsel
8372 || hppa_fix->fx_r_field == e_ltsel
8373 || hppa_fix->fx_r_field == e_rtsel
8374 || hppa_fix->fx_r_field == e_psel
8375 || hppa_fix->fx_r_field == e_rpsel
8376 || hppa_fix->fx_r_field == e_lpsel)
8377 return 0;
8378
252b5132
RH
8379 /* Reject absolute calls (jumps). */
8380 if (hppa_fix->fx_r_type == R_HPPA_ABS_CALL)
8381 return 0;
8382
8383 /* Reject reductions of function symbols. */
5506e1a5
AM
8384 if (fixp->fx_addsy != 0 && S_IS_FUNCTION (fixp->fx_addsy))
8385 return 0;
252b5132 8386
5506e1a5 8387 return 1;
252b5132
RH
8388}
8389
8390/* Return nonzero if the fixup in FIXP will require a relocation,
8391 even it if appears that the fixup could be completely handled
8392 within GAS. */
8393
8394int
8395hppa_force_relocation (fixp)
ad1079af 8396 struct fix *fixp;
252b5132
RH
8397{
8398 struct hppa_fix_struct *hppa_fixp;
252b5132
RH
8399
8400 hppa_fixp = (struct hppa_fix_struct *) fixp->tc_fix_data;
8401#ifdef OBJ_SOM
ad1079af
AM
8402 if (fixp->fx_r_type == (int) R_HPPA_ENTRY
8403 || fixp->fx_r_type == (int) R_HPPA_EXIT
8404 || fixp->fx_r_type == (int) R_HPPA_BEGIN_BRTAB
8405 || fixp->fx_r_type == (int) R_HPPA_END_BRTAB
8406 || fixp->fx_r_type == (int) R_HPPA_BEGIN_TRY
8407 || fixp->fx_r_type == (int) R_HPPA_END_TRY
252b5132
RH
8408 || (fixp->fx_addsy != NULL && fixp->fx_subsy != NULL
8409 && (hppa_fixp->segment->flags & SEC_CODE) != 0))
8410 return 1;
8411#endif
904a31bf
AM
8412#ifdef OBJ_ELF
8413 if (fixp->fx_r_type == (int) R_PARISC_GNU_VTINHERIT
8414 || fixp->fx_r_type == (int) R_PARISC_GNU_VTENTRY)
8415 return 1;
5506e1a5
AM
8416#endif
8417
8418 assert (fixp->fx_addsy != NULL);
252b5132 8419
9e754211
AM
8420 /* Ensure we emit a relocation for global symbols so that dynamic
8421 linking works. */
5506e1a5 8422 if (S_IS_EXTERNAL (fixp->fx_addsy) || S_IS_WEAK (fixp->fx_addsy))
9e754211
AM
8423 return 1;
8424
252b5132
RH
8425 /* It is necessary to force PC-relative calls/jumps to have a relocation
8426 entry if they're going to need either a argument relocation or long
9e754211 8427 call stub. */
5506e1a5
AM
8428 if (fixp->fx_pcrel
8429 && arg_reloc_stub_needed (symbol_arg_reloc_info (fixp->fx_addsy),
8430 hppa_fixp->fx_arg_reloc))
252b5132 8431 return 1;
ad1079af 8432
5506e1a5
AM
8433 /* Now check to see if we're going to need a long-branch stub. */
8434 if (fixp->fx_r_type == (int) R_HPPA_PCREL_CALL)
8435 {
8436 valueT distance;
8437
8438 distance = (fixp->fx_offset + S_GET_VALUE (fixp->fx_addsy)
8439 - md_pcrel_from (fixp) - 8);
8440 if (distance + 8388608 >= 16777216
8441 || (hppa_fixp->fx_r_format == 17 && distance + 262144 >= 524288)
27df9f40
AM
8442#ifdef OBJ_ELF
8443 || (hppa_fixp->fx_r_format == 12 && distance + 8192 >= 16384)
8444#endif
8445 )
5506e1a5
AM
8446 return 1;
8447 }
252b5132 8448
ad1079af 8449 if (fixp->fx_r_type == (int) R_HPPA_ABS_CALL)
252b5132 8450 return 1;
252b5132
RH
8451
8452 /* No need (yet) to force another relocations to be emitted. */
8453 return 0;
8454}
8455
8456/* Now for some ELF specific code. FIXME. */
8457#ifdef OBJ_ELF
8458/* Mark the end of a function so that it's possible to compute
8459 the size of the function in hppa_elf_final_processing. */
8460
8461static void
8462hppa_elf_mark_end_of_function ()
8463{
8464 /* ELF does not have EXIT relocations. All we do is create a
8465 temporary symbol marking the end of the function. */
ad1079af
AM
8466 char *name;
8467
8468 if (last_call_info == NULL || last_call_info->start_symbol == NULL)
8469 {
8470 /* We have already warned about a missing label,
8471 or other problems. */
8472 return;
8473 }
252b5132 8474
ad1079af
AM
8475 name = (char *) xmalloc (strlen ("L$\001end_")
8476 + strlen (S_GET_NAME (last_call_info->start_symbol))
8477 + 1);
252b5132
RH
8478 if (name)
8479 {
8480 symbolS *symbolP;
8481
8482 strcpy (name, "L$\001end_");
8483 strcat (name, S_GET_NAME (last_call_info->start_symbol));
8484
8485 /* If we have a .exit followed by a .procend, then the
8486 symbol will have already been defined. */
8487 symbolP = symbol_find (name);
8488 if (symbolP)
8489 {
8490 /* The symbol has already been defined! This can
8491 happen if we have a .exit followed by a .procend.
8492
8493 This is *not* an error. All we want to do is free
8494 the memory we just allocated for the name and continue. */
8495 xfree (name);
8496 }
8497 else
8498 {
8499 /* symbol value should be the offset of the
8500 last instruction of the function */
8501 symbolP = symbol_new (name, now_seg, (valueT) (frag_now_fix () - 4),
8502 frag_now);
8503
8504 assert (symbolP);
a0f75b47 8505 S_CLEAR_EXTERNAL (symbolP);
252b5132
RH
8506 symbol_table_insert (symbolP);
8507 }
8508
8509 if (symbolP)
8510 last_call_info->end_symbol = symbolP;
8511 else
8512 as_bad (_("Symbol '%s' could not be created."), name);
8513
8514 }
8515 else
8516 as_bad (_("No memory for symbol name."));
8517
8518}
8519
8520/* For ELF, this function serves one purpose: to setup the st_size
8521 field of STT_FUNC symbols. To do this, we need to scan the
8522 call_info structure list, determining st_size in by taking the
8523 difference in the address of the beginning/end marker symbols. */
8524
8525void
8526elf_hppa_final_processing ()
8527{
8528 struct call_info *call_info_pointer;
8529
8530 for (call_info_pointer = call_info_root;
8531 call_info_pointer;
8532 call_info_pointer = call_info_pointer->ci_next)
8533 {
8534 elf_symbol_type *esym
a0f75b47
ILT
8535 = ((elf_symbol_type *)
8536 symbol_get_bfdsym (call_info_pointer->start_symbol));
252b5132
RH
8537 esym->internal_elf_sym.st_size =
8538 S_GET_VALUE (call_info_pointer->end_symbol)
8539 - S_GET_VALUE (call_info_pointer->start_symbol) + 4;
8540 }
8541}
2d93dcc4 8542
ad1079af
AM
8543void
8544pa_end_of_source ()
2d93dcc4
JL
8545{
8546 if (debug_type == DEBUG_DWARF2)
8547 dwarf2_finish ();
8548}
904a31bf
AM
8549
8550static void
8551pa_vtable_entry (ignore)
8552 int ignore ATTRIBUTE_UNUSED;
8553{
8554 struct fix *new_fix;
8555
8556 new_fix = obj_elf_vtable_entry (0);
8557
8558 if (new_fix)
8559 {
8560 struct hppa_fix_struct *hppa_fix = (struct hppa_fix_struct *)
8561 obstack_alloc (&notes, sizeof (struct hppa_fix_struct));
8562 hppa_fix->fx_r_type = R_HPPA;
8563 hppa_fix->fx_r_field = e_fsel;
8564 hppa_fix->fx_r_format = 32;
8565 hppa_fix->fx_arg_reloc = 0;
8566 hppa_fix->segment = now_seg;
8567 new_fix->tc_fix_data = (void *) hppa_fix;
8568 new_fix->fx_r_type = (int) R_PARISC_GNU_VTENTRY;
8569 }
8570}
8571
8572static void
8573pa_vtable_inherit (ignore)
8574 int ignore ATTRIBUTE_UNUSED;
8575{
8576 struct fix *new_fix;
8577
8578 new_fix = obj_elf_vtable_inherit (0);
8579
8580 if (new_fix)
8581 {
8582 struct hppa_fix_struct *hppa_fix = (struct hppa_fix_struct *)
8583 obstack_alloc (&notes, sizeof (struct hppa_fix_struct));
8584 hppa_fix->fx_r_type = R_HPPA;
8585 hppa_fix->fx_r_field = e_fsel;
8586 hppa_fix->fx_r_format = 32;
8587 hppa_fix->fx_arg_reloc = 0;
8588 hppa_fix->segment = now_seg;
8589 new_fix->tc_fix_data = (void *) hppa_fix;
8590 new_fix->fx_r_type = (int) R_PARISC_GNU_VTINHERIT;
8591 }
8592}
2d93dcc4 8593#endif
This page took 0.456894 seconds and 4 git commands to generate.