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