Merge branch 'vendor/LIBARCHIVE'
[dragonfly.git] / contrib / binutils-2.22 / bfd / ihex.c
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@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 };