1 /* bfd back-end for HP PA-RISC SOM objects.
2 Copyright (C) 1990, 91, 92, 93, 94, 95, 96, 97, 1998, 2000
3 Free Software Foundation, Inc.
5 Contributed by the Center for Software Science at the
8 This file is part of BFD, the Binary File Descriptor library.
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
25 #include "alloca-conf.h"
29 #if defined (HOST_HPPAHPUX) || defined (HOST_HPPABSD) || defined (HOST_HPPAOSF) || defined(HOST_HPPAMPEIX)
34 #include <sys/param.h>
36 #include <machine/reg.h>
40 /* Magic not defined in standard HP-UX header files until 8.0 */
42 #ifndef CPU_PA_RISC1_0
43 #define CPU_PA_RISC1_0 0x20B
44 #endif /* CPU_PA_RISC1_0 */
46 #ifndef CPU_PA_RISC1_1
47 #define CPU_PA_RISC1_1 0x210
48 #endif /* CPU_PA_RISC1_1 */
50 #ifndef CPU_PA_RISC2_0
51 #define CPU_PA_RISC2_0 0x214
52 #endif /* CPU_PA_RISC2_0 */
54 #ifndef _PA_RISC1_0_ID
55 #define _PA_RISC1_0_ID CPU_PA_RISC1_0
56 #endif /* _PA_RISC1_0_ID */
58 #ifndef _PA_RISC1_1_ID
59 #define _PA_RISC1_1_ID CPU_PA_RISC1_1
60 #endif /* _PA_RISC1_1_ID */
62 #ifndef _PA_RISC2_0_ID
63 #define _PA_RISC2_0_ID CPU_PA_RISC2_0
64 #endif /* _PA_RISC2_0_ID */
66 #ifndef _PA_RISC_MAXID
67 #define _PA_RISC_MAXID 0x2FF
68 #endif /* _PA_RISC_MAXID */
71 #define _PA_RISC_ID(__m_num) \
72 (((__m_num) == _PA_RISC1_0_ID) || \
73 ((__m_num) >= _PA_RISC1_1_ID && (__m_num) <= _PA_RISC_MAXID))
74 #endif /* _PA_RISC_ID */
77 /* HIUX in it's infinite stupidity changed the names for several "well
78 known" constants. Work around such braindamage. Try the HPUX version
79 first, then the HIUX version, and finally provide a default. */
81 #define EXEC_AUX_ID HPUX_AUX_ID
84 #if !defined (EXEC_AUX_ID) && defined (HIUX_AUX_ID)
85 #define EXEC_AUX_ID HIUX_AUX_ID
92 /* Size (in chars) of the temporary buffers used during fixup and string
95 #define SOM_TMP_BUFSIZE 8192
97 /* Size of the hash table in archives. */
98 #define SOM_LST_HASH_SIZE 31
100 /* Max number of SOMs to be found in an archive. */
101 #define SOM_LST_MODULE_LIMIT 1024
103 /* Generic alignment macro. */
104 #define SOM_ALIGN(val, alignment) \
105 (((val) + (alignment) - 1) & ~((alignment) - 1))
107 /* SOM allows any one of the four previous relocations to be reused
108 with a "R_PREV_FIXUP" relocation entry. Since R_PREV_FIXUP
109 relocations are always a single byte, using a R_PREV_FIXUP instead
110 of some multi-byte relocation makes object files smaller.
112 Note one side effect of using a R_PREV_FIXUP is the relocation that
113 is being repeated moves to the front of the queue. */
116 unsigned char *reloc;
120 /* This fully describes the symbol types which may be attached to
121 an EXPORT or IMPORT directive. Only SOM uses this formation
122 (ELF has no need for it). */
126 SYMBOL_TYPE_ABSOLUTE,
130 SYMBOL_TYPE_MILLICODE,
132 SYMBOL_TYPE_PRI_PROG,
133 SYMBOL_TYPE_SEC_PROG,
136 struct section_to_type
142 /* Assorted symbol information that needs to be derived from the BFD symbol
143 and/or the BFD backend private symbol data. */
144 struct som_misc_symbol_info
146 unsigned int symbol_type;
147 unsigned int symbol_scope;
148 unsigned int arg_reloc;
149 unsigned int symbol_info;
150 unsigned int symbol_value;
151 unsigned int priv_level;
152 unsigned int secondary_def;
155 /* Forward declarations */
157 static boolean som_mkobject PARAMS ((bfd *));
158 static const bfd_target * som_object_setup PARAMS ((bfd *,
160 struct som_exec_auxhdr *,
162 static boolean setup_sections PARAMS ((bfd *, struct header *, unsigned long));
163 static const bfd_target * som_object_p PARAMS ((bfd *));
164 static boolean som_write_object_contents PARAMS ((bfd *));
165 static boolean som_slurp_string_table PARAMS ((bfd *));
166 static unsigned int som_slurp_symbol_table PARAMS ((bfd *));
167 static long som_get_symtab_upper_bound PARAMS ((bfd *));
168 static long som_canonicalize_reloc PARAMS ((bfd *, sec_ptr,
169 arelent **, asymbol **));
170 static long som_get_reloc_upper_bound PARAMS ((bfd *, sec_ptr));
171 static unsigned int som_set_reloc_info PARAMS ((unsigned char *, unsigned int,
172 arelent *, asection *,
173 asymbol **, boolean));
174 static boolean som_slurp_reloc_table PARAMS ((bfd *, asection *,
175 asymbol **, boolean));
176 static long som_get_symtab PARAMS ((bfd *, asymbol **));
177 static asymbol * som_make_empty_symbol PARAMS ((bfd *));
178 static void som_print_symbol PARAMS ((bfd *, PTR,
179 asymbol *, bfd_print_symbol_type));
180 static boolean som_new_section_hook PARAMS ((bfd *, asection *));
181 static boolean som_bfd_copy_private_symbol_data PARAMS ((bfd *, asymbol *,
183 static boolean som_bfd_copy_private_section_data PARAMS ((bfd *, asection *,
185 static boolean som_bfd_copy_private_bfd_data PARAMS ((bfd *, bfd *));
186 #define som_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
187 #define som_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
188 static boolean som_bfd_is_local_label_name PARAMS ((bfd *, const char *));
189 static boolean som_set_section_contents PARAMS ((bfd *, sec_ptr, PTR,
190 file_ptr, bfd_size_type));
191 static boolean som_get_section_contents PARAMS ((bfd *, sec_ptr, PTR,
192 file_ptr, bfd_size_type));
193 static boolean som_set_arch_mach PARAMS ((bfd *, enum bfd_architecture,
195 static boolean som_find_nearest_line PARAMS ((bfd *, asection *,
200 static void som_get_symbol_info PARAMS ((bfd *, asymbol *, symbol_info *));
201 static asection * bfd_section_from_som_symbol PARAMS ((bfd *,
202 struct symbol_dictionary_record *));
203 static int log2 PARAMS ((unsigned int));
204 static bfd_reloc_status_type hppa_som_reloc PARAMS ((bfd *, arelent *,
208 static void som_initialize_reloc_queue PARAMS ((struct reloc_queue *));
209 static void som_reloc_queue_insert PARAMS ((unsigned char *, unsigned int,
210 struct reloc_queue *));
211 static void som_reloc_queue_fix PARAMS ((struct reloc_queue *, unsigned int));
212 static int som_reloc_queue_find PARAMS ((unsigned char *, unsigned int,
213 struct reloc_queue *));
214 static unsigned char * try_prev_fixup PARAMS ((bfd *, int *, unsigned char *,
216 struct reloc_queue *));
218 static unsigned char * som_reloc_skip PARAMS ((bfd *, unsigned int,
219 unsigned char *, unsigned int *,
220 struct reloc_queue *));
221 static unsigned char * som_reloc_addend PARAMS ((bfd *, int, unsigned char *,
223 struct reloc_queue *));
224 static unsigned char * som_reloc_call PARAMS ((bfd *, unsigned char *,
227 struct reloc_queue *));
228 static unsigned long som_count_spaces PARAMS ((bfd *));
229 static unsigned long som_count_subspaces PARAMS ((bfd *));
230 static int compare_syms PARAMS ((const void *, const void *));
231 static int compare_subspaces PARAMS ((const void *, const void *));
232 static unsigned long som_compute_checksum PARAMS ((bfd *));
233 static boolean som_prep_headers PARAMS ((bfd *));
234 static int som_sizeof_headers PARAMS ((bfd *, boolean));
235 static boolean som_finish_writing PARAMS ((bfd *));
236 static boolean som_build_and_write_symbol_table PARAMS ((bfd *));
237 static void som_prep_for_fixups PARAMS ((bfd *, asymbol **, unsigned long));
238 static boolean som_write_fixups PARAMS ((bfd *, unsigned long, unsigned int *));
239 static boolean som_write_space_strings PARAMS ((bfd *, unsigned long,
241 static boolean som_write_symbol_strings PARAMS ((bfd *, unsigned long,
242 asymbol **, unsigned int,
245 static boolean som_begin_writing PARAMS ((bfd *));
246 static reloc_howto_type * som_bfd_reloc_type_lookup
247 PARAMS ((bfd *, bfd_reloc_code_real_type));
248 static char som_section_type PARAMS ((const char *));
249 static int som_decode_symclass PARAMS ((asymbol *));
250 static boolean som_bfd_count_ar_symbols PARAMS ((bfd *, struct lst_header *,
253 static boolean som_bfd_fill_in_ar_symbols PARAMS ((bfd *, struct lst_header *,
255 static boolean som_slurp_armap PARAMS ((bfd *));
256 static boolean som_write_armap PARAMS ((bfd *, unsigned int, struct orl *,
258 static void som_bfd_derive_misc_symbol_info PARAMS ((bfd *, asymbol *,
259 struct som_misc_symbol_info *));
260 static boolean som_bfd_prep_for_ar_write PARAMS ((bfd *, unsigned int *,
262 static unsigned int som_bfd_ar_symbol_hash PARAMS ((asymbol *));
263 static boolean som_bfd_ar_write_symbol_stuff PARAMS ((bfd *, unsigned int,
267 static boolean som_is_space PARAMS ((asection *));
268 static boolean som_is_subspace PARAMS ((asection *));
269 static boolean som_is_container PARAMS ((asection *, asection *));
270 static boolean som_bfd_free_cached_info PARAMS ((bfd *));
271 static boolean som_bfd_link_split_section PARAMS ((bfd *, asection *));
273 /* Map SOM section names to POSIX/BSD single-character symbol types.
275 This table includes all the standard subspaces as defined in the
276 current "PRO ABI for PA-RISC Systems", $UNWIND$ which for
277 some reason was left out, and sections specific to embedded stabs. */
279 static const struct section_to_type stt[] = {
281 {"$SHLIB_INFO$", 't'},
282 {"$MILLICODE$", 't'},
285 {"$UNWIND_START$", 't'},
289 {"$SHLIB_DATA$", 'd'},
291 {"$SHORTDATA$", 'g'},
296 {"$GDB_STRINGS$", 'N'},
297 {"$GDB_SYMBOLS$", 'N'},
301 /* About the relocation formatting table...
303 There are 256 entries in the table, one for each possible
304 relocation opcode available in SOM. We index the table by
305 the relocation opcode. The names and operations are those
306 defined by a.out_800 (4).
308 Right now this table is only used to count and perform minimal
309 processing on relocation streams so that they can be internalized
310 into BFD and symbolically printed by utilities. To make actual use
311 of them would be much more difficult, BFD's concept of relocations
312 is far too simple to handle SOM relocations. The basic assumption
313 that a relocation can be completely processed independent of other
314 relocations before an object file is written is invalid for SOM.
316 The SOM relocations are meant to be processed as a stream, they
317 specify copying of data from the input section to the output section
318 while possibly modifying the data in some manner. They also can
319 specify that a variable number of zeros or uninitialized data be
320 inserted on in the output segment at the current offset. Some
321 relocations specify that some previous relocation be re-applied at
322 the current location in the input/output sections. And finally a number
323 of relocations have effects on other sections (R_ENTRY, R_EXIT,
324 R_UNWIND_AUX and a variety of others). There isn't even enough room
325 in the BFD relocation data structure to store enough information to
326 perform all the relocations.
328 Each entry in the table has three fields.
330 The first entry is an index into this "class" of relocations. This
331 index can then be used as a variable within the relocation itself.
333 The second field is a format string which actually controls processing
334 of the relocation. It uses a simple postfix machine to do calculations
335 based on variables/constants found in the string and the relocation
338 The third field specifys whether or not this relocation may use
339 a constant (V) from the previous R_DATA_OVERRIDE rather than a constant
340 stored in the instruction.
344 L = input space byte count
345 D = index into class of relocations
346 M = output space byte count
347 N = statement number (unused?)
349 R = parameter relocation bits
351 T = first 32 bits of stack unwind information
352 U = second 32 bits of stack unwind information
353 V = a literal constant (usually used in the next relocation)
354 P = a previous relocation
356 Lower case letters (starting with 'b') refer to following
357 bytes in the relocation stream. 'b' is the next 1 byte,
358 c is the next 2 bytes, d is the next 3 bytes, etc...
359 This is the variable part of the relocation entries that
360 makes our life a living hell.
362 numerical constants are also used in the format string. Note
363 the constants are represented in decimal.
365 '+', "*" and "=" represents the obvious postfix operators.
366 '<' represents a left shift.
370 Parameter Relocation Bits:
374 Previous Relocations: The index field represents which in the queue
375 of 4 previous fixups should be re-applied.
377 Literal Constants: These are generally used to represent addend
378 parts of relocations when these constants are not stored in the
379 fields of the instructions themselves. For example the instruction
380 addil foo-$global$-0x1234 would use an override for "0x1234" rather
381 than storing it into the addil itself. */
389 static const struct fixup_format som_fixup_formats[256] =
391 /* R_NO_RELOCATION */
392 0, "LD1+4*=", /* 0x00 */
393 1, "LD1+4*=", /* 0x01 */
394 2, "LD1+4*=", /* 0x02 */
395 3, "LD1+4*=", /* 0x03 */
396 4, "LD1+4*=", /* 0x04 */
397 5, "LD1+4*=", /* 0x05 */
398 6, "LD1+4*=", /* 0x06 */
399 7, "LD1+4*=", /* 0x07 */
400 8, "LD1+4*=", /* 0x08 */
401 9, "LD1+4*=", /* 0x09 */
402 10, "LD1+4*=", /* 0x0a */
403 11, "LD1+4*=", /* 0x0b */
404 12, "LD1+4*=", /* 0x0c */
405 13, "LD1+4*=", /* 0x0d */
406 14, "LD1+4*=", /* 0x0e */
407 15, "LD1+4*=", /* 0x0f */
408 16, "LD1+4*=", /* 0x10 */
409 17, "LD1+4*=", /* 0x11 */
410 18, "LD1+4*=", /* 0x12 */
411 19, "LD1+4*=", /* 0x13 */
412 20, "LD1+4*=", /* 0x14 */
413 21, "LD1+4*=", /* 0x15 */
414 22, "LD1+4*=", /* 0x16 */
415 23, "LD1+4*=", /* 0x17 */
416 0, "LD8<b+1+4*=", /* 0x18 */
417 1, "LD8<b+1+4*=", /* 0x19 */
418 2, "LD8<b+1+4*=", /* 0x1a */
419 3, "LD8<b+1+4*=", /* 0x1b */
420 0, "LD16<c+1+4*=", /* 0x1c */
421 1, "LD16<c+1+4*=", /* 0x1d */
422 2, "LD16<c+1+4*=", /* 0x1e */
423 0, "Ld1+=", /* 0x1f */
425 0, "Lb1+4*=", /* 0x20 */
426 1, "Ld1+=", /* 0x21 */
428 0, "Lb1+4*=", /* 0x22 */
429 1, "Ld1+=", /* 0x23 */
432 /* R_DATA_ONE_SYMBOL */
433 0, "L4=Sb=", /* 0x25 */
434 1, "L4=Sd=", /* 0x26 */
436 0, "L4=Sb=", /* 0x27 */
437 1, "L4=Sd=", /* 0x28 */
440 /* R_REPEATED_INIT */
441 0, "L4=Mb1+4*=", /* 0x2a */
442 1, "Lb4*=Mb1+L*=", /* 0x2b */
443 2, "Lb4*=Md1+4*=", /* 0x2c */
444 3, "Ld1+=Me1+=", /* 0x2d */
448 0, "L4=RD=Sb=", /* 0x30 */
449 1, "L4=RD=Sb=", /* 0x31 */
450 2, "L4=RD=Sb=", /* 0x32 */
451 3, "L4=RD=Sb=", /* 0x33 */
452 4, "L4=RD=Sb=", /* 0x34 */
453 5, "L4=RD=Sb=", /* 0x35 */
454 6, "L4=RD=Sb=", /* 0x36 */
455 7, "L4=RD=Sb=", /* 0x37 */
456 8, "L4=RD=Sb=", /* 0x38 */
457 9, "L4=RD=Sb=", /* 0x39 */
458 0, "L4=RD8<b+=Sb=",/* 0x3a */
459 1, "L4=RD8<b+=Sb=",/* 0x3b */
460 0, "L4=RD8<b+=Sd=",/* 0x3c */
461 1, "L4=RD8<b+=Sd=",/* 0x3d */
462 /* R_SHORT_PCREL_MODE */
464 /* R_LONG_PCREL_MODE */
467 0, "L4=RD=Sb=", /* 0x40 */
468 1, "L4=RD=Sb=", /* 0x41 */
469 2, "L4=RD=Sb=", /* 0x42 */
470 3, "L4=RD=Sb=", /* 0x43 */
471 4, "L4=RD=Sb=", /* 0x44 */
472 5, "L4=RD=Sb=", /* 0x45 */
473 6, "L4=RD=Sb=", /* 0x46 */
474 7, "L4=RD=Sb=", /* 0x47 */
475 8, "L4=RD=Sb=", /* 0x48 */
476 9, "L4=RD=Sb=", /* 0x49 */
477 0, "L4=RD8<b+=Sb=",/* 0x4a */
478 1, "L4=RD8<b+=Sb=",/* 0x4b */
479 0, "L4=RD8<b+=Sd=",/* 0x4c */
480 1, "L4=RD8<b+=Sd=",/* 0x4d */
485 0, "L4=SD=", /* 0x50 */
486 1, "L4=SD=", /* 0x51 */
487 2, "L4=SD=", /* 0x52 */
488 3, "L4=SD=", /* 0x53 */
489 4, "L4=SD=", /* 0x54 */
490 5, "L4=SD=", /* 0x55 */
491 6, "L4=SD=", /* 0x56 */
492 7, "L4=SD=", /* 0x57 */
493 8, "L4=SD=", /* 0x58 */
494 9, "L4=SD=", /* 0x59 */
495 10, "L4=SD=", /* 0x5a */
496 11, "L4=SD=", /* 0x5b */
497 12, "L4=SD=", /* 0x5c */
498 13, "L4=SD=", /* 0x5d */
499 14, "L4=SD=", /* 0x5e */
500 15, "L4=SD=", /* 0x5f */
501 16, "L4=SD=", /* 0x60 */
502 17, "L4=SD=", /* 0x61 */
503 18, "L4=SD=", /* 0x62 */
504 19, "L4=SD=", /* 0x63 */
505 20, "L4=SD=", /* 0x64 */
506 21, "L4=SD=", /* 0x65 */
507 22, "L4=SD=", /* 0x66 */
508 23, "L4=SD=", /* 0x67 */
509 24, "L4=SD=", /* 0x68 */
510 25, "L4=SD=", /* 0x69 */
511 26, "L4=SD=", /* 0x6a */
512 27, "L4=SD=", /* 0x6b */
513 28, "L4=SD=", /* 0x6c */
514 29, "L4=SD=", /* 0x6d */
515 30, "L4=SD=", /* 0x6e */
516 31, "L4=SD=", /* 0x6f */
517 32, "L4=Sb=", /* 0x70 */
518 33, "L4=Sd=", /* 0x71 */
527 0, "L4=Sb=", /* 0x78 */
528 1, "L4=Sd=", /* 0x79 */
536 /* R_CODE_ONE_SYMBOL */
537 0, "L4=SD=", /* 0x80 */
538 1, "L4=SD=", /* 0x81 */
539 2, "L4=SD=", /* 0x82 */
540 3, "L4=SD=", /* 0x83 */
541 4, "L4=SD=", /* 0x84 */
542 5, "L4=SD=", /* 0x85 */
543 6, "L4=SD=", /* 0x86 */
544 7, "L4=SD=", /* 0x87 */
545 8, "L4=SD=", /* 0x88 */
546 9, "L4=SD=", /* 0x89 */
547 10, "L4=SD=", /* 0x8q */
548 11, "L4=SD=", /* 0x8b */
549 12, "L4=SD=", /* 0x8c */
550 13, "L4=SD=", /* 0x8d */
551 14, "L4=SD=", /* 0x8e */
552 15, "L4=SD=", /* 0x8f */
553 16, "L4=SD=", /* 0x90 */
554 17, "L4=SD=", /* 0x91 */
555 18, "L4=SD=", /* 0x92 */
556 19, "L4=SD=", /* 0x93 */
557 20, "L4=SD=", /* 0x94 */
558 21, "L4=SD=", /* 0x95 */
559 22, "L4=SD=", /* 0x96 */
560 23, "L4=SD=", /* 0x97 */
561 24, "L4=SD=", /* 0x98 */
562 25, "L4=SD=", /* 0x99 */
563 26, "L4=SD=", /* 0x9a */
564 27, "L4=SD=", /* 0x9b */
565 28, "L4=SD=", /* 0x9c */
566 29, "L4=SD=", /* 0x9d */
567 30, "L4=SD=", /* 0x9e */
568 31, "L4=SD=", /* 0x9f */
569 32, "L4=Sb=", /* 0xa0 */
570 33, "L4=Sd=", /* 0xa1 */
585 0, "L4=Sb=", /* 0xae */
586 1, "L4=Sd=", /* 0xaf */
588 0, "L4=Sb=", /* 0xb0 */
589 1, "L4=Sd=", /* 0xb1 */
593 0, "Te=Ue=", /* 0xb3 */
603 1, "Rb4*=", /* 0xb9 */
604 2, "Rd4*=", /* 0xba */
631 /* R_DATA_OVERRIDE */
640 0, "Sd=Vf=Ef=", /* 0xcf */
644 0, "Ob=Sd=", /* 0xd1 */
646 0, "Ob=Ve=", /* 0xd2 */
659 0, "Eb=Sd=Ve=", /* 0xda */
661 0, "Eb=Mb=", /* 0xdb */
665 0, "Ob=Ve=", /* 0xdd */
703 static const int comp1_opcodes[] =
725 static const int comp2_opcodes[] =
734 static const int comp3_opcodes[] =
741 /* These apparently are not in older versions of hpux reloc.h (hpux7). */
743 #define R_DLT_REL 0x78
747 #define R_AUX_UNWIND 0xcf
751 #define R_SEC_STMT 0xd7
754 /* And these first appeared in hpux10. */
755 #ifndef R_SHORT_PCREL_MODE
756 #define NO_PCREL_MODES
757 #define R_SHORT_PCREL_MODE 0x3e
760 #ifndef R_LONG_PCREL_MODE
761 #define R_LONG_PCREL_MODE 0x3f
773 #define R_LINETAB 0xda
776 #ifndef R_LINETAB_ESC
777 #define R_LINETAB_ESC 0xdb
780 #ifndef R_LTP_OVERRIDE
781 #define R_LTP_OVERRIDE 0xdc
785 #define R_COMMENT 0xdd
788 #define SOM_HOWTO(TYPE, NAME) \
789 HOWTO(TYPE, 0, 0, 32, false, 0, 0, hppa_som_reloc, NAME, false, 0, 0, false)
791 static reloc_howto_type som_hppa_howto_table[] =
793 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
794 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
795 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
796 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
797 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
798 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
799 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
800 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
801 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
802 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
803 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
804 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
805 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
806 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
807 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
808 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
809 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
810 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
811 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
812 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
813 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
814 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
815 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
816 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
817 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
818 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
819 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
820 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
821 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
822 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
823 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
824 SOM_HOWTO (R_NO_RELOCATION, "R_NO_RELOCATION"),
825 SOM_HOWTO (R_ZEROES, "R_ZEROES"),
826 SOM_HOWTO (R_ZEROES, "R_ZEROES"),
827 SOM_HOWTO (R_UNINIT, "R_UNINIT"),
828 SOM_HOWTO (R_UNINIT, "R_UNINIT"),
829 SOM_HOWTO (R_RELOCATION, "R_RELOCATION"),
830 SOM_HOWTO (R_DATA_ONE_SYMBOL, "R_DATA_ONE_SYMBOL"),
831 SOM_HOWTO (R_DATA_ONE_SYMBOL, "R_DATA_ONE_SYMBOL"),
832 SOM_HOWTO (R_DATA_PLABEL, "R_DATA_PLABEL"),
833 SOM_HOWTO (R_DATA_PLABEL, "R_DATA_PLABEL"),
834 SOM_HOWTO (R_SPACE_REF, "R_SPACE_REF"),
835 SOM_HOWTO (R_REPEATED_INIT, "REPEATED_INIT"),
836 SOM_HOWTO (R_REPEATED_INIT, "REPEATED_INIT"),
837 SOM_HOWTO (R_REPEATED_INIT, "REPEATED_INIT"),
838 SOM_HOWTO (R_REPEATED_INIT, "REPEATED_INIT"),
839 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
840 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
841 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
842 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
843 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
844 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
845 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
846 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
847 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
848 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
849 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
850 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
851 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
852 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
853 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
854 SOM_HOWTO (R_PCREL_CALL, "R_PCREL_CALL"),
855 SOM_HOWTO (R_SHORT_PCREL_MODE, "R_SHORT_PCREL_MODE"),
856 SOM_HOWTO (R_LONG_PCREL_MODE, "R_LONG_PCREL_MODE"),
857 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
858 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
859 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
860 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
861 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
862 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
863 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
864 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
865 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
866 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
867 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
868 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
869 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
870 SOM_HOWTO (R_ABS_CALL, "R_ABS_CALL"),
871 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
872 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
873 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
874 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
875 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
876 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
877 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
878 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
879 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
880 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
881 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
882 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
883 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
884 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
885 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
886 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
887 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
888 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
889 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
890 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
891 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
892 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
893 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
894 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
895 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
896 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
897 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
898 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
899 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
900 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
901 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
902 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
903 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
904 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
905 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
906 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
907 SOM_HOWTO (R_DP_RELATIVE, "R_DP_RELATIVE"),
908 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
909 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
910 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
911 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
912 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
913 SOM_HOWTO (R_DLT_REL, "R_DLT_REL"),
914 SOM_HOWTO (R_DLT_REL, "R_DLT_REL"),
915 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
916 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
917 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
918 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
919 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
920 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
921 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
922 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
923 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
924 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
925 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
926 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
927 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
928 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
929 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
930 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
931 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
932 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
933 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
934 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
935 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
936 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
937 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
938 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
939 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
940 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
941 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
942 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
943 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
944 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
945 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
946 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
947 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
948 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
949 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
950 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
951 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
952 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
953 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
954 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
955 SOM_HOWTO (R_CODE_ONE_SYMBOL, "R_CODE_ONE_SYMBOL"),
956 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
957 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
958 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
959 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
960 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
961 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
962 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
963 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
964 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
965 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
966 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
967 SOM_HOWTO (R_MILLI_REL, "R_MILLI_REL"),
968 SOM_HOWTO (R_MILLI_REL, "R_MILLI_REL"),
969 SOM_HOWTO (R_CODE_PLABEL, "R_CODE_PLABEL"),
970 SOM_HOWTO (R_CODE_PLABEL, "R_CODE_PLABEL"),
971 SOM_HOWTO (R_BREAKPOINT, "R_BREAKPOINT"),
972 SOM_HOWTO (R_ENTRY, "R_ENTRY"),
973 SOM_HOWTO (R_ENTRY, "R_ENTRY"),
974 SOM_HOWTO (R_ALT_ENTRY, "R_ALT_ENTRY"),
975 SOM_HOWTO (R_EXIT, "R_EXIT"),
976 SOM_HOWTO (R_BEGIN_TRY, "R_BEGIN_TRY"),
977 SOM_HOWTO (R_END_TRY, "R_END_TRY"),
978 SOM_HOWTO (R_END_TRY, "R_END_TRY"),
979 SOM_HOWTO (R_END_TRY, "R_END_TRY"),
980 SOM_HOWTO (R_BEGIN_BRTAB, "R_BEGIN_BRTAB"),
981 SOM_HOWTO (R_END_BRTAB, "R_END_BRTAB"),
982 SOM_HOWTO (R_STATEMENT, "R_STATEMENT"),
983 SOM_HOWTO (R_STATEMENT, "R_STATEMENT"),
984 SOM_HOWTO (R_STATEMENT, "R_STATEMENT"),
985 SOM_HOWTO (R_DATA_EXPR, "R_DATA_EXPR"),
986 SOM_HOWTO (R_CODE_EXPR, "R_CODE_EXPR"),
987 SOM_HOWTO (R_FSEL, "R_FSEL"),
988 SOM_HOWTO (R_LSEL, "R_LSEL"),
989 SOM_HOWTO (R_RSEL, "R_RSEL"),
990 SOM_HOWTO (R_N_MODE, "R_N_MODE"),
991 SOM_HOWTO (R_S_MODE, "R_S_MODE"),
992 SOM_HOWTO (R_D_MODE, "R_D_MODE"),
993 SOM_HOWTO (R_R_MODE, "R_R_MODE"),
994 SOM_HOWTO (R_DATA_OVERRIDE, "R_DATA_OVERRIDE"),
995 SOM_HOWTO (R_DATA_OVERRIDE, "R_DATA_OVERRIDE"),
996 SOM_HOWTO (R_DATA_OVERRIDE, "R_DATA_OVERRIDE"),
997 SOM_HOWTO (R_DATA_OVERRIDE, "R_DATA_OVERRIDE"),
998 SOM_HOWTO (R_DATA_OVERRIDE, "R_DATA_OVERRIDE"),
999 SOM_HOWTO (R_TRANSLATED, "R_TRANSLATED"),
1000 SOM_HOWTO (R_AUX_UNWIND, "R_AUX_UNWIND"),
1001 SOM_HOWTO (R_COMP1, "R_COMP1"),
1002 SOM_HOWTO (R_COMP2, "R_COMP2"),
1003 SOM_HOWTO (R_COMP3, "R_COMP3"),
1004 SOM_HOWTO (R_PREV_FIXUP, "R_PREV_FIXUP"),
1005 SOM_HOWTO (R_PREV_FIXUP, "R_PREV_FIXUP"),
1006 SOM_HOWTO (R_PREV_FIXUP, "R_PREV_FIXUP"),
1007 SOM_HOWTO (R_PREV_FIXUP, "R_PREV_FIXUP"),
1008 SOM_HOWTO (R_SEC_STMT, "R_SEC_STMT"),
1009 SOM_HOWTO (R_N0SEL, "R_N0SEL"),
1010 SOM_HOWTO (R_N1SEL, "R_N1SEL"),
1011 SOM_HOWTO (R_LINETAB, "R_LINETAB"),
1012 SOM_HOWTO (R_LINETAB_ESC, "R_LINETAB_ESC"),
1013 SOM_HOWTO (R_LTP_OVERRIDE, "R_LTP_OVERRIDE"),
1014 SOM_HOWTO (R_COMMENT, "R_COMMENT"),
1015 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1016 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1017 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1018 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1019 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1020 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1021 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1022 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1023 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1024 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1025 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1026 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1027 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1028 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1029 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1030 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1031 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1032 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1033 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1034 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1035 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1036 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1037 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1038 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1039 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1040 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1041 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1042 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1043 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1044 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1045 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1046 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1047 SOM_HOWTO (R_RESERVED, "R_RESERVED"),
1048 SOM_HOWTO (R_RESERVED, "R_RESERVED")};
1050 /* Initialize the SOM relocation queue. By definition the queue holds
1051 the last four multibyte fixups. */
1054 som_initialize_reloc_queue (queue)
1055 struct reloc_queue *queue;
1057 queue[0].reloc = NULL;
1059 queue[1].reloc = NULL;
1061 queue[2].reloc = NULL;
1063 queue[3].reloc = NULL;
1067 /* Insert a new relocation into the relocation queue. */
1070 som_reloc_queue_insert (p, size, queue)
1073 struct reloc_queue *queue;
1075 queue[3].reloc = queue[2].reloc;
1076 queue[3].size = queue[2].size;
1077 queue[2].reloc = queue[1].reloc;
1078 queue[2].size = queue[1].size;
1079 queue[1].reloc = queue[0].reloc;
1080 queue[1].size = queue[0].size;
1082 queue[0].size = size;
1085 /* When an entry in the relocation queue is reused, the entry moves
1086 to the front of the queue. */
1089 som_reloc_queue_fix (queue, index)
1090 struct reloc_queue *queue;
1098 unsigned char *tmp1 = queue[0].reloc;
1099 unsigned int tmp2 = queue[0].size;
1100 queue[0].reloc = queue[1].reloc;
1101 queue[0].size = queue[1].size;
1102 queue[1].reloc = tmp1;
1103 queue[1].size = tmp2;
1109 unsigned char *tmp1 = queue[0].reloc;
1110 unsigned int tmp2 = queue[0].size;
1111 queue[0].reloc = queue[2].reloc;
1112 queue[0].size = queue[2].size;
1113 queue[2].reloc = queue[1].reloc;
1114 queue[2].size = queue[1].size;
1115 queue[1].reloc = tmp1;
1116 queue[1].size = tmp2;
1122 unsigned char *tmp1 = queue[0].reloc;
1123 unsigned int tmp2 = queue[0].size;
1124 queue[0].reloc = queue[3].reloc;
1125 queue[0].size = queue[3].size;
1126 queue[3].reloc = queue[2].reloc;
1127 queue[3].size = queue[2].size;
1128 queue[2].reloc = queue[1].reloc;
1129 queue[2].size = queue[1].size;
1130 queue[1].reloc = tmp1;
1131 queue[1].size = tmp2;
1137 /* Search for a particular relocation in the relocation queue. */
1140 som_reloc_queue_find (p, size, queue)
1143 struct reloc_queue *queue;
1145 if (queue[0].reloc && !memcmp (p, queue[0].reloc, size)
1146 && size == queue[0].size)
1148 if (queue[1].reloc && !memcmp (p, queue[1].reloc, size)
1149 && size == queue[1].size)
1151 if (queue[2].reloc && !memcmp (p, queue[2].reloc, size)
1152 && size == queue[2].size)
1154 if (queue[3].reloc && !memcmp (p, queue[3].reloc, size)
1155 && size == queue[3].size)
1160 static unsigned char *
1161 try_prev_fixup (abfd, subspace_reloc_sizep, p, size, queue)
1162 bfd *abfd ATTRIBUTE_UNUSED;
1163 int *subspace_reloc_sizep;
1166 struct reloc_queue *queue;
1168 int queue_index = som_reloc_queue_find (p, size, queue);
1170 if (queue_index != -1)
1172 /* Found this in a previous fixup. Undo the fixup we
1173 just built and use R_PREV_FIXUP instead. We saved
1174 a total of size - 1 bytes in the fixup stream. */
1175 bfd_put_8 (abfd, R_PREV_FIXUP + queue_index, p);
1177 *subspace_reloc_sizep += 1;
1178 som_reloc_queue_fix (queue, queue_index);
1182 som_reloc_queue_insert (p, size, queue);
1183 *subspace_reloc_sizep += size;
1189 /* Emit the proper R_NO_RELOCATION fixups to map the next SKIP
1190 bytes without any relocation. Update the size of the subspace
1191 relocation stream via SUBSPACE_RELOC_SIZE_P; also return the
1192 current pointer into the relocation stream. */
1194 static unsigned char *
1195 som_reloc_skip (abfd, skip, p, subspace_reloc_sizep, queue)
1199 unsigned int *subspace_reloc_sizep;
1200 struct reloc_queue *queue;
1202 /* Use a 4 byte R_NO_RELOCATION entry with a maximal value
1203 then R_PREV_FIXUPs to get the difference down to a
1205 if (skip >= 0x1000000)
1208 bfd_put_8 (abfd, R_NO_RELOCATION + 31, p);
1209 bfd_put_8 (abfd, 0xff, p + 1);
1210 bfd_put_16 (abfd, 0xffff, p + 2);
1211 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 4, queue);
1212 while (skip >= 0x1000000)
1215 bfd_put_8 (abfd, R_PREV_FIXUP, p);
1217 *subspace_reloc_sizep += 1;
1218 /* No need to adjust queue here since we are repeating the
1219 most recent fixup. */
1223 /* The difference must be less than 0x1000000. Use one
1224 more R_NO_RELOCATION entry to get to the right difference. */
1225 if ((skip & 3) == 0 && skip <= 0xc0000 && skip > 0)
1227 /* Difference can be handled in a simple single-byte
1228 R_NO_RELOCATION entry. */
1231 bfd_put_8 (abfd, R_NO_RELOCATION + (skip >> 2) - 1, p);
1232 *subspace_reloc_sizep += 1;
1235 /* Handle it with a two byte R_NO_RELOCATION entry. */
1236 else if (skip <= 0x1000)
1238 bfd_put_8 (abfd, R_NO_RELOCATION + 24 + (((skip >> 2) - 1) >> 8), p);
1239 bfd_put_8 (abfd, (skip >> 2) - 1, p + 1);
1240 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 2, queue);
1242 /* Handle it with a three byte R_NO_RELOCATION entry. */
1245 bfd_put_8 (abfd, R_NO_RELOCATION + 28 + (((skip >> 2) - 1) >> 16), p);
1246 bfd_put_16 (abfd, (skip >> 2) - 1, p + 1);
1247 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 3, queue);
1250 /* Ugh. Punt and use a 4 byte entry. */
1253 bfd_put_8 (abfd, R_NO_RELOCATION + 31, p);
1254 bfd_put_8 (abfd, (skip - 1) >> 16, p + 1);
1255 bfd_put_16 (abfd, skip - 1, p + 2);
1256 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 4, queue);
1261 /* Emit the proper R_DATA_OVERRIDE fixups to handle a nonzero addend
1262 from a BFD relocation. Update the size of the subspace relocation
1263 stream via SUBSPACE_RELOC_SIZE_P; also return the current pointer
1264 into the relocation stream. */
1266 static unsigned char *
1267 som_reloc_addend (abfd, addend, p, subspace_reloc_sizep, queue)
1271 unsigned int *subspace_reloc_sizep;
1272 struct reloc_queue *queue;
1274 if ((unsigned)(addend) + 0x80 < 0x100)
1276 bfd_put_8 (abfd, R_DATA_OVERRIDE + 1, p);
1277 bfd_put_8 (abfd, addend, p + 1);
1278 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 2, queue);
1280 else if ((unsigned) (addend) + 0x8000 < 0x10000)
1282 bfd_put_8 (abfd, R_DATA_OVERRIDE + 2, p);
1283 bfd_put_16 (abfd, addend, p + 1);
1284 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 3, queue);
1286 else if ((unsigned) (addend) + 0x800000 < 0x1000000)
1288 bfd_put_8 (abfd, R_DATA_OVERRIDE + 3, p);
1289 bfd_put_8 (abfd, addend >> 16, p + 1);
1290 bfd_put_16 (abfd, addend, p + 2);
1291 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 4, queue);
1295 bfd_put_8 (abfd, R_DATA_OVERRIDE + 4, p);
1296 bfd_put_32 (abfd, addend, p + 1);
1297 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 5, queue);
1302 /* Handle a single function call relocation. */
1304 static unsigned char *
1305 som_reloc_call (abfd, p, subspace_reloc_sizep, bfd_reloc, sym_num, queue)
1308 unsigned int *subspace_reloc_sizep;
1311 struct reloc_queue *queue;
1313 int arg_bits = HPPA_R_ARG_RELOC (bfd_reloc->addend);
1314 int rtn_bits = arg_bits & 0x3;
1317 /* You'll never believe all this is necessary to handle relocations
1318 for function calls. Having to compute and pack the argument
1319 relocation bits is the real nightmare.
1321 If you're interested in how this works, just forget it. You really
1322 do not want to know about this braindamage. */
1324 /* First see if this can be done with a "simple" relocation. Simple
1325 relocations have a symbol number < 0x100 and have simple encodings
1326 of argument relocations. */
1328 if (sym_num < 0x100)
1340 case 1 << 8 | 1 << 6:
1341 case 1 << 8 | 1 << 6 | 1:
1344 case 1 << 8 | 1 << 6 | 1 << 4:
1345 case 1 << 8 | 1 << 6 | 1 << 4 | 1:
1348 case 1 << 8 | 1 << 6 | 1 << 4 | 1 << 2:
1349 case 1 << 8 | 1 << 6 | 1 << 4 | 1 << 2 | 1:
1353 /* Not one of the easy encodings. This will have to be
1354 handled by the more complex code below. */
1360 /* Account for the return value too. */
1364 /* Emit a 2 byte relocation. Then see if it can be handled
1365 with a relocation which is already in the relocation queue. */
1366 bfd_put_8 (abfd, bfd_reloc->howto->type + type, p);
1367 bfd_put_8 (abfd, sym_num, p + 1);
1368 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 2, queue);
1373 /* If this could not be handled with a simple relocation, then do a hard
1374 one. Hard relocations occur if the symbol number was too high or if
1375 the encoding of argument relocation bits is too complex. */
1378 /* Don't ask about these magic sequences. I took them straight
1379 from gas-1.36 which took them from the a.out man page. */
1381 if ((arg_bits >> 6 & 0xf) == 0xe)
1384 type += (3 * (arg_bits >> 8 & 3) + (arg_bits >> 6 & 3)) * 40;
1385 if ((arg_bits >> 2 & 0xf) == 0xe)
1388 type += (3 * (arg_bits >> 4 & 3) + (arg_bits >> 2 & 3)) * 4;
1390 /* Output the first two bytes of the relocation. These describe
1391 the length of the relocation and encoding style. */
1392 bfd_put_8 (abfd, bfd_reloc->howto->type + 10
1393 + 2 * (sym_num >= 0x100) + (type >= 0x100),
1395 bfd_put_8 (abfd, type, p + 1);
1397 /* Now output the symbol index and see if this bizarre relocation
1398 just happened to be in the relocation queue. */
1399 if (sym_num < 0x100)
1401 bfd_put_8 (abfd, sym_num, p + 2);
1402 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 3, queue);
1406 bfd_put_8 (abfd, sym_num >> 16, p + 2);
1407 bfd_put_16 (abfd, sym_num, p + 3);
1408 p = try_prev_fixup (abfd, subspace_reloc_sizep, p, 5, queue);
1415 /* Return the logarithm of X, base 2, considering X unsigned.
1416 Abort -1 if X is not a power or two or is zero. */
1424 /* Test for 0 or a power of 2. */
1425 if (x == 0 || x != (x & -x))
1428 while ((x >>= 1) != 0)
1433 static bfd_reloc_status_type
1434 hppa_som_reloc (abfd, reloc_entry, symbol_in, data,
1435 input_section, output_bfd, error_message)
1436 bfd *abfd ATTRIBUTE_UNUSED;
1437 arelent *reloc_entry;
1438 asymbol *symbol_in ATTRIBUTE_UNUSED;
1439 PTR data ATTRIBUTE_UNUSED;
1440 asection *input_section;
1442 char **error_message ATTRIBUTE_UNUSED;
1446 reloc_entry->address += input_section->output_offset;
1447 return bfd_reloc_ok;
1449 return bfd_reloc_ok;
1452 /* Given a generic HPPA relocation type, the instruction format,
1453 and a field selector, return one or more appropriate SOM relocations. */
1456 hppa_som_gen_reloc_type (abfd, base_type, format, field, sym_diff, sym)
1460 enum hppa_reloc_field_selector_type_alt field;
1464 int *final_type, **final_types;
1466 final_types = (int **) bfd_alloc (abfd, sizeof (int *) * 6);
1467 final_type = (int *) bfd_alloc (abfd, sizeof (int));
1468 if (!final_types || !final_type)
1471 /* The field selector may require additional relocations to be
1472 generated. It's impossible to know at this moment if additional
1473 relocations will be needed, so we make them. The code to actually
1474 write the relocation/fixup stream is responsible for removing
1475 any redundant relocations. */
1482 final_types[0] = final_type;
1483 final_types[1] = NULL;
1484 final_types[2] = NULL;
1485 *final_type = base_type;
1491 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1492 if (!final_types[0])
1494 if (field == e_tsel)
1495 *final_types[0] = R_FSEL;
1496 else if (field == e_ltsel)
1497 *final_types[0] = R_LSEL;
1499 *final_types[0] = R_RSEL;
1500 final_types[1] = final_type;
1501 final_types[2] = NULL;
1502 *final_type = base_type;
1507 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1508 if (!final_types[0])
1510 *final_types[0] = R_S_MODE;
1511 final_types[1] = final_type;
1512 final_types[2] = NULL;
1513 *final_type = base_type;
1518 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1519 if (!final_types[0])
1521 *final_types[0] = R_N_MODE;
1522 final_types[1] = final_type;
1523 final_types[2] = NULL;
1524 *final_type = base_type;
1529 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1530 if (!final_types[0])
1532 *final_types[0] = R_D_MODE;
1533 final_types[1] = final_type;
1534 final_types[2] = NULL;
1535 *final_type = base_type;
1540 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1541 if (!final_types[0])
1543 *final_types[0] = R_R_MODE;
1544 final_types[1] = final_type;
1545 final_types[2] = NULL;
1546 *final_type = base_type;
1550 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1551 if (!final_types[0])
1553 *final_types[0] = R_N1SEL;
1554 final_types[1] = final_type;
1555 final_types[2] = NULL;
1556 *final_type = base_type;
1561 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1562 if (!final_types[0])
1564 *final_types[0] = R_N0SEL;
1565 final_types[1] = (int *) bfd_alloc (abfd, sizeof (int));
1566 if (!final_types[1])
1568 if (field == e_nlsel)
1569 *final_types[1] = R_N_MODE;
1571 *final_types[1] = R_R_MODE;
1572 final_types[2] = final_type;
1573 final_types[3] = NULL;
1574 *final_type = base_type;
1581 /* The difference of two symbols needs *very* special handling. */
1584 final_types[0] = (int *)bfd_alloc (abfd, sizeof (int));
1585 final_types[1] = (int *)bfd_alloc (abfd, sizeof (int));
1586 final_types[2] = (int *)bfd_alloc (abfd, sizeof (int));
1587 final_types[3] = (int *)bfd_alloc (abfd, sizeof (int));
1588 if (!final_types[0] || !final_types[1] || !final_types[2])
1590 if (field == e_fsel)
1591 *final_types[0] = R_FSEL;
1592 else if (field == e_rsel)
1593 *final_types[0] = R_RSEL;
1594 else if (field == e_lsel)
1595 *final_types[0] = R_LSEL;
1596 *final_types[1] = R_COMP2;
1597 *final_types[2] = R_COMP2;
1598 *final_types[3] = R_COMP1;
1599 final_types[4] = final_type;
1601 *final_types[4] = R_DATA_EXPR;
1603 *final_types[4] = R_CODE_EXPR;
1604 final_types[5] = NULL;
1607 /* PLABELs get their own relocation type. */
1608 else if (field == e_psel
1610 || field == e_rpsel)
1612 /* A PLABEL relocation that has a size of 32 bits must
1613 be a R_DATA_PLABEL. All others are R_CODE_PLABELs. */
1615 *final_type = R_DATA_PLABEL;
1617 *final_type = R_CODE_PLABEL;
1620 else if (field == e_tsel
1622 || field == e_rtsel)
1623 *final_type = R_DLT_REL;
1624 /* A relocation in the data space is always a full 32bits. */
1625 else if (format == 32)
1627 *final_type = R_DATA_ONE_SYMBOL;
1629 /* If there's no SOM symbol type associated with this BFD
1630 symbol, then set the symbol type to ST_DATA.
1632 Only do this if the type is going to default later when
1633 we write the object file.
1635 This is done so that the linker never encounters an
1636 R_DATA_ONE_SYMBOL reloc involving an ST_CODE symbol.
1638 This allows the compiler to generate exception handling
1641 Note that one day we may need to also emit BEGIN_BRTAB and
1642 END_BRTAB to prevent the linker from optimizing away insns
1643 in exception handling regions. */
1644 if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_UNKNOWN
1645 && (sym->flags & BSF_SECTION_SYM) == 0
1646 && (sym->flags & BSF_FUNCTION) == 0
1647 && ! bfd_is_com_section (sym->section))
1648 som_symbol_data (sym)->som_type = SYMBOL_TYPE_DATA;
1654 /* More PLABEL special cases. */
1657 || field == e_rpsel)
1658 *final_type = R_DATA_PLABEL;
1661 case R_HPPA_COMPLEX:
1662 /* The difference of two symbols needs *very* special handling. */
1665 final_types[0] = (int *)bfd_alloc (abfd, sizeof (int));
1666 final_types[1] = (int *)bfd_alloc (abfd, sizeof (int));
1667 final_types[2] = (int *)bfd_alloc (abfd, sizeof (int));
1668 final_types[3] = (int *)bfd_alloc (abfd, sizeof (int));
1669 if (!final_types[0] || !final_types[1] || !final_types[2])
1671 if (field == e_fsel)
1672 *final_types[0] = R_FSEL;
1673 else if (field == e_rsel)
1674 *final_types[0] = R_RSEL;
1675 else if (field == e_lsel)
1676 *final_types[0] = R_LSEL;
1677 *final_types[1] = R_COMP2;
1678 *final_types[2] = R_COMP2;
1679 *final_types[3] = R_COMP1;
1680 final_types[4] = final_type;
1682 *final_types[4] = R_DATA_EXPR;
1684 *final_types[4] = R_CODE_EXPR;
1685 final_types[5] = NULL;
1692 case R_HPPA_ABS_CALL:
1693 /* Right now we can default all these. */
1696 case R_HPPA_PCREL_CALL:
1698 #ifndef NO_PCREL_MODES
1699 /* If we have short and long pcrel modes, then generate the proper
1700 mode selector, then the pcrel relocation. Redundant selectors
1701 will be eliminted as the relocs are sized and emitted. */
1702 final_types[0] = (int *) bfd_alloc (abfd, sizeof (int));
1703 if (!final_types[0])
1706 *final_types[0] = R_SHORT_PCREL_MODE;
1708 *final_types[0] = R_LONG_PCREL_MODE;
1709 final_types[1] = final_type;
1710 final_types[2] = NULL;
1711 *final_type = base_type;
1719 /* Return the address of the correct entry in the PA SOM relocation
1723 static reloc_howto_type *
1724 som_bfd_reloc_type_lookup (abfd, code)
1725 bfd *abfd ATTRIBUTE_UNUSED;
1726 bfd_reloc_code_real_type code;
1728 if ((int) code < (int) R_NO_RELOCATION + 255)
1730 BFD_ASSERT ((int) som_hppa_howto_table[(int) code].type == (int) code);
1731 return &som_hppa_howto_table[(int) code];
1734 return (reloc_howto_type *) 0;
1737 /* Perform some initialization for an object. Save results of this
1738 initialization in the BFD. */
1740 static const bfd_target *
1741 som_object_setup (abfd, file_hdrp, aux_hdrp, current_offset)
1743 struct header *file_hdrp;
1744 struct som_exec_auxhdr *aux_hdrp;
1745 unsigned long current_offset;
1750 /* som_mkobject will set bfd_error if som_mkobject fails. */
1751 if (som_mkobject (abfd) != true)
1754 /* Set BFD flags based on what information is available in the SOM. */
1755 abfd->flags = BFD_NO_FLAGS;
1756 if (file_hdrp->symbol_total)
1757 abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
1759 switch (file_hdrp->a_magic)
1762 abfd->flags |= (D_PAGED | WP_TEXT | EXEC_P);
1765 abfd->flags |= (WP_TEXT | EXEC_P);
1768 abfd->flags |= (EXEC_P);
1771 abfd->flags |= HAS_RELOC;
1779 abfd->flags |= DYNAMIC;
1786 /* Allocate space to hold the saved exec header information. */
1787 obj_som_exec_data (abfd) = (struct som_exec_data *)
1788 bfd_zalloc (abfd, sizeof (struct som_exec_data ));
1789 if (obj_som_exec_data (abfd) == NULL)
1792 /* The braindamaged OSF1 linker switched exec_flags and exec_entry!
1794 We used to identify OSF1 binaries based on NEW_VERSION_ID, but
1795 apparently the latest HPUX linker is using NEW_VERSION_ID now.
1797 It's about time, OSF has used the new id since at least 1992;
1798 HPUX didn't start till nearly 1995!.
1800 The new approach examines the entry field. If it's zero or not 4
1801 byte aligned then it's not a proper code address and we guess it's
1802 really the executable flags. */
1804 for (section = abfd->sections; section; section = section->next)
1806 if ((section->flags & SEC_CODE) == 0)
1808 if (aux_hdrp->exec_entry >= section->vma
1809 && aux_hdrp->exec_entry < section->vma + section->_cooked_size)
1812 if (aux_hdrp->exec_entry == 0
1813 || (aux_hdrp->exec_entry & 0x3) != 0
1816 bfd_get_start_address (abfd) = aux_hdrp->exec_flags;
1817 obj_som_exec_data (abfd)->exec_flags = aux_hdrp->exec_entry;
1821 bfd_get_start_address (abfd) = aux_hdrp->exec_entry + current_offset;
1822 obj_som_exec_data (abfd)->exec_flags = aux_hdrp->exec_flags;
1825 bfd_default_set_arch_mach (abfd, bfd_arch_hppa, pa10);
1826 bfd_get_symcount (abfd) = file_hdrp->symbol_total;
1828 /* Initialize the saved symbol table and string table to NULL.
1829 Save important offsets and sizes from the SOM header into
1831 obj_som_stringtab (abfd) = (char *) NULL;
1832 obj_som_symtab (abfd) = (som_symbol_type *) NULL;
1833 obj_som_sorted_syms (abfd) = NULL;
1834 obj_som_stringtab_size (abfd) = file_hdrp->symbol_strings_size;
1835 obj_som_sym_filepos (abfd) = file_hdrp->symbol_location + current_offset;
1836 obj_som_str_filepos (abfd) = (file_hdrp->symbol_strings_location
1838 obj_som_reloc_filepos (abfd) = (file_hdrp->fixup_request_location
1840 obj_som_exec_data (abfd)->system_id = file_hdrp->system_id;
1845 /* Convert all of the space and subspace info into BFD sections. Each space
1846 contains a number of subspaces, which in turn describe the mapping between
1847 regions of the exec file, and the address space that the program runs in.
1848 BFD sections which correspond to spaces will overlap the sections for the
1849 associated subspaces. */
1852 setup_sections (abfd, file_hdr, current_offset)
1854 struct header *file_hdr;
1855 unsigned long current_offset;
1857 char *space_strings;
1858 unsigned int space_index, i;
1859 unsigned int total_subspaces = 0;
1860 asection **subspace_sections, *section;
1862 /* First, read in space names */
1864 space_strings = bfd_malloc (file_hdr->space_strings_size);
1865 if (!space_strings && file_hdr->space_strings_size != 0)
1868 if (bfd_seek (abfd, current_offset + file_hdr->space_strings_location,
1871 if (bfd_read (space_strings, 1, file_hdr->space_strings_size, abfd)
1872 != file_hdr->space_strings_size)
1875 /* Loop over all of the space dictionaries, building up sections */
1876 for (space_index = 0; space_index < file_hdr->space_total; space_index++)
1878 struct space_dictionary_record space;
1879 struct subspace_dictionary_record subspace, save_subspace;
1881 asection *space_asect;
1884 /* Read the space dictionary element */
1886 (current_offset + file_hdr->space_location
1887 + space_index * sizeof space),
1890 if (bfd_read (&space, 1, sizeof space, abfd) != sizeof space)
1893 /* Setup the space name string */
1894 space.name.n_name = space.name.n_strx + space_strings;
1896 /* Make a section out of it */
1897 newname = bfd_alloc (abfd, strlen (space.name.n_name) + 1);
1900 strcpy (newname, space.name.n_name);
1902 space_asect = bfd_make_section_anyway (abfd, newname);
1906 if (space.is_loadable == 0)
1907 space_asect->flags |= SEC_DEBUGGING;
1909 /* Set up all the attributes for the space. */
1910 if (bfd_som_set_section_attributes (space_asect, space.is_defined,
1911 space.is_private, space.sort_key,
1912 space.space_number) == false)
1915 /* If the space has no subspaces, then we're done. */
1916 if (space.subspace_quantity == 0)
1919 /* Now, read in the first subspace for this space */
1921 (current_offset + file_hdr->subspace_location
1922 + space.subspace_index * sizeof subspace),
1925 if (bfd_read (&subspace, 1, sizeof subspace, abfd) != sizeof subspace)
1927 /* Seek back to the start of the subspaces for loop below */
1929 (current_offset + file_hdr->subspace_location
1930 + space.subspace_index * sizeof subspace),
1934 /* Setup the start address and file loc from the first subspace record */
1935 space_asect->vma = subspace.subspace_start;
1936 space_asect->filepos = subspace.file_loc_init_value + current_offset;
1937 space_asect->alignment_power = log2 (subspace.alignment);
1938 if (space_asect->alignment_power == -1)
1941 /* Initialize save_subspace so we can reliably determine if this
1942 loop placed any useful values into it. */
1943 memset (&save_subspace, 0, sizeof (struct subspace_dictionary_record));
1945 /* Loop over the rest of the subspaces, building up more sections */
1946 for (subspace_index = 0; subspace_index < space.subspace_quantity;
1949 asection *subspace_asect;
1951 /* Read in the next subspace */
1952 if (bfd_read (&subspace, 1, sizeof subspace, abfd)
1956 /* Setup the subspace name string */
1957 subspace.name.n_name = subspace.name.n_strx + space_strings;
1959 newname = bfd_alloc (abfd, strlen (subspace.name.n_name) + 1);
1962 strcpy (newname, subspace.name.n_name);
1964 /* Make a section out of this subspace */
1965 subspace_asect = bfd_make_section_anyway (abfd, newname);
1966 if (!subspace_asect)
1969 /* Store private information about the section. */
1970 if (bfd_som_set_subsection_attributes (subspace_asect, space_asect,
1971 subspace.access_control_bits,
1973 subspace.quadrant) == false)
1976 /* Keep an easy mapping between subspaces and sections.
1977 Note we do not necessarily read the subspaces in the
1978 same order in which they appear in the object file.
1980 So to make the target index come out correctly, we
1981 store the location of the subspace header in target
1982 index, then sort using the location of the subspace
1983 header as the key. Then we can assign correct
1984 subspace indices. */
1986 subspace_asect->target_index = bfd_tell (abfd) - sizeof (subspace);
1988 /* Set SEC_READONLY and SEC_CODE/SEC_DATA as specified
1989 by the access_control_bits in the subspace header. */
1990 switch (subspace.access_control_bits >> 4)
1992 /* Readonly data. */
1994 subspace_asect->flags |= SEC_DATA | SEC_READONLY;
1999 subspace_asect->flags |= SEC_DATA;
2002 /* Readonly code and the gateways.
2003 Gateways have other attributes which do not map
2004 into anything BFD knows about. */
2010 subspace_asect->flags |= SEC_CODE | SEC_READONLY;
2013 /* dynamic (writable) code. */
2015 subspace_asect->flags |= SEC_CODE;
2019 if (subspace.dup_common || subspace.is_common)
2020 subspace_asect->flags |= SEC_IS_COMMON;
2021 else if (subspace.subspace_length > 0)
2022 subspace_asect->flags |= SEC_HAS_CONTENTS;
2024 if (subspace.is_loadable)
2025 subspace_asect->flags |= SEC_ALLOC | SEC_LOAD;
2027 subspace_asect->flags |= SEC_DEBUGGING;
2029 if (subspace.code_only)
2030 subspace_asect->flags |= SEC_CODE;
2032 /* Both file_loc_init_value and initialization_length will
2033 be zero for a BSS like subspace. */
2034 if (subspace.file_loc_init_value == 0
2035 && subspace.initialization_length == 0)
2036 subspace_asect->flags &= ~(SEC_DATA | SEC_LOAD | SEC_HAS_CONTENTS);
2038 /* This subspace has relocations.
2039 The fixup_request_quantity is a byte count for the number of
2040 entries in the relocation stream; it is not the actual number
2041 of relocations in the subspace. */
2042 if (subspace.fixup_request_quantity != 0)
2044 subspace_asect->flags |= SEC_RELOC;
2045 subspace_asect->rel_filepos = subspace.fixup_request_index;
2046 som_section_data (subspace_asect)->reloc_size
2047 = subspace.fixup_request_quantity;
2048 /* We can not determine this yet. When we read in the
2049 relocation table the correct value will be filled in. */
2050 subspace_asect->reloc_count = -1;
2053 /* Update save_subspace if appropriate. */
2054 if (subspace.file_loc_init_value > save_subspace.file_loc_init_value)
2055 save_subspace = subspace;
2057 subspace_asect->vma = subspace.subspace_start;
2058 subspace_asect->_cooked_size = subspace.subspace_length;
2059 subspace_asect->_raw_size = subspace.subspace_length;
2060 subspace_asect->filepos = (subspace.file_loc_init_value
2062 subspace_asect->alignment_power = log2 (subspace.alignment);
2063 if (subspace_asect->alignment_power == -1)
2067 /* This can happen for a .o which defines symbols in otherwise
2069 if (!save_subspace.file_loc_init_value)
2071 space_asect->_cooked_size = 0;
2072 space_asect->_raw_size = 0;
2076 /* Setup the sizes for the space section based upon the info in the
2077 last subspace of the space. */
2078 space_asect->_cooked_size = (save_subspace.subspace_start
2080 + save_subspace.subspace_length);
2081 space_asect->_raw_size = (save_subspace.file_loc_init_value
2082 - space_asect->filepos
2083 + save_subspace.initialization_length);
2086 /* Now that we've read in all the subspace records, we need to assign
2087 a target index to each subspace. */
2088 subspace_sections = (asection **) bfd_malloc (total_subspaces
2089 * sizeof (asection *));
2090 if (subspace_sections == NULL)
2093 for (i = 0, section = abfd->sections; section; section = section->next)
2095 if (!som_is_subspace (section))
2098 subspace_sections[i] = section;
2101 qsort (subspace_sections, total_subspaces,
2102 sizeof (asection *), compare_subspaces);
2104 /* subspace_sections is now sorted in the order in which the subspaces
2105 appear in the object file. Assign an index to each one now. */
2106 for (i = 0; i < total_subspaces; i++)
2107 subspace_sections[i]->target_index = i;
2109 if (space_strings != NULL)
2110 free (space_strings);
2112 if (subspace_sections != NULL)
2113 free (subspace_sections);
2118 if (space_strings != NULL)
2119 free (space_strings);
2121 if (subspace_sections != NULL)
2122 free (subspace_sections);
2126 /* Read in a SOM object and make it into a BFD. */
2128 static const bfd_target *
2132 struct header file_hdr;
2133 struct som_exec_auxhdr aux_hdr;
2134 unsigned long current_offset = 0;
2135 struct lst_header lst_header;
2136 struct som_entry som_entry;
2137 #define ENTRY_SIZE sizeof(struct som_entry)
2139 if (bfd_read ((PTR) & file_hdr, 1, FILE_HDR_SIZE, abfd) != FILE_HDR_SIZE)
2141 if (bfd_get_error () != bfd_error_system_call)
2142 bfd_set_error (bfd_error_wrong_format);
2146 if (!_PA_RISC_ID (file_hdr.system_id))
2148 bfd_set_error (bfd_error_wrong_format);
2152 switch (file_hdr.a_magic)
2164 #ifdef SHARED_MAGIC_CNX
2165 case SHARED_MAGIC_CNX:
2171 /* Read the lst header and determine where the SOM directory begins */
2173 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) < 0)
2175 if (bfd_get_error () != bfd_error_system_call)
2176 bfd_set_error (bfd_error_wrong_format);
2180 if (bfd_read ((PTR) & lst_header, 1, SLSTHDR, abfd) != SLSTHDR)
2182 if (bfd_get_error () != bfd_error_system_call)
2183 bfd_set_error (bfd_error_wrong_format);
2187 /* Position to and read the first directory entry */
2189 if (bfd_seek (abfd, lst_header.dir_loc, SEEK_SET) < 0)
2191 if (bfd_get_error () != bfd_error_system_call)
2192 bfd_set_error (bfd_error_wrong_format);
2196 if (bfd_read ((PTR) & som_entry, 1, ENTRY_SIZE, abfd) != ENTRY_SIZE)
2198 if (bfd_get_error () != bfd_error_system_call)
2199 bfd_set_error (bfd_error_wrong_format);
2203 /* Now position to the first SOM */
2205 if (bfd_seek (abfd, som_entry.location, SEEK_SET) < 0)
2207 if (bfd_get_error () != bfd_error_system_call)
2208 bfd_set_error (bfd_error_wrong_format);
2212 current_offset = som_entry.location;
2214 /* And finally, re-read the som header */
2216 if (bfd_read ((PTR) & file_hdr, 1, FILE_HDR_SIZE, abfd) != FILE_HDR_SIZE)
2218 if (bfd_get_error () != bfd_error_system_call)
2219 bfd_set_error (bfd_error_wrong_format);
2227 bfd_set_error (bfd_error_wrong_format);
2231 if (file_hdr.version_id != VERSION_ID
2232 && file_hdr.version_id != NEW_VERSION_ID)
2234 bfd_set_error (bfd_error_wrong_format);
2238 /* If the aux_header_size field in the file header is zero, then this
2239 object is an incomplete executable (a .o file). Do not try to read
2240 a non-existant auxiliary header. */
2241 memset (&aux_hdr, 0, sizeof (struct som_exec_auxhdr));
2242 if (file_hdr.aux_header_size != 0)
2244 if (bfd_read ((PTR) & aux_hdr, 1, AUX_HDR_SIZE, abfd) != AUX_HDR_SIZE)
2246 if (bfd_get_error () != bfd_error_system_call)
2247 bfd_set_error (bfd_error_wrong_format);
2252 if (!setup_sections (abfd, &file_hdr, current_offset))
2254 /* setup_sections does not bubble up a bfd error code. */
2255 bfd_set_error (bfd_error_bad_value);
2259 /* This appears to be a valid SOM object. Do some initialization. */
2260 return som_object_setup (abfd, &file_hdr, &aux_hdr, current_offset);
2263 /* Create a SOM object. */
2269 /* Allocate memory to hold backend information. */
2270 abfd->tdata.som_data = (struct som_data_struct *)
2271 bfd_zalloc (abfd, sizeof (struct som_data_struct));
2272 if (abfd->tdata.som_data == NULL)
2277 /* Initialize some information in the file header. This routine makes
2278 not attempt at doing the right thing for a full executable; it
2279 is only meant to handle relocatable objects. */
2282 som_prep_headers (abfd)
2285 struct header *file_hdr;
2288 /* Make and attach a file header to the BFD. */
2289 file_hdr = (struct header *) bfd_zalloc (abfd, sizeof (struct header));
2290 if (file_hdr == NULL)
2292 obj_som_file_hdr (abfd) = file_hdr;
2294 if (abfd->flags & (EXEC_P | DYNAMIC))
2297 /* Make and attach an exec header to the BFD. */
2298 obj_som_exec_hdr (abfd) = (struct som_exec_auxhdr *)
2299 bfd_zalloc (abfd, sizeof (struct som_exec_auxhdr));
2300 if (obj_som_exec_hdr (abfd) == NULL)
2303 if (abfd->flags & D_PAGED)
2304 file_hdr->a_magic = DEMAND_MAGIC;
2305 else if (abfd->flags & WP_TEXT)
2306 file_hdr->a_magic = SHARE_MAGIC;
2308 else if (abfd->flags & DYNAMIC)
2309 file_hdr->a_magic = SHL_MAGIC;
2312 file_hdr->a_magic = EXEC_MAGIC;
2315 file_hdr->a_magic = RELOC_MAGIC;
2317 /* Only new format SOM is supported. */
2318 file_hdr->version_id = NEW_VERSION_ID;
2320 /* These fields are optional, and embedding timestamps is not always
2321 a wise thing to do, it makes comparing objects during a multi-stage
2322 bootstrap difficult. */
2323 file_hdr->file_time.secs = 0;
2324 file_hdr->file_time.nanosecs = 0;
2326 file_hdr->entry_space = 0;
2327 file_hdr->entry_subspace = 0;
2328 file_hdr->entry_offset = 0;
2329 file_hdr->presumed_dp = 0;
2331 /* Now iterate over the sections translating information from
2332 BFD sections to SOM spaces/subspaces. */
2334 for (section = abfd->sections; section != NULL; section = section->next)
2336 /* Ignore anything which has not been marked as a space or
2338 if (!som_is_space (section) && !som_is_subspace (section))
2341 if (som_is_space (section))
2343 /* Allocate space for the space dictionary. */
2344 som_section_data (section)->space_dict
2345 = (struct space_dictionary_record *)
2346 bfd_zalloc (abfd, sizeof (struct space_dictionary_record));
2347 if (som_section_data (section)->space_dict == NULL)
2349 /* Set space attributes. Note most attributes of SOM spaces
2350 are set based on the subspaces it contains. */
2351 som_section_data (section)->space_dict->loader_fix_index = -1;
2352 som_section_data (section)->space_dict->init_pointer_index = -1;
2354 /* Set more attributes that were stuffed away in private data. */
2355 som_section_data (section)->space_dict->sort_key =
2356 som_section_data (section)->copy_data->sort_key;
2357 som_section_data (section)->space_dict->is_defined =
2358 som_section_data (section)->copy_data->is_defined;
2359 som_section_data (section)->space_dict->is_private =
2360 som_section_data (section)->copy_data->is_private;
2361 som_section_data (section)->space_dict->space_number =
2362 som_section_data (section)->copy_data->space_number;
2366 /* Allocate space for the subspace dictionary. */
2367 som_section_data (section)->subspace_dict
2368 = (struct subspace_dictionary_record *)
2369 bfd_zalloc (abfd, sizeof (struct subspace_dictionary_record));
2370 if (som_section_data (section)->subspace_dict == NULL)
2373 /* Set subspace attributes. Basic stuff is done here, additional
2374 attributes are filled in later as more information becomes
2376 if (section->flags & SEC_IS_COMMON)
2378 som_section_data (section)->subspace_dict->dup_common = 1;
2379 som_section_data (section)->subspace_dict->is_common = 1;
2382 if (section->flags & SEC_ALLOC)
2383 som_section_data (section)->subspace_dict->is_loadable = 1;
2385 if (section->flags & SEC_CODE)
2386 som_section_data (section)->subspace_dict->code_only = 1;
2388 som_section_data (section)->subspace_dict->subspace_start =
2390 som_section_data (section)->subspace_dict->subspace_length =
2391 bfd_section_size (abfd, section);
2392 som_section_data (section)->subspace_dict->initialization_length =
2393 bfd_section_size (abfd, section);
2394 som_section_data (section)->subspace_dict->alignment =
2395 1 << section->alignment_power;
2397 /* Set more attributes that were stuffed away in private data. */
2398 som_section_data (section)->subspace_dict->sort_key =
2399 som_section_data (section)->copy_data->sort_key;
2400 som_section_data (section)->subspace_dict->access_control_bits =
2401 som_section_data (section)->copy_data->access_control_bits;
2402 som_section_data (section)->subspace_dict->quadrant =
2403 som_section_data (section)->copy_data->quadrant;
2409 /* Return true if the given section is a SOM space, false otherwise. */
2412 som_is_space (section)
2415 /* If no copy data is available, then it's neither a space nor a
2417 if (som_section_data (section)->copy_data == NULL)
2420 /* If the containing space isn't the same as the given section,
2421 then this isn't a space. */
2422 if (som_section_data (section)->copy_data->container != section
2423 && (som_section_data (section)->copy_data->container->output_section
2427 /* OK. Must be a space. */
2431 /* Return true if the given section is a SOM subspace, false otherwise. */
2434 som_is_subspace (section)
2437 /* If no copy data is available, then it's neither a space nor a
2439 if (som_section_data (section)->copy_data == NULL)
2442 /* If the containing space is the same as the given section,
2443 then this isn't a subspace. */
2444 if (som_section_data (section)->copy_data->container == section
2445 || (som_section_data (section)->copy_data->container->output_section
2449 /* OK. Must be a subspace. */
2453 /* Return true if the given space containins the given subspace. It
2454 is safe to assume space really is a space, and subspace really
2458 som_is_container (space, subspace)
2459 asection *space, *subspace;
2461 return (som_section_data (subspace)->copy_data->container == space
2462 || (som_section_data (subspace)->copy_data->container->output_section
2466 /* Count and return the number of spaces attached to the given BFD. */
2468 static unsigned long
2469 som_count_spaces (abfd)
2475 for (section = abfd->sections; section != NULL; section = section->next)
2476 count += som_is_space (section);
2481 /* Count the number of subspaces attached to the given BFD. */
2483 static unsigned long
2484 som_count_subspaces (abfd)
2490 for (section = abfd->sections; section != NULL; section = section->next)
2491 count += som_is_subspace (section);
2496 /* Return -1, 0, 1 indicating the relative ordering of sym1 and sym2.
2498 We desire symbols to be ordered starting with the symbol with the
2499 highest relocation count down to the symbol with the lowest relocation
2500 count. Doing so compacts the relocation stream. */
2503 compare_syms (arg1, arg2)
2508 asymbol **sym1 = (asymbol **) arg1;
2509 asymbol **sym2 = (asymbol **) arg2;
2510 unsigned int count1, count2;
2512 /* Get relocation count for each symbol. Note that the count
2513 is stored in the udata pointer for section symbols! */
2514 if ((*sym1)->flags & BSF_SECTION_SYM)
2515 count1 = (*sym1)->udata.i;
2517 count1 = som_symbol_data (*sym1)->reloc_count;
2519 if ((*sym2)->flags & BSF_SECTION_SYM)
2520 count2 = (*sym2)->udata.i;
2522 count2 = som_symbol_data (*sym2)->reloc_count;
2524 /* Return the appropriate value. */
2525 if (count1 < count2)
2527 else if (count1 > count2)
2532 /* Return -1, 0, 1 indicating the relative ordering of subspace1
2536 compare_subspaces (arg1, arg2)
2541 asection **subspace1 = (asection **) arg1;
2542 asection **subspace2 = (asection **) arg2;
2544 if ((*subspace1)->target_index < (*subspace2)->target_index)
2546 else if ((*subspace2)->target_index < (*subspace1)->target_index)
2552 /* Perform various work in preparation for emitting the fixup stream. */
2555 som_prep_for_fixups (abfd, syms, num_syms)
2558 unsigned long num_syms;
2562 asymbol **sorted_syms;
2564 /* Most SOM relocations involving a symbol have a length which is
2565 dependent on the index of the symbol. So symbols which are
2566 used often in relocations should have a small index. */
2568 /* First initialize the counters for each symbol. */
2569 for (i = 0; i < num_syms; i++)
2571 /* Handle a section symbol; these have no pointers back to the
2572 SOM symbol info. So we just use the udata field to hold the
2573 relocation count. */
2574 if (som_symbol_data (syms[i]) == NULL
2575 || syms[i]->flags & BSF_SECTION_SYM)
2577 syms[i]->flags |= BSF_SECTION_SYM;
2578 syms[i]->udata.i = 0;
2581 som_symbol_data (syms[i])->reloc_count = 0;
2584 /* Now that the counters are initialized, make a weighted count
2585 of how often a given symbol is used in a relocation. */
2586 for (section = abfd->sections; section != NULL; section = section->next)
2590 /* Does this section have any relocations? */
2591 if (section->reloc_count <= 0)
2594 /* Walk through each relocation for this section. */
2595 for (i = 1; i < section->reloc_count; i++)
2597 arelent *reloc = section->orelocation[i];
2600 /* A relocation against a symbol in the *ABS* section really
2601 does not have a symbol. Likewise if the symbol isn't associated
2602 with any section. */
2603 if (reloc->sym_ptr_ptr == NULL
2604 || bfd_is_abs_section ((*reloc->sym_ptr_ptr)->section))
2607 /* Scaling to encourage symbols involved in R_DP_RELATIVE
2608 and R_CODE_ONE_SYMBOL relocations to come first. These
2609 two relocations have single byte versions if the symbol
2610 index is very small. */
2611 if (reloc->howto->type == R_DP_RELATIVE
2612 || reloc->howto->type == R_CODE_ONE_SYMBOL)
2617 /* Handle section symbols by storing the count in the udata
2618 field. It will not be used and the count is very important
2619 for these symbols. */
2620 if ((*reloc->sym_ptr_ptr)->flags & BSF_SECTION_SYM)
2622 (*reloc->sym_ptr_ptr)->udata.i =
2623 (*reloc->sym_ptr_ptr)->udata.i + scale;
2627 /* A normal symbol. Increment the count. */
2628 som_symbol_data (*reloc->sym_ptr_ptr)->reloc_count += scale;
2632 /* Sort a copy of the symbol table, rather than the canonical
2633 output symbol table. */
2634 sorted_syms = (asymbol **) bfd_zalloc (abfd, num_syms * sizeof (asymbol *));
2635 memcpy (sorted_syms, syms, num_syms * sizeof (asymbol *));
2636 qsort (sorted_syms, num_syms, sizeof (asymbol *), compare_syms);
2637 obj_som_sorted_syms (abfd) = sorted_syms;
2639 /* Compute the symbol indexes, they will be needed by the relocation
2641 for (i = 0; i < num_syms; i++)
2643 /* A section symbol. Again, there is no pointer to backend symbol
2644 information, so we reuse the udata field again. */
2645 if (sorted_syms[i]->flags & BSF_SECTION_SYM)
2646 sorted_syms[i]->udata.i = i;
2648 som_symbol_data (sorted_syms[i])->index = i;
2653 som_write_fixups (abfd, current_offset, total_reloc_sizep)
2655 unsigned long current_offset;
2656 unsigned int *total_reloc_sizep;
2659 /* Chunk of memory that we can use as buffer space, then throw
2661 unsigned char tmp_space[SOM_TMP_BUFSIZE];
2663 unsigned int total_reloc_size = 0;
2664 unsigned int subspace_reloc_size = 0;
2665 unsigned int num_spaces = obj_som_file_hdr (abfd)->space_total;
2666 asection *section = abfd->sections;
2668 memset (tmp_space, 0, SOM_TMP_BUFSIZE);
2671 /* All the fixups for a particular subspace are emitted in a single
2672 stream. All the subspaces for a particular space are emitted
2675 So, to get all the locations correct one must iterate through all the
2676 spaces, for each space iterate through its subspaces and output a
2678 for (i = 0; i < num_spaces; i++)
2680 asection *subsection;
2683 while (!som_is_space (section))
2684 section = section->next;
2686 /* Now iterate through each of its subspaces. */
2687 for (subsection = abfd->sections;
2689 subsection = subsection->next)
2691 int reloc_offset, current_rounding_mode;
2692 #ifndef NO_PCREL_MODES
2693 int current_call_mode;
2696 /* Find a subspace of this space. */
2697 if (!som_is_subspace (subsection)
2698 || !som_is_container (section, subsection))
2701 /* If this subspace does not have real data, then we are
2703 if ((subsection->flags & SEC_HAS_CONTENTS) == 0)
2705 som_section_data (subsection)->subspace_dict->fixup_request_index
2710 /* This subspace has some relocations. Put the relocation stream
2711 index into the subspace record. */
2712 som_section_data (subsection)->subspace_dict->fixup_request_index
2715 /* To make life easier start over with a clean slate for
2716 each subspace. Seek to the start of the relocation stream
2717 for this subspace in preparation for writing out its fixup
2719 if (bfd_seek (abfd, current_offset + total_reloc_size, SEEK_SET) < 0)
2722 /* Buffer space has already been allocated. Just perform some
2723 initialization here. */
2725 subspace_reloc_size = 0;
2727 som_initialize_reloc_queue (reloc_queue);
2728 current_rounding_mode = R_N_MODE;
2729 #ifndef NO_PCREL_MODES
2730 current_call_mode = R_SHORT_PCREL_MODE;
2733 /* Translate each BFD relocation into one or more SOM
2735 for (j = 0; j < subsection->reloc_count; j++)
2737 arelent *bfd_reloc = subsection->orelocation[j];
2741 /* Get the symbol number. Remember it's stored in a
2742 special place for section symbols. */
2743 if ((*bfd_reloc->sym_ptr_ptr)->flags & BSF_SECTION_SYM)
2744 sym_num = (*bfd_reloc->sym_ptr_ptr)->udata.i;
2746 sym_num = som_symbol_data (*bfd_reloc->sym_ptr_ptr)->index;
2748 /* If there is not enough room for the next couple relocations,
2749 then dump the current buffer contents now. Also reinitialize
2750 the relocation queue.
2752 No single BFD relocation could ever translate into more
2753 than 100 bytes of SOM relocations (20bytes is probably the
2754 upper limit, but leave lots of space for growth). */
2755 if (p - tmp_space + 100 > SOM_TMP_BUFSIZE)
2757 if (bfd_write ((PTR) tmp_space, p - tmp_space, 1, abfd)
2762 som_initialize_reloc_queue (reloc_queue);
2765 /* Emit R_NO_RELOCATION fixups to map any bytes which were
2767 skip = bfd_reloc->address - reloc_offset;
2768 p = som_reloc_skip (abfd, skip, p,
2769 &subspace_reloc_size, reloc_queue);
2771 /* Update reloc_offset for the next iteration.
2773 Many relocations do not consume input bytes. They
2774 are markers, or set state necessary to perform some
2775 later relocation. */
2776 switch (bfd_reloc->howto->type)
2796 #ifndef NO_PCREL_MODES
2797 case R_SHORT_PCREL_MODE:
2798 case R_LONG_PCREL_MODE:
2800 reloc_offset = bfd_reloc->address;
2804 reloc_offset = bfd_reloc->address + 4;
2808 /* Now the actual relocation we care about. */
2809 switch (bfd_reloc->howto->type)
2813 p = som_reloc_call (abfd, p, &subspace_reloc_size,
2814 bfd_reloc, sym_num, reloc_queue);
2817 case R_CODE_ONE_SYMBOL:
2819 /* Account for any addend. */
2820 if (bfd_reloc->addend)
2821 p = som_reloc_addend (abfd, bfd_reloc->addend, p,
2822 &subspace_reloc_size, reloc_queue);
2826 bfd_put_8 (abfd, bfd_reloc->howto->type + sym_num, p);
2827 subspace_reloc_size += 1;
2830 else if (sym_num < 0x100)
2832 bfd_put_8 (abfd, bfd_reloc->howto->type + 32, p);
2833 bfd_put_8 (abfd, sym_num, p + 1);
2834 p = try_prev_fixup (abfd, &subspace_reloc_size, p,
2837 else if (sym_num < 0x10000000)
2839 bfd_put_8 (abfd, bfd_reloc->howto->type + 33, p);
2840 bfd_put_8 (abfd, sym_num >> 16, p + 1);
2841 bfd_put_16 (abfd, sym_num, p + 2);
2842 p = try_prev_fixup (abfd, &subspace_reloc_size,
2849 case R_DATA_ONE_SYMBOL:
2853 /* Account for any addend using R_DATA_OVERRIDE. */
2854 if (bfd_reloc->howto->type != R_DATA_ONE_SYMBOL
2855 && bfd_reloc->addend)
2856 p = som_reloc_addend (abfd, bfd_reloc->addend, p,
2857 &subspace_reloc_size, reloc_queue);
2859 if (sym_num < 0x100)
2861 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2862 bfd_put_8 (abfd, sym_num, p + 1);
2863 p = try_prev_fixup (abfd, &subspace_reloc_size, p,
2866 else if (sym_num < 0x10000000)
2868 bfd_put_8 (abfd, bfd_reloc->howto->type + 1, p);
2869 bfd_put_8 (abfd, sym_num >> 16, p + 1);
2870 bfd_put_16 (abfd, sym_num, p + 2);
2871 p = try_prev_fixup (abfd, &subspace_reloc_size,
2881 arelent *tmp_reloc = NULL;
2882 bfd_put_8 (abfd, R_ENTRY, p);
2884 /* R_ENTRY relocations have 64 bits of associated
2885 data. Unfortunately the addend field of a bfd
2886 relocation is only 32 bits. So, we split up
2887 the 64bit unwind information and store part in
2888 the R_ENTRY relocation, and the rest in the R_EXIT
2890 bfd_put_32 (abfd, bfd_reloc->addend, p + 1);
2892 /* Find the next R_EXIT relocation. */
2893 for (tmp = j; tmp < subsection->reloc_count; tmp++)
2895 tmp_reloc = subsection->orelocation[tmp];
2896 if (tmp_reloc->howto->type == R_EXIT)
2900 if (tmp == subsection->reloc_count)
2903 bfd_put_32 (abfd, tmp_reloc->addend, p + 5);
2904 p = try_prev_fixup (abfd, &subspace_reloc_size,
2913 /* If this relocation requests the current rounding
2914 mode, then it is redundant. */
2915 if (bfd_reloc->howto->type != current_rounding_mode)
2917 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2918 subspace_reloc_size += 1;
2920 current_rounding_mode = bfd_reloc->howto->type;
2924 #ifndef NO_PCREL_MODES
2925 case R_LONG_PCREL_MODE:
2926 case R_SHORT_PCREL_MODE:
2927 if (bfd_reloc->howto->type != current_call_mode)
2929 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2930 subspace_reloc_size += 1;
2932 current_call_mode = bfd_reloc->howto->type;
2947 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2948 subspace_reloc_size += 1;
2953 /* The end of a exception handling region. The reloc's
2954 addend contains the offset of the exception handling
2956 if (bfd_reloc->addend == 0)
2957 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2958 else if (bfd_reloc->addend < 1024)
2960 bfd_put_8 (abfd, bfd_reloc->howto->type + 1, p);
2961 bfd_put_8 (abfd, bfd_reloc->addend / 4, p + 1);
2962 p = try_prev_fixup (abfd, &subspace_reloc_size,
2967 bfd_put_8 (abfd, bfd_reloc->howto->type + 2, p);
2968 bfd_put_8 (abfd, (bfd_reloc->addend / 4) >> 16, p + 1);
2969 bfd_put_16 (abfd, bfd_reloc->addend / 4, p + 2);
2970 p = try_prev_fixup (abfd, &subspace_reloc_size,
2976 /* The only time we generate R_COMP1, R_COMP2 and
2977 R_CODE_EXPR relocs is for the difference of two
2978 symbols. Hence we can cheat here. */
2979 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2980 bfd_put_8 (abfd, 0x44, p + 1);
2981 p = try_prev_fixup (abfd, &subspace_reloc_size,
2986 /* The only time we generate R_COMP1, R_COMP2 and
2987 R_CODE_EXPR relocs is for the difference of two
2988 symbols. Hence we can cheat here. */
2989 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
2990 bfd_put_8 (abfd, 0x80, p + 1);
2991 bfd_put_8 (abfd, sym_num >> 16, p + 2);
2992 bfd_put_16 (abfd, sym_num, p + 3);
2993 p = try_prev_fixup (abfd, &subspace_reloc_size,
2999 /* The only time we generate R_COMP1, R_COMP2 and
3000 R_CODE_EXPR relocs is for the difference of two
3001 symbols. Hence we can cheat here. */
3002 bfd_put_8 (abfd, bfd_reloc->howto->type, p);
3003 subspace_reloc_size += 1;
3007 /* Put a "R_RESERVED" relocation in the stream if
3008 we hit something we do not understand. The linker
3009 will complain loudly if this ever happens. */
3011 bfd_put_8 (abfd, 0xff, p);
3012 subspace_reloc_size += 1;
3018 /* Last BFD relocation for a subspace has been processed.
3019 Map the rest of the subspace with R_NO_RELOCATION fixups. */
3020 p = som_reloc_skip (abfd, bfd_section_size (abfd, subsection)
3022 p, &subspace_reloc_size, reloc_queue);
3024 /* Scribble out the relocations. */
3025 if (bfd_write ((PTR) tmp_space, p - tmp_space, 1, abfd)
3030 total_reloc_size += subspace_reloc_size;
3031 som_section_data (subsection)->subspace_dict->fixup_request_quantity
3032 = subspace_reloc_size;
3034 section = section->next;
3036 *total_reloc_sizep = total_reloc_size;
3040 /* Write out the space/subspace string table. */
3043 som_write_space_strings (abfd, current_offset, string_sizep)
3045 unsigned long current_offset;
3046 unsigned int *string_sizep;
3048 /* Chunk of memory that we can use as buffer space, then throw
3050 size_t tmp_space_size = SOM_TMP_BUFSIZE;
3051 unsigned char *tmp_space = alloca (tmp_space_size);
3052 unsigned char *p = tmp_space;
3053 unsigned int strings_size = 0;
3056 /* Seek to the start of the space strings in preparation for writing
3058 if (bfd_seek (abfd, current_offset, SEEK_SET) < 0)
3061 /* Walk through all the spaces and subspaces (order is not important)
3062 building up and writing string table entries for their names. */
3063 for (section = abfd->sections; section != NULL; section = section->next)
3067 /* Only work with space/subspaces; avoid any other sections
3068 which might have been made (.text for example). */
3069 if (!som_is_space (section) && !som_is_subspace (section))
3072 /* Get the length of the space/subspace name. */
3073 length = strlen (section->name);
3075 /* If there is not enough room for the next entry, then dump the
3076 current buffer contents now and maybe allocate a larger
3077 buffer. Each entry will take 4 bytes to hold the string
3078 length + the string itself + null terminator. */
3079 if (p - tmp_space + 5 + length > tmp_space_size)
3081 /* Flush buffer before refilling or reallocating. */
3082 if (bfd_write ((PTR) &tmp_space[0], p - tmp_space, 1, abfd)
3086 /* Reallocate if now empty buffer still too small. */
3087 if (5 + length > tmp_space_size)
3089 /* Ensure a minimum growth factor to avoid O(n**2) space
3090 consumption for n strings. The optimal minimum
3091 factor seems to be 2, as no other value can guarantee
3092 wasting less then 50% space. (Note that we cannot
3093 deallocate space allocated by `alloca' without
3094 returning from this function.) The same technique is
3095 used a few more times below when a buffer is
3097 tmp_space_size = MAX (2 * tmp_space_size, 5 + length);
3098 tmp_space = alloca (tmp_space_size);
3101 /* Reset to beginning of the (possibly new) buffer space. */
3105 /* First element in a string table entry is the length of the
3106 string. Alignment issues are already handled. */
3107 bfd_put_32 (abfd, length, p);
3111 /* Record the index in the space/subspace records. */
3112 if (som_is_space (section))
3113 som_section_data (section)->space_dict->name.n_strx = strings_size;
3115 som_section_data (section)->subspace_dict->name.n_strx = strings_size;
3117 /* Next comes the string itself + a null terminator. */
3118 strcpy (p, section->name);
3120 strings_size += length + 1;
3122 /* Always align up to the next word boundary. */
3123 while (strings_size % 4)
3125 bfd_put_8 (abfd, 0, p);
3131 /* Done with the space/subspace strings. Write out any information
3132 contained in a partial block. */
3133 if (bfd_write ((PTR) &tmp_space[0], p - tmp_space, 1, abfd) != p - tmp_space)
3135 *string_sizep = strings_size;
3139 /* Write out the symbol string table. */
3142 som_write_symbol_strings (abfd, current_offset, syms, num_syms, string_sizep,
3145 unsigned long current_offset;
3147 unsigned int num_syms;
3148 unsigned int *string_sizep;
3149 COMPUNIT *compilation_unit;
3153 /* Chunk of memory that we can use as buffer space, then throw
3155 size_t tmp_space_size = SOM_TMP_BUFSIZE;
3156 unsigned char *tmp_space = alloca (tmp_space_size);
3157 unsigned char *p = tmp_space;
3159 unsigned int strings_size = 0;
3160 unsigned char *comp[4];
3162 /* This gets a bit gruesome because of the compilation unit. The
3163 strings within the compilation unit are part of the symbol
3164 strings, but don't have symbol_dictionary entries. So, manually
3165 write them and update the compliation unit header. On input, the
3166 compilation unit header contains local copies of the strings.
3168 if (compilation_unit)
3170 comp[0] = compilation_unit->name.n_name;
3171 comp[1] = compilation_unit->language_name.n_name;
3172 comp[2] = compilation_unit->product_id.n_name;
3173 comp[3] = compilation_unit->version_id.n_name;
3176 /* Seek to the start of the space strings in preparation for writing
3178 if (bfd_seek (abfd, current_offset, SEEK_SET) < 0)
3181 if (compilation_unit)
3183 for (i = 0; i < 4; i++)
3185 size_t length = strlen (comp[i]);
3187 /* If there is not enough room for the next entry, then dump
3188 the current buffer contents now and maybe allocate a
3190 if (p - tmp_space + 5 + length > tmp_space_size)
3192 /* Flush buffer before refilling or reallocating. */
3193 if (bfd_write ((PTR) &tmp_space[0], p - tmp_space, 1, abfd)
3197 /* Reallocate if now empty buffer still too small. */
3198 if (5 + length > tmp_space_size)
3200 /* See alloca above for discussion of new size. */
3201 tmp_space_size = MAX (2 * tmp_space_size, 5 + length);
3202 tmp_space = alloca (tmp_space_size);
3205 /* Reset to beginning of the (possibly new) buffer
3210 /* First element in a string table entry is the length of
3211 the string. This must always be 4 byte aligned. This is
3212 also an appropriate time to fill in the string index
3213 field in the symbol table entry. */
3214 bfd_put_32 (abfd, length, p);
3218 /* Next comes the string itself + a null terminator. */
3219 strcpy (p, comp[i]);
3224 obj_som_compilation_unit (abfd)->name.n_strx = strings_size;
3227 obj_som_compilation_unit (abfd)->language_name.n_strx =
3231 obj_som_compilation_unit (abfd)->product_id.n_strx =
3235 obj_som_compilation_unit (abfd)->version_id.n_strx =
3241 strings_size += length + 1;
3243 /* Always align up to the next word boundary. */
3244 while (strings_size % 4)
3246 bfd_put_8 (abfd, 0, p);
3253 for (i = 0; i < num_syms; i++)
3255 size_t length = strlen (syms[i]->name);
3257 /* If there is not enough room for the next entry, then dump the
3258 current buffer contents now and maybe allocate a larger buffer. */
3259 if (p - tmp_space + 5 + length > tmp_space_size)
3261 /* Flush buffer before refilling or reallocating. */
3262 if (bfd_write ((PTR) &tmp_space[0], p - tmp_space, 1, abfd)
3266 /* Reallocate if now empty buffer still too small. */
3267 if (5 + length > tmp_space_size)
3269 /* See alloca above for discussion of new size. */
3270 tmp_space_size = MAX (2 * tmp_space_size, 5 + length);
3271 tmp_space = alloca (tmp_space_size);
3274 /* Reset to beginning of the (possibly new) buffer space. */
3278 /* First element in a string table entry is the length of the
3279 string. This must always be 4 byte aligned. This is also
3280 an appropriate time to fill in the string index field in the
3281 symbol table entry. */
3282 bfd_put_32 (abfd, length, p);
3286 /* Next comes the string itself + a null terminator. */
3287 strcpy (p, syms[i]->name);
3289 som_symbol_data(syms[i])->stringtab_offset = strings_size;
3291 strings_size += length + 1;
3293 /* Always align up to the next word boundary. */
3294 while (strings_size % 4)
3296 bfd_put_8 (abfd, 0, p);
3302 /* Scribble out any partial block. */
3303 if (bfd_write ((PTR) &tmp_space[0], p - tmp_space, 1, abfd) != p - tmp_space)
3306 *string_sizep = strings_size;
3310 /* Compute variable information to be placed in the SOM headers,
3311 space/subspace dictionaries, relocation streams, etc. Begin
3312 writing parts of the object file. */
3315 som_begin_writing (abfd)
3318 unsigned long current_offset = 0;
3319 int strings_size = 0;
3320 unsigned long num_spaces, num_subspaces, i;
3322 unsigned int total_subspaces = 0;
3323 struct som_exec_auxhdr *exec_header = NULL;
3325 /* The file header will always be first in an object file,
3326 everything else can be in random locations. To keep things
3327 "simple" BFD will lay out the object file in the manner suggested
3328 by the PRO ABI for PA-RISC Systems. */
3330 /* Before any output can really begin offsets for all the major
3331 portions of the object file must be computed. So, starting
3332 with the initial file header compute (and sometimes write)
3333 each portion of the object file. */
3335 /* Make room for the file header, it's contents are not complete
3336 yet, so it can not be written at this time. */
3337 current_offset += sizeof (struct header);
3339 /* Any auxiliary headers will follow the file header. Right now
3340 we support only the copyright and version headers. */
3341 obj_som_file_hdr (abfd)->aux_header_location = current_offset;
3342 obj_som_file_hdr (abfd)->aux_header_size = 0;
3343 if (abfd->flags & (EXEC_P | DYNAMIC))
3345 /* Parts of the exec header will be filled in later, so
3346 delay writing the header itself. Fill in the defaults,
3347 and write it later. */
3348 current_offset += sizeof (struct som_exec_auxhdr);
3349 obj_som_file_hdr (abfd)->aux_header_size
3350 += sizeof (struct som_exec_auxhdr);
3351 exec_header = obj_som_exec_hdr (abfd);
3352 exec_header->som_auxhdr.type = EXEC_AUX_ID;
3353 exec_header->som_auxhdr.length = 40;
3355 if (obj_som_version_hdr (abfd) != NULL)
3359 if (bfd_seek (abfd, current_offset, SEEK_SET) < 0)
3362 /* Write the aux_id structure and the string length. */
3363 len = sizeof (struct aux_id) + sizeof (unsigned int);
3364 obj_som_file_hdr (abfd)->aux_header_size += len;
3365 current_offset += len;
3366 if (bfd_write ((PTR) obj_som_version_hdr (abfd), len, 1, abfd) != len)
3369 /* Write the version string. */
3370 len = obj_som_version_hdr (abfd)->header_id.length - sizeof (int);
3371 obj_som_file_hdr (abfd)->aux_header_size += len;
3372 current_offset += len;
3373 if (bfd_write ((PTR) obj_som_version_hdr (abfd)->user_string,
3374 len, 1, abfd) != len)
3378 if (obj_som_copyright_hdr (abfd) != NULL)
3382 if (bfd_seek (abfd, current_offset, SEEK_SET) < 0)
3385 /* Write the aux_id structure and the string length. */
3386 len = sizeof (struct aux_id) + sizeof (unsigned int);
3387 obj_som_file_hdr (abfd)->aux_header_size += len;
3388 current_offset += len;
3389 if (bfd_write ((PTR) obj_som_copyright_hdr (abfd), len, 1, abfd) != len)
3392 /* Write the copyright string. */
3393 len = obj_som_copyright_hdr (abfd)->header_id.length - sizeof (int);
3394 obj_som_file_hdr (abfd)->aux_header_size += len;
3395 current_offset += len;
3396 if (bfd_write ((PTR) obj_som_copyright_hdr (abfd)->copyright,
3397 len, 1, abfd) != len)
3401 /* Next comes the initialization pointers; we have no initialization
3402 pointers, so current offset does not change. */
3403 obj_som_file_hdr (abfd)->init_array_location = current_offset;
3404 obj_som_file_hdr (abfd)->init_array_total = 0;
3406 /* Next are the space records. These are fixed length records.
3408 Count the number of spaces to determine how much room is needed
3409 in the object file for the space records.
3411 The names of the spaces are stored in a separate string table,
3412 and the index for each space into the string table is computed
3413 below. Therefore, it is not possible to write the space headers
3415 num_spaces = som_count_spaces (abfd);
3416 obj_som_file_hdr (abfd)->space_location = current_offset;
3417 obj_som_file_hdr (abfd)->space_total = num_spaces;
3418 current_offset += num_spaces * sizeof (struct space_dictionary_record);
3420 /* Next are the subspace records. These are fixed length records.
3422 Count the number of subspaes to determine how much room is needed
3423 in the object file for the subspace records.
3425 A variety if fields in the subspace record are still unknown at
3426 this time (index into string table, fixup stream location/size, etc). */
3427 num_subspaces = som_count_subspaces (abfd);
3428 obj_som_file_hdr (abfd)->subspace_location = current_offset;
3429 obj_som_file_hdr (abfd)->subspace_total = num_subspaces;
3430 current_offset += num_subspaces * sizeof (struct subspace_dictionary_record);
3432 /* Next is the string table for the space/subspace names. We will
3433 build and write the string table on the fly. At the same time
3434 we will fill in the space/subspace name index fields. */
3436 /* The string table needs to be aligned on a word boundary. */
3437 if (current_offset % 4)
3438 current_offset += (4 - (current_offset % 4));
3440 /* Mark the offset of the space/subspace string table in the
3442 obj_som_file_hdr (abfd)->space_strings_location = current_offset;
3444 /* Scribble out the space strings. */
3445 if (som_write_space_strings (abfd, current_offset, &strings_size) == false)
3448 /* Record total string table size in the header and update the
3450 obj_som_file_hdr (abfd)->space_strings_size = strings_size;
3451 current_offset += strings_size;
3453 /* Next is the compilation unit. */
3454 obj_som_file_hdr (abfd)->compiler_location = current_offset;
3455 obj_som_file_hdr (abfd)->compiler_total = 0;
3456 if (obj_som_compilation_unit (abfd))
3458 obj_som_file_hdr (abfd)->compiler_total = 1;
3459 current_offset += COMPUNITSZ;
3462 /* Now compute the file positions for the loadable subspaces, taking
3463 care to make sure everything stays properly aligned. */
3465 section = abfd->sections;
3466 for (i = 0; i < num_spaces; i++)
3468 asection *subsection;
3470 unsigned int subspace_offset = 0;
3473 while (!som_is_space (section))
3474 section = section->next;
3477 /* Now look for all its subspaces. */
3478 for (subsection = abfd->sections;
3480 subsection = subsection->next)
3483 if (!som_is_subspace (subsection)
3484 || !som_is_container (section, subsection)
3485 || (subsection->flags & SEC_ALLOC) == 0)
3488 /* If this is the first subspace in the space, and we are
3489 building an executable, then take care to make sure all
3490 the alignments are correct and update the exec header. */
3492 && (abfd->flags & (EXEC_P | DYNAMIC)))
3494 /* Demand paged executables have each space aligned to a
3495 page boundary. Sharable executables (write-protected
3496 text) have just the private (aka data & bss) space aligned
3497 to a page boundary. Ugh. Not true for HPUX.
3499 The HPUX kernel requires the text to always be page aligned
3500 within the file regardless of the executable's type. */
3501 if (abfd->flags & (D_PAGED | DYNAMIC)
3502 || (subsection->flags & SEC_CODE)
3503 || ((abfd->flags & WP_TEXT)
3504 && (subsection->flags & SEC_DATA)))
3505 current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE);
3507 /* Update the exec header. */
3508 if (subsection->flags & SEC_CODE && exec_header->exec_tfile == 0)
3510 exec_header->exec_tmem = section->vma;
3511 exec_header->exec_tfile = current_offset;
3513 if (subsection->flags & SEC_DATA && exec_header->exec_dfile == 0)
3515 exec_header->exec_dmem = section->vma;
3516 exec_header->exec_dfile = current_offset;
3519 /* Keep track of exactly where we are within a particular
3520 space. This is necessary as the braindamaged HPUX
3521 loader will create holes between subspaces *and*
3522 subspace alignments are *NOT* preserved. What a crock. */
3523 subspace_offset = subsection->vma;
3525 /* Only do this for the first subspace within each space. */
3528 else if (abfd->flags & (EXEC_P | DYNAMIC))
3530 /* The braindamaged HPUX loader may have created a hole
3531 between two subspaces. It is *not* sufficient to use
3532 the alignment specifications within the subspaces to
3533 account for these holes -- I've run into at least one
3534 case where the loader left one code subspace unaligned
3535 in a final executable.
3537 To combat this we keep a current offset within each space,
3538 and use the subspace vma fields to detect and preserve
3539 holes. What a crock!
3541 ps. This is not necessary for unloadable space/subspaces. */
3542 current_offset += subsection->vma - subspace_offset;
3543 if (subsection->flags & SEC_CODE)
3544 exec_header->exec_tsize += subsection->vma - subspace_offset;
3546 exec_header->exec_dsize += subsection->vma - subspace_offset;
3547 subspace_offset += subsection->vma - subspace_offset;
3551 subsection->target_index = total_subspaces++;
3552 /* This is real data to be loaded from the file. */
3553 if (subsection->flags & SEC_LOAD)
3555 /* Update the size of the code & data. */
3556 if (abfd->flags & (EXEC_P | DYNAMIC)
3557 && subsection->flags & SEC_CODE)
3558 exec_header->exec_tsize += subsection->_cooked_size;
3559 else if (abfd->flags & (EXEC_P | DYNAMIC)
3560 && subsection->flags & SEC_DATA)
3561 exec_header->exec_dsize += subsection->_cooked_size;
3562 som_section_data (subsection)->subspace_dict->file_loc_init_value
3564 subsection->filepos = current_offset;
3565 current_offset += bfd_section_size (abfd, subsection);
3566 subspace_offset += bfd_section_size (abfd, subsection);
3568 /* Looks like uninitialized data. */
3571 /* Update the size of the bss section. */
3572 if (abfd->flags & (EXEC_P | DYNAMIC))
3573 exec_header->exec_bsize += subsection->_cooked_size;
3575 som_section_data (subsection)->subspace_dict->file_loc_init_value
3577 som_section_data (subsection)->subspace_dict->
3578 initialization_length = 0;
3581 /* Goto the next section. */
3582 section = section->next;
3585 /* Finally compute the file positions for unloadable subspaces.
3586 If building an executable, start the unloadable stuff on its
3589 if (abfd->flags & (EXEC_P | DYNAMIC))
3590 current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE);
3592 obj_som_file_hdr (abfd)->unloadable_sp_location = current_offset;
3593 section = abfd->sections;
3594 for (i = 0; i < num_spaces; i++)
3596 asection *subsection;
3599 while (!som_is_space (section))
3600 section = section->next;
3602 if (abfd->flags & (EXEC_P | DYNAMIC))
3603 current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE);
3605 /* Now look for all its subspaces. */
3606 for (subsection = abfd->sections;
3608 subsection = subsection->next)
3611 if (!som_is_subspace (subsection)
3612 || !som_is_container (section, subsection)
3613 || (subsection->flags & SEC_ALLOC) != 0)
3616 subsection->target_index = total_subspaces++;
3617 /* This is real data to be loaded from the file. */
3618 if ((subsection->flags & SEC_LOAD) == 0)
3620 som_section_data (subsection)->subspace_dict->file_loc_init_value
3622 subsection->filepos = current_offset;
3623 current_offset += bfd_section_size (abfd, subsection);
3625 /* Looks like uninitialized data. */
3628 som_section_data (subsection)->subspace_dict->file_loc_init_value
3630 som_section_data (subsection)->subspace_dict->
3631 initialization_length = bfd_section_size (abfd, subsection);
3634 /* Goto the next section. */
3635 section = section->next;
3638 /* If building an executable, then make sure to seek to and write
3639 one byte at the end of the file to make sure any necessary
3640 zeros are filled in. Ugh. */
3641 if (abfd->flags & (EXEC_P | DYNAMIC))
3642 current_offset = SOM_ALIGN (current_offset, PA_PAGESIZE);
3643 if (bfd_seek (abfd, current_offset - 1, SEEK_SET) < 0)
3645 if (bfd_write ((PTR) "", 1, 1, abfd) != 1)
3648 obj_som_file_hdr (abfd)->unloadable_sp_size
3649 = current_offset - obj_som_file_hdr (abfd)->unloadable_sp_location;
3651 /* Loader fixups are not supported in any way shape or form. */
3652 obj_som_file_hdr (abfd)->loader_fixup_location = 0;
3653 obj_som_file_hdr (abfd)->loader_fixup_total = 0;
3655 /* Done. Store the total size of the SOM so far. */
3656 obj_som_file_hdr (abfd)->som_length = current_offset;
3661 /* Finally, scribble out the various headers to the disk. */
3664 som_finish_writing (abfd)
3667 int num_spaces = som_count_spaces (abfd);
3668 asymbol **syms = bfd_get_outsymbols (abfd);
3669 int i, num_syms, strings_size;
3670 int subspace_index = 0;
3673 unsigned long current_offset;
3674 unsigned int total_reloc_size;
3676 /* Next is the symbol table. These are fixed length records.
3678 Count the number of symbols to determine how much room is needed
3679 in the object file for the symbol table.
3681 The names of the symbols are stored in a separate string table,
3682 and the index for each symbol name into the string table is computed
3683 below. Therefore, it is not possible to write the symbol table
3686 These used to be output before the subspace contents, but they
3687 were moved here to work around a stupid bug in the hpux linker
3688 (fixed in hpux10). */
3689 current_offset = obj_som_file_hdr (abfd)->som_length;
3691 /* Make sure we're on a word boundary. */
3692 if (current_offset % 4)
3693 current_offset += (4 - (current_offset % 4));
3695 num_syms = bfd_get_symcount (abfd);
3696 obj_som_file_hdr (abfd)->symbol_location = current_offset;
3697 obj_som_file_hdr (abfd)->symbol_total = num_syms;
3698 current_offset += num_syms * sizeof (struct symbol_dictionary_record);
3700 /* Next are the symbol strings.
3701 Align them to a word boundary. */
3702 if (current_offset % 4)
3703 current_offset += (4 - (current_offset % 4));
3704 obj_som_file_hdr (abfd)->symbol_strings_location = current_offset;
3706 /* Scribble out the symbol strings. */
3707 if (som_write_symbol_strings (abfd, current_offset, syms,
3708 num_syms, &strings_size,
3709 obj_som_compilation_unit (abfd))
3713 /* Record total string table size in header and update the
3715 obj_som_file_hdr (abfd)->symbol_strings_size = strings_size;
3716 current_offset += strings_size;
3718 /* Do prep work before handling fixups. */
3719 som_prep_for_fixups (abfd,
3720 bfd_get_outsymbols (abfd),
3721 bfd_get_symcount (abfd));
3723 /* At the end of the file is the fixup stream which starts on a
3725 if (current_offset % 4)
3726 current_offset += (4 - (current_offset % 4));
3727 obj_som_file_hdr (abfd)->fixup_request_location = current_offset;
3729 /* Write the fixups and update fields in subspace headers which
3730 relate to the fixup stream. */
3731 if (som_write_fixups (abfd, current_offset, &total_reloc_size) == false)
3734 /* Record the total size of the fixup stream in the file header. */
3735 obj_som_file_hdr (abfd)->fixup_request_total = total_reloc_size;
3737 /* Done. Store the total size of the SOM. */
3738 obj_som_file_hdr (abfd)->som_length = current_offset + total_reloc_size;
3740 /* Now that the symbol table information is complete, build and
3741 write the symbol table. */
3742 if (som_build_and_write_symbol_table (abfd) == false)
3745 /* Subspaces are written first so that we can set up information
3746 about them in their containing spaces as the subspace is written. */
3748 /* Seek to the start of the subspace dictionary records. */
3749 location = obj_som_file_hdr (abfd)->subspace_location;
3750 if (bfd_seek (abfd, location, SEEK_SET) < 0)
3753 section = abfd->sections;
3754 /* Now for each loadable space write out records for its subspaces. */
3755 for (i = 0; i < num_spaces; i++)
3757 asection *subsection;
3760 while (!som_is_space (section))
3761 section = section->next;
3763 /* Now look for all its subspaces. */
3764 for (subsection = abfd->sections;
3766 subsection = subsection->next)
3769 /* Skip any section which does not correspond to a space
3770 or subspace. Or does not have SEC_ALLOC set (and therefore
3771 has no real bits on the disk). */
3772 if (!som_is_subspace (subsection)
3773 || !som_is_container (section, subsection)
3774 || (subsection->flags & SEC_ALLOC) == 0)
3777 /* If this is the first subspace for this space, then save
3778 the index of the subspace in its containing space. Also
3779 set "is_loadable" in the containing space. */
3781 if (som_section_data (section)->space_dict->subspace_quantity == 0)
3783 som_section_data (section)->space_dict->is_loadable = 1;
3784 som_section_data (section)->space_dict->subspace_index
3788 /* Increment the number of subspaces seen and the number of
3789 subspaces contained within the current space. */
3791 som_section_data (section)->space_dict->subspace_quantity++;
3793 /* Mark the index of the current space within the subspace's
3794 dictionary record. */
3795 som_section_data (subsection)->subspace_dict->space_index = i;
3797 /* Dump the current subspace header. */
3798 if (bfd_write ((PTR) som_section_data (subsection)->subspace_dict,
3799 sizeof (struct subspace_dictionary_record), 1, abfd)
3800 != sizeof (struct subspace_dictionary_record))
3803 /* Goto the next section. */
3804 section = section->next;
3807 /* Now repeat the process for unloadable subspaces. */
3808 section = abfd->sections;
3809 /* Now for each space write out records for its subspaces. */
3810 for (i = 0; i < num_spaces; i++)
3812 asection *subsection;
3815 while (!som_is_space (section))
3816 section = section->next;
3818 /* Now look for all its subspaces. */
3819 for (subsection = abfd->sections;
3821 subsection = subsection->next)
3824 /* Skip any section which does not correspond to a space or
3825 subspace, or which SEC_ALLOC set (and therefore handled
3826 in the loadable spaces/subspaces code above). */
3828 if (!som_is_subspace (subsection)
3829 || !som_is_container (section, subsection)
3830 || (subsection->flags & SEC_ALLOC) != 0)
3833 /* If this is the first subspace for this space, then save
3834 the index of the subspace in its containing space. Clear
3837 if (som_section_data (section)->space_dict->subspace_quantity == 0)
3839 som_section_data (section)->space_dict->is_loadable = 0;
3840 som_section_data (section)->space_dict->subspace_index
3844 /* Increment the number of subspaces seen and the number of
3845 subspaces contained within the current space. */
3846 som_section_data (section)->space_dict->subspace_quantity++;
3849 /* Mark the index of the current space within the subspace's
3850 dictionary record. */
3851 som_section_data (subsection)->subspace_dict->space_index = i;
3853 /* Dump this subspace header. */
3854 if (bfd_write ((PTR) som_section_data (subsection)->subspace_dict,
3855 sizeof (struct subspace_dictionary_record), 1, abfd)
3856 != sizeof (struct subspace_dictionary_record))
3859 /* Goto the next section. */
3860 section = section->next;
3863 /* All the subspace dictiondary records are written, and all the
3864 fields are set up in the space dictionary records.
3866 Seek to the right location and start writing the space
3867 dictionary records. */
3868 location = obj_som_file_hdr (abfd)->space_location;
3869 if (bfd_seek (abfd, location, SEEK_SET) < 0)
3872 section = abfd->sections;
3873 for (i = 0; i < num_spaces; i++)
3877 while (!som_is_space (section))
3878 section = section->next;
3880 /* Dump its header */
3881 if (bfd_write ((PTR) som_section_data (section)->space_dict,
3882 sizeof (struct space_dictionary_record), 1, abfd)
3883 != sizeof (struct space_dictionary_record))
3886 /* Goto the next section. */
3887 section = section->next;
3890 /* Write the compilation unit record if there is one. */
3891 if (obj_som_compilation_unit (abfd))
3893 location = obj_som_file_hdr (abfd)->compiler_location;
3894 if (bfd_seek (abfd, location, SEEK_SET) < 0)
3897 if (bfd_write ((PTR) obj_som_compilation_unit (abfd),
3898 COMPUNITSZ, 1, abfd) != COMPUNITSZ)
3902 /* Setting of the system_id has to happen very late now that copying of
3903 BFD private data happens *after* section contents are set. */
3904 if (abfd->flags & (EXEC_P | DYNAMIC))
3905 obj_som_file_hdr(abfd)->system_id = obj_som_exec_data (abfd)->system_id;
3906 else if (bfd_get_mach (abfd) == pa20)
3907 obj_som_file_hdr(abfd)->system_id = CPU_PA_RISC2_0;
3908 else if (bfd_get_mach (abfd) == pa11)
3909 obj_som_file_hdr(abfd)->system_id = CPU_PA_RISC1_1;
3911 obj_som_file_hdr(abfd)->system_id = CPU_PA_RISC1_0;
3913 /* Compute the checksum for the file header just before writing
3914 the header to disk. */
3915 obj_som_file_hdr (abfd)->checksum = som_compute_checksum (abfd);
3917 /* Only thing left to do is write out the file header. It is always
3918 at location zero. Seek there and write it. */
3919 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) < 0)
3921 if (bfd_write ((PTR) obj_som_file_hdr (abfd),
3922 sizeof (struct header), 1, abfd)
3923 != sizeof (struct header))
3926 /* Now write the exec header. */
3927 if (abfd->flags & (EXEC_P | DYNAMIC))
3929 long tmp, som_length;
3930 struct som_exec_auxhdr *exec_header;
3932 exec_header = obj_som_exec_hdr (abfd);
3933 exec_header->exec_entry = bfd_get_start_address (abfd);
3934 exec_header->exec_flags = obj_som_exec_data (abfd)->exec_flags;
3936 /* Oh joys. Ram some of the BSS data into the DATA section
3937 to be compatable with how the hp linker makes objects
3938 (saves memory space). */
3939 tmp = exec_header->exec_dsize;
3940 tmp = SOM_ALIGN (tmp, PA_PAGESIZE);
3941 exec_header->exec_bsize -= (tmp - exec_header->exec_dsize);
3942 if (exec_header->exec_bsize < 0)
3943 exec_header->exec_bsize = 0;
3944 exec_header->exec_dsize = tmp;
3946 /* Now perform some sanity checks. The idea is to catch bogons now and
3947 inform the user, instead of silently generating a bogus file. */
3948 som_length = obj_som_file_hdr (abfd)->som_length;
3949 if (exec_header->exec_tfile + exec_header->exec_tsize > som_length
3950 || exec_header->exec_dfile + exec_header->exec_dsize > som_length)
3952 bfd_set_error (bfd_error_bad_value);
3956 if (bfd_seek (abfd, obj_som_file_hdr (abfd)->aux_header_location,
3960 if (bfd_write ((PTR) exec_header, AUX_HDR_SIZE, 1, abfd)
3967 /* Compute and return the checksum for a SOM file header. */
3969 static unsigned long
3970 som_compute_checksum (abfd)
3973 unsigned long checksum, count, i;
3974 unsigned long *buffer = (unsigned long *) obj_som_file_hdr (abfd);
3977 count = sizeof (struct header) / sizeof (unsigned long);
3978 for (i = 0; i < count; i++)
3979 checksum ^= *(buffer + i);
3985 som_bfd_derive_misc_symbol_info (abfd, sym, info)
3986 bfd *abfd ATTRIBUTE_UNUSED;
3988 struct som_misc_symbol_info *info;
3991 memset (info, 0, sizeof (struct som_misc_symbol_info));
3993 /* The HP SOM linker requires detailed type information about
3994 all symbols (including undefined symbols!). Unfortunately,
3995 the type specified in an import/export statement does not
3996 always match what the linker wants. Severe braindamage. */
3998 /* Section symbols will not have a SOM symbol type assigned to
3999 them yet. Assign all section symbols type ST_DATA. */
4000 if (sym->flags & BSF_SECTION_SYM)
4001 info->symbol_type = ST_DATA;
4004 /* Common symbols must have scope SS_UNSAT and type
4005 ST_STORAGE or the linker will choke. */
4006 if (bfd_is_com_section (sym->section))
4008 info->symbol_scope = SS_UNSAT;
4009 info->symbol_type = ST_STORAGE;
4012 /* It is possible to have a symbol without an associated
4013 type. This happens if the user imported the symbol
4014 without a type and the symbol was never defined
4015 locally. If BSF_FUNCTION is set for this symbol, then
4016 assign it type ST_CODE (the HP linker requires undefined
4017 external functions to have type ST_CODE rather than ST_ENTRY). */
4018 else if ((som_symbol_data (sym)->som_type == SYMBOL_TYPE_UNKNOWN
4019 || som_symbol_data (sym)->som_type == SYMBOL_TYPE_CODE)
4020 && bfd_is_und_section (sym->section)
4021 && sym->flags & BSF_FUNCTION)
4022 info->symbol_type = ST_CODE;
4024 /* Handle function symbols which were defined in this file.
4025 They should have type ST_ENTRY. Also retrieve the argument
4026 relocation bits from the SOM backend information. */
4027 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_ENTRY
4028 || (som_symbol_data (sym)->som_type == SYMBOL_TYPE_CODE
4029 && (sym->flags & BSF_FUNCTION))
4030 || (som_symbol_data (sym)->som_type == SYMBOL_TYPE_UNKNOWN
4031 && (sym->flags & BSF_FUNCTION)))
4033 info->symbol_type = ST_ENTRY;
4034 info->arg_reloc = som_symbol_data (sym)->tc_data.ap.hppa_arg_reloc;
4035 info->priv_level= som_symbol_data (sym)->tc_data.ap.hppa_priv_level;
4038 /* For unknown symbols set the symbol's type based on the symbol's
4039 section (ST_DATA for DATA sections, ST_CODE for CODE sections). */
4040 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_UNKNOWN)
4042 if (sym->section->flags & SEC_CODE)
4043 info->symbol_type = ST_CODE;
4045 info->symbol_type = ST_DATA;
4048 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_UNKNOWN)
4049 info->symbol_type = ST_DATA;
4051 /* From now on it's a very simple mapping. */
4052 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_ABSOLUTE)
4053 info->symbol_type = ST_ABSOLUTE;
4054 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_CODE)
4055 info->symbol_type = ST_CODE;
4056 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_DATA)
4057 info->symbol_type = ST_DATA;
4058 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_MILLICODE)
4059 info->symbol_type = ST_MILLICODE;
4060 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_PLABEL)
4061 info->symbol_type = ST_PLABEL;
4062 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_PRI_PROG)
4063 info->symbol_type = ST_PRI_PROG;
4064 else if (som_symbol_data (sym)->som_type == SYMBOL_TYPE_SEC_PROG)
4065 info->symbol_type = ST_SEC_PROG;
4068 /* Now handle the symbol's scope. Exported data which is not
4069 in the common section has scope SS_UNIVERSAL. Note scope
4070 of common symbols was handled earlier! */
4071 if (bfd_is_und_section (sym->section))
4072 info->symbol_scope = SS_UNSAT;
4073 else if (sym->flags & (BSF_EXPORT | BSF_WEAK)
4074 && ! bfd_is_com_section (sym->section))
4075 info->symbol_scope = SS_UNIVERSAL;
4076 /* Anything else which is not in the common section has scope
4078 else if (! bfd_is_com_section (sym->section))
4079 info->symbol_scope = SS_LOCAL;
4081 /* Now set the symbol_info field. It has no real meaning
4082 for undefined or common symbols, but the HP linker will
4083 choke if it's not set to some "reasonable" value. We
4084 use zero as a reasonable value. */
4085 if (bfd_is_com_section (sym->section)
4086 || bfd_is_und_section (sym->section)
4087 || bfd_is_abs_section (sym->section))
4088 info->symbol_info = 0;
4089 /* For all other symbols, the symbol_info field contains the
4090 subspace index of the space this symbol is contained in. */
4092 info->symbol_info = sym->section->target_index;
4094 /* Set the symbol's value. */
4095 info->symbol_value = sym->value + sym->section->vma;
4097 /* The secondary_def field is for weak symbols. */
4098 if (sym->flags & BSF_WEAK)
4099 info->secondary_def = true;
4101 info->secondary_def = false;
4105 /* Build and write, in one big chunk, the entire symbol table for
4109 som_build_and_write_symbol_table (abfd)
4112 unsigned int num_syms = bfd_get_symcount (abfd);
4113 file_ptr symtab_location = obj_som_file_hdr (abfd)->symbol_location;
4114 asymbol **bfd_syms = obj_som_sorted_syms (abfd);
4115 struct symbol_dictionary_record *som_symtab = NULL;
4118 /* Compute total symbol table size and allocate a chunk of memory
4119 to hold the symbol table as we build it. */
4120 symtab_size = num_syms * sizeof (struct symbol_dictionary_record);
4121 som_symtab = (struct symbol_dictionary_record *) bfd_malloc (symtab_size);
4122 if (som_symtab == NULL && symtab_size != 0)
4124 memset (som_symtab, 0, symtab_size);
4126 /* Walk over each symbol. */
4127 for (i = 0; i < num_syms; i++)
4129 struct som_misc_symbol_info info;
4131 /* This is really an index into the symbol strings table.
4132 By the time we get here, the index has already been
4133 computed and stored into the name field in the BFD symbol. */
4134 som_symtab[i].name.n_strx = som_symbol_data(bfd_syms[i])->stringtab_offset;
4136 /* Derive SOM information from the BFD symbol. */
4137 som_bfd_derive_misc_symbol_info (abfd, bfd_syms[i], &info);
4140 som_symtab[i].symbol_type = info.symbol_type;
4141 som_symtab[i].symbol_scope = info.symbol_scope;
4142 som_symtab[i].arg_reloc = info.arg_reloc;
4143 som_symtab[i].symbol_info = info.symbol_info;
4144 som_symtab[i].xleast = 3;
4145 som_symtab[i].symbol_value = info.symbol_value | info.priv_level;
4146 som_symtab[i].secondary_def = info.secondary_def;
4149 /* Everything is ready, seek to the right location and
4150 scribble out the symbol table. */
4151 if (bfd_seek (abfd, symtab_location, SEEK_SET) != 0)
4154 if (bfd_write ((PTR) som_symtab, symtab_size, 1, abfd) != symtab_size)
4157 if (som_symtab != NULL)
4161 if (som_symtab != NULL)
4166 /* Write an object in SOM format. */
4169 som_write_object_contents (abfd)
4172 if (abfd->output_has_begun == false)
4174 /* Set up fixed parts of the file, space, and subspace headers.
4175 Notify the world that output has begun. */
4176 som_prep_headers (abfd);
4177 abfd->output_has_begun = true;
4178 /* Start writing the object file. This include all the string
4179 tables, fixup streams, and other portions of the object file. */
4180 som_begin_writing (abfd);
4183 return (som_finish_writing (abfd));
4187 /* Read and save the string table associated with the given BFD. */
4190 som_slurp_string_table (abfd)
4195 /* Use the saved version if its available. */
4196 if (obj_som_stringtab (abfd) != NULL)
4199 /* I don't think this can currently happen, and I'm not sure it should
4200 really be an error, but it's better than getting unpredictable results
4201 from the host's malloc when passed a size of zero. */
4202 if (obj_som_stringtab_size (abfd) == 0)
4204 bfd_set_error (bfd_error_no_symbols);
4208 /* Allocate and read in the string table. */
4209 stringtab = bfd_malloc (obj_som_stringtab_size (abfd));
4210 if (stringtab == NULL)
4212 memset (stringtab, 0, obj_som_stringtab_size (abfd));
4214 if (bfd_seek (abfd, obj_som_str_filepos (abfd), SEEK_SET) < 0)
4217 if (bfd_read (stringtab, obj_som_stringtab_size (abfd), 1, abfd)
4218 != obj_som_stringtab_size (abfd))
4221 /* Save our results and return success. */
4222 obj_som_stringtab (abfd) = stringtab;
4226 /* Return the amount of data (in bytes) required to hold the symbol
4227 table for this object. */
4230 som_get_symtab_upper_bound (abfd)
4233 if (!som_slurp_symbol_table (abfd))
4236 return (bfd_get_symcount (abfd) + 1) * (sizeof (asymbol *));
4239 /* Convert from a SOM subspace index to a BFD section. */
4242 bfd_section_from_som_symbol (abfd, symbol)
4244 struct symbol_dictionary_record *symbol;
4248 /* The meaning of the symbol_info field changes for functions
4249 within executables. So only use the quick symbol_info mapping for
4250 incomplete objects and non-function symbols in executables. */
4251 if ((abfd->flags & (EXEC_P | DYNAMIC)) == 0
4252 || (symbol->symbol_type != ST_ENTRY
4253 && symbol->symbol_type != ST_PRI_PROG
4254 && symbol->symbol_type != ST_SEC_PROG
4255 && symbol->symbol_type != ST_MILLICODE))
4257 unsigned int index = symbol->symbol_info;
4258 for (section = abfd->sections; section != NULL; section = section->next)
4259 if (section->target_index == index && som_is_subspace (section))
4262 /* Could be a symbol from an external library (such as an OMOS
4263 shared library). Don't abort. */
4264 return bfd_abs_section_ptr;
4269 unsigned int value = symbol->symbol_value;
4271 /* For executables we will have to use the symbol's address and
4272 find out what section would contain that address. Yuk. */
4273 for (section = abfd->sections; section; section = section->next)
4275 if (value >= section->vma
4276 && value <= section->vma + section->_cooked_size
4277 && som_is_subspace (section))
4281 /* Could be a symbol from an external library (such as an OMOS
4282 shared library). Don't abort. */
4283 return bfd_abs_section_ptr;
4288 /* Read and save the symbol table associated with the given BFD. */
4291 som_slurp_symbol_table (abfd)
4294 int symbol_count = bfd_get_symcount (abfd);
4295 int symsize = sizeof (struct symbol_dictionary_record);
4297 struct symbol_dictionary_record *buf = NULL, *bufp, *endbufp;
4298 som_symbol_type *sym, *symbase;
4300 /* Return saved value if it exists. */
4301 if (obj_som_symtab (abfd) != NULL)
4302 goto successful_return;
4304 /* Special case. This is *not* an error. */
4305 if (symbol_count == 0)
4306 goto successful_return;
4308 if (!som_slurp_string_table (abfd))
4311 stringtab = obj_som_stringtab (abfd);
4313 symbase = ((som_symbol_type *)
4314 bfd_malloc (symbol_count * sizeof (som_symbol_type)));
4315 if (symbase == NULL)
4317 memset (symbase, 0, symbol_count * sizeof (som_symbol_type));
4319 /* Read in the external SOM representation. */
4320 buf = bfd_malloc (symbol_count * symsize);
4321 if (buf == NULL && symbol_count * symsize != 0)
4323 if (bfd_seek (abfd, obj_som_sym_filepos (abfd), SEEK_SET) < 0)
4325 if (bfd_read (buf, symbol_count * symsize, 1, abfd)
4326 != symbol_count * symsize)
4329 /* Iterate over all the symbols and internalize them. */
4330 endbufp = buf + symbol_count;
4331 for (bufp = buf, sym = symbase; bufp < endbufp; ++bufp)
4334 /* I don't think we care about these. */
4335 if (bufp->symbol_type == ST_SYM_EXT
4336 || bufp->symbol_type == ST_ARG_EXT)
4339 /* Set some private data we care about. */
4340 if (bufp->symbol_type == ST_NULL)
4341 som_symbol_data (sym)->som_type = SYMBOL_TYPE_UNKNOWN;
4342 else if (bufp->symbol_type == ST_ABSOLUTE)
4343 som_symbol_data (sym)->som_type = SYMBOL_TYPE_ABSOLUTE;
4344 else if (bufp->symbol_type == ST_DATA)
4345 som_symbol_data (sym)->som_type = SYMBOL_TYPE_DATA;
4346 else if (bufp->symbol_type == ST_CODE)
4347 som_symbol_data (sym)->som_type = SYMBOL_TYPE_CODE;
4348 else if (bufp->symbol_type == ST_PRI_PROG)
4349 som_symbol_data (sym)->som_type = SYMBOL_TYPE_PRI_PROG;
4350 else if (bufp->symbol_type == ST_SEC_PROG)
4351 som_symbol_data (sym)->som_type = SYMBOL_TYPE_SEC_PROG;
4352 else if (bufp->symbol_type == ST_ENTRY)
4353 som_symbol_data (sym)->som_type = SYMBOL_TYPE_ENTRY;
4354 else if (bufp->symbol_type == ST_MILLICODE)
4355 som_symbol_data (sym)->som_type = SYMBOL_TYPE_MILLICODE;
4356 else if (bufp->symbol_type == ST_PLABEL)
4357 som_symbol_data (sym)->som_type = SYMBOL_TYPE_PLABEL;
4359 som_symbol_data (sym)->som_type = SYMBOL_TYPE_UNKNOWN;
4360 som_symbol_data (sym)->tc_data.ap.hppa_arg_reloc = bufp->arg_reloc;
4362 /* Some reasonable defaults. */
4363 sym->symbol.the_bfd = abfd;
4364 sym->symbol.name = bufp->name.n_strx + stringtab;
4365 sym->symbol.value = bufp->symbol_value;
4366 sym->symbol.section = 0;
4367 sym->symbol.flags = 0;
4369 switch (bufp->symbol_type)
4373 sym->symbol.flags |= BSF_FUNCTION;
4374 som_symbol_data (sym)->tc_data.ap.hppa_priv_level =
4375 sym->symbol.value & 0x3;
4376 sym->symbol.value &= ~0x3;
4383 som_symbol_data (sym)->tc_data.ap.hppa_priv_level =
4384 sym->symbol.value & 0x3;
4385 sym->symbol.value &= ~0x3;
4386 /* If the symbol's scope is SS_UNSAT, then these are
4387 undefined function symbols. */
4388 if (bufp->symbol_scope == SS_UNSAT)
4389 sym->symbol.flags |= BSF_FUNCTION;
4396 /* Handle scoping and section information. */
4397 switch (bufp->symbol_scope)
4399 /* symbol_info field is undefined for SS_EXTERNAL and SS_UNSAT symbols,
4400 so the section associated with this symbol can't be known. */
4402 if (bufp->symbol_type != ST_STORAGE)
4403 sym->symbol.section = bfd_und_section_ptr;
4405 sym->symbol.section = bfd_com_section_ptr;
4406 sym->symbol.flags |= (BSF_EXPORT | BSF_GLOBAL);
4410 if (bufp->symbol_type != ST_STORAGE)
4411 sym->symbol.section = bfd_und_section_ptr;
4413 sym->symbol.section = bfd_com_section_ptr;
4417 sym->symbol.flags |= (BSF_EXPORT | BSF_GLOBAL);
4418 sym->symbol.section = bfd_section_from_som_symbol (abfd, bufp);
4419 sym->symbol.value -= sym->symbol.section->vma;
4423 /* SS_GLOBAL and SS_LOCAL are two names for the same thing.
4424 Sound dumb? It is. */
4428 sym->symbol.flags |= BSF_LOCAL;
4429 sym->symbol.section = bfd_section_from_som_symbol (abfd, bufp);
4430 sym->symbol.value -= sym->symbol.section->vma;
4434 /* Check for a weak symbol. */
4435 if (bufp->secondary_def)
4436 sym->symbol.flags |= BSF_WEAK;
4438 /* Mark section symbols and symbols used by the debugger.
4439 Note $START$ is a magic code symbol, NOT a section symbol. */
4440 if (sym->symbol.name[0] == '$'
4441 && sym->symbol.name[strlen (sym->symbol.name) - 1] == '$'
4442 && !strcmp (sym->symbol.name, sym->symbol.section->name))
4443 sym->symbol.flags |= BSF_SECTION_SYM;
4444 else if (!strncmp (sym->symbol.name, "L$0\002", 4))
4446 sym->symbol.flags |= BSF_SECTION_SYM;
4447 sym->symbol.name = sym->symbol.section->name;
4449 else if (!strncmp (sym->symbol.name, "L$0\001", 4))
4450 sym->symbol.flags |= BSF_DEBUGGING;
4452 /* Note increment at bottom of loop, since we skip some symbols
4453 we can not include it as part of the for statement. */
4457 /* We modify the symbol count to record the number of BFD symbols we
4459 bfd_get_symcount (abfd) = sym - symbase;
4461 /* Save our results and return success. */
4462 obj_som_symtab (abfd) = symbase;
4474 /* Canonicalize a SOM symbol table. Return the number of entries
4475 in the symbol table. */
4478 som_get_symtab (abfd, location)
4483 som_symbol_type *symbase;
4485 if (!som_slurp_symbol_table (abfd))
4488 i = bfd_get_symcount (abfd);
4489 symbase = obj_som_symtab (abfd);
4491 for (; i > 0; i--, location++, symbase++)
4492 *location = &symbase->symbol;
4494 /* Final null pointer. */
4496 return (bfd_get_symcount (abfd));
4499 /* Make a SOM symbol. There is nothing special to do here. */
4502 som_make_empty_symbol (abfd)
4505 som_symbol_type *new =
4506 (som_symbol_type *) bfd_zalloc (abfd, sizeof (som_symbol_type));
4509 new->symbol.the_bfd = abfd;
4511 return &new->symbol;
4514 /* Print symbol information. */
4517 som_print_symbol (ignore_abfd, afile, symbol, how)
4518 bfd *ignore_abfd ATTRIBUTE_UNUSED;
4521 bfd_print_symbol_type how;
4523 FILE *file = (FILE *) afile;
4526 case bfd_print_symbol_name:
4527 fprintf (file, "%s", symbol->name);
4529 case bfd_print_symbol_more:
4530 fprintf (file, "som ");
4531 fprintf_vma (file, symbol->value);
4532 fprintf (file, " %lx", (long) symbol->flags);
4534 case bfd_print_symbol_all:
4536 CONST char *section_name;
4537 section_name = symbol->section ? symbol->section->name : "(*none*)";
4538 bfd_print_symbol_vandf ((PTR) file, symbol);
4539 fprintf (file, " %s\t%s", section_name, symbol->name);
4546 som_bfd_is_local_label_name (abfd, name)
4547 bfd *abfd ATTRIBUTE_UNUSED;
4550 return (name[0] == 'L' && name[1] == '$');
4553 /* Count or process variable-length SOM fixup records.
4555 To avoid code duplication we use this code both to compute the number
4556 of relocations requested by a stream, and to internalize the stream.
4558 When computing the number of relocations requested by a stream the
4559 variables rptr, section, and symbols have no meaning.
4561 Return the number of relocations requested by the fixup stream. When
4564 This needs at least two or three more passes to get it cleaned up. */
4567 som_set_reloc_info (fixup, end, internal_relocs, section, symbols, just_count)
4568 unsigned char *fixup;
4570 arelent *internal_relocs;
4575 unsigned int op, varname, deallocate_contents = 0;
4576 unsigned char *end_fixups = &fixup[end];
4577 const struct fixup_format *fp;
4579 unsigned char *save_fixup;
4580 int variables[26], stack[20], c, v, count, prev_fixup, *sp, saved_unwind_bits;
4582 arelent *rptr= internal_relocs;
4583 unsigned int offset = 0;
4585 #define var(c) variables[(c) - 'A']
4586 #define push(v) (*sp++ = (v))
4587 #define pop() (*--sp)
4588 #define emptystack() (sp == stack)
4590 som_initialize_reloc_queue (reloc_queue);
4591 memset (variables, 0, sizeof (variables));
4592 memset (stack, 0, sizeof (stack));
4595 saved_unwind_bits = 0;
4598 while (fixup < end_fixups)
4601 /* Save pointer to the start of this fixup. We'll use
4602 it later to determine if it is necessary to put this fixup
4606 /* Get the fixup code and its associated format. */
4608 fp = &som_fixup_formats[op];
4610 /* Handle a request for a previous fixup. */
4611 if (*fp->format == 'P')
4613 /* Get pointer to the beginning of the prev fixup, move
4614 the repeated fixup to the head of the queue. */
4615 fixup = reloc_queue[fp->D].reloc;
4616 som_reloc_queue_fix (reloc_queue, fp->D);
4619 /* Get the fixup code and its associated format. */
4621 fp = &som_fixup_formats[op];
4624 /* If this fixup will be passed to BFD, set some reasonable defaults. */
4626 && som_hppa_howto_table[op].type != R_NO_RELOCATION
4627 && som_hppa_howto_table[op].type != R_DATA_OVERRIDE)
4629 rptr->address = offset;
4630 rptr->howto = &som_hppa_howto_table[op];
4632 rptr->sym_ptr_ptr = bfd_abs_section_ptr->symbol_ptr_ptr;
4635 /* Set default input length to 0. Get the opcode class index
4639 var ('U') = saved_unwind_bits;
4641 /* Get the opcode format. */
4644 /* Process the format string. Parsing happens in two phases,
4645 parse RHS, then assign to LHS. Repeat until no more
4646 characters in the format string. */
4649 /* The variable this pass is going to compute a value for. */
4652 /* Start processing RHS. Continue until a NULL or '=' is found. */
4657 /* If this is a variable, push it on the stack. */
4661 /* If this is a lower case letter, then it represents
4662 additional data from the fixup stream to be pushed onto
4664 else if (islower (c))
4666 int bits = (c - 'a') * 8;
4667 for (v = 0; c > 'a'; --c)
4668 v = (v << 8) | *fixup++;
4670 v = sign_extend (v, bits);
4674 /* A decimal constant. Push it on the stack. */
4675 else if (isdigit (c))
4678 while (isdigit (*cp))
4679 v = (v * 10) + (*cp++ - '0');
4684 /* An operator. Pop two two values from the stack and
4685 use them as operands to the given operation. Push
4686 the result of the operation back on the stack. */
4708 while (*cp && *cp != '=');
4710 /* Move over the equal operator. */
4713 /* Pop the RHS off the stack. */
4716 /* Perform the assignment. */
4719 /* Handle side effects. and special 'O' stack cases. */
4722 /* Consume some bytes from the input space. */
4726 /* A symbol to use in the relocation. Make a note
4727 of this if we are not just counting. */
4730 rptr->sym_ptr_ptr = &symbols[c];
4732 /* Argument relocation bits for a function call. */
4736 unsigned int tmp = var ('R');
4739 if ((som_hppa_howto_table[op].type == R_PCREL_CALL
4740 && R_PCREL_CALL + 10 > op)
4741 || (som_hppa_howto_table[op].type == R_ABS_CALL
4742 && R_ABS_CALL + 10 > op))
4744 /* Simple encoding. */
4751 rptr->addend |= 1 << 8 | 1 << 6 | 1 << 4 | 1 << 2;
4753 rptr->addend |= 1 << 8 | 1 << 6 | 1 << 4;
4755 rptr->addend |= 1 << 8 | 1 << 6;
4757 rptr->addend |= 1 << 8;
4761 unsigned int tmp1, tmp2;
4763 /* First part is easy -- low order two bits are
4764 directly copied, then shifted away. */
4765 rptr->addend = tmp & 0x3;
4768 /* Diving the result by 10 gives us the second
4769 part. If it is 9, then the first two words
4770 are a double precision paramater, else it is
4771 3 * the first arg bits + the 2nd arg bits. */
4775 rptr->addend += (0xe << 6);
4778 /* Get the two pieces. */
4781 /* Put them in the addend. */
4782 rptr->addend += (tmp2 << 8) + (tmp1 << 6);
4785 /* What's left is the third part. It's unpacked
4786 just like the second. */
4788 rptr->addend += (0xe << 2);
4793 rptr->addend += (tmp2 << 4) + (tmp << 2);
4796 rptr->addend = HPPA_R_ADDEND (rptr->addend, 0);
4799 /* Handle the linker expression stack. */
4804 subop = comp1_opcodes;
4807 subop = comp2_opcodes;
4810 subop = comp3_opcodes;
4815 while (*subop <= (unsigned char) c)
4819 /* The lower 32unwind bits must be persistent. */
4821 saved_unwind_bits = var ('U');
4829 /* If we used a previous fixup, clean up after it. */
4832 fixup = save_fixup + 1;
4836 else if (fixup > save_fixup + 1)
4837 som_reloc_queue_insert (save_fixup, fixup - save_fixup, reloc_queue);
4839 /* We do not pass R_DATA_OVERRIDE or R_NO_RELOCATION
4841 if (som_hppa_howto_table[op].type != R_DATA_OVERRIDE
4842 && som_hppa_howto_table[op].type != R_NO_RELOCATION)
4844 /* Done with a single reloction. Loop back to the top. */
4847 if (som_hppa_howto_table[op].type == R_ENTRY)
4848 rptr->addend = var ('T');
4849 else if (som_hppa_howto_table[op].type == R_EXIT)
4850 rptr->addend = var ('U');
4851 else if (som_hppa_howto_table[op].type == R_PCREL_CALL
4852 || som_hppa_howto_table[op].type == R_ABS_CALL)
4854 else if (som_hppa_howto_table[op].type == R_DATA_ONE_SYMBOL)
4856 /* Try what was specified in R_DATA_OVERRIDE first
4857 (if anything). Then the hard way using the
4858 section contents. */
4859 rptr->addend = var ('V');
4861 if (rptr->addend == 0 && !section->contents)
4863 /* Got to read the damn contents first. We don't
4864 bother saving the contents (yet). Add it one
4865 day if the need arises. */
4866 section->contents = bfd_malloc (section->_raw_size);
4867 if (section->contents == NULL)
4870 deallocate_contents = 1;
4871 bfd_get_section_contents (section->owner,
4875 section->_raw_size);
4877 else if (rptr->addend == 0)
4878 rptr->addend = bfd_get_32 (section->owner,
4880 + offset - var ('L')));
4884 rptr->addend = var ('V');
4888 /* Now that we've handled a "full" relocation, reset
4890 memset (variables, 0, sizeof (variables));
4891 memset (stack, 0, sizeof (stack));
4894 if (deallocate_contents)
4895 free (section->contents);
4905 /* Read in the relocs (aka fixups in SOM terms) for a section.
4907 som_get_reloc_upper_bound calls this routine with JUST_COUNT
4908 set to true to indicate it only needs a count of the number
4909 of actual relocations. */
4912 som_slurp_reloc_table (abfd, section, symbols, just_count)
4918 char *external_relocs;
4919 unsigned int fixup_stream_size;
4920 arelent *internal_relocs;
4921 unsigned int num_relocs;
4923 fixup_stream_size = som_section_data (section)->reloc_size;
4924 /* If there were no relocations, then there is nothing to do. */
4925 if (section->reloc_count == 0)
4928 /* If reloc_count is -1, then the relocation stream has not been
4929 parsed. We must do so now to know how many relocations exist. */
4930 if (section->reloc_count == -1)
4932 external_relocs = (char *) bfd_malloc (fixup_stream_size);
4933 if (external_relocs == (char *) NULL)
4935 /* Read in the external forms. */
4937 obj_som_reloc_filepos (abfd) + section->rel_filepos,
4941 if (bfd_read (external_relocs, 1, fixup_stream_size, abfd)
4942 != fixup_stream_size)
4945 /* Let callers know how many relocations found.
4946 also save the relocation stream as we will
4948 section->reloc_count = som_set_reloc_info (external_relocs,
4950 NULL, NULL, NULL, true);
4952 som_section_data (section)->reloc_stream = external_relocs;
4955 /* If the caller only wanted a count, then return now. */
4959 num_relocs = section->reloc_count;
4960 external_relocs = som_section_data (section)->reloc_stream;
4961 /* Return saved information about the relocations if it is available. */
4962 if (section->relocation != (arelent *) NULL)
4965 internal_relocs = (arelent *)
4966 bfd_zalloc (abfd, (num_relocs * sizeof (arelent)));
4967 if (internal_relocs == (arelent *) NULL)
4970 /* Process and internalize the relocations. */
4971 som_set_reloc_info (external_relocs, fixup_stream_size,
4972 internal_relocs, section, symbols, false);
4974 /* We're done with the external relocations. Free them. */
4975 free (external_relocs);
4976 som_section_data (section)->reloc_stream = NULL;
4978 /* Save our results and return success. */
4979 section->relocation = internal_relocs;
4983 /* Return the number of bytes required to store the relocation
4984 information associated with the given section. */
4987 som_get_reloc_upper_bound (abfd, asect)
4991 /* If section has relocations, then read in the relocation stream
4992 and parse it to determine how many relocations exist. */
4993 if (asect->flags & SEC_RELOC)
4995 if (! som_slurp_reloc_table (abfd, asect, NULL, true))
4997 return (asect->reloc_count + 1) * sizeof (arelent *);
4999 /* There are no relocations. */
5003 /* Convert relocations from SOM (external) form into BFD internal
5004 form. Return the number of relocations. */
5007 som_canonicalize_reloc (abfd, section, relptr, symbols)
5016 if (som_slurp_reloc_table (abfd, section, symbols, false) == false)
5019 count = section->reloc_count;
5020 tblptr = section->relocation;
5023 *relptr++ = tblptr++;
5025 *relptr = (arelent *) NULL;
5026 return section->reloc_count;
5029 extern const bfd_target som_vec;
5031 /* A hook to set up object file dependent section information. */
5034 som_new_section_hook (abfd, newsect)
5038 newsect->used_by_bfd =
5039 (PTR) bfd_zalloc (abfd, sizeof (struct som_section_data_struct));
5040 if (!newsect->used_by_bfd)
5042 newsect->alignment_power = 3;
5044 /* We allow more than three sections internally */
5048 /* Copy any private info we understand from the input symbol
5049 to the output symbol. */
5052 som_bfd_copy_private_symbol_data (ibfd, isymbol, obfd, osymbol)
5058 struct som_symbol *input_symbol = (struct som_symbol *) isymbol;
5059 struct som_symbol *output_symbol = (struct som_symbol *) osymbol;
5061 /* One day we may try to grok other private data. */
5062 if (ibfd->xvec->flavour != bfd_target_som_flavour
5063 || obfd->xvec->flavour != bfd_target_som_flavour)
5066 /* The only private information we need to copy is the argument relocation
5068 output_symbol->tc_data.ap.hppa_arg_reloc =
5069 input_symbol->tc_data.ap.hppa_arg_reloc;
5074 /* Copy any private info we understand from the input section
5075 to the output section. */
5077 som_bfd_copy_private_section_data (ibfd, isection, obfd, osection)
5083 /* One day we may try to grok other private data. */
5084 if (ibfd->xvec->flavour != bfd_target_som_flavour
5085 || obfd->xvec->flavour != bfd_target_som_flavour
5086 || (!som_is_space (isection) && !som_is_subspace (isection)))
5089 som_section_data (osection)->copy_data
5090 = (struct som_copyable_section_data_struct *)
5091 bfd_zalloc (obfd, sizeof (struct som_copyable_section_data_struct));
5092 if (som_section_data (osection)->copy_data == NULL)
5095 memcpy (som_section_data (osection)->copy_data,
5096 som_section_data (isection)->copy_data,
5097 sizeof (struct som_copyable_section_data_struct));
5099 /* Reparent if necessary. */
5100 if (som_section_data (osection)->copy_data->container)
5101 som_section_data (osection)->copy_data->container =
5102 som_section_data (osection)->copy_data->container->output_section;
5107 /* Copy any private info we understand from the input bfd
5108 to the output bfd. */
5111 som_bfd_copy_private_bfd_data (ibfd, obfd)
5114 /* One day we may try to grok other private data. */
5115 if (ibfd->xvec->flavour != bfd_target_som_flavour
5116 || obfd->xvec->flavour != bfd_target_som_flavour)
5119 /* Allocate some memory to hold the data we need. */
5120 obj_som_exec_data (obfd) = (struct som_exec_data *)
5121 bfd_zalloc (obfd, sizeof (struct som_exec_data));
5122 if (obj_som_exec_data (obfd) == NULL)
5125 /* Now copy the data. */
5126 memcpy (obj_som_exec_data (obfd), obj_som_exec_data (ibfd),
5127 sizeof (struct som_exec_data));
5132 /* Set backend info for sections which can not be described
5133 in the BFD data structures. */
5136 bfd_som_set_section_attributes (section, defined, private, sort_key, spnum)
5140 unsigned int sort_key;
5143 /* Allocate memory to hold the magic information. */
5144 if (som_section_data (section)->copy_data == NULL)
5146 som_section_data (section)->copy_data
5147 = (struct som_copyable_section_data_struct *)
5148 bfd_zalloc (section->owner,
5149 sizeof (struct som_copyable_section_data_struct));
5150 if (som_section_data (section)->copy_data == NULL)
5153 som_section_data (section)->copy_data->sort_key = sort_key;
5154 som_section_data (section)->copy_data->is_defined = defined;
5155 som_section_data (section)->copy_data->is_private = private;
5156 som_section_data (section)->copy_data->container = section;
5157 som_section_data (section)->copy_data->space_number = spnum;
5161 /* Set backend info for subsections which can not be described
5162 in the BFD data structures. */
5165 bfd_som_set_subsection_attributes (section, container, access,
5168 asection *container;
5170 unsigned int sort_key;
5173 /* Allocate memory to hold the magic information. */
5174 if (som_section_data (section)->copy_data == NULL)
5176 som_section_data (section)->copy_data
5177 = (struct som_copyable_section_data_struct *)
5178 bfd_zalloc (section->owner,
5179 sizeof (struct som_copyable_section_data_struct));
5180 if (som_section_data (section)->copy_data == NULL)
5183 som_section_data (section)->copy_data->sort_key = sort_key;
5184 som_section_data (section)->copy_data->access_control_bits = access;
5185 som_section_data (section)->copy_data->quadrant = quadrant;
5186 som_section_data (section)->copy_data->container = container;
5190 /* Set the full SOM symbol type. SOM needs far more symbol information
5191 than any other object file format I'm aware of. It is mandatory
5192 to be able to know if a symbol is an entry point, millicode, data,
5193 code, absolute, storage request, or procedure label. If you get
5194 the symbol type wrong your program will not link. */
5197 bfd_som_set_symbol_type (symbol, type)
5201 som_symbol_data (symbol)->som_type = type;
5204 /* Attach an auxiliary header to the BFD backend so that it may be
5205 written into the object file. */
5207 bfd_som_attach_aux_hdr (abfd, type, string)
5212 if (type == VERSION_AUX_ID)
5214 int len = strlen (string);
5218 pad = (4 - (len % 4));
5219 obj_som_version_hdr (abfd) = (struct user_string_aux_hdr *)
5220 bfd_zalloc (abfd, sizeof (struct aux_id)
5221 + sizeof (unsigned int) + len + pad);
5222 if (!obj_som_version_hdr (abfd))
5224 obj_som_version_hdr (abfd)->header_id.type = VERSION_AUX_ID;
5225 obj_som_version_hdr (abfd)->header_id.length = len + pad;
5226 obj_som_version_hdr (abfd)->header_id.length += sizeof (int);
5227 obj_som_version_hdr (abfd)->string_length = len;
5228 strncpy (obj_som_version_hdr (abfd)->user_string, string, len);
5230 else if (type == COPYRIGHT_AUX_ID)
5232 int len = strlen (string);
5236 pad = (4 - (len % 4));
5237 obj_som_copyright_hdr (abfd) = (struct copyright_aux_hdr *)
5238 bfd_zalloc (abfd, sizeof (struct aux_id)
5239 + sizeof (unsigned int) + len + pad);
5240 if (!obj_som_copyright_hdr (abfd))
5242 obj_som_copyright_hdr (abfd)->header_id.type = COPYRIGHT_AUX_ID;
5243 obj_som_copyright_hdr (abfd)->header_id.length = len + pad;
5244 obj_som_copyright_hdr (abfd)->header_id.length += sizeof (int);
5245 obj_som_copyright_hdr (abfd)->string_length = len;
5246 strcpy (obj_som_copyright_hdr (abfd)->copyright, string);
5251 /* Attach an compilation unit header to the BFD backend so that it may be
5252 written into the object file. */
5255 bfd_som_attach_compilation_unit (abfd, name, language_name, product_id,
5259 const char *language_name;
5260 const char *product_id;
5261 const char *version_id;
5263 COMPUNIT *n = (COMPUNIT *) bfd_zalloc (abfd, COMPUNITSZ);
5270 n->f.n_name = bfd_alloc (abfd, strlen (f) + 1); \
5271 if (n->f.n_name == NULL) \
5273 strcpy (n->f.n_name, f); \
5277 STRDUP (language_name);
5278 STRDUP (product_id);
5279 STRDUP (version_id);
5283 obj_som_compilation_unit (abfd) = n;
5289 som_get_section_contents (abfd, section, location, offset, count)
5294 bfd_size_type count;
5296 if (count == 0 || ((section->flags & SEC_HAS_CONTENTS) == 0))
5298 if ((bfd_size_type)(offset+count) > section->_raw_size
5299 || bfd_seek (abfd, (file_ptr)(section->filepos + offset), SEEK_SET) == -1
5300 || bfd_read (location, (bfd_size_type)1, count, abfd) != count)
5301 return (false); /* on error */
5306 som_set_section_contents (abfd, section, location, offset, count)
5311 bfd_size_type count;
5313 if (abfd->output_has_begun == false)
5315 /* Set up fixed parts of the file, space, and subspace headers.
5316 Notify the world that output has begun. */
5317 som_prep_headers (abfd);
5318 abfd->output_has_begun = true;
5319 /* Start writing the object file. This include all the string
5320 tables, fixup streams, and other portions of the object file. */
5321 som_begin_writing (abfd);
5324 /* Only write subspaces which have "real" contents (eg. the contents
5325 are not generated at run time by the OS). */
5326 if (!som_is_subspace (section)
5327 || ((section->flags & SEC_HAS_CONTENTS) == 0))
5330 /* Seek to the proper offset within the object file and write the
5332 offset += som_section_data (section)->subspace_dict->file_loc_init_value;
5333 if (bfd_seek (abfd, offset, SEEK_SET) == -1)
5336 if (bfd_write ((PTR) location, 1, count, abfd) != count)
5342 som_set_arch_mach (abfd, arch, machine)
5344 enum bfd_architecture arch;
5345 unsigned long machine;
5347 /* Allow any architecture to be supported by the SOM backend */
5348 return bfd_default_set_arch_mach (abfd, arch, machine);
5352 som_find_nearest_line (abfd, section, symbols, offset, filename_ptr,
5353 functionname_ptr, line_ptr)
5354 bfd *abfd ATTRIBUTE_UNUSED;
5355 asection *section ATTRIBUTE_UNUSED;
5356 asymbol **symbols ATTRIBUTE_UNUSED;
5357 bfd_vma offset ATTRIBUTE_UNUSED;
5358 CONST char **filename_ptr ATTRIBUTE_UNUSED;
5359 CONST char **functionname_ptr ATTRIBUTE_UNUSED;
5360 unsigned int *line_ptr ATTRIBUTE_UNUSED;
5366 som_sizeof_headers (abfd, reloc)
5367 bfd *abfd ATTRIBUTE_UNUSED;
5368 boolean reloc ATTRIBUTE_UNUSED;
5370 (*_bfd_error_handler) (_("som_sizeof_headers unimplemented"));
5376 /* Return the single-character symbol type corresponding to
5377 SOM section S, or '?' for an unknown SOM section. */
5380 som_section_type (s)
5383 const struct section_to_type *t;
5385 for (t = &stt[0]; t->section; t++)
5386 if (!strcmp (s, t->section))
5392 som_decode_symclass (symbol)
5397 if (bfd_is_com_section (symbol->section))
5399 if (bfd_is_und_section (symbol->section))
5401 if (bfd_is_ind_section (symbol->section))
5403 if (symbol->flags & BSF_WEAK)
5405 if (!(symbol->flags & (BSF_GLOBAL|BSF_LOCAL)))
5408 if (bfd_is_abs_section (symbol->section)
5409 || (som_symbol_data (symbol) != NULL
5410 && som_symbol_data (symbol)->som_type == SYMBOL_TYPE_ABSOLUTE))
5412 else if (symbol->section)
5413 c = som_section_type (symbol->section->name);
5416 if (symbol->flags & BSF_GLOBAL)
5421 /* Return information about SOM symbol SYMBOL in RET. */
5424 som_get_symbol_info (ignore_abfd, symbol, ret)
5425 bfd *ignore_abfd ATTRIBUTE_UNUSED;
5429 ret->type = som_decode_symclass (symbol);
5430 if (ret->type != 'U')
5431 ret->value = symbol->value+symbol->section->vma;
5434 ret->name = symbol->name;
5437 /* Count the number of symbols in the archive symbol table. Necessary
5438 so that we can allocate space for all the carsyms at once. */
5441 som_bfd_count_ar_symbols (abfd, lst_header, count)
5443 struct lst_header *lst_header;
5447 unsigned int *hash_table = NULL;
5448 file_ptr lst_filepos = bfd_tell (abfd) - sizeof (struct lst_header);
5451 (unsigned int *) bfd_malloc (lst_header->hash_size
5452 * sizeof (unsigned int));
5453 if (hash_table == NULL && lst_header->hash_size != 0)
5456 /* Don't forget to initialize the counter! */
5459 /* Read in the hash table. The has table is an array of 32bit file offsets
5460 which point to the hash chains. */
5461 if (bfd_read ((PTR) hash_table, lst_header->hash_size, 4, abfd)
5462 != lst_header->hash_size * 4)
5465 /* Walk each chain counting the number of symbols found on that particular
5467 for (i = 0; i < lst_header->hash_size; i++)
5469 struct lst_symbol_record lst_symbol;
5471 /* An empty chain has zero as it's file offset. */
5472 if (hash_table[i] == 0)
5475 /* Seek to the first symbol in this hash chain. */
5476 if (bfd_seek (abfd, lst_filepos + hash_table[i], SEEK_SET) < 0)
5479 /* Read in this symbol and update the counter. */
5480 if (bfd_read ((PTR) & lst_symbol, 1, sizeof (lst_symbol), abfd)
5481 != sizeof (lst_symbol))
5486 /* Now iterate through the rest of the symbols on this chain. */
5487 while (lst_symbol.next_entry)
5490 /* Seek to the next symbol. */
5491 if (bfd_seek (abfd, lst_filepos + lst_symbol.next_entry, SEEK_SET)
5495 /* Read the symbol in and update the counter. */
5496 if (bfd_read ((PTR) & lst_symbol, 1, sizeof (lst_symbol), abfd)
5497 != sizeof (lst_symbol))
5503 if (hash_table != NULL)
5508 if (hash_table != NULL)
5513 /* Fill in the canonical archive symbols (SYMS) from the archive described
5514 by ABFD and LST_HEADER. */
5517 som_bfd_fill_in_ar_symbols (abfd, lst_header, syms)
5519 struct lst_header *lst_header;
5522 unsigned int i, len;
5523 carsym *set = syms[0];
5524 unsigned int *hash_table = NULL;
5525 struct som_entry *som_dict = NULL;
5526 file_ptr lst_filepos = bfd_tell (abfd) - sizeof (struct lst_header);
5529 (unsigned int *) bfd_malloc (lst_header->hash_size
5530 * sizeof (unsigned int));
5531 if (hash_table == NULL && lst_header->hash_size != 0)
5535 (struct som_entry *) bfd_malloc (lst_header->module_count
5536 * sizeof (struct som_entry));
5537 if (som_dict == NULL && lst_header->module_count != 0)
5540 /* Read in the hash table. The has table is an array of 32bit file offsets
5541 which point to the hash chains. */
5542 if (bfd_read ((PTR) hash_table, lst_header->hash_size, 4, abfd)
5543 != lst_header->hash_size * 4)
5546 /* Seek to and read in the SOM dictionary. We will need this to fill
5547 in the carsym's filepos field. */
5548 if (bfd_seek (abfd, lst_filepos + lst_header->dir_loc, SEEK_SET) < 0)
5551 if (bfd_read ((PTR) som_dict, lst_header->module_count,
5552 sizeof (struct som_entry), abfd)
5553 != lst_header->module_count * sizeof (struct som_entry))
5556 /* Walk each chain filling in the carsyms as we go along. */
5557 for (i = 0; i < lst_header->hash_size; i++)
5559 struct lst_symbol_record lst_symbol;
5561 /* An empty chain has zero as it's file offset. */
5562 if (hash_table[i] == 0)
5565 /* Seek to and read the first symbol on the chain. */
5566 if (bfd_seek (abfd, lst_filepos + hash_table[i], SEEK_SET) < 0)
5569 if (bfd_read ((PTR) & lst_symbol, 1, sizeof (lst_symbol), abfd)
5570 != sizeof (lst_symbol))
5573 /* Get the name of the symbol, first get the length which is stored
5574 as a 32bit integer just before the symbol.
5576 One might ask why we don't just read in the entire string table
5577 and index into it. Well, according to the SOM ABI the string
5578 index can point *anywhere* in the archive to save space, so just
5579 using the string table would not be safe. */
5580 if (bfd_seek (abfd, lst_filepos + lst_header->string_loc
5581 + lst_symbol.name.n_strx - 4, SEEK_SET) < 0)
5584 if (bfd_read (&len, 1, 4, abfd) != 4)
5587 /* Allocate space for the name and null terminate it too. */
5588 set->name = bfd_zalloc (abfd, len + 1);
5591 if (bfd_read (set->name, 1, len, abfd) != len)
5596 /* Fill in the file offset. Note that the "location" field points
5597 to the SOM itself, not the ar_hdr in front of it. */
5598 set->file_offset = som_dict[lst_symbol.som_index].location
5599 - sizeof (struct ar_hdr);
5601 /* Go to the next symbol. */
5604 /* Iterate through the rest of the chain. */
5605 while (lst_symbol.next_entry)
5607 /* Seek to the next symbol and read it in. */
5608 if (bfd_seek (abfd, lst_filepos + lst_symbol.next_entry, SEEK_SET) <0)
5611 if (bfd_read ((PTR) & lst_symbol, 1, sizeof (lst_symbol), abfd)
5612 != sizeof (lst_symbol))
5615 /* Seek to the name length & string and read them in. */
5616 if (bfd_seek (abfd, lst_filepos + lst_header->string_loc
5617 + lst_symbol.name.n_strx - 4, SEEK_SET) < 0)
5620 if (bfd_read (&len, 1, 4, abfd) != 4)
5623 /* Allocate space for the name and null terminate it too. */
5624 set->name = bfd_zalloc (abfd, len + 1);
5628 if (bfd_read (set->name, 1, len, abfd) != len)
5632 /* Fill in the file offset. Note that the "location" field points
5633 to the SOM itself, not the ar_hdr in front of it. */
5634 set->file_offset = som_dict[lst_symbol.som_index].location
5635 - sizeof (struct ar_hdr);
5637 /* Go on to the next symbol. */
5641 /* If we haven't died by now, then we successfully read the entire
5642 archive symbol table. */
5643 if (hash_table != NULL)
5645 if (som_dict != NULL)
5650 if (hash_table != NULL)
5652 if (som_dict != NULL)
5657 /* Read in the LST from the archive. */
5659 som_slurp_armap (abfd)
5662 struct lst_header lst_header;
5663 struct ar_hdr ar_header;
5664 unsigned int parsed_size;
5665 struct artdata *ardata = bfd_ardata (abfd);
5667 int i = bfd_read ((PTR) nextname, 1, 16, abfd);
5669 /* Special cases. */
5675 if (bfd_seek (abfd, (file_ptr) - 16, SEEK_CUR) < 0)
5678 /* For archives without .o files there is no symbol table. */
5679 if (strncmp (nextname, "/ ", 16))
5681 bfd_has_map (abfd) = false;
5685 /* Read in and sanity check the archive header. */
5686 if (bfd_read ((PTR) &ar_header, 1, sizeof (struct ar_hdr), abfd)
5687 != sizeof (struct ar_hdr))
5690 if (strncmp (ar_header.ar_fmag, ARFMAG, 2))
5692 bfd_set_error (bfd_error_malformed_archive);
5696 /* How big is the archive symbol table entry? */
5698 parsed_size = strtol (ar_header.ar_size, NULL, 10);
5701 bfd_set_error (bfd_error_malformed_archive);
5705 /* Save off the file offset of the first real user data. */
5706 ardata->first_file_filepos = bfd_tell (abfd) + parsed_size;
5708 /* Read in the library symbol table. We'll make heavy use of this
5709 in just a minute. */
5710 if (bfd_read ((PTR) & lst_header, 1, sizeof (struct lst_header), abfd)
5711 != sizeof (struct lst_header))
5715 if (lst_header.a_magic != LIBMAGIC)
5717 bfd_set_error (bfd_error_malformed_archive);
5721 /* Count the number of symbols in the library symbol table. */
5722 if (som_bfd_count_ar_symbols (abfd, &lst_header, &ardata->symdef_count)
5726 /* Get back to the start of the library symbol table. */
5727 if (bfd_seek (abfd, ardata->first_file_filepos - parsed_size
5728 + sizeof (struct lst_header), SEEK_SET) < 0)
5731 /* Initializae the cache and allocate space for the library symbols. */
5733 ardata->symdefs = (carsym *) bfd_alloc (abfd,
5734 (ardata->symdef_count
5735 * sizeof (carsym)));
5736 if (!ardata->symdefs)
5739 /* Now fill in the canonical archive symbols. */
5740 if (som_bfd_fill_in_ar_symbols (abfd, &lst_header, &ardata->symdefs)
5744 /* Seek back to the "first" file in the archive. Note the "first"
5745 file may be the extended name table. */
5746 if (bfd_seek (abfd, ardata->first_file_filepos, SEEK_SET) < 0)
5749 /* Notify the generic archive code that we have a symbol map. */
5750 bfd_has_map (abfd) = true;
5754 /* Begin preparing to write a SOM library symbol table.
5756 As part of the prep work we need to determine the number of symbols
5757 and the size of the associated string section. */
5760 som_bfd_prep_for_ar_write (abfd, num_syms, stringsize)
5762 unsigned int *num_syms, *stringsize;
5764 bfd *curr_bfd = abfd->archive_head;
5766 /* Some initialization. */
5770 /* Iterate over each BFD within this archive. */
5771 while (curr_bfd != NULL)
5773 unsigned int curr_count, i;
5774 som_symbol_type *sym;
5776 /* Don't bother for non-SOM objects. */
5777 if (curr_bfd->format != bfd_object
5778 || curr_bfd->xvec->flavour != bfd_target_som_flavour)
5780 curr_bfd = curr_bfd->next;
5784 /* Make sure the symbol table has been read, then snag a pointer
5785 to it. It's a little slimey to grab the symbols via obj_som_symtab,
5786 but doing so avoids allocating lots of extra memory. */
5787 if (som_slurp_symbol_table (curr_bfd) == false)
5790 sym = obj_som_symtab (curr_bfd);
5791 curr_count = bfd_get_symcount (curr_bfd);
5793 /* Examine each symbol to determine if it belongs in the
5794 library symbol table. */
5795 for (i = 0; i < curr_count; i++, sym++)
5797 struct som_misc_symbol_info info;
5799 /* Derive SOM information from the BFD symbol. */
5800 som_bfd_derive_misc_symbol_info (curr_bfd, &sym->symbol, &info);
5802 /* Should we include this symbol? */
5803 if (info.symbol_type == ST_NULL
5804 || info.symbol_type == ST_SYM_EXT
5805 || info.symbol_type == ST_ARG_EXT)
5808 /* Only global symbols and unsatisfied commons. */
5809 if (info.symbol_scope != SS_UNIVERSAL
5810 && info.symbol_type != ST_STORAGE)
5813 /* Do no include undefined symbols. */
5814 if (bfd_is_und_section (sym->symbol.section))
5817 /* Bump the various counters, being careful to honor
5818 alignment considerations in the string table. */
5820 *stringsize = *stringsize + strlen (sym->symbol.name) + 5;
5821 while (*stringsize % 4)
5825 curr_bfd = curr_bfd->next;
5830 /* Hash a symbol name based on the hashing algorithm presented in the
5833 som_bfd_ar_symbol_hash (symbol)
5836 unsigned int len = strlen (symbol->name);
5838 /* Names with length 1 are special. */
5840 return 0x1000100 | (symbol->name[0] << 16) | symbol->name[0];
5842 return ((len & 0x7f) << 24) | (symbol->name[1] << 16)
5843 | (symbol->name[len-2] << 8) | symbol->name[len-1];
5846 /* Do the bulk of the work required to write the SOM library
5850 som_bfd_ar_write_symbol_stuff (abfd, nsyms, string_size, lst, elength)
5852 unsigned int nsyms, string_size;
5853 struct lst_header lst;
5856 file_ptr lst_filepos;
5857 char *strings = NULL, *p;
5858 struct lst_symbol_record *lst_syms = NULL, *curr_lst_sym;
5860 unsigned int *hash_table = NULL;
5861 struct som_entry *som_dict = NULL;
5862 struct lst_symbol_record **last_hash_entry = NULL;
5863 unsigned int curr_som_offset, som_index = 0;
5866 (unsigned int *) bfd_malloc (lst.hash_size * sizeof (unsigned int));
5867 if (hash_table == NULL && lst.hash_size != 0)
5870 (struct som_entry *) bfd_malloc (lst.module_count
5871 * sizeof (struct som_entry));
5872 if (som_dict == NULL && lst.module_count != 0)
5876 ((struct lst_symbol_record **)
5877 bfd_malloc (lst.hash_size * sizeof (struct lst_symbol_record *)));
5878 if (last_hash_entry == NULL && lst.hash_size != 0)
5881 /* Lots of fields are file positions relative to the start
5882 of the lst record. So save its location. */
5883 lst_filepos = bfd_tell (abfd) - sizeof (struct lst_header);
5885 /* Some initialization. */
5886 memset (hash_table, 0, 4 * lst.hash_size);
5887 memset (som_dict, 0, lst.module_count * sizeof (struct som_entry));
5888 memset (last_hash_entry, 0,
5889 lst.hash_size * sizeof (struct lst_symbol_record *));
5891 /* Symbols have som_index fields, so we have to keep track of the
5892 index of each SOM in the archive.
5894 The SOM dictionary has (among other things) the absolute file
5895 position for the SOM which a particular dictionary entry
5896 describes. We have to compute that information as we iterate
5897 through the SOMs/symbols. */
5900 /* We add in the size of the archive header twice as the location
5901 in the SOM dictionary is the actual offset of the SOM, not the
5902 archive header before the SOM. */
5903 curr_som_offset = 8 + 2 * sizeof (struct ar_hdr) + lst.file_end;
5905 /* Make room for the archive header and the contents of the
5906 extended string table. Note that elength includes the size
5907 of the archive header for the extended name table! */
5909 curr_som_offset += elength;
5911 /* Make sure we're properly aligned. */
5912 curr_som_offset = (curr_som_offset + 0x1) & ~0x1;
5914 /* FIXME should be done with buffers just like everything else... */
5915 lst_syms = bfd_malloc (nsyms * sizeof (struct lst_symbol_record));
5916 if (lst_syms == NULL && nsyms != 0)
5918 strings = bfd_malloc (string_size);
5919 if (strings == NULL && string_size != 0)
5923 curr_lst_sym = lst_syms;
5925 curr_bfd = abfd->archive_head;
5926 while (curr_bfd != NULL)
5928 unsigned int curr_count, i;
5929 som_symbol_type *sym;
5931 /* Don't bother for non-SOM objects. */
5932 if (curr_bfd->format != bfd_object
5933 || curr_bfd->xvec->flavour != bfd_target_som_flavour)
5935 curr_bfd = curr_bfd->next;
5939 /* Make sure the symbol table has been read, then snag a pointer
5940 to it. It's a little slimey to grab the symbols via obj_som_symtab,
5941 but doing so avoids allocating lots of extra memory. */
5942 if (som_slurp_symbol_table (curr_bfd) == false)
5945 sym = obj_som_symtab (curr_bfd);
5946 curr_count = bfd_get_symcount (curr_bfd);
5948 for (i = 0; i < curr_count; i++, sym++)
5950 struct som_misc_symbol_info info;
5952 /* Derive SOM information from the BFD symbol. */
5953 som_bfd_derive_misc_symbol_info (curr_bfd, &sym->symbol, &info);
5955 /* Should we include this symbol? */
5956 if (info.symbol_type == ST_NULL
5957 || info.symbol_type == ST_SYM_EXT
5958 || info.symbol_type == ST_ARG_EXT)
5961 /* Only global symbols and unsatisfied commons. */
5962 if (info.symbol_scope != SS_UNIVERSAL
5963 && info.symbol_type != ST_STORAGE)
5966 /* Do no include undefined symbols. */
5967 if (bfd_is_und_section (sym->symbol.section))
5970 /* If this is the first symbol from this SOM, then update
5971 the SOM dictionary too. */
5972 if (som_dict[som_index].location == 0)
5974 som_dict[som_index].location = curr_som_offset;
5975 som_dict[som_index].length = arelt_size (curr_bfd);
5978 /* Fill in the lst symbol record. */
5979 curr_lst_sym->hidden = 0;
5980 curr_lst_sym->secondary_def = info.secondary_def;
5981 curr_lst_sym->symbol_type = info.symbol_type;
5982 curr_lst_sym->symbol_scope = info.symbol_scope;
5983 curr_lst_sym->check_level = 0;
5984 curr_lst_sym->must_qualify = 0;
5985 curr_lst_sym->initially_frozen = 0;
5986 curr_lst_sym->memory_resident = 0;
5987 curr_lst_sym->is_common = bfd_is_com_section (sym->symbol.section);
5988 curr_lst_sym->dup_common = 0;
5989 curr_lst_sym->xleast = 3;
5990 curr_lst_sym->arg_reloc = info.arg_reloc;
5991 curr_lst_sym->name.n_strx = p - strings + 4;
5992 curr_lst_sym->qualifier_name.n_strx = 0;
5993 curr_lst_sym->symbol_info = info.symbol_info;
5994 curr_lst_sym->symbol_value = info.symbol_value | info.priv_level;
5995 curr_lst_sym->symbol_descriptor = 0;
5996 curr_lst_sym->reserved = 0;
5997 curr_lst_sym->som_index = som_index;
5998 curr_lst_sym->symbol_key = som_bfd_ar_symbol_hash (&sym->symbol);
5999 curr_lst_sym->next_entry = 0;
6001 /* Insert into the hash table. */
6002 if (hash_table[curr_lst_sym->symbol_key % lst.hash_size])
6004 struct lst_symbol_record *tmp;
6006 /* There is already something at the head of this hash chain,
6007 so tack this symbol onto the end of the chain. */
6008 tmp = last_hash_entry[curr_lst_sym->symbol_key % lst.hash_size];
6010 = (curr_lst_sym - lst_syms) * sizeof (struct lst_symbol_record)
6012 + lst.module_count * sizeof (struct som_entry)
6013 + sizeof (struct lst_header);
6017 /* First entry in this hash chain. */
6018 hash_table[curr_lst_sym->symbol_key % lst.hash_size]
6019 = (curr_lst_sym - lst_syms) * sizeof (struct lst_symbol_record)
6021 + lst.module_count * sizeof (struct som_entry)
6022 + sizeof (struct lst_header);
6025 /* Keep track of the last symbol we added to this chain so we can
6026 easily update its next_entry pointer. */
6027 last_hash_entry[curr_lst_sym->symbol_key % lst.hash_size]
6031 /* Update the string table. */
6032 bfd_put_32 (abfd, strlen (sym->symbol.name), p);
6034 strcpy (p, sym->symbol.name);
6035 p += strlen (sym->symbol.name) + 1;
6038 bfd_put_8 (abfd, 0, p);
6042 /* Head to the next symbol. */
6046 /* Keep track of where each SOM will finally reside; then look
6048 curr_som_offset += arelt_size (curr_bfd) + sizeof (struct ar_hdr);
6050 /* A particular object in the archive may have an odd length; the
6051 linker requires objects begin on an even boundary. So round
6052 up the current offset as necessary. */
6053 curr_som_offset = (curr_som_offset + 0x1) & ~0x1;
6054 curr_bfd = curr_bfd->next;
6058 /* Now scribble out the hash table. */
6059 if (bfd_write ((PTR) hash_table, lst.hash_size, 4, abfd)
6060 != lst.hash_size * 4)
6063 /* Then the SOM dictionary. */
6064 if (bfd_write ((PTR) som_dict, lst.module_count,
6065 sizeof (struct som_entry), abfd)
6066 != lst.module_count * sizeof (struct som_entry))
6069 /* The library symbols. */
6070 if (bfd_write ((PTR) lst_syms, nsyms, sizeof (struct lst_symbol_record), abfd)
6071 != nsyms * sizeof (struct lst_symbol_record))
6074 /* And finally the strings. */
6075 if (bfd_write ((PTR) strings, string_size, 1, abfd) != string_size)
6078 if (hash_table != NULL)
6080 if (som_dict != NULL)
6082 if (last_hash_entry != NULL)
6083 free (last_hash_entry);
6084 if (lst_syms != NULL)
6086 if (strings != NULL)
6091 if (hash_table != NULL)
6093 if (som_dict != NULL)
6095 if (last_hash_entry != NULL)
6096 free (last_hash_entry);
6097 if (lst_syms != NULL)
6099 if (strings != NULL)
6105 /* Write out the LST for the archive.
6107 You'll never believe this is really how armaps are handled in SOM... */
6111 som_write_armap (abfd, elength, map, orl_count, stridx)
6113 unsigned int elength;
6114 struct orl *map ATTRIBUTE_UNUSED;
6115 unsigned int orl_count ATTRIBUTE_UNUSED;
6116 int stridx ATTRIBUTE_UNUSED;
6119 struct stat statbuf;
6120 unsigned int i, lst_size, nsyms, stringsize;
6122 struct lst_header lst;
6125 /* We'll use this for the archive's date and mode later. */
6126 if (stat (abfd->filename, &statbuf) != 0)
6128 bfd_set_error (bfd_error_system_call);
6132 bfd_ardata (abfd)->armap_timestamp = statbuf.st_mtime + 60;
6134 /* Account for the lst header first. */
6135 lst_size = sizeof (struct lst_header);
6137 /* Start building the LST header. */
6138 /* FIXME: Do we need to examine each element to determine the
6139 largest id number? */
6140 lst.system_id = CPU_PA_RISC1_0;
6141 lst.a_magic = LIBMAGIC;
6142 lst.version_id = VERSION_ID;
6143 lst.file_time.secs = 0;
6144 lst.file_time.nanosecs = 0;
6146 lst.hash_loc = lst_size;
6147 lst.hash_size = SOM_LST_HASH_SIZE;
6149 /* Hash table is a SOM_LST_HASH_SIZE 32bit offsets. */
6150 lst_size += 4 * SOM_LST_HASH_SIZE;
6152 /* We need to count the number of SOMs in this archive. */
6153 curr_bfd = abfd->archive_head;
6154 lst.module_count = 0;
6155 while (curr_bfd != NULL)
6157 /* Only true SOM objects count. */
6158 if (curr_bfd->format == bfd_object
6159 && curr_bfd->xvec->flavour == bfd_target_som_flavour)
6161 curr_bfd = curr_bfd->next;
6163 lst.module_limit = lst.module_count;
6164 lst.dir_loc = lst_size;
6165 lst_size += sizeof (struct som_entry) * lst.module_count;
6167 /* We don't support import/export tables, auxiliary headers,
6168 or free lists yet. Make the linker work a little harder
6169 to make our life easier. */
6172 lst.export_count = 0;
6177 /* Count how many symbols we will have on the hash chains and the
6178 size of the associated string table. */
6179 if (som_bfd_prep_for_ar_write (abfd, &nsyms, &stringsize) == false)
6182 lst_size += sizeof (struct lst_symbol_record) * nsyms;
6184 /* For the string table. One day we might actually use this info
6185 to avoid small seeks/reads when reading archives. */
6186 lst.string_loc = lst_size;
6187 lst.string_size = stringsize;
6188 lst_size += stringsize;
6190 /* SOM ABI says this must be zero. */
6192 lst.file_end = lst_size;
6194 /* Compute the checksum. Must happen after the entire lst header
6198 for (i = 0; i < sizeof (struct lst_header)/sizeof (int) - 1; i++)
6199 lst.checksum ^= *p++;
6201 sprintf (hdr.ar_name, "/ ");
6202 sprintf (hdr.ar_date, "%ld", bfd_ardata (abfd)->armap_timestamp);
6203 sprintf (hdr.ar_uid, "%ld", (long) getuid ());
6204 sprintf (hdr.ar_gid, "%ld", (long) getgid ());
6205 sprintf (hdr.ar_mode, "%-8o", (unsigned int) statbuf.st_mode);
6206 sprintf (hdr.ar_size, "%-10d", (int) lst_size);
6207 hdr.ar_fmag[0] = '`';
6208 hdr.ar_fmag[1] = '\012';
6210 /* Turn any nulls into spaces. */
6211 for (i = 0; i < sizeof (struct ar_hdr); i++)
6212 if (((char *) (&hdr))[i] == '\0')
6213 (((char *) (&hdr))[i]) = ' ';
6215 /* Scribble out the ar header. */
6216 if (bfd_write ((PTR) &hdr, 1, sizeof (struct ar_hdr), abfd)
6217 != sizeof (struct ar_hdr))
6220 /* Now scribble out the lst header. */
6221 if (bfd_write ((PTR) &lst, 1, sizeof (struct lst_header), abfd)
6222 != sizeof (struct lst_header))
6225 /* Build and write the armap. */
6226 if (som_bfd_ar_write_symbol_stuff (abfd, nsyms, stringsize, lst, elength)
6234 /* Free all information we have cached for this BFD. We can always
6235 read it again later if we need it. */
6238 som_bfd_free_cached_info (abfd)
6243 if (bfd_get_format (abfd) != bfd_object)
6246 #define FREE(x) if (x != NULL) { free (x); x = NULL; }
6247 /* Free the native string and symbol tables. */
6248 FREE (obj_som_symtab (abfd));
6249 FREE (obj_som_stringtab (abfd));
6250 for (o = abfd->sections; o != (asection *) NULL; o = o->next)
6252 /* Free the native relocations. */
6253 o->reloc_count = -1;
6254 FREE (som_section_data (o)->reloc_stream);
6255 /* Free the generic relocations. */
6256 FREE (o->relocation);
6263 /* End of miscellaneous support functions. */
6265 /* Linker support functions. */
6267 som_bfd_link_split_section (abfd, sec)
6268 bfd *abfd ATTRIBUTE_UNUSED;
6271 return (som_is_subspace (sec) && sec->_raw_size > 240000);
6274 #define som_close_and_cleanup som_bfd_free_cached_info
6276 #define som_read_ar_hdr _bfd_generic_read_ar_hdr
6277 #define som_openr_next_archived_file bfd_generic_openr_next_archived_file
6278 #define som_get_elt_at_index _bfd_generic_get_elt_at_index
6279 #define som_generic_stat_arch_elt bfd_generic_stat_arch_elt
6280 #define som_truncate_arname bfd_bsd_truncate_arname
6281 #define som_slurp_extended_name_table _bfd_slurp_extended_name_table
6282 #define som_construct_extended_name_table \
6283 _bfd_archive_coff_construct_extended_name_table
6284 #define som_update_armap_timestamp bfd_true
6285 #define som_bfd_print_private_bfd_data _bfd_generic_bfd_print_private_bfd_data
6287 #define som_get_lineno _bfd_nosymbols_get_lineno
6288 #define som_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
6289 #define som_read_minisymbols _bfd_generic_read_minisymbols
6290 #define som_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
6291 #define som_get_section_contents_in_window \
6292 _bfd_generic_get_section_contents_in_window
6294 #define som_bfd_get_relocated_section_contents \
6295 bfd_generic_get_relocated_section_contents
6296 #define som_bfd_relax_section bfd_generic_relax_section
6297 #define som_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
6298 #define som_bfd_link_add_symbols _bfd_generic_link_add_symbols
6299 #define som_bfd_final_link _bfd_generic_final_link
6301 #define som_bfd_gc_sections bfd_generic_gc_sections
6304 const bfd_target som_vec =
6307 bfd_target_som_flavour,
6308 BFD_ENDIAN_BIG, /* target byte order */
6309 BFD_ENDIAN_BIG, /* target headers byte order */
6310 (HAS_RELOC | EXEC_P | /* object flags */
6311 HAS_LINENO | HAS_DEBUG |
6312 HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED | DYNAMIC),
6313 (SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
6314 | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
6316 /* leading_symbol_char: is the first char of a user symbol
6317 predictable, and if so what is it */
6319 '/', /* ar_pad_char */
6320 14, /* ar_max_namelen */
6321 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
6322 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
6323 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
6324 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
6325 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
6326 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
6328 som_object_p, /* bfd_check_format */
6329 bfd_generic_archive_p,
6335 _bfd_generic_mkarchive,
6340 som_write_object_contents,
6341 _bfd_write_archive_contents,
6346 BFD_JUMP_TABLE_GENERIC (som),
6347 BFD_JUMP_TABLE_COPY (som),
6348 BFD_JUMP_TABLE_CORE (_bfd_nocore),
6349 BFD_JUMP_TABLE_ARCHIVE (som),
6350 BFD_JUMP_TABLE_SYMBOLS (som),
6351 BFD_JUMP_TABLE_RELOCS (som),
6352 BFD_JUMP_TABLE_WRITE (som),
6353 BFD_JUMP_TABLE_LINK (som),
6354 BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic),
6361 #endif /* HOST_HPPAHPUX || HOST_HPPABSD || HOST_HPPAOSF */