* hppa.c (hppa_object_setup): Get rid of all knowledge of stabs
[deliverable/binutils-gdb.git] / bfd / hppa.c
CommitLineData
e3c01e92
SG
1/* bfd back-end for HP PA-RISC SOM objects.
2 Copyright (C) 1990-1991 Free Software Foundation, Inc.
3
4 Contributed by the Center for Software Science at the
5 University of Utah (pa-gdb-bugs@cs.utah.edu).
6
7This file is part of BFD, the Binary File Descriptor library.
8
9This program is free software; you can redistribute it and/or modify
10it under the terms of the GNU General Public License as published by
11the Free Software Foundation; either version 2 of the License, or
12(at your option) any later version.
13
14This program is distributed in the hope that it will be useful,
15but WITHOUT ANY WARRANTY; without even the implied warranty of
16MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17GNU General Public License for more details.
18
19You should have received a copy of the GNU General Public License
20along with this program; if not, write to the Free Software
21Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
22
e3c01e92 23#include "bfd.h"
76c7e44d 24#include "sysdep.h"
205d660d
SG
25
26#ifdef HOST_HPPAHPUX
27
e3c01e92
SG
28#include "libbfd.h"
29#include "libhppa.h"
30
e3c01e92
SG
31#include <stdio.h>
32#include <sys/types.h>
33#include <sys/param.h>
34#include <sys/dir.h>
35#include <signal.h>
36#include <machine/reg.h>
e3c01e92 37#include <sys/user.h> /* After a.out.h */
e3c01e92
SG
38#include <sys/file.h>
39#include <errno.h>
40
41struct container {
42 struct header f;
43 struct som_exec_auxhdr e;
44};
45
edff0587
SG
46static bfd_target *
47hppa_object_setup (abfd, file_hdrp, aux_hdrp)
e3c01e92 48 bfd *abfd;
edff0587
SG
49 struct header *file_hdrp;
50 struct som_exec_auxhdr *aux_hdrp;
e3c01e92
SG
51{
52 struct container *rawptr;
53 struct header *f;
54 struct hppa_data_struct *rawptr1;
d0a650a4 55 asection *text, *data, *bss;
e3c01e92
SG
56
57 rawptr = (struct container *) bfd_zalloc (abfd, sizeof (struct container));
58 if (rawptr == NULL) {
59 bfd_error = no_memory;
60 return 0;
61 }
62
63 rawptr1 = (struct hppa_data_struct *) bfd_zalloc (abfd, sizeof (struct hppa_data_struct));
64 if (rawptr1 == NULL) {
65 bfd_error = no_memory;
66 return 0;
67 }
68
69 abfd->tdata.hppa_data = rawptr1;
70 obj_file_hdr (abfd) = &rawptr->f;
71 obj_aux_hdr (abfd) = &rawptr->e;
72 *obj_file_hdr (abfd) = *file_hdrp;
73 *obj_aux_hdr (abfd) = *aux_hdrp;
74
75 /* Set the file flags */
76 abfd->flags = NO_FLAGS;
77 if (file_hdrp->entry_offset)
78 abfd->flags |= HAS_RELOC;
79 if (file_hdrp->symbol_total)
80 abfd->flags |= HAS_LINENO | HAS_DEBUG | HAS_SYMS | HAS_LOCALS;
81
82 bfd_get_start_address (abfd) = aux_hdrp->exec_entry;
83
e3c01e92 84 obj_pa_symbols (abfd) = (hppa_symbol_type *)NULL;
d0a650a4 85 bfd_get_symcount (abfd) = file_hdrp->symbol_total;
e3c01e92
SG
86
87 bfd_default_set_arch_mach(abfd, bfd_arch_hppa, 0);
88
89 /* create the sections. This is raunchy, but bfd_close wants to reclaim
90 them */
d0a650a4
SG
91
92 text = bfd_make_section(abfd, ".text");
93 data = bfd_make_section(abfd, ".data");
94 bss = bfd_make_section(abfd, ".bss");
95
96 text->_raw_size = aux_hdrp->exec_tsize;
97 data->_raw_size = aux_hdrp->exec_dsize;
98 bss->_raw_size = aux_hdrp->exec_bsize;
99
100 text->flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS);
101 data->flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS);
102 bss->flags = SEC_ALLOC;
e3c01e92
SG
103
104 /* The virtual memory addresses of the sections */
d0a650a4
SG
105 text->vma = aux_hdrp->exec_tmem;
106 data->vma = aux_hdrp->exec_dmem;
107 bss->vma = aux_hdrp->exec_bfill;
e3c01e92
SG
108
109 /* The file offsets of the sections */
d0a650a4
SG
110 text->filepos = aux_hdrp->exec_tfile;
111 data->filepos = aux_hdrp->exec_dfile;
e3c01e92
SG
112
113 /* The file offsets of the relocation info */
d0a650a4
SG
114 text->rel_filepos = 0;
115 data->rel_filepos = 0;
e3c01e92
SG
116
117 /* The file offsets of the string table and symbol table. */
d0a650a4
SG
118 obj_sym_filepos (abfd) = file_hdrp->symbol_location;
119 bfd_get_symcount (abfd) = file_hdrp->symbol_total;
120 obj_str_filepos (abfd) = file_hdrp->symbol_strings_location;
121 obj_stringtab_size (abfd) = file_hdrp->symbol_strings_size;
e3c01e92
SG
122
123 return abfd->xvec;
124}
125
edff0587
SG
126/* Create a new BFD section for NAME. If NAME already exists, then create a
127 new unique name, with NAME as the prefix. This exists because SOM .o files
128 created by the native compiler can have a $CODE$ section for each
129 subroutine.
130 */
131
132static asection *
133make_unique_section (abfd, name, num)
134 bfd *abfd;
135 CONST char *name;
136 int num;
137{
138 asection *sect;
139 char *newname;
140 char altname[100];
141
142 sect = bfd_make_section (abfd, name);
143 while (!sect)
144 {
145 sprintf(altname, "%s-%d", name, num++);
146 sect = bfd_make_section (abfd, altname);
147 }
148
149 newname = bfd_alloc (abfd, strlen(sect->name) + 1);
150 strcpy (newname, sect->name);
151
152 sect->name = newname;
153 return sect;
154}
155
156/* Convert all of the space and subspace info into BFD sections. Each space
157 contains a number of subspaces, which in turn describe the mapping between
158 regions of the exec file, and the address space that the program runs in.
159 BFD sections which correspond to spaces will overlap the sections for the
160 associated subspaces. */
161
162static int
163setup_sections (abfd, file_hdr)
164 bfd *abfd;
165 struct header *file_hdr;
166{
167 char *space_strings;
168 int space_index;
169
170/* First, read in space names */
171
172 space_strings = alloca (file_hdr->space_strings_size);
173 if (!space_strings)
174 return 0;
175
176 if (bfd_seek (abfd, file_hdr->space_strings_location, SEEK_SET) < 0)
177 return 0;
178 if (bfd_read (space_strings, 1, file_hdr->space_strings_size, abfd)
179 != file_hdr->space_strings_size)
180 return 0;
181
182 /* Loop over all of the space dictionaries, building up sections */
183
184 for (space_index = 0; space_index < file_hdr->space_total; space_index++)
185 {
186 struct space_dictionary_record space;
187 struct subspace_dictionary_record subspace;
188 int subspace_index, tmp;
189 asection *space_asect;
190
191 /* Read the space dictionary element */
192 if (bfd_seek (abfd, file_hdr->space_location
193 + space_index * sizeof space, SEEK_SET) < 0)
194 return 0;
195 if (bfd_read (&space, 1, sizeof space, abfd) != sizeof space)
196 return 0;
197
198 /* Setup the space name string */
199 space.name.n_name = space.name.n_strx + space_strings;
200
201 /* Make a section out of it */
202 space_asect = make_unique_section (abfd, space.name.n_name, space_index);
203 if (!space_asect)
204 return 0;
205
206 /* Now, read in the first subspace for this space */
207 if (bfd_seek (abfd, file_hdr->subspace_location
208 + space.subspace_index * sizeof subspace,
209 SEEK_SET) < 0)
210 return 0;
211 if (bfd_read (&subspace, 1, sizeof subspace, abfd) != sizeof subspace)
212 return 0;
213 /* Seek back to the start of the subspaces for loop below */
214 if (bfd_seek (abfd, file_hdr->subspace_location
215 + space.subspace_index * sizeof subspace,
216 SEEK_SET) < 0)
217 return 0;
218
219 /* Setup the section flags as appropriate (this is somewhat bogus, as
220 there isn't a clear mapping between what's in the space record, and
221 what BFD can describe here). */
222 if (space.is_loadable)
223 space_asect->flags |= SEC_ALLOC;
224 if (space.is_defined)
225 space_asect->flags |= SEC_LOAD;
226
227 /* Setup the start address and file loc from the first subspace record */
228 space_asect->vma = subspace.subspace_start;
229 space_asect->filepos = subspace.file_loc_init_value;
230 space_asect->alignment_power = subspace.alignment;
231
232 /* Loop over the rest of the subspaces, building up more sections */
233 for (subspace_index = 0; subspace_index < space.subspace_quantity;
234 subspace_index++)
235 {
236 asection *subspace_asect;
237
238 /* Read in the next subspace */
239 if (bfd_read (&subspace, 1, sizeof subspace, abfd)
240 != sizeof subspace)
241 return 0;
242
243 /* Setup the subspace name string */
244 subspace.name.n_name = subspace.name.n_strx + space_strings;
245
246 /* Make a section out of this subspace */
247 subspace_asect = make_unique_section (abfd, subspace.name.n_name,
248 space.subspace_index + subspace_index);
249
250 if (!subspace_asect)
251 return 0;
252
253 if (subspace.is_loadable)
254 subspace_asect->flags |= SEC_ALLOC | SEC_LOAD;
255 if (subspace.code_only)
256 subspace_asect->flags |= SEC_CODE;
257
258 subspace_asect->vma = subspace.subspace_start;
259 subspace_asect->_cooked_size = subspace.subspace_length;
260 subspace_asect->_raw_size = subspace.initialization_length;
261 subspace_asect->alignment_power = subspace.alignment;
262 subspace_asect->filepos = subspace.file_loc_init_value;
263
264 }
265 /* Setup the sizes for the space section based upon the info in the
266 last subspace of the space. */
267 space_asect->_cooked_size = (subspace.subspace_start - space_asect->vma)
268 + subspace.subspace_length;
269 space_asect->_raw_size = (subspace.file_loc_init_value
270 - space_asect->filepos)
271 + subspace.initialization_length;
272 }
273}
274
275static bfd_target *
276hppa_object_p (abfd)
277 bfd *abfd;
e3c01e92
SG
278{
279 struct header file_hdr;
280 struct som_exec_auxhdr aux_hdr;
e3c01e92
SG
281
282 if (bfd_read ((PTR) &file_hdr, 1, FILE_HDR_SIZE, abfd) != FILE_HDR_SIZE)
edff0587
SG
283 return 0;
284
285 if (!_PA_RISC_ID (file_hdr.system_id))
e3c01e92
SG
286 {
287 bfd_error = wrong_format;
288 return 0;
289 }
205d660d 290
205d660d
SG
291 switch (file_hdr.a_magic)
292 {
edff0587 293 case RELOC_MAGIC: /* I'm not really sure about all of these types... */
205d660d
SG
294 case EXEC_MAGIC:
295 case SHARE_MAGIC:
296 case DEMAND_MAGIC:
297 case DL_MAGIC:
298 case SHL_MAGIC:
299 break;
300 default:
edff0587 301 bfd_error = wrong_format;
205d660d
SG
302 return 0;
303 }
304
edff0587
SG
305 if (file_hdr.version_id != VERSION_ID
306 && file_hdr.version_id != NEW_VERSION_ID)
e3c01e92
SG
307 {
308 bfd_error = wrong_format;
309 return 0;
310 }
e3c01e92 311
edff0587
SG
312 if (bfd_read ((PTR) &aux_hdr, 1, AUX_HDR_SIZE, abfd) != AUX_HDR_SIZE)
313 bfd_error = wrong_format;
e3c01e92 314
edff0587
SG
315 if (!setup_sections (abfd, &file_hdr))
316 return 0;
317
318 return hppa_object_setup(abfd, &file_hdr, &aux_hdr);
319}
e3c01e92
SG
320
321static boolean
322DEFUN(hppa_mkobject,(abfd),
323 bfd *abfd)
324{
325 fprintf (stderr, "hppa_mkobject unimplemented\n");
326 fflush (stderr);
327 abort ();
328 return (false);
329}
330
331boolean
332DEFUN(hppa_write_object_contents,(abfd),
333 bfd *abfd)
334{
335 fprintf (stderr, "hppa_write_object_contents unimplemented\n");
336 fflush (stderr);
337 abort ();
338 return (false);
339}
340
edff0587
SG
341static unsigned int
342hppa_get_symtab_upper_bound (abfd)
343 bfd *abfd;
e3c01e92
SG
344{
345 fprintf (stderr, "hppa_get_symtab_upper_bound unimplemented\n");
346 fflush (stderr);
347 abort ();
348 return (0);
349}
350
edff0587
SG
351static unsigned int
352hppa_get_reloc_upper_bound (abfd, asect)
353 bfd *abfd;
354 sec_ptr asect;
e3c01e92
SG
355{
356 fprintf (stderr, "hppa_get_reloc_upper_bound unimplemented\n");
357 fflush (stderr);
358 abort ();
359 return (0);
360}
361
edff0587
SG
362static unsigned int
363hppa_canonicalize_reloc (abfd, section, relptr, symbols)
364 bfd *abfd;
365 sec_ptr section;
366 arelent **relptr;
367 asymbol **symbols;
e3c01e92
SG
368{
369 fprintf (stderr, "hppa_canonicalize_reloc unimplemented\n");
370 fflush (stderr);
371 abort ();
372}
373
374extern bfd_target hppa_vec;
edff0587
SG
375
376static unsigned int
377hppa_get_symtab (abfd, location)
378 bfd *abfd;
379 asymbol **location;
e3c01e92
SG
380{
381 fprintf (stderr, "hppa_get_symtab unimplemented\n");
382 fflush (stderr);
383 abort ();
384 return (0);
385}
386
edff0587
SG
387static asymbol *
388hppa_make_empty_symbol (abfd)
389 bfd *abfd;
e3c01e92
SG
390{
391 hppa_symbol_type *new =
392 (hppa_symbol_type *)bfd_zalloc (abfd, sizeof (hppa_symbol_type));
393 new->symbol.the_bfd = abfd;
394
395 return &new->symbol;
396}
397
edff0587
SG
398static void
399hppa_print_symbol (ignore_abfd, afile, symbol, how)
400 bfd *ignore_abfd;
401 PTR afile;
402 asymbol *symbol;
403 bfd_print_symbol_type how;
e3c01e92
SG
404{
405 fprintf (stderr, "hppa_print_symbol unimplemented\n");
406 fflush (stderr);
407 abort ();
408}
409
edff0587
SG
410static boolean
411hppa_new_section_hook (abfd, newsect)
412 bfd *abfd;
413 asection *newsect;
e3c01e92 414{
e3c01e92
SG
415 newsect->alignment_power = 3;
416
e3c01e92
SG
417 /* We allow more than three sections internally */
418 return true;
419}
420
edff0587
SG
421static boolean
422hppa_set_section_contents (abfd, section, location, offset, count)
423 bfd *abfd;
424 sec_ptr section;
425 PTR location;
426 file_ptr offset;
427 bfd_size_type count;
e3c01e92
SG
428{
429 fprintf (stderr, "hppa_set_section_contents unimplimented\n");
430 fflush (stderr);
431 abort();
432 return false;
433}
434
edff0587
SG
435static boolean
436hppa_set_arch_mach (abfd, arch, machine)
437 bfd *abfd;
438 enum bfd_architecture arch;
439 unsigned long machine;
e3c01e92
SG
440{
441 fprintf (stderr, "hppa_set_arch_mach unimplemented\n");
442 fflush (stderr);
443 /* Allow any architecture to be supported by the hppa backend */
444 return bfd_default_set_arch_mach(abfd, arch, machine);
445}
446
e3c01e92 447static boolean
edff0587
SG
448hppa_find_nearest_line (abfd, section, symbols, offset, filename_ptr,
449 functionname_ptr, line_ptr)
450 bfd *abfd;
451 asection *section;
452 asymbol **symbols;
453 bfd_vma offset;
454 CONST char **filename_ptr;
455 CONST char **functionname_ptr;
456 unsigned int *line_ptr;
e3c01e92
SG
457{
458 fprintf (stderr, "hppa_find_nearest_line unimplemented\n");
459 fflush (stderr);
460 abort ();
461 return (false);
462}
463
464static int
edff0587
SG
465hppa_sizeof_headers (abfd, reloc)
466 bfd *abfd;
467 boolean reloc;
e3c01e92
SG
468{
469 fprintf (stderr, "hppa_sizeof_headers unimplemented\n");
470 fflush (stderr);
471 abort ();
472 return (0);
473}
474
205d660d
SG
475static asection *
476make_bfd_asection (abfd, name, flags, _raw_size, vma, alignment_power)
e3c01e92 477 bfd *abfd;
75dd6a3e 478 CONST char *name;
205d660d
SG
479 flagword flags;
480 bfd_size_type _raw_size;
481 bfd_vma vma;
482 unsigned int alignment_power;
e3c01e92 483{
205d660d 484 asection *asect;
e3c01e92 485
edff0587 486 asect = bfd_make_section (abfd, name);
205d660d 487 if (!asect)
edff0587 488 return NULL;
e3c01e92 489
205d660d
SG
490 asect->flags = flags;
491 asect->_raw_size = _raw_size;
492 asect->vma = vma;
493 asect->filepos = bfd_tell (abfd);
494 asect->alignment_power = alignment_power;
e3c01e92 495
205d660d
SG
496 return asect;
497}
498
edff0587 499static bfd_target *
205d660d
SG
500hppa_core_file_p (abfd)
501 bfd *abfd;
502{
503 core_hdr (abfd) = bfd_zalloc (abfd, sizeof (struct hppa_core_struct));
504 if (!core_hdr (abfd))
505 return NULL;
e3c01e92 506
205d660d
SG
507 while (1)
508 {
509 int val;
510 struct corehead core_header;
511
512 val = bfd_read ((void *)&core_header, 1, sizeof core_header, abfd);
513 if (val <= 0)
514 break;
515 switch (core_header.type)
516 {
517 case CORE_KERNEL:
518 case CORE_FORMAT:
519 bfd_seek (abfd, core_header.len, SEEK_CUR); /* Just skip this */
520 break;
521 case CORE_EXEC:
522 {
523 struct proc_exec proc_exec;
524 bfd_read ((void *)&proc_exec, 1, core_header.len, abfd);
525 strncpy (core_command (abfd), proc_exec.cmd, MAXCOMLEN + 1);
526 }
527 break;
528 case CORE_PROC:
529 {
530 struct proc_info proc_info;
531 core_regsec (abfd) = make_bfd_asection (abfd, ".reg",
532 SEC_ALLOC+SEC_HAS_CONTENTS,
533 core_header.len,
534 (int)&proc_info - (int)&proc_info.hw_regs,
535 2);
536 bfd_read (&proc_info, 1, core_header.len, abfd);
537 core_signal (abfd) = proc_info.sig;
538 }
539 if (!core_regsec (abfd))
540 return NULL;
541 break;
542 case CORE_DATA:
543 core_datasec (abfd) = make_bfd_asection (abfd, ".data",
544 SEC_ALLOC+SEC_LOAD+SEC_HAS_CONTENTS,
545 core_header.len,
546 core_header.addr,
547 2);
548 if (!core_datasec (abfd))
549 return NULL;
550 bfd_seek (abfd, core_header.len, SEEK_CUR);
551 break;
552 case CORE_STACK:
edff0587 553 core_stacksec (abfd) = make_bfd_asection (abfd, ".stack",
205d660d
SG
554 SEC_ALLOC+SEC_LOAD+SEC_HAS_CONTENTS,
555 core_header.len,
556 core_header.addr,
557 2);
558 if (!core_stacksec (abfd))
559 return NULL;
560 bfd_seek (abfd, core_header.len, SEEK_CUR);
561 break;
562 default:
563 fprintf (stderr, "Unknown HPPA/HPUX core file section type %d\n",
564 core_header.type);
565 bfd_seek (abfd, core_header.len, SEEK_CUR);
566 break;
567 }
568 }
e3c01e92 569
205d660d 570 /* OK, we believe you. You're a core file (sure, sure). */
e3c01e92
SG
571
572 return abfd->xvec;
573}
e3c01e92 574
edff0587 575static char *
e3c01e92
SG
576hppa_core_file_failing_command (abfd)
577 bfd *abfd;
578{
205d660d 579 return core_command (abfd);
e3c01e92 580}
e3c01e92
SG
581
582/* ARGSUSED */
edff0587 583static int
205d660d
SG
584hppa_core_file_failing_signal (abfd)
585 bfd *abfd;
e3c01e92 586{
205d660d 587 return core_signal (abfd);
e3c01e92
SG
588}
589
590/* ARGSUSED */
edff0587 591static boolean
e3c01e92
SG
592hppa_core_file_matches_executable_p (core_bfd, exec_bfd)
593 bfd *core_bfd, *exec_bfd;
594{
595 return true; /* FIXME, We have no way of telling at this point */
596}
597
598#define hppa_bfd_debug_info_start bfd_void
599#define hppa_bfd_debug_info_end bfd_void
600#define hppa_bfd_debug_info_accumulate (PROTO(void,(*),(bfd*, struct sec *))) bfd_void
601
602
603
604#define hppa_openr_next_archived_file bfd_generic_openr_next_archived_file
605#define hppa_generic_stat_arch_elt bfd_generic_stat_arch_elt
606#define hppa_slurp_armap bfd_false
607#define hppa_slurp_extended_name_table _bfd_slurp_extended_name_table
608#define hppa_truncate_arname (void (*)())bfd_nullvoidptr
609#define hppa_write_armap 0
610
611#define hppa_get_lineno (struct lineno_cache_entry *(*)())bfd_nullvoidptr
612#define hppa_close_and_cleanup bfd_generic_close_and_cleanup
613#define hppa_get_section_contents bfd_generic_get_section_contents
614
615#define hppa_bfd_get_relocated_section_contents \
616 bfd_generic_get_relocated_section_contents
617#define hppa_bfd_relax_section bfd_generic_relax_section
618
e3c01e92
SG
619bfd_target hppa_vec =
620{
621 "hppa", /* name */
622 bfd_target_hppa_flavour,
623 true, /* target byte order */
624 true, /* target headers byte order */
625 (HAS_RELOC | EXEC_P | /* object flags */
626 HAS_LINENO | HAS_DEBUG |
627 HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
628 (SEC_CODE|SEC_DATA|SEC_ROM|SEC_HAS_CONTENTS
629 |SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
4e98653c
SC
630
631 /* leading_symbol_char: is the first char of a user symbol
632 predictable, and if so what is it */
633 0,
e3c01e92
SG
634 ' ', /* ar_pad_char */
635 16, /* ar_max_namelen */
636 3, /* minimum alignment */
637_do_getb64, _do_putb64, _do_getb32, _do_putb32, _do_getb16, _do_putb16, /* data */
638_do_getb64, _do_putb64, _do_getb32, _do_putb32, _do_getb16, _do_putb16, /* hdrs */
e3c01e92
SG
639 { _bfd_dummy_target,
640 hppa_object_p, /* bfd_check_format */
641 bfd_generic_archive_p,
642 hppa_core_file_p,
643 },
644 {
645 bfd_false,
646 hppa_mkobject,
647 _bfd_generic_mkarchive,
648 bfd_false
649 },
650 {
651 bfd_false,
652 hppa_write_object_contents,
653 _bfd_write_archive_contents,
654 bfd_false,
655 },
acc7c493 656#undef hppa
e3c01e92
SG
657 JUMP_TABLE(hppa)
658};
659
205d660d 660#endif /* HOST_HPPAHPUX */
This page took 0.061403 seconds and 4 git commands to generate.