160484Sobrien/* BFD back-end for PPCbug boot records.
2218822Sdim   Copyright 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2006,
3218822Sdim   2007 Free Software Foundation, Inc.
460484Sobrien   Written by Michael Meissner, Cygnus Support, <meissner@cygnus.com>
560484Sobrien
660484SobrienThis file is part of BFD, the Binary File Descriptor library.
760484Sobrien
860484SobrienThis program is free software; you can redistribute it and/or modify
960484Sobrienit under the terms of the GNU General Public License as published by
1060484Sobrienthe Free Software Foundation; either version 2 of the License, or
1160484Sobrien(at your option) any later version.
1260484Sobrien
1360484SobrienThis program is distributed in the hope that it will be useful,
1460484Sobrienbut WITHOUT ANY WARRANTY; without even the implied warranty of
1560484SobrienMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1660484SobrienGNU General Public License for more details.
1760484Sobrien
1860484SobrienYou should have received a copy of the GNU General Public License
1960484Sobrienalong with this program; if not, write to the Free Software
20218822SdimFoundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
2160484Sobrien
2260484Sobrien/* This is a BFD backend which may be used to write PowerPCBug boot objects.
2360484Sobrien   It may only be used for output, not input.  The intention is that this may
2460484Sobrien   be used as an output format for objcopy in order to generate raw binary
2560484Sobrien   data.
2660484Sobrien
2760484Sobrien   This is very simple.  The only complication is that the real data
2860484Sobrien   will start at some address X, and in some cases we will not want to
2960484Sobrien   include X zeroes just to get to that point.  Since the start
3060484Sobrien   address is not meaningful for this object file format, we use it
3160484Sobrien   instead to indicate the number of zeroes to skip at the start of
3260484Sobrien   the file.  objcopy cooperates by specially setting the start
3360484Sobrien   address to zero by default.  */
3460484Sobrien
35218822Sdim#include "sysdep.h"
3689857Sobrien#include "safe-ctype.h"
3760484Sobrien#include "bfd.h"
3860484Sobrien#include "libbfd.h"
3960484Sobrien
4060484Sobrien/* PPCbug location structure */
4160484Sobrientypedef struct ppcboot_location {
4260484Sobrien  bfd_byte	ind;
4360484Sobrien  bfd_byte	head;
4460484Sobrien  bfd_byte	sector;
4560484Sobrien  bfd_byte	cylinder;
4660484Sobrien} ppcboot_location_t;
4760484Sobrien
4860484Sobrien/* PPCbug partition table layout */
4960484Sobrientypedef struct ppcboot_partition {
5060484Sobrien  ppcboot_location_t	partition_begin;	/* partition begin */
5160484Sobrien  ppcboot_location_t	partition_end;		/* partition end */
5260484Sobrien  bfd_byte		sector_begin[4];	/* 32-bit start RBA (zero-based), little endian */
5360484Sobrien  bfd_byte		sector_length[4];	/* 32-bit RBA count (one-based), little endian */
5460484Sobrien} ppcboot_partition_t;
5560484Sobrien
5660484Sobrien/* PPCbug boot layout.  */
5760484Sobrientypedef struct ppcboot_hdr {
5860484Sobrien  bfd_byte		pc_compatibility[446];	/* x86 instruction field */
5960484Sobrien  ppcboot_partition_t	partition[4];		/* partition information */
6060484Sobrien  bfd_byte		signature[2];		/* 0x55 and 0xaa */
6160484Sobrien  bfd_byte		entry_offset[4];	/* entry point offset, little endian */
6260484Sobrien  bfd_byte		length[4];		/* load image length, little endian */
6360484Sobrien  bfd_byte		flags;			/* flag field */
6460484Sobrien  bfd_byte		os_id;			/* OS_ID */
6560484Sobrien  char			partition_name[32];	/* partition name */
6660484Sobrien  bfd_byte		reserved1[470];		/* reserved */
6761843Sobrien}
6861843Sobrien#ifdef __GNUC__
6961843Sobrien  __attribute__ ((packed))
7061843Sobrien#endif
7161843Sobrienppcboot_hdr_t;
7260484Sobrien
7360484Sobrien/* Signature bytes for last 2 bytes of the 512 byte record */
7460484Sobrien#define SIGNATURE0 0x55
7560484Sobrien#define SIGNATURE1 0xaa
7660484Sobrien
7760484Sobrien/* PowerPC boot type */
7860484Sobrien#define PPC_IND 0x41
7960484Sobrien
8060484Sobrien/* Information needed for ppcboot header */
8160484Sobrientypedef struct ppcboot_data {
8260484Sobrien  ppcboot_hdr_t	header;				/* raw header */
8360484Sobrien  asection *sec;				/* single section */
8460484Sobrien} ppcboot_data_t;
8560484Sobrien
8660484Sobrien/* Any bfd we create by reading a ppcboot file has three symbols:
8760484Sobrien   a start symbol, an end symbol, and an absolute length symbol.  */
8860484Sobrien#define PPCBOOT_SYMS 3
8960484Sobrien
90130561Sobrienstatic bfd_boolean ppcboot_mkobject PARAMS ((bfd *));
9160484Sobrienstatic const bfd_target *ppcboot_object_p PARAMS ((bfd *));
92130561Sobrienstatic bfd_boolean ppcboot_set_arch_mach
9360484Sobrien  PARAMS ((bfd *, enum bfd_architecture, unsigned long));
94130561Sobrienstatic bfd_boolean ppcboot_get_section_contents
9560484Sobrien  PARAMS ((bfd *, asection *, PTR, file_ptr, bfd_size_type));
9660484Sobrienstatic long ppcboot_get_symtab_upper_bound PARAMS ((bfd *));
9760484Sobrienstatic char *mangle_name PARAMS ((bfd *, char *));
98130561Sobrienstatic long ppcboot_canonicalize_symtab PARAMS ((bfd *, asymbol **));
9960484Sobrienstatic void ppcboot_get_symbol_info PARAMS ((bfd *, asymbol *, symbol_info *));
100130561Sobrienstatic bfd_boolean ppcboot_set_section_contents
101130561Sobrien  PARAMS ((bfd *, asection *, const PTR, file_ptr, bfd_size_type));
102130561Sobrienstatic bfd_boolean ppcboot_bfd_print_private_bfd_data PARAMS ((bfd *, PTR));
10360484Sobrien
10460484Sobrien#define ppcboot_set_tdata(abfd, ptr) ((abfd)->tdata.any = (PTR) (ptr))
10560484Sobrien#define ppcboot_get_tdata(abfd) ((ppcboot_data_t *) ((abfd)->tdata.any))
10660484Sobrien
10760484Sobrien/* Create a ppcboot object.  Invoked via bfd_set_format.  */
10860484Sobrien
109130561Sobrienstatic bfd_boolean
11060484Sobrienppcboot_mkobject (abfd)
11160484Sobrien     bfd *abfd;
11260484Sobrien{
11360484Sobrien  if (!ppcboot_get_tdata (abfd))
11489857Sobrien    {
11589857Sobrien      bfd_size_type amt = sizeof (ppcboot_data_t);
11689857Sobrien      ppcboot_set_tdata (abfd, bfd_zalloc (abfd, amt));
11789857Sobrien    }
11860484Sobrien
119130561Sobrien  return TRUE;
12060484Sobrien}
12160484Sobrien
12260484Sobrien
12360484Sobrien/* Set the architecture to PowerPC */
124130561Sobrienstatic bfd_boolean
12560484Sobrienppcboot_set_arch_mach (abfd, arch, machine)
12660484Sobrien     bfd *abfd;
12760484Sobrien     enum bfd_architecture arch;
12860484Sobrien     unsigned long machine;
12960484Sobrien{
13060484Sobrien  if (arch == bfd_arch_unknown)
13160484Sobrien    arch = bfd_arch_powerpc;
13260484Sobrien
13360484Sobrien  else if (arch != bfd_arch_powerpc)
134130561Sobrien    return FALSE;
13560484Sobrien
13660484Sobrien  return bfd_default_set_arch_mach (abfd, arch, machine);
13760484Sobrien}
13860484Sobrien
13960484Sobrien
14060484Sobrien/* Any file may be considered to be a ppcboot file, provided the target
14160484Sobrien   was not defaulted.  That is, it must be explicitly specified as
14260484Sobrien   being ppcboot.  */
14360484Sobrien
14460484Sobrienstatic const bfd_target *
14560484Sobrienppcboot_object_p (abfd)
14660484Sobrien     bfd *abfd;
14760484Sobrien{
14860484Sobrien  struct stat statbuf;
14960484Sobrien  asection *sec;
15060484Sobrien  ppcboot_hdr_t hdr;
15160484Sobrien  size_t i;
15260484Sobrien  ppcboot_data_t *tdata;
153218822Sdim  flagword flags;
15460484Sobrien
15560484Sobrien  BFD_ASSERT (sizeof (ppcboot_hdr_t) == 1024);
15660484Sobrien
15760484Sobrien  if (abfd->target_defaulted)
15860484Sobrien    {
15960484Sobrien      bfd_set_error (bfd_error_wrong_format);
16060484Sobrien      return NULL;
16160484Sobrien    }
16260484Sobrien
16360484Sobrien  /* Find the file size.  */
16460484Sobrien  if (bfd_stat (abfd, &statbuf) < 0)
16560484Sobrien    {
16660484Sobrien      bfd_set_error (bfd_error_system_call);
16760484Sobrien      return NULL;
16860484Sobrien    }
16960484Sobrien
17060484Sobrien  if ((size_t) statbuf.st_size < sizeof (ppcboot_hdr_t))
17160484Sobrien    {
17260484Sobrien      bfd_set_error (bfd_error_wrong_format);
17360484Sobrien      return NULL;
17460484Sobrien    }
17560484Sobrien
17689857Sobrien  if (bfd_bread ((PTR) &hdr, (bfd_size_type) sizeof (hdr), abfd)
17789857Sobrien      != sizeof (hdr))
17860484Sobrien    {
17960484Sobrien      if (bfd_get_error () != bfd_error_system_call)
18060484Sobrien	bfd_set_error (bfd_error_wrong_format);
18160484Sobrien
18260484Sobrien      return NULL;
18360484Sobrien    }
18460484Sobrien
18560484Sobrien  /* Now do some basic checks.  */
18660484Sobrien  for (i = 0; i < sizeof (hdr.pc_compatibility); i++)
18760484Sobrien    if (hdr.pc_compatibility[i])
18860484Sobrien      {
18960484Sobrien	bfd_set_error (bfd_error_wrong_format);
19060484Sobrien	return NULL;
19160484Sobrien      }
19260484Sobrien
19360484Sobrien  if (hdr.signature[0] != SIGNATURE0 || hdr.signature[1] != SIGNATURE1)
19460484Sobrien    {
19560484Sobrien      bfd_set_error (bfd_error_wrong_format);
19660484Sobrien      return NULL;
19760484Sobrien    }
19860484Sobrien
19960484Sobrien  if (hdr.partition[0].partition_end.ind != PPC_IND)
20060484Sobrien    {
20160484Sobrien      bfd_set_error (bfd_error_wrong_format);
20260484Sobrien      return NULL;
20360484Sobrien    }
20460484Sobrien
20560484Sobrien  abfd->symcount = PPCBOOT_SYMS;
20660484Sobrien
20760484Sobrien  /* One data section.  */
208218822Sdim  flags = SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_CODE | SEC_HAS_CONTENTS;
209218822Sdim  sec = bfd_make_section_with_flags (abfd, ".data", flags);
21060484Sobrien  if (sec == NULL)
21160484Sobrien    return NULL;
21260484Sobrien  sec->vma = 0;
213218822Sdim  sec->size = statbuf.st_size - sizeof (ppcboot_hdr_t);
21460484Sobrien  sec->filepos = sizeof (ppcboot_hdr_t);
21560484Sobrien
21660484Sobrien  ppcboot_mkobject (abfd);
21760484Sobrien  tdata = ppcboot_get_tdata (abfd);
21860484Sobrien  tdata->sec = sec;
21960484Sobrien  memcpy ((PTR) &tdata->header, (PTR) &hdr, sizeof (ppcboot_hdr_t));
22060484Sobrien
22189857Sobrien  ppcboot_set_arch_mach (abfd, bfd_arch_powerpc, 0L);
22260484Sobrien  return abfd->xvec;
22360484Sobrien}
22460484Sobrien
22560484Sobrien#define ppcboot_close_and_cleanup _bfd_generic_close_and_cleanup
22660484Sobrien#define ppcboot_bfd_free_cached_info _bfd_generic_bfd_free_cached_info
22760484Sobrien#define ppcboot_new_section_hook _bfd_generic_new_section_hook
22860484Sobrien
22960484Sobrien
23060484Sobrien/* Get contents of the only section.  */
23160484Sobrien
232130561Sobrienstatic bfd_boolean
23360484Sobrienppcboot_get_section_contents (abfd, section, location, offset, count)
23460484Sobrien     bfd *abfd;
23560484Sobrien     asection *section ATTRIBUTE_UNUSED;
23660484Sobrien     PTR location;
23760484Sobrien     file_ptr offset;
23860484Sobrien     bfd_size_type count;
23960484Sobrien{
24089857Sobrien  if (bfd_seek (abfd, offset + (file_ptr) sizeof (ppcboot_hdr_t), SEEK_SET) != 0
24189857Sobrien      || bfd_bread (location, count, abfd) != count)
242130561Sobrien    return FALSE;
243130561Sobrien  return TRUE;
24460484Sobrien}
24560484Sobrien
24660484Sobrien
24760484Sobrien/* Return the amount of memory needed to read the symbol table.  */
24860484Sobrien
24960484Sobrienstatic long
25060484Sobrienppcboot_get_symtab_upper_bound (abfd)
25160484Sobrien     bfd *abfd ATTRIBUTE_UNUSED;
25260484Sobrien{
25360484Sobrien  return (PPCBOOT_SYMS + 1) * sizeof (asymbol *);
25460484Sobrien}
25560484Sobrien
25660484Sobrien
25760484Sobrien/* Create a symbol name based on the bfd's filename.  */
25860484Sobrien
25960484Sobrienstatic char *
26060484Sobrienmangle_name (abfd, suffix)
26160484Sobrien     bfd *abfd;
26260484Sobrien     char *suffix;
26360484Sobrien{
26489857Sobrien  bfd_size_type size;
26560484Sobrien  char *buf;
26660484Sobrien  char *p;
26760484Sobrien
26860484Sobrien  size = (strlen (bfd_get_filename (abfd))
26960484Sobrien	  + strlen (suffix)
27060484Sobrien	  + sizeof "_ppcboot__");
27160484Sobrien
27260484Sobrien  buf = (char *) bfd_alloc (abfd, size);
27360484Sobrien  if (buf == NULL)
27460484Sobrien    return "";
27560484Sobrien
27660484Sobrien  sprintf (buf, "_ppcboot_%s_%s", bfd_get_filename (abfd), suffix);
27760484Sobrien
27860484Sobrien  /* Change any non-alphanumeric characters to underscores.  */
27960484Sobrien  for (p = buf; *p; p++)
28089857Sobrien    if (! ISALNUM (*p))
28160484Sobrien      *p = '_';
28260484Sobrien
28360484Sobrien  return buf;
28460484Sobrien}
28560484Sobrien
28660484Sobrien
28760484Sobrien/* Return the symbol table.  */
28860484Sobrien
28960484Sobrienstatic long
290130561Sobrienppcboot_canonicalize_symtab (abfd, alocation)
29160484Sobrien     bfd *abfd;
29260484Sobrien     asymbol **alocation;
29360484Sobrien{
29460484Sobrien  asection *sec = ppcboot_get_tdata (abfd)->sec;
29560484Sobrien  asymbol *syms;
29660484Sobrien  unsigned int i;
29789857Sobrien  bfd_size_type amt = PPCBOOT_SYMS * sizeof (asymbol);
29860484Sobrien
29989857Sobrien  syms = (asymbol *) bfd_alloc (abfd, amt);
30060484Sobrien  if (syms == NULL)
301130561Sobrien    return FALSE;
30260484Sobrien
30360484Sobrien  /* Start symbol.  */
30460484Sobrien  syms[0].the_bfd = abfd;
30560484Sobrien  syms[0].name = mangle_name (abfd, "start");
30660484Sobrien  syms[0].value = 0;
30760484Sobrien  syms[0].flags = BSF_GLOBAL;
30860484Sobrien  syms[0].section = sec;
30960484Sobrien  syms[0].udata.p = NULL;
31060484Sobrien
31160484Sobrien  /* End symbol.  */
31260484Sobrien  syms[1].the_bfd = abfd;
31360484Sobrien  syms[1].name = mangle_name (abfd, "end");
314218822Sdim  syms[1].value = sec->size;
31560484Sobrien  syms[1].flags = BSF_GLOBAL;
31660484Sobrien  syms[1].section = sec;
31760484Sobrien  syms[1].udata.p = NULL;
31860484Sobrien
31960484Sobrien  /* Size symbol.  */
32060484Sobrien  syms[2].the_bfd = abfd;
32160484Sobrien  syms[2].name = mangle_name (abfd, "size");
322218822Sdim  syms[2].value = sec->size;
32360484Sobrien  syms[2].flags = BSF_GLOBAL;
32460484Sobrien  syms[2].section = bfd_abs_section_ptr;
32560484Sobrien  syms[2].udata.p = NULL;
32660484Sobrien
32760484Sobrien  for (i = 0; i < PPCBOOT_SYMS; i++)
32860484Sobrien    *alocation++ = syms++;
32960484Sobrien  *alocation = NULL;
33060484Sobrien
33160484Sobrien  return PPCBOOT_SYMS;
33260484Sobrien}
33360484Sobrien
33489857Sobrien#define ppcboot_make_empty_symbol _bfd_generic_make_empty_symbol
33560484Sobrien#define ppcboot_print_symbol _bfd_nosymbols_print_symbol
33660484Sobrien
33760484Sobrien/* Get information about a symbol.  */
33860484Sobrien
33960484Sobrienstatic void
34060484Sobrienppcboot_get_symbol_info (ignore_abfd, symbol, ret)
34160484Sobrien     bfd *ignore_abfd ATTRIBUTE_UNUSED;
34260484Sobrien     asymbol *symbol;
34360484Sobrien     symbol_info *ret;
34460484Sobrien{
34560484Sobrien  bfd_symbol_info (symbol, ret);
34660484Sobrien}
34760484Sobrien
348218822Sdim#define ppcboot_bfd_is_target_special_symbol \
349218822Sdim  ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
35060484Sobrien#define ppcboot_bfd_is_local_label_name bfd_generic_is_local_label_name
35160484Sobrien#define ppcboot_get_lineno _bfd_nosymbols_get_lineno
35260484Sobrien#define ppcboot_find_nearest_line _bfd_nosymbols_find_nearest_line
353218822Sdim#define ppcboot_find_inliner_info _bfd_nosymbols_find_inliner_info
35460484Sobrien#define ppcboot_bfd_make_debug_symbol _bfd_nosymbols_bfd_make_debug_symbol
35560484Sobrien#define ppcboot_read_minisymbols _bfd_generic_read_minisymbols
35660484Sobrien#define ppcboot_minisymbol_to_symbol _bfd_generic_minisymbol_to_symbol
35760484Sobrien
35860484Sobrien/* Write section contents of a ppcboot file.  */
35960484Sobrien
360130561Sobrienstatic bfd_boolean
36160484Sobrienppcboot_set_section_contents (abfd, sec, data, offset, size)
36260484Sobrien     bfd *abfd;
36360484Sobrien     asection *sec;
364130561Sobrien     const PTR data;
36560484Sobrien     file_ptr offset;
36660484Sobrien     bfd_size_type size;
36760484Sobrien{
36860484Sobrien  if (! abfd->output_has_begun)
36960484Sobrien    {
37060484Sobrien      bfd_vma low;
37160484Sobrien      asection *s;
37260484Sobrien
37360484Sobrien      /* The lowest section VMA sets the virtual address of the start
37460484Sobrien         of the file.  We use the set the file position of all the
37560484Sobrien         sections.  */
37660484Sobrien      low = abfd->sections->vma;
37760484Sobrien      for (s = abfd->sections->next; s != NULL; s = s->next)
37860484Sobrien	if (s->vma < low)
37960484Sobrien	  low = s->vma;
38060484Sobrien
38160484Sobrien      for (s = abfd->sections; s != NULL; s = s->next)
38260484Sobrien	s->filepos = s->vma - low;
38360484Sobrien
384130561Sobrien      abfd->output_has_begun = TRUE;
38560484Sobrien    }
38660484Sobrien
38760484Sobrien  return _bfd_generic_set_section_contents (abfd, sec, data, offset, size);
38860484Sobrien}
38960484Sobrien
39060484Sobrien
39160484Sobrienstatic int
392218822Sdimppcboot_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
393218822Sdim			struct bfd_link_info *info ATTRIBUTE_UNUSED)
39460484Sobrien{
39560484Sobrien  return sizeof (ppcboot_hdr_t);
39660484Sobrien}
39760484Sobrien
39860484Sobrien
39960484Sobrien/* Print out the program headers.  */
40060484Sobrien
401130561Sobrienstatic bfd_boolean
40260484Sobrienppcboot_bfd_print_private_bfd_data (abfd, farg)
40360484Sobrien     bfd *abfd;
40460484Sobrien     PTR farg;
40560484Sobrien{
40660484Sobrien  FILE *f = (FILE *)farg;
40760484Sobrien  ppcboot_data_t *tdata = ppcboot_get_tdata (abfd);
40860484Sobrien  long entry_offset = bfd_getl_signed_32 ((PTR) tdata->header.entry_offset);
40960484Sobrien  long length = bfd_getl_signed_32 ((PTR) tdata->header.length);
41060484Sobrien  int i;
41160484Sobrien
41260484Sobrien  fprintf (f, _("\nppcboot header:\n"));
41360484Sobrien  fprintf (f, _("Entry offset        = 0x%.8lx (%ld)\n"), entry_offset, entry_offset);
41460484Sobrien  fprintf (f, _("Length              = 0x%.8lx (%ld)\n"), length, length);
41560484Sobrien
41660484Sobrien  if (tdata->header.flags)
41760484Sobrien    fprintf (f, _("Flag field          = 0x%.2x\n"), tdata->header.flags);
41860484Sobrien
41960484Sobrien  if (tdata->header.os_id)
42060484Sobrien    fprintf (f, "OS_ID               = 0x%.2x\n", tdata->header.os_id);
42160484Sobrien
42260484Sobrien  if (tdata->header.partition_name)
42360484Sobrien    fprintf (f, _("Partition name      = \"%s\"\n"), tdata->header.partition_name);
42460484Sobrien
42560484Sobrien  for (i = 0; i < 4; i++)
42660484Sobrien    {
42760484Sobrien      long sector_begin  = bfd_getl_signed_32 ((PTR) tdata->header.partition[i].sector_begin);
42860484Sobrien      long sector_length = bfd_getl_signed_32 ((PTR) tdata->header.partition[i].sector_length);
42960484Sobrien
43060484Sobrien      /* Skip all 0 entries */
43160484Sobrien      if (!tdata->header.partition[i].partition_begin.ind
43260484Sobrien	  && !tdata->header.partition[i].partition_begin.head
43360484Sobrien	  && !tdata->header.partition[i].partition_begin.sector
43460484Sobrien	  && !tdata->header.partition[i].partition_begin.cylinder
43560484Sobrien	  && !tdata->header.partition[i].partition_end.ind
43660484Sobrien	  && !tdata->header.partition[i].partition_end.head
43760484Sobrien	  && !tdata->header.partition[i].partition_end.sector
43860484Sobrien	  && !tdata->header.partition[i].partition_end.cylinder
43960484Sobrien	  && !sector_begin && !sector_length)
44060484Sobrien	continue;
44160484Sobrien
44260484Sobrien      fprintf (f, _("\nPartition[%d] start  = { 0x%.2x, 0x%.2x, 0x%.2x, 0x%.2x }\n"), i,
44360484Sobrien	       tdata->header.partition[i].partition_begin.ind,
44460484Sobrien	       tdata->header.partition[i].partition_begin.head,
44560484Sobrien	       tdata->header.partition[i].partition_begin.sector,
44660484Sobrien	       tdata->header.partition[i].partition_begin.cylinder);
44760484Sobrien
44860484Sobrien      fprintf (f, _("Partition[%d] end    = { 0x%.2x, 0x%.2x, 0x%.2x, 0x%.2x }\n"), i,
44960484Sobrien	       tdata->header.partition[i].partition_end.ind,
45060484Sobrien	       tdata->header.partition[i].partition_end.head,
45160484Sobrien	       tdata->header.partition[i].partition_end.sector,
45260484Sobrien	       tdata->header.partition[i].partition_end.cylinder);
45360484Sobrien
45460484Sobrien      fprintf (f, _("Partition[%d] sector = 0x%.8lx (%ld)\n"), i, sector_begin, sector_begin);
45560484Sobrien      fprintf (f, _("Partition[%d] length = 0x%.8lx (%ld)\n"), i, sector_length, sector_length);
45660484Sobrien    }
45760484Sobrien
45860484Sobrien  fprintf (f, "\n");
459130561Sobrien  return TRUE;
46060484Sobrien}
46160484Sobrien
46260484Sobrien
46360484Sobrien#define ppcboot_bfd_get_relocated_section_contents \
46460484Sobrien  bfd_generic_get_relocated_section_contents
46560484Sobrien#define ppcboot_bfd_relax_section bfd_generic_relax_section
46660484Sobrien#define ppcboot_bfd_gc_sections bfd_generic_gc_sections
46789857Sobrien#define ppcboot_bfd_merge_sections bfd_generic_merge_sections
468218822Sdim#define ppcboot_bfd_is_group_section bfd_generic_is_group_section
469104834Sobrien#define ppcboot_bfd_discard_group bfd_generic_discard_group
470218822Sdim#define ppcboot_section_already_linked \
471218822Sdim  _bfd_generic_section_already_linked
47260484Sobrien#define ppcboot_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
473104834Sobrien#define ppcboot_bfd_link_hash_table_free _bfd_generic_link_hash_table_free
47460484Sobrien#define ppcboot_bfd_link_add_symbols _bfd_generic_link_add_symbols
475104834Sobrien#define ppcboot_bfd_link_just_syms _bfd_generic_link_just_syms
47660484Sobrien#define ppcboot_bfd_final_link _bfd_generic_final_link
47760484Sobrien#define ppcboot_bfd_link_split_section _bfd_generic_link_split_section
47860484Sobrien#define ppcboot_get_section_contents_in_window \
47960484Sobrien  _bfd_generic_get_section_contents_in_window
48060484Sobrien
48160484Sobrien#define ppcboot_bfd_copy_private_bfd_data _bfd_generic_bfd_copy_private_bfd_data
48260484Sobrien#define ppcboot_bfd_merge_private_bfd_data _bfd_generic_bfd_merge_private_bfd_data
48360484Sobrien#define ppcboot_bfd_copy_private_section_data _bfd_generic_bfd_copy_private_section_data
48460484Sobrien#define ppcboot_bfd_copy_private_symbol_data _bfd_generic_bfd_copy_private_symbol_data
485218822Sdim#define ppcboot_bfd_copy_private_header_data _bfd_generic_bfd_copy_private_header_data
48660484Sobrien#define ppcboot_bfd_set_private_flags _bfd_generic_bfd_set_private_flags
48760484Sobrien#define ppcboot_bfd_print_private_bfd_dat ppcboot_bfd_print_private_bfd_data
48860484Sobrien
48960484Sobrienconst bfd_target ppcboot_vec =
49060484Sobrien{
49160484Sobrien  "ppcboot",			/* name */
49260484Sobrien  bfd_target_unknown_flavour,	/* flavour */
49360484Sobrien  BFD_ENDIAN_BIG,		/* byteorder is big endian for code */
49460484Sobrien  BFD_ENDIAN_LITTLE,		/* header_byteorder */
49560484Sobrien  EXEC_P,			/* object_flags */
49660484Sobrien  (SEC_ALLOC | SEC_LOAD | SEC_READONLY | SEC_CODE | SEC_DATA
49760484Sobrien   | SEC_ROM | SEC_HAS_CONTENTS), /* section_flags */
49860484Sobrien  0,				/* symbol_leading_char */
49960484Sobrien  ' ',				/* ar_pad_char */
50060484Sobrien  16,				/* ar_max_namelen */
50160484Sobrien  bfd_getb64, bfd_getb_signed_64, bfd_putb64,
50260484Sobrien  bfd_getb32, bfd_getb_signed_32, bfd_putb32,
50360484Sobrien  bfd_getb16, bfd_getb_signed_16, bfd_putb16,	/* data */
50460484Sobrien  bfd_getl64, bfd_getl_signed_64, bfd_putl64,
50560484Sobrien  bfd_getl32, bfd_getl_signed_32, bfd_putl32,
50660484Sobrien  bfd_getl16, bfd_getl_signed_16, bfd_putl16,	/* hdrs */
50760484Sobrien  {				/* bfd_check_format */
50860484Sobrien    _bfd_dummy_target,
50960484Sobrien    ppcboot_object_p,		/* bfd_check_format */
51060484Sobrien    _bfd_dummy_target,
51160484Sobrien    _bfd_dummy_target,
51260484Sobrien  },
51360484Sobrien  {				/* bfd_set_format */
51460484Sobrien    bfd_false,
51560484Sobrien    ppcboot_mkobject,
51660484Sobrien    bfd_false,
51760484Sobrien    bfd_false,
51860484Sobrien  },
51960484Sobrien  {				/* bfd_write_contents */
52060484Sobrien    bfd_false,
52160484Sobrien    bfd_true,
52260484Sobrien    bfd_false,
52360484Sobrien    bfd_false,
52460484Sobrien  },
52560484Sobrien
52660484Sobrien  BFD_JUMP_TABLE_GENERIC (ppcboot),
52760484Sobrien  BFD_JUMP_TABLE_COPY (ppcboot),
52860484Sobrien  BFD_JUMP_TABLE_CORE (_bfd_nocore),
52960484Sobrien  BFD_JUMP_TABLE_ARCHIVE (_bfd_noarchive),
53060484Sobrien  BFD_JUMP_TABLE_SYMBOLS (ppcboot),
531218822Sdim  BFD_JUMP_TABLE_RELOCS (_bfd_norelocs),
53260484Sobrien  BFD_JUMP_TABLE_WRITE (ppcboot),
53360484Sobrien  BFD_JUMP_TABLE_LINK (ppcboot),
53460484Sobrien  BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic),
53560484Sobrien
53660484Sobrien  NULL,
53777298Sobrien
53860484Sobrien  NULL
53960484Sobrien};
540