Home | History | Annotate | Line # | Download | only in bfd
ihex.c revision 1.1.1.1
      1 /* BFD back-end for Intel Hex objects.
      2    Copyright 1995, 1996, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
      3    2006, 2007, 2009, 2011 Free Software Foundation, Inc.
      4    Written by Ian Lance Taylor of Cygnus Support <ian (at) cygnus.com>.
      5 
      6    This file is part of BFD, the Binary File Descriptor library.
      7 
      8    This program is free software; you can redistribute it and/or modify
      9    it under the terms of the GNU General Public License as published by
     10    the Free Software Foundation; either version 3 of the License, or
     11    (at your option) any later version.
     12 
     13    This program is distributed in the hope that it will be useful,
     14    but WITHOUT ANY WARRANTY; without even the implied warranty of
     15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
     16    GNU General Public License for more details.
     17 
     18    You should have received a copy of the GNU General Public License
     19    along with this program; if not, write to the Free Software
     20    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
     21    MA 02110-1301, USA.  */
     22 
     23 
     24 /* This is what Intel Hex files look like:
     25 
     26 1. INTEL FORMATS
     27 
     28 A. Intel 1
     29 
     30    16-bit address-field format, for files 64k bytes in length or less.
     31 
     32    DATA RECORD
     33    Byte 1	Header = colon(:)
     34    2..3		The number of data bytes in hex notation
     35    4..5		High byte of the record load address
     36    6..7		Low byte of the record load address
     37    8..9		Record type, must be "00"
     38    10..x	Data bytes in hex notation:
     39 	x = (number of bytes - 1) * 2 + 11
     40    x+1..x+2	Checksum in hex notation
     41    x+3..x+4	Carriage return, line feed
     42 
     43    END RECORD
     44    Byte 1	Header = colon (:)
     45    2..3		The byte count, must be "00"
     46    4..7		Transfer-address (usually "0000")
     47 		the jump-to address, execution start address
     48    8..9		Record type, must be "01"
     49    10..11	Checksum, in hex notation
     50    12..13	Carriage return, line feed
     51 
     52 B. INTEL 2
     53 
     54    MCS-86 format, using a 20-bit address for files larger than 64K bytes.
     55 
     56    DATA RECORD
     57    Byte 1	Header = colon (:)
     58    2..3		The byte count of this record, hex notation
     59    4..5		High byte of the record load address
     60    6..7		Low byte of the record load address
     61    8..9		Record type, must be "00"
     62    10..x	The data bytes in hex notation:
     63 	x = (number of data bytes - 1) * 2 + 11
     64    x+1..x+2	Checksum in hex notation
     65    x+3..x+4	Carriage return, line feed
     66 
     67    EXTENDED ADDRESS RECORD
     68    Byte 1	Header = colon(:)
     69    2..3		The byte count, must be "02"
     70    4..7		Load address, must be "0000"
     71    8..9		Record type, must be "02"
     72    10..11	High byte of the offset address
     73    12..13	Low byte of the offset address
     74    14..15	Checksum in hex notation
     75    16..17	Carriage return, line feed
     76 
     77    The checksums are the two's complement of the 8-bit sum
     78    without carry of the byte count, offset address, and the
     79    record type.
     80 
     81    START ADDRESS RECORD
     82    Byte 1	Header = colon (:)
     83    2..3		The byte count, must be "04"
     84    4..7		Load address, must be "0000"
     85    8..9		Record type, must be "03"
     86    10..13	8086 CS value
     87    14..17	8086 IP value
     88    18..19	Checksum in hex notation
     89    20..21	Carriage return, line feed
     90 
     91 Another document reports these additional types:
     92 
     93    EXTENDED LINEAR ADDRESS RECORD
     94    Byte 1	Header = colon (:)
     95    2..3		The byte count, must be "02"
     96    4..7		Load address, must be "0000"
     97    8..9		Record type, must be "04"
     98    10..13	Upper 16 bits of address of subsequent records
     99    14..15	Checksum in hex notation
    100    16..17	Carriage return, line feed
    101 
    102    START LINEAR ADDRESS RECORD
    103    Byte 1	Header = colon (:)
    104    2..3		The byte count, must be "02"
    105    4..7		Load address, must be "0000"
    106    8..9		Record type, must be "05"
    107    10..13	Upper 16 bits of start address
    108    14..15	Checksum in hex notation
    109    16..17	Carriage return, line feed
    110 
    111 The MRI compiler uses this, which is a repeat of type 5:
    112 
    113   EXTENDED START RECORD
    114    Byte 1	Header = colon (:)
    115    2..3		The byte count, must be "04"
    116    4..7		Load address, must be "0000"
    117    8..9		Record type, must be "05"
    118    10..13	Upper 16 bits of start address
    119    14..17	Lower 16 bits of start address
    120    18..19	Checksum in hex notation
    121    20..21	Carriage return, line feed.  */
    122 
    123 #include "sysdep.h"
    124 #include "bfd.h"
    125 #include "libbfd.h"
    126 #include "libiberty.h"
    127 #include "safe-ctype.h"
    128 
    129 /* The number of bytes we put on one line during output.  */
    130 
    131 #define CHUNK 16
    132 
    133 /* Macros for converting between hex and binary.  */
    134 
    135 #define NIBBLE(x)    (hex_value (x))
    136 #define HEX2(buffer) ((NIBBLE ((buffer)[0]) << 4) + NIBBLE ((buffer)[1]))
    137 #define HEX4(buffer) ((HEX2 (buffer) << 8) + HEX2 ((buffer) + 2))
    138 #define ISHEX(x)     (hex_p (x))
    139 
    140 /* When we write out an ihex value, the values can not be output as
    141    they are seen.  Instead, we hold them in memory in this structure.  */
    142 
    143 struct ihex_data_list
    144 {
    145   struct ihex_data_list *next;
    146   bfd_byte *data;
    147   bfd_vma where;
    148   bfd_size_type size;
    149 };
    150 
    151 /* The ihex tdata information.  */
    152 
    153 struct ihex_data_struct
    154 {
    155   struct ihex_data_list *head;
    156   struct ihex_data_list *tail;
    157 };
    158 
    159 /* Initialize by filling in the hex conversion array.  */
    160 
    161 static void
    162 ihex_init (void)
    163 {
    164   static bfd_boolean inited;
    165 
    166   if (! inited)
    167     {
    168       inited = TRUE;
    169       hex_init ();
    170     }
    171 }
    172 
    173 /* Create an ihex object.  */
    174 
    175 static bfd_boolean
    176 ihex_mkobject (bfd *abfd)
    177 {
    178   struct ihex_data_struct *tdata;
    179 
    180   tdata = (struct ihex_data_struct *) bfd_alloc (abfd, sizeof (* tdata));
    181   if (tdata == NULL)
    182     return FALSE;
    183 
    184   abfd->tdata.ihex_data = tdata;
    185   tdata->head = NULL;
    186   tdata->tail = NULL;
    187   return TRUE;
    188 }
    189 
    190 /* Read a byte from a BFD.  Set *ERRORPTR if an error occurred.
    191    Return EOF on error or end of file.  */
    192 
    193 static INLINE int
    194 ihex_get_byte (bfd *abfd, bfd_boolean *errorptr)
    195 {
    196   bfd_byte c;
    197 
    198   if (bfd_bread (&c, (bfd_size_type) 1, abfd) != 1)
    199     {
    200       if (bfd_get_error () != bfd_error_file_truncated)
    201 	*errorptr = TRUE;
    202       return EOF;
    203     }
    204 
    205   return (int) (c & 0xff);
    206 }
    207 
    208 /* Report a problem in an Intel Hex file.  */
    209 
    210 static void
    211 ihex_bad_byte (bfd *abfd, unsigned int lineno, int c, bfd_boolean error)
    212 {
    213   if (c == EOF)
    214     {
    215       if (! error)
    216 	bfd_set_error (bfd_error_file_truncated);
    217     }
    218   else
    219     {
    220       char buf[10];
    221 
    222       if (! ISPRINT (c))
    223 	sprintf (buf, "\\%03o", (unsigned int) c);
    224       else
    225 	{
    226 	  buf[0] = c;
    227 	  buf[1] = '\0';
    228 	}
    229       (*_bfd_error_handler)
    230 	(_("%B:%d: unexpected character `%s' in Intel Hex file"),
    231 	 abfd, lineno, buf);
    232       bfd_set_error (bfd_error_bad_value);
    233     }
    234 }
    235 
    236 /* Read an Intel hex file and turn it into sections.  We create a new
    237    section for each contiguous set of bytes.  */
    238 
    239 static bfd_boolean
    240 ihex_scan (bfd *abfd)
    241 {
    242   bfd_vma segbase;
    243   bfd_vma extbase;
    244   asection *sec;
    245   unsigned int lineno;
    246   bfd_boolean error;
    247   bfd_byte *buf = NULL;
    248   size_t bufsize;
    249   int c;
    250 
    251   if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
    252     goto error_return;
    253 
    254   abfd->start_address = 0;
    255 
    256   segbase = 0;
    257   extbase = 0;
    258   sec = NULL;
    259   lineno = 1;
    260   error = FALSE;
    261   bufsize = 0;
    262 
    263   while ((c = ihex_get_byte (abfd, &error)) != EOF)
    264     {
    265       if (c == '\r')
    266 	continue;
    267       else if (c == '\n')
    268 	{
    269 	  ++lineno;
    270 	  continue;
    271 	}
    272       else if (c != ':')
    273 	{
    274 	  ihex_bad_byte (abfd, lineno, c, error);
    275 	  goto error_return;
    276 	}
    277       else
    278 	{
    279 	  file_ptr pos;
    280 	  char hdr[8];
    281 	  unsigned int i;
    282 	  unsigned int len;
    283 	  bfd_vma addr;
    284 	  unsigned int type;
    285 	  unsigned int chars;
    286 	  unsigned int chksum;
    287 
    288 	  /* This is a data record.  */
    289 	  pos = bfd_tell (abfd) - 1;
    290 
    291 	  /* Read the header bytes.  */
    292 	  if (bfd_bread (hdr, (bfd_size_type) 8, abfd) != 8)
    293 	    goto error_return;
    294 
    295 	  for (i = 0; i < 8; i++)
    296 	    {
    297 	      if (! ISHEX (hdr[i]))
    298 		{
    299 		  ihex_bad_byte (abfd, lineno, hdr[i], error);
    300 		  goto error_return;
    301 		}
    302 	    }
    303 
    304 	  len = HEX2 (hdr);
    305 	  addr = HEX4 (hdr + 2);
    306 	  type = HEX2 (hdr + 6);
    307 
    308 	  /* Read the data bytes.  */
    309 	  chars = len * 2 + 2;
    310 	  if (chars >= bufsize)
    311 	    {
    312 	      buf = (bfd_byte *) bfd_realloc (buf, (bfd_size_type) chars);
    313 	      if (buf == NULL)
    314 		goto error_return;
    315 	      bufsize = chars;
    316 	    }
    317 
    318 	  if (bfd_bread (buf, (bfd_size_type) chars, abfd) != chars)
    319 	    goto error_return;
    320 
    321 	  for (i = 0; i < chars; i++)
    322 	    {
    323 	      if (! ISHEX (buf[i]))
    324 		{
    325 		  ihex_bad_byte (abfd, lineno, hdr[i], error);
    326 		  goto error_return;
    327 		}
    328 	    }
    329 
    330 	  /* Check the checksum.  */
    331 	  chksum = len + addr + (addr >> 8) + type;
    332 	  for (i = 0; i < len; i++)
    333 	    chksum += HEX2 (buf + 2 * i);
    334 	  if (((- chksum) & 0xff) != (unsigned int) HEX2 (buf + 2 * i))
    335 	    {
    336 	      (*_bfd_error_handler)
    337 		(_("%B:%u: bad checksum in Intel Hex file (expected %u, found %u)"),
    338 		 abfd, lineno,
    339 		 (- chksum) & 0xff, (unsigned int) HEX2 (buf + 2 * i));
    340 	      bfd_set_error (bfd_error_bad_value);
    341 	      goto error_return;
    342 	    }
    343 
    344 	  switch (type)
    345 	    {
    346 	    case 0:
    347 	      /* This is a data record.  */
    348 	      if (sec != NULL
    349 		  && sec->vma + sec->size == extbase + segbase + addr)
    350 		{
    351 		  /* This data goes at the end of the section we are
    352                      currently building.  */
    353 		  sec->size += len;
    354 		}
    355 	      else if (len > 0)
    356 		{
    357 		  char secbuf[20];
    358 		  char *secname;
    359 		  bfd_size_type amt;
    360 		  flagword flags;
    361 
    362 		  sprintf (secbuf, ".sec%d", bfd_count_sections (abfd) + 1);
    363 		  amt = strlen (secbuf) + 1;
    364 		  secname = (char *) bfd_alloc (abfd, amt);
    365 		  if (secname == NULL)
    366 		    goto error_return;
    367 		  strcpy (secname, secbuf);
    368 		  flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC;
    369 		  sec = bfd_make_section_with_flags (abfd, secname, flags);
    370 		  if (sec == NULL)
    371 		    goto error_return;
    372 		  sec->vma = extbase + segbase + addr;
    373 		  sec->lma = extbase + segbase + addr;
    374 		  sec->size = len;
    375 		  sec->filepos = pos;
    376 		}
    377 	      break;
    378 
    379 	    case 1:
    380 	      /* An end record.  */
    381 	      if (abfd->start_address == 0)
    382 		abfd->start_address = addr;
    383 	      if (buf != NULL)
    384 		free (buf);
    385 	      return TRUE;
    386 
    387 	    case 2:
    388 	      /* An extended address record.  */
    389 	      if (len != 2)
    390 		{
    391 		  (*_bfd_error_handler)
    392 		    (_("%B:%u: bad extended address record length in Intel Hex file"),
    393 		     abfd, lineno);
    394 		  bfd_set_error (bfd_error_bad_value);
    395 		  goto error_return;
    396 		}
    397 
    398 	      segbase = HEX4 (buf) << 4;
    399 
    400 	      sec = NULL;
    401 
    402 	      break;
    403 
    404 	    case 3:
    405 	      /* An extended start address record.  */
    406 	      if (len != 4)
    407 		{
    408 		  (*_bfd_error_handler)
    409 		    (_("%B:%u: bad extended start address length in Intel Hex file"),
    410 		     abfd, lineno);
    411 		  bfd_set_error (bfd_error_bad_value);
    412 		  goto error_return;
    413 		}
    414 
    415 	      abfd->start_address += (HEX4 (buf) << 4) + HEX4 (buf + 4);
    416 
    417 	      sec = NULL;
    418 
    419 	      break;
    420 
    421 	    case 4:
    422 	      /* An extended linear address record.  */
    423 	      if (len != 2)
    424 		{
    425 		  (*_bfd_error_handler)
    426 		    (_("%B:%u: bad extended linear address record length in Intel Hex file"),
    427 		     abfd, lineno);
    428 		  bfd_set_error (bfd_error_bad_value);
    429 		  goto error_return;
    430 		}
    431 
    432 	      extbase = HEX4 (buf) << 16;
    433 
    434 	      sec = NULL;
    435 
    436 	      break;
    437 
    438 	    case 5:
    439 	      /* An extended linear start address record.  */
    440 	      if (len != 2 && len != 4)
    441 		{
    442 		  (*_bfd_error_handler)
    443 		    (_("%B:%u: bad extended linear start address length in Intel Hex file"),
    444 		     abfd, lineno);
    445 		  bfd_set_error (bfd_error_bad_value);
    446 		  goto error_return;
    447 		}
    448 
    449 	      if (len == 2)
    450 		abfd->start_address += HEX4 (buf) << 16;
    451 	      else
    452 		abfd->start_address = (HEX4 (buf) << 16) + HEX4 (buf + 4);
    453 
    454 	      sec = NULL;
    455 
    456 	      break;
    457 
    458 	    default:
    459 	      (*_bfd_error_handler)
    460 		(_("%B:%u: unrecognized ihex type %u in Intel Hex file"),
    461 		 abfd, lineno, type);
    462 	      bfd_set_error (bfd_error_bad_value);
    463 	      goto error_return;
    464 	    }
    465 	}
    466     }
    467 
    468   if (error)
    469     goto error_return;
    470 
    471   if (buf != NULL)
    472     free (buf);
    473 
    474   return TRUE;
    475 
    476  error_return:
    477   if (buf != NULL)
    478     free (buf);
    479   return FALSE;
    480 }
    481 
    482 /* Try to recognize an Intel Hex file.  */
    483 
    484 static const bfd_target *
    485 ihex_object_p (bfd *abfd)
    486 {
    487   void * tdata_save;
    488   bfd_byte b[9];
    489   unsigned int i;
    490   unsigned int type;
    491 
    492   ihex_init ();
    493 
    494   if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
    495     return NULL;
    496   if (bfd_bread (b, (bfd_size_type) 9, abfd) != 9)
    497     {
    498       if (bfd_get_error () == bfd_error_file_truncated)
    499 	bfd_set_error (bfd_error_wrong_format);
    500       return NULL;
    501     }
    502 
    503   if (b[0] != ':')
    504     {
    505       bfd_set_error (bfd_error_wrong_format);
    506       return NULL;
    507     }
    508 
    509   for (i = 1; i < 9; i++)
    510     {
    511       if (! ISHEX (b[i]))
    512 	{
    513 	  bfd_set_error (bfd_error_wrong_format);
    514 	  return NULL;
    515 	}
    516     }
    517 
    518   type = HEX2 (b + 7);
    519   if (type > 5)
    520     {
    521       bfd_set_error (bfd_error_wrong_format);
    522       return NULL;
    523     }
    524 
    525   /* OK, it looks like it really is an Intel Hex file.  */
    526   tdata_save = abfd->tdata.any;
    527   if (! ihex_mkobject (abfd) || ! ihex_scan (abfd))
    528     {
    529       if (abfd->tdata.any != tdata_save && abfd->tdata.any != NULL)
    530 	bfd_release (abfd, abfd->tdata.any);
    531       abfd->tdata.any = tdata_save;
    532       return NULL;
    533     }
    534 
    535   return abfd->xvec;
    536 }
    537 
    538 /* Read the contents of a section in an Intel Hex file.  */
    539 
    540 static bfd_boolean
    541 ihex_read_section (bfd *abfd, asection *section, bfd_byte *contents)
    542 {
    543   int c;
    544   bfd_byte *p;
    545   bfd_byte *buf = NULL;
    546   size_t bufsize;
    547   bfd_boolean error;
    548 
    549   if (bfd_seek (abfd, section->filepos, SEEK_SET) != 0)
    550     goto error_return;
    551 
    552   p = contents;
    553   bufsize = 0;
    554   error = FALSE;
    555   while ((c = ihex_get_byte (abfd, &error)) != EOF)
    556     {
    557       char hdr[8];
    558       unsigned int len;
    559       unsigned int type;
    560       unsigned int i;
    561 
    562       if (c == '\r' || c == '\n')
    563 	continue;
    564 
    565       /* This is called after ihex_scan has succeeded, so we ought to
    566          know the exact format.  */
    567       BFD_ASSERT (c == ':');
    568 
    569       if (bfd_bread (hdr, (bfd_size_type) 8, abfd) != 8)
    570 	goto error_return;
    571 
    572       len = HEX2 (hdr);
    573       type = HEX2 (hdr + 6);
    574 
    575       /* We should only see type 0 records here.  */
    576       if (type != 0)
    577 	{
    578 	  (*_bfd_error_handler)
    579 	    (_("%B: internal error in ihex_read_section"), abfd);
    580 	  bfd_set_error (bfd_error_bad_value);
    581 	  goto error_return;
    582 	}
    583 
    584       if (len * 2 > bufsize)
    585 	{
    586 	  buf = (bfd_byte *) bfd_realloc (buf, (bfd_size_type) len * 2);
    587 	  if (buf == NULL)
    588 	    goto error_return;
    589 	  bufsize = len * 2;
    590 	}
    591 
    592       if (bfd_bread (buf, (bfd_size_type) len * 2, abfd) != len * 2)
    593 	goto error_return;
    594 
    595       for (i = 0; i < len; i++)
    596 	*p++ = HEX2 (buf + 2 * i);
    597       if ((bfd_size_type) (p - contents) >= section->size)
    598 	{
    599 	  /* We've read everything in the section.  */
    600 	  if (buf != NULL)
    601 	    free (buf);
    602 	  return TRUE;
    603 	}
    604 
    605       /* Skip the checksum.  */
    606       if (bfd_bread (buf, (bfd_size_type) 2, abfd) != 2)
    607 	goto error_return;
    608     }
    609 
    610   if ((bfd_size_type) (p - contents) < section->size)
    611     {
    612       (*_bfd_error_handler)
    613 	(_("%B: bad section length in ihex_read_section"), abfd);
    614       bfd_set_error (bfd_error_bad_value);
    615       goto error_return;
    616     }
    617 
    618   if (buf != NULL)
    619     free (buf);
    620 
    621   return TRUE;
    622 
    623  error_return:
    624   if (buf != NULL)
    625     free (buf);
    626   return FALSE;
    627 }
    628 
    629 /* Get the contents of a section in an Intel Hex file.  */
    630 
    631 static bfd_boolean
    632 ihex_get_section_contents (bfd *abfd,
    633 			   asection *section,
    634 			   void * location,
    635 			   file_ptr offset,
    636 			   bfd_size_type count)
    637 {
    638   if (section->used_by_bfd == NULL)
    639     {
    640       section->used_by_bfd = bfd_alloc (abfd, section->size);
    641       if (section->used_by_bfd == NULL)
    642 	return FALSE;
    643       if (! ihex_read_section (abfd, section,
    644                                (bfd_byte *) section->used_by_bfd))
    645 	return FALSE;
    646     }
    647 
    648   memcpy (location, (bfd_byte *) section->used_by_bfd + offset,
    649 	  (size_t) count);
    650 
    651   return TRUE;
    652 }
    653 
    654 /* Set the contents of a section in an Intel Hex file.  */
    655 
    656 static bfd_boolean
    657 ihex_set_section_contents (bfd *abfd,
    658 			   asection *section,
    659 			   const void * location,
    660 			   file_ptr offset,
    661 			   bfd_size_type count)
    662 {
    663   struct ihex_data_list *n;
    664   bfd_byte *data;
    665   struct ihex_data_struct *tdata;
    666 
    667   if (count == 0
    668       || (section->flags & SEC_ALLOC) == 0
    669       || (section->flags & SEC_LOAD) == 0)
    670     return TRUE;
    671 
    672   n = (struct ihex_data_list *) bfd_alloc (abfd, sizeof (* n));
    673   if (n == NULL)
    674     return FALSE;
    675 
    676   data = (bfd_byte *) bfd_alloc (abfd, count);
    677   if (data == NULL)
    678     return FALSE;
    679   memcpy (data, location, (size_t) count);
    680 
    681   n->data = data;
    682   n->where = section->lma + offset;
    683   n->size = count;
    684 
    685   /* Sort the records by address.  Optimize for the common case of
    686      adding a record to the end of the list.  */
    687   tdata = abfd->tdata.ihex_data;
    688   if (tdata->tail != NULL
    689       && n->where >= tdata->tail->where)
    690     {
    691       tdata->tail->next = n;
    692       n->next = NULL;
    693       tdata->tail = n;
    694     }
    695   else
    696     {
    697       struct ihex_data_list **pp;
    698 
    699       for (pp = &tdata->head;
    700 	   *pp != NULL && (*pp)->where < n->where;
    701 	   pp = &(*pp)->next)
    702 	;
    703       n->next = *pp;
    704       *pp = n;
    705       if (n->next == NULL)
    706 	tdata->tail = n;
    707     }
    708 
    709   return TRUE;
    710 }
    711 
    712 /* Write a record out to an Intel Hex file.  */
    713 
    714 static bfd_boolean
    715 ihex_write_record (bfd *abfd,
    716 		   size_t count,
    717 		   unsigned int addr,
    718 		   unsigned int type,
    719 		   bfd_byte *data)
    720 {
    721   static const char digs[] = "0123456789ABCDEF";
    722   char buf[9 + CHUNK * 2 + 4];
    723   char *p;
    724   unsigned int chksum;
    725   unsigned int i;
    726   size_t total;
    727 
    728 #define TOHEX(buf, v) \
    729   ((buf)[0] = digs[((v) >> 4) & 0xf], (buf)[1] = digs[(v) & 0xf])
    730 
    731   buf[0] = ':';
    732   TOHEX (buf + 1, count);
    733   TOHEX (buf + 3, (addr >> 8) & 0xff);
    734   TOHEX (buf + 5, addr & 0xff);
    735   TOHEX (buf + 7, type);
    736 
    737   chksum = count + addr + (addr >> 8) + type;
    738 
    739   for (i = 0, p = buf + 9; i < count; i++, p += 2, data++)
    740     {
    741       TOHEX (p, *data);
    742       chksum += *data;
    743     }
    744 
    745   TOHEX (p, (- chksum) & 0xff);
    746   p[2] = '\r';
    747   p[3] = '\n';
    748 
    749   total = 9 + count * 2 + 4;
    750   if (bfd_bwrite (buf, (bfd_size_type) total, abfd) != total)
    751     return FALSE;
    752 
    753   return TRUE;
    754 }
    755 
    756 /* Write out an Intel Hex file.  */
    757 
    758 static bfd_boolean
    759 ihex_write_object_contents (bfd *abfd)
    760 {
    761   bfd_vma segbase;
    762   bfd_vma extbase;
    763   struct ihex_data_list *l;
    764 
    765   segbase = 0;
    766   extbase = 0;
    767   for (l = abfd->tdata.ihex_data->head; l != NULL; l = l->next)
    768     {
    769       bfd_vma where;
    770       bfd_byte *p;
    771       bfd_size_type count;
    772 
    773       where = l->where;
    774       p = l->data;
    775       count = l->size;
    776 
    777       while (count > 0)
    778 	{
    779 	  size_t now;
    780 	  unsigned int rec_addr;
    781 
    782 	  now = count;
    783 	  if (count > CHUNK)
    784 	    now = CHUNK;
    785 
    786 	  if (where > segbase + extbase + 0xffff)
    787 	    {
    788 	      bfd_byte addr[2];
    789 
    790 	      /* We need a new base address.  */
    791 	      if (where <= 0xfffff)
    792 		{
    793 		  /* The addresses should be sorted.  */
    794 		  BFD_ASSERT (extbase == 0);
    795 
    796 		  segbase = where & 0xf0000;
    797 		  addr[0] = (bfd_byte)(segbase >> 12) & 0xff;
    798 		  addr[1] = (bfd_byte)(segbase >> 4) & 0xff;
    799 		  if (! ihex_write_record (abfd, 2, 0, 2, addr))
    800 		    return FALSE;
    801 		}
    802 	      else
    803 		{
    804 		  /* The extended address record and the extended
    805                      linear address record are combined, at least by
    806                      some readers.  We need an extended linear address
    807                      record here, so if we've already written out an
    808                      extended address record, zero it out to avoid
    809                      confusion.  */
    810 		  if (segbase != 0)
    811 		    {
    812 		      addr[0] = 0;
    813 		      addr[1] = 0;
    814 		      if (! ihex_write_record (abfd, 2, 0, 2, addr))
    815 			return FALSE;
    816 		      segbase = 0;
    817 		    }
    818 
    819 		  extbase = where & 0xffff0000;
    820 		  if (where > extbase + 0xffff)
    821 		    {
    822 		      char buf[20];
    823 
    824 		      sprintf_vma (buf, where);
    825 		      (*_bfd_error_handler)
    826 			(_("%s: address 0x%s out of range for Intel Hex file"),
    827 			 bfd_get_filename (abfd), buf);
    828 		      bfd_set_error (bfd_error_bad_value);
    829 		      return FALSE;
    830 		    }
    831 		  addr[0] = (bfd_byte)(extbase >> 24) & 0xff;
    832 		  addr[1] = (bfd_byte)(extbase >> 16) & 0xff;
    833 		  if (! ihex_write_record (abfd, 2, 0, 4, addr))
    834 		    return FALSE;
    835 		}
    836 	    }
    837 
    838 	  rec_addr = where - (extbase + segbase);
    839 
    840           /* Output records shouldn't cross 64K boundaries.  */
    841           if (rec_addr + now > 0xffff)
    842             now = 0x10000 - rec_addr;
    843 
    844 	  if (! ihex_write_record (abfd, now, rec_addr, 0, p))
    845 	    return FALSE;
    846 
    847 	  where += now;
    848 	  p += now;
    849 	  count -= now;
    850 	}
    851     }
    852 
    853   if (abfd->start_address != 0)
    854     {
    855       bfd_vma start;
    856       bfd_byte startbuf[4];
    857 
    858       start = abfd->start_address;
    859 
    860       if (start <= 0xfffff)
    861 	{
    862 	  startbuf[0] = (bfd_byte)((start & 0xf0000) >> 12) & 0xff;
    863 	  startbuf[1] = 0;
    864 	  startbuf[2] = (bfd_byte)(start >> 8) & 0xff;
    865 	  startbuf[3] = (bfd_byte)start & 0xff;
    866 	  if (! ihex_write_record (abfd, 4, 0, 3, startbuf))
    867 	    return FALSE;
    868 	}
    869       else
    870 	{
    871 	  startbuf[0] = (bfd_byte)(start >> 24) & 0xff;
    872 	  startbuf[1] = (bfd_byte)(start >> 16) & 0xff;
    873 	  startbuf[2] = (bfd_byte)(start >> 8) & 0xff;
    874 	  startbuf[3] = (bfd_byte)start & 0xff;
    875 	  if (! ihex_write_record (abfd, 4, 0, 5, startbuf))
    876 	    return FALSE;
    877 	}
    878     }
    879 
    880   if (! ihex_write_record (abfd, 0, 0, 1, NULL))
    881     return FALSE;
    882 
    883   return TRUE;
    884 }
    885 
    886 /* Set the architecture for the output file.  The architecture is
    887    irrelevant, so we ignore errors about unknown architectures.  */
    888 
    889 static bfd_boolean
    890 ihex_set_arch_mach (bfd *abfd,
    891 		    enum bfd_architecture arch,
    892 		    unsigned long mach)
    893 {
    894   if (! bfd_default_set_arch_mach (abfd, arch, mach))
    895     {
    896       if (arch != bfd_arch_unknown)
    897 	return FALSE;
    898     }
    899   return TRUE;
    900 }
    901 
    902 /* Get the size of the headers, for the linker.  */
    903 
    904 static int
    905 ihex_sizeof_headers (bfd *abfd ATTRIBUTE_UNUSED,
    906 		     struct bfd_link_info *info ATTRIBUTE_UNUSED)
    907 {
    908   return 0;
    909 }
    910 
    911 /* Some random definitions for the target vector.  */
    912 
    913 #define	ihex_close_and_cleanup                    _bfd_generic_close_and_cleanup
    914 #define ihex_bfd_free_cached_info                 _bfd_generic_bfd_free_cached_info
    915 #define ihex_new_section_hook                     _bfd_generic_new_section_hook
    916 #define ihex_get_section_contents_in_window       _bfd_generic_get_section_contents_in_window
    917 #define ihex_get_symtab_upper_bound               bfd_0l
    918 #define ihex_canonicalize_symtab                  ((long (*) (bfd *, asymbol **)) bfd_0l)
    919 #define ihex_make_empty_symbol                    _bfd_generic_make_empty_symbol
    920 #define ihex_print_symbol                         _bfd_nosymbols_print_symbol
    921 #define ihex_get_symbol_info                      _bfd_nosymbols_get_symbol_info
    922 #define ihex_bfd_is_target_special_symbol         ((bfd_boolean (*) (bfd *, asymbol *)) bfd_false)
    923 #define ihex_bfd_is_local_label_name              _bfd_nosymbols_bfd_is_local_label_name
    924 #define ihex_get_lineno                           _bfd_nosymbols_get_lineno
    925 #define ihex_find_nearest_line                    _bfd_nosymbols_find_nearest_line
    926 #define ihex_find_inliner_info                    _bfd_nosymbols_find_inliner_info
    927 #define ihex_bfd_make_debug_symbol                _bfd_nosymbols_bfd_make_debug_symbol
    928 #define ihex_read_minisymbols                     _bfd_nosymbols_read_minisymbols
    929 #define ihex_minisymbol_to_symbol                 _bfd_nosymbols_minisymbol_to_symbol
    930 #define ihex_bfd_get_relocated_section_contents   bfd_generic_get_relocated_section_contents
    931 #define ihex_bfd_relax_section                    bfd_generic_relax_section
    932 #define ihex_bfd_gc_sections                      bfd_generic_gc_sections
    933 #define ihex_bfd_lookup_section_flags             bfd_generic_lookup_section_flags
    934 #define ihex_bfd_merge_sections                   bfd_generic_merge_sections
    935 #define ihex_bfd_is_group_section                 bfd_generic_is_group_section
    936 #define ihex_bfd_discard_group                    bfd_generic_discard_group
    937 #define ihex_section_already_linked               _bfd_generic_section_already_linked
    938 #define ihex_bfd_define_common_symbol             bfd_generic_define_common_symbol
    939 #define ihex_bfd_link_hash_table_create           _bfd_generic_link_hash_table_create
    940 #define ihex_bfd_link_hash_table_free             _bfd_generic_link_hash_table_free
    941 #define ihex_bfd_link_add_symbols                 _bfd_generic_link_add_symbols
    942 #define ihex_bfd_link_just_syms                   _bfd_generic_link_just_syms
    943 #define ihex_bfd_copy_link_hash_symbol_type \
    944   _bfd_generic_copy_link_hash_symbol_type
    945 #define ihex_bfd_final_link                       _bfd_generic_final_link
    946 #define ihex_bfd_link_split_section               _bfd_generic_link_split_section
    947 
    948 /* The Intel Hex target vector.  */
    949 
    950 const bfd_target ihex_vec =
    951 {
    952   "ihex",			/* Name.  */
    953   bfd_target_ihex_flavour,
    954   BFD_ENDIAN_UNKNOWN,		/* Target byte order.  */
    955   BFD_ENDIAN_UNKNOWN,		/* Target headers byte order.  */
    956   0,				/* Object flags.  */
    957   (SEC_HAS_CONTENTS | SEC_ALLOC | SEC_LOAD),	/* Section flags.  */
    958   0,				/* Leading underscore.  */
    959   ' ',				/* AR_pad_char.  */
    960   16,				/* AR_max_namelen.  */
    961   0,				/* match priority.  */
    962   bfd_getb64, bfd_getb_signed_64, bfd_putb64,
    963   bfd_getb32, bfd_getb_signed_32, bfd_putb32,
    964   bfd_getb16, bfd_getb_signed_16, bfd_putb16,	/* Data.  */
    965   bfd_getb64, bfd_getb_signed_64, bfd_putb64,
    966   bfd_getb32, bfd_getb_signed_32, bfd_putb32,
    967   bfd_getb16, bfd_getb_signed_16, bfd_putb16,	/* Headers. */
    968 
    969   {
    970     _bfd_dummy_target,
    971     ihex_object_p,		/* bfd_check_format.  */
    972     _bfd_dummy_target,
    973     _bfd_dummy_target,
    974   },
    975   {
    976     bfd_false,
    977     ihex_mkobject,
    978     _bfd_generic_mkarchive,
    979     bfd_false,
    980   },
    981   {				/* bfd_write_contents.  */
    982     bfd_false,
    983     ihex_write_object_contents,
    984     _bfd_write_archive_contents,
    985     bfd_false,
    986   },
    987 
    988   BFD_JUMP_TABLE_GENERIC (ihex),
    989   BFD_JUMP_TABLE_COPY (_bfd_generic),
    990   BFD_JUMP_TABLE_CORE (_bfd_nocore),
    991   BFD_JUMP_TABLE_ARCHIVE (_bfd_noarchive),
    992   BFD_JUMP_TABLE_SYMBOLS (ihex),
    993   BFD_JUMP_TABLE_RELOCS (_bfd_norelocs),
    994   BFD_JUMP_TABLE_WRITE (ihex),
    995   BFD_JUMP_TABLE_LINK (ihex),
    996   BFD_JUMP_TABLE_DYNAMIC (_bfd_nodynamic),
    997 
    998   NULL,
    999 
   1000   NULL
   1001 };
   1002