Made sure that every call to bfd_read, bfd_write, and bfd_seek
[deliverable/binutils-gdb.git] / bfd / srec.c
1 /* BFD back-end for s-record objects.
2 Copyright 1990, 1991, 1992, 1993, 1994 Free Software Foundation, Inc.
3 Written by Steve Chamberlain of Cygnus Support <sac@cygnus.com>.
4
5 This file is part of BFD, the Binary File Descriptor library.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
20
21 /*
22 SUBSECTION
23 S-Record handling
24
25 DESCRIPTION
26
27 Ordinary S-Records cannot hold anything but addresses and
28 data, so that's all that we implement.
29
30 The only interesting thing is that S-Records may come out of
31 order and there is no header, so an initial scan is required
32 to discover the minimum and maximum addresses used to create
33 the vma and size of the only section we create. We
34 arbitrarily call this section ".text".
35
36 When bfd_get_section_contents is called the file is read
37 again, and this time the data is placed into a bfd_alloc'd
38 area.
39
40 Any number of sections may be created for output, we save them
41 up and output them when it's time to close the bfd.
42
43 An s record looks like:
44
45 EXAMPLE
46 S<type><length><address><data><checksum>
47
48 DESCRIPTION
49 Where
50 o length
51 is the number of bytes following upto the checksum. Note that
52 this is not the number of chars following, since it takes two
53 chars to represent a byte.
54 o type
55 is one of:
56 0) header record
57 1) two byte address data record
58 2) three byte address data record
59 3) four byte address data record
60 7) four byte address termination record
61 8) three byte address termination record
62 9) two byte address termination record
63
64 o address
65 is the start address of the data following, or in the case of
66 a termination record, the start address of the image
67 o data
68 is the data.
69 o checksum
70 is the sum of all the raw byte data in the record, from the length
71 upwards, modulo 256 and subtracted from 255.
72
73
74 SUBSECTION
75 Symbol S-Record handling
76
77 DESCRIPTION
78 Some ICE equipment understands an addition to the standard
79 S-Record format; symbols and their addresses can be sent
80 before the data.
81
82 The format of this is:
83 ($$ <modulename>
84 (<space> <symbol> <address>)*)
85 $$
86
87 so a short symbol table could look like:
88
89 EXAMPLE
90 $$ flash.x
91 $$ flash.c
92 _port6 $0
93 _delay $4
94 _start $14
95 _etext $8036
96 _edata $8036
97 _end $8036
98 $$
99
100 DESCRIPTION
101 We allow symbols to be anywhere in the data stream - the module names
102 are always ignored.
103
104 */
105
106 #include "bfd.h"
107 #include "sysdep.h"
108 #include "libbfd.h"
109
110 static boolean srec_write_record PARAMS ((bfd *, int, bfd_vma,
111 const unsigned char *,
112 const unsigned char *));
113 static boolean srec_write_header PARAMS ((bfd *));
114 static boolean srec_write_symbols PARAMS ((bfd *));
115
116 /* Macros for converting between hex and binary. */
117
118 static CONST char digs[] = "0123456789ABCDEF";
119
120 /* Table that gets filled in with numbers corresponding to hex chars. */
121
122 static char hex_value[256];
123
124 #define NOT_HEX 20
125 #define NIBBLE(x) hex_value[(unsigned char)(x)]
126 #define HEX(buffer) ((NIBBLE((buffer)[0])<<4) + NIBBLE((buffer)[1]))
127 #define TOHEX(d, x, ch) \
128 d[1] = digs[(x) & 0xf]; \
129 d[0] = digs[((x)>>4)&0xf]; \
130 ch += ((x) & 0xff);
131 #define ISHEX(x) (hex_value[(unsigned char)(x)] != NOT_HEX)
132
133 /* Initialize by filling in the hex conversion array. */
134
135 static void
136 srec_init ()
137 {
138 unsigned int i;
139 static boolean inited = false;
140
141 if (inited == false)
142 {
143 inited = true;
144
145 for (i = 0; i < sizeof (hex_value); i++)
146 {
147 hex_value[i] = NOT_HEX;
148 }
149 for (i = 0; i < 10; i++)
150 {
151 hex_value[i + '0'] = i;
152 }
153 for (i = 0; i < 6; i++)
154 {
155 hex_value[i + 'a'] = i + 10;
156 hex_value[i + 'A'] = i + 10;
157 }
158 }
159 }
160
161
162 /* The maximum number of bytes on a line is FF */
163 #define MAXCHUNK 0xff
164 /* The number of bytes we fit onto a line on output */
165 #define CHUNK 21
166
167 /* We cannot output our srecords as we see them, we have to glue them
168 together, this is done in this structure : */
169
170 struct srec_data_list_struct
171 {
172 unsigned char *data;
173 bfd_vma where;
174 bfd_size_type size;
175 struct srec_data_list_struct *next;
176
177
178 };
179 typedef struct srec_data_list_struct srec_data_list_type;
180
181
182 typedef struct srec_data_struct
183 {
184 srec_data_list_type *head;
185 unsigned int type;
186
187 int done_symbol_read;
188 int count;
189 asymbol *symbols;
190 char *strings;
191 int symbol_idx;
192 int string_size;
193 int string_idx;
194 }
195 tdata_type;
196
197 static boolean srec_write_section PARAMS ((bfd *, tdata_type *,
198 srec_data_list_type *));
199 static boolean srec_write_terminator PARAMS ((bfd *, tdata_type *));
200
201 /*
202 called once per input S-Record, used to work out vma and size of data.
203 */
204
205 static bfd_vma low, high;
206
207 /*ARGSUSED*/
208 static void
209 size_symbols (abfd, buf, len, val)
210 bfd *abfd;
211 char *buf;
212 int len;
213 int val;
214 {
215 abfd->symcount++;
216 abfd->tdata.srec_data->string_size += len + 1;
217 }
218
219 static void
220 fillup_symbols (abfd, buf, len, val)
221 bfd *abfd;
222 char *buf;
223 int len;
224 int val;
225 {
226 if (!abfd->tdata.srec_data->done_symbol_read)
227 {
228 asymbol *p;
229 if (abfd->tdata.srec_data->symbols == 0)
230 {
231 abfd->tdata.srec_data->symbols = (asymbol *) bfd_alloc (abfd, abfd->symcount * sizeof (asymbol));
232 abfd->tdata.srec_data->strings = (char *) bfd_alloc (abfd, abfd->tdata.srec_data->string_size);
233 if (!abfd->tdata.srec_data->symbols || !abfd->tdata.srec_data->strings)
234 {
235 bfd_set_error (bfd_error_no_memory);
236 abort (); /* FIXME */
237 }
238 abfd->tdata.srec_data->symbol_idx = 0;
239 abfd->tdata.srec_data->string_idx = 0;
240 }
241
242 p = abfd->tdata.srec_data->symbols + abfd->tdata.srec_data->symbol_idx++;
243 p->the_bfd = abfd;
244 p->name = abfd->tdata.srec_data->strings + abfd->tdata.srec_data->string_idx;
245 memcpy ((char *) (p->name), buf, len + 1);
246 abfd->tdata.srec_data->string_idx += len + 1;
247 p->value = val;
248 p->flags = BSF_EXPORT | BSF_GLOBAL;
249 p->section = &bfd_abs_section;
250 p->udata = 0;
251 }
252 }
253 /*ARGSUSED*/
254 static void
255 size_srec (abfd, section, address, raw, length)
256 bfd *abfd;
257 asection *section;
258 bfd_vma address;
259 bfd_byte *raw;
260 unsigned int length;
261 {
262 if (address < low)
263 low = address;
264 if (address + length > high)
265 high = address + length - 1;
266 }
267
268
269 /*
270 called once per input S-Record, copies data from input into bfd_alloc'd area
271 */
272
273 /*ARGSUSED*/
274 static void
275 fillup (abfd, section, address, raw, length)
276 bfd *abfd;
277 asection *section;
278 bfd_vma address;
279 bfd_byte *raw;
280 unsigned int length;
281 {
282 unsigned int i;
283 bfd_byte *dst =
284 (bfd_byte *) (section->used_by_bfd) + address - section->vma;
285 /* length -1 because we don't read in the checksum */
286 for (i = 0; i < length - 1; i++)
287 {
288 *dst = HEX (raw);
289 dst++;
290 raw += 2;
291 }
292 }
293
294 /* Pass over an S-Record file, calling one of the above functions on each
295 record. */
296
297 static int
298 white (x)
299 char x;
300 {
301 return (x == ' ' || x == '\t' || x == '\n' || x == '\r');
302 }
303 static int
304 skipwhite (src, abfd)
305 char *src;
306 bfd *abfd;
307 {
308 int eof = 0;
309 while (white (*src) && !eof)
310 {
311 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
312 }
313 return eof;
314 }
315
316 static boolean
317 srec_mkobject (abfd)
318 bfd *abfd;
319 {
320 if (abfd->tdata.srec_data == 0)
321 {
322 tdata_type *tdata = (tdata_type *) bfd_alloc (abfd, sizeof (tdata_type));
323 if (!tdata)
324 {
325 bfd_set_error (bfd_error_no_memory);
326 return false;
327 }
328 abfd->tdata.srec_data = tdata;
329 tdata->type = 1;
330 tdata->head = (srec_data_list_type *) NULL;
331 }
332 return true;
333
334 }
335
336 static void
337 pass_over (abfd, func, symbolfunc, section)
338 bfd *abfd;
339 void (*func) ();
340 void (*symbolfunc) ();
341 asection *section;
342 {
343 unsigned int bytes_on_line;
344 boolean eof = false;
345
346 srec_mkobject (abfd);
347 /* To the front of the file */
348 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0)
349 abort ();
350 while (eof == false)
351 {
352 char buffer[MAXCHUNK];
353 char *src = buffer;
354 char type;
355 bfd_vma address = 0;
356
357 /* Find first 'S' or $ */
358 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
359 switch (*src)
360 {
361 default:
362 if (eof)
363 return;
364 break;
365
366 case '$':
367 /* Inside a symbol definition - just ignore the module name */
368 while (*src != '\n' && !eof)
369 {
370 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
371 }
372 break;
373
374 case ' ':
375 /* spaces - maybe just before a symbol */
376 while (*src != '\n' && *src != '\r' && white (*src))
377 {
378 eof = skipwhite (src, abfd);
379
380 {
381 int val = 0;
382 int slen = 0;
383 char symbol[MAXCHUNK];
384
385 /* get the symbol part */
386 while (!eof && !white (*src) && slen < MAXCHUNK)
387 {
388 symbol[slen++] = *src;
389 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
390 }
391 symbol[slen] = 0;
392 eof = skipwhite (src, abfd);
393 /* skip the $ for the hex value */
394 if (*src == '$')
395 {
396 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
397 }
398
399 /* Scan off the hex number */
400 while (isxdigit (*src))
401 {
402 val *= 16;
403 if (isdigit (*src))
404 val += *src - '0';
405 else if (isupper (*src))
406 {
407 val += *src - 'A' + 10;
408 }
409 else
410 {
411 val += *src - 'a' + 10;
412 }
413 eof = (boolean) (bfd_read (src, 1, 1, abfd) != 1);
414 }
415 symbolfunc (abfd, symbol, slen, val);
416 }
417 }
418 break;
419 case 'S':
420 src++;
421
422 /* Fetch the type and the length */
423 if (bfd_read (src, 1, 3, abfd) != 3)
424 abort (); /* FIXME */
425
426 type = *src++;
427
428 if (!ISHEX (src[0]) || !ISHEX (src[1]))
429 break;
430
431 bytes_on_line = HEX (src);
432
433 if (bytes_on_line > MAXCHUNK / 2)
434 break;
435 src += 2;
436
437 if (bfd_read (src, 1, bytes_on_line * 2, abfd) != bytes_on_line * 2)
438 abort (); /* FIXME */
439
440 switch (type)
441 {
442 case '0':
443 case '5':
444 /* Prologue - ignore */
445 break;
446 case '3':
447 address = HEX (src);
448 src += 2;
449 bytes_on_line--;
450
451 case '2':
452 address = HEX (src) | (address << 8);
453 src += 2;
454 bytes_on_line--;
455 case '1':
456 address = HEX (src) | (address << 8);
457 src += 2;
458 address = HEX (src) | (address << 8);
459 src += 2;
460 bytes_on_line -= 2;
461 func (abfd, section, address, src, bytes_on_line);
462 break;
463 default:
464 return;
465 }
466 }
467 }
468
469 }
470
471 static bfd_target *
472 object_p (abfd)
473 bfd *abfd;
474 {
475 asection *section;
476 /* We create one section called .text for all the contents,
477 and allocate enough room for the entire file. */
478
479 section = bfd_make_section (abfd, ".text");
480 section->_raw_size = 0;
481 section->vma = 0xffffffff;
482 low = 0xffffffff;
483 high = 0;
484 pass_over (abfd, size_srec, size_symbols, section);
485 section->_raw_size = high - low;
486 section->vma = low;
487 section->flags = SEC_HAS_CONTENTS | SEC_LOAD | SEC_ALLOC;
488
489 if (abfd->symcount)
490 abfd->flags |= HAS_SYMS;
491 return abfd->xvec;
492 }
493
494 static bfd_target *
495 srec_object_p (abfd)
496 bfd *abfd;
497 {
498 char b[4];
499
500 srec_init ();
501
502 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
503 || bfd_read (b, 1, 4, abfd) != 4)
504 return NULL;
505
506 if (b[0] != 'S' || !ISHEX (b[1]) || !ISHEX (b[2]) || !ISHEX (b[3]))
507 return (bfd_target *) NULL;
508
509 /* We create one section called .text for all the contents,
510 and allocate enough room for the entire file. */
511
512 return object_p (abfd);
513 }
514
515
516 static bfd_target *
517 symbolsrec_object_p (abfd)
518 bfd *abfd;
519 {
520 char b[4];
521
522 srec_init ();
523
524 if (bfd_seek (abfd, (file_ptr) 0, SEEK_SET) != 0
525 || bfd_read (b, 1, 4, abfd) != 4)
526 return NULL;
527
528 if (b[0] != '$' || b[1] != '$')
529 return (bfd_target *) NULL;
530
531 return object_p (abfd);
532 }
533
534
535 static boolean
536 srec_get_section_contents (abfd, section, location, offset, count)
537 bfd *abfd;
538 asection *section;
539 PTR location;
540 file_ptr offset;
541 bfd_size_type count;
542 {
543 if (section->used_by_bfd == (PTR) NULL)
544 {
545 section->used_by_bfd = (PTR) bfd_alloc (abfd, section->_raw_size);
546 if (!section->used_by_bfd)
547 {
548 bfd_set_error (bfd_error_no_memory);
549 return false;
550 }
551
552 pass_over (abfd, fillup, fillup_symbols, section);
553 }
554 memcpy ((PTR) location,
555 (PTR) ((char *) (section->used_by_bfd) + offset),
556 count);
557 return true;
558 }
559
560
561
562 boolean
563 srec_set_arch_mach (abfd, arch, machine)
564 bfd *abfd;
565 enum bfd_architecture arch;
566 unsigned long machine;
567 {
568 return bfd_default_set_arch_mach (abfd, arch, machine);
569 }
570
571
572 /* we have to save up all the Srecords for a splurge before output,
573 also remember */
574
575 static boolean
576 srec_set_section_contents (abfd, section, location, offset, bytes_to_do)
577 bfd *abfd;
578 sec_ptr section;
579 PTR location;
580 file_ptr offset;
581 bfd_size_type bytes_to_do;
582 {
583 tdata_type *tdata = abfd->tdata.srec_data;
584 srec_data_list_type *entry = (srec_data_list_type *)
585 bfd_alloc (abfd, sizeof (srec_data_list_type));
586
587 if (!entry)
588 {
589 bfd_set_error (bfd_error_no_memory);
590 return false;
591 }
592
593 if ((section->flags & SEC_ALLOC)
594 && (section->flags & SEC_LOAD))
595 {
596 unsigned char *data = (unsigned char *) bfd_alloc (abfd, bytes_to_do);
597 if (!data)
598 {
599 bfd_set_error (bfd_error_no_memory);
600 return false;
601 }
602 memcpy ((PTR) data, location, bytes_to_do);
603
604 if ((section->lma + offset + bytes_to_do) <= 0xffff)
605 {
606
607 }
608 else if ((section->lma + offset + bytes_to_do) <= 0xffffff
609 && tdata->type < 2)
610 {
611 tdata->type = 2;
612 }
613 else
614 {
615 tdata->type = 3;
616 }
617
618 entry->data = data;
619 entry->where = section->lma + offset;
620 entry->size = bytes_to_do;
621 entry->next = tdata->head;
622 tdata->head = entry;
623 }
624 return true;
625 }
626
627 /* Write a record of type, of the supplied number of bytes. The
628 supplied bytes and length don't have a checksum. That's worked out
629 here
630 */
631 static boolean
632 srec_write_record (abfd, type, address, data, end)
633 bfd *abfd;
634 int type;
635 bfd_vma address;
636 const unsigned char *data;
637 const unsigned char *end;
638 {
639 char buffer[MAXCHUNK];
640
641 unsigned int check_sum = 0;
642 CONST unsigned char *src = data;
643 char *dst = buffer;
644 char *length;
645
646
647 *dst++ = 'S';
648 *dst++ = '0' + type;
649
650 length = dst;
651 dst += 2; /* leave room for dst*/
652
653 switch (type)
654 {
655 case 3:
656 case 7:
657 TOHEX (dst, (address >> 24), check_sum);
658 dst += 2;
659 case 8:
660 case 2:
661 TOHEX (dst, (address >> 16), check_sum);
662 dst += 2;
663 case 9:
664 case 1:
665 case 0:
666 TOHEX (dst, (address >> 8), check_sum);
667 dst += 2;
668 TOHEX (dst, (address), check_sum);
669 dst += 2;
670 break;
671
672 }
673 for (src = data; src < end; src++)
674 {
675 TOHEX (dst, *src, check_sum);
676 dst += 2;
677 }
678
679 /* Fill in the length */
680 TOHEX (length, (dst - length) / 2, check_sum);
681 check_sum &= 0xff;
682 check_sum = 255 - check_sum;
683 TOHEX (dst, check_sum, check_sum);
684 dst += 2;
685
686 *dst++ = '\r';
687 *dst++ = '\n';
688 if (bfd_write ((PTR) buffer, 1, dst - buffer, abfd) != dst - buffer)
689 return false;
690 return true;
691 }
692
693
694
695 static boolean
696 srec_write_header (abfd)
697 bfd *abfd;
698 {
699 unsigned char buffer[MAXCHUNK];
700 unsigned char *dst = buffer;
701 unsigned int i;
702
703 /* I'll put an arbitary 40 char limit on header size */
704 for (i = 0; i < 40 && abfd->filename[i]; i++)
705 {
706 *dst++ = abfd->filename[i];
707 }
708 return srec_write_record (abfd, 0, 0, buffer, dst);
709 }
710
711 static boolean
712 srec_write_section (abfd, tdata, list)
713 bfd *abfd;
714 tdata_type *tdata;
715 srec_data_list_type *list;
716 {
717 unsigned int bytes_written = 0;
718 unsigned char *location = list->data;
719
720 while (bytes_written < list->size)
721 {
722 bfd_vma address;
723
724 unsigned int bytes_this_chunk = list->size - bytes_written;
725
726 if (bytes_this_chunk > CHUNK)
727 {
728 bytes_this_chunk = CHUNK;
729 }
730
731 address = list->where + bytes_written;
732
733 if (! srec_write_record (abfd,
734 tdata->type,
735 address,
736 location,
737 location + bytes_this_chunk))
738 return false;
739
740 bytes_written += bytes_this_chunk;
741 location += bytes_this_chunk;
742 }
743
744 return true;
745 }
746
747 static boolean
748 srec_write_terminator (abfd, tdata)
749 bfd *abfd;
750 tdata_type *tdata;
751 {
752 unsigned char buffer[2];
753
754 return srec_write_record (abfd, 10 - tdata->type,
755 abfd->start_address, buffer, buffer);
756 }
757
758
759
760 static boolean
761 srec_write_symbols (abfd)
762 bfd *abfd;
763 {
764 char buffer[MAXCHUNK];
765 /* Dump out the symbols of a bfd */
766 int i;
767 int len = bfd_get_symcount (abfd);
768
769 if (len)
770 {
771 size_t len;
772 asymbol **table = bfd_get_outsymbols (abfd);
773 sprintf (buffer, "$$ %s\r\n", abfd->filename);
774
775 len = strlen (buffer) + 1;
776 if (bfd_write (buffer, len, 1, abfd) != len)
777 return false;
778
779 for (i = 0; i < len; i++)
780 {
781 asymbol *s = table[i];
782 #if 0
783 int len = strlen (s->name);
784
785 /* If this symbol has a .[ocs] in it, it's probably a file name
786 and we'll output that as the module name */
787
788 if (len > 3 && s->name[len - 2] == '.')
789 {
790 int l;
791 sprintf (buffer, "$$ %s\r\n", s->name);
792 l = strlen (buffer);
793 if (bfd_write (buffer, l, 1, abfd) != l)
794 return false;
795 }
796 else
797 #endif
798 if (s->flags & (BSF_GLOBAL | BSF_LOCAL)
799 && (s->flags & BSF_DEBUGGING) == 0
800 && s->name[0] != '.'
801 && s->name[0] != 't')
802 {
803 /* Just dump out non debug symbols */
804
805 int l;
806 char buf2[40], *p;
807
808 sprintf_vma (buf2,
809 s->value + s->section->output_section->lma
810 + s->section->output_offset);
811 p = buf2;
812 while (p[0] == '0' && p[1] != 0)
813 p++;
814 sprintf (buffer, " %s $%s\r\n", s->name, p);
815 l = strlen (buffer);
816 if (bfd_write (buffer, l, 1, abfd) != l)
817 return false;
818 }
819 }
820 sprintf (buffer, "$$ \r\n");
821 len = strlen (buffer) + 1;
822 if (bfd_write (buffer, len, 1, abfd) != len)
823 return false;
824 }
825
826 return true;
827 }
828
829 static boolean
830 internal_srec_write_object_contents (abfd, symbols)
831 bfd *abfd;
832 int symbols;
833 {
834 tdata_type *tdata = abfd->tdata.srec_data;
835 srec_data_list_type *list;
836
837 if (symbols)
838 {
839 if (! srec_write_symbols (abfd))
840 return false;
841 }
842
843 if (! srec_write_header (abfd))
844 return false;
845
846 /* Now wander though all the sections provided and output them */
847 list = tdata->head;
848
849 while (list != (srec_data_list_type *) NULL)
850 {
851 if (! srec_write_section (abfd, tdata, list))
852 return false;
853 list = list->next;
854 }
855 return srec_write_terminator (abfd, tdata);
856 }
857
858 static boolean
859 srec_write_object_contents (abfd)
860 bfd *abfd;
861 {
862 return internal_srec_write_object_contents (abfd, 0);
863 }
864
865 static boolean
866 symbolsrec_write_object_contents (abfd)
867 bfd *abfd;
868 {
869 return internal_srec_write_object_contents (abfd, 1);
870 }
871
872 /*ARGSUSED*/
873 static int
874 srec_sizeof_headers (abfd, exec)
875 bfd *abfd;
876 boolean exec;
877 {
878 return 0;
879 }
880
881 static asymbol *
882 srec_make_empty_symbol (abfd)
883 bfd *abfd;
884 {
885 asymbol *new = (asymbol *) bfd_zalloc (abfd, sizeof (asymbol));
886 if (new)
887 new->the_bfd = abfd;
888 return new;
889 }
890
891 static long
892 srec_get_symtab_upper_bound (abfd)
893 bfd *abfd;
894 {
895 /* Read in all the info */
896 if (! srec_get_section_contents (abfd, abfd->sections, 0, 0, 0))
897 return -1;
898 return (bfd_get_symcount (abfd) + 1) * (sizeof (asymbol *));
899 }
900
901 static long
902 srec_get_symtab (abfd, alocation)
903 bfd *abfd;
904 asymbol **alocation;
905 {
906 int lim = abfd->symcount;
907 int i;
908 for (i = 0; i < lim; i++)
909 {
910 alocation[i] = abfd->tdata.srec_data->symbols + i;
911 }
912 alocation[i] = 0;
913 return lim;
914 }
915
916 /*ARGSUSED*/
917 void
918 srec_get_symbol_info (ignore_abfd, symbol, ret)
919 bfd *ignore_abfd;
920 asymbol *symbol;
921 symbol_info *ret;
922 {
923 bfd_symbol_info (symbol, ret);
924 }
925
926 /*ARGSUSED*/
927 void
928 srec_print_symbol (ignore_abfd, afile, symbol, how)
929 bfd *ignore_abfd;
930 PTR afile;
931 asymbol *symbol;
932 bfd_print_symbol_type how;
933 {
934 FILE *file = (FILE *) afile;
935 switch (how)
936 {
937 case bfd_print_symbol_name:
938 fprintf (file, "%s", symbol->name);
939 break;
940 default:
941 bfd_print_symbol_vandf ((PTR) file, symbol);
942 fprintf (file, " %-5s %s",
943 symbol->section->name,
944 symbol->name);
945
946 }
947 }
948
949 #define FOO PROTO
950 #define srec_new_section_hook (FOO(boolean, (*), (bfd *, asection *)))bfd_true
951
952 #define srec_get_reloc_upper_bound (FOO(long, (*),(bfd*, asection *)))bfd_0l
953 #define srec_canonicalize_reloc (FOO(long, (*),(bfd*,asection *, arelent **, asymbol **))) bfd_0l
954
955
956
957 #define srec_openr_next_archived_file (FOO(bfd *, (*), (bfd*,bfd*))) bfd_nullvoidptr
958 #define srec_find_nearest_line (FOO(boolean, (*),(bfd*,asection*,asymbol**,bfd_vma, CONST char**, CONST char**, unsigned int *))) bfd_false
959 #define srec_generic_stat_arch_elt (FOO(int, (*), (bfd *,struct stat *))) bfd_0
960
961
962 #define srec_core_file_failing_command (char *(*)())(bfd_nullvoidptr)
963 #define srec_core_file_failing_signal (int (*)())bfd_0
964 #define srec_core_file_matches_executable_p (FOO(boolean, (*),(bfd*, bfd*)))bfd_false
965 #define srec_slurp_armap bfd_true
966 #define srec_slurp_extended_name_table bfd_true
967 #define srec_truncate_arname (void (*)())bfd_nullvoidptr
968 #define srec_write_armap (FOO( boolean, (*),(bfd *, unsigned int, struct orl *, unsigned int, int))) bfd_nullvoidptr
969 #define srec_get_lineno (struct lineno_cache_entry *(*)())bfd_nullvoidptr
970 #define srec_close_and_cleanup bfd_generic_close_and_cleanup
971 #define srec_bfd_debug_info_start bfd_void
972 #define srec_bfd_debug_info_end bfd_void
973 #define srec_bfd_debug_info_accumulate (FOO(void, (*), (bfd *, asection *))) bfd_void
974 #define srec_bfd_get_relocated_section_contents bfd_generic_get_relocated_section_contents
975 #define srec_bfd_relax_section bfd_generic_relax_section
976 #define srec_bfd_reloc_type_lookup \
977 ((CONST struct reloc_howto_struct *(*) PARAMS ((bfd *, bfd_reloc_code_real_type))) bfd_nullvoidptr)
978 #define srec_bfd_make_debug_symbol \
979 ((asymbol *(*) PARAMS ((bfd *, void *, unsigned long))) bfd_nullvoidptr)
980 #define srec_bfd_link_hash_table_create _bfd_generic_link_hash_table_create
981 #define srec_bfd_link_add_symbols _bfd_generic_link_add_symbols
982 #define srec_bfd_final_link _bfd_generic_final_link
983
984 #define srec_bfd_copy_private_section_data \
985 ((boolean (*) PARAMS ((bfd *, asection *, bfd *, asection *))) bfd_true)
986 #define srec_bfd_copy_private_bfd_data \
987 ((boolean (*) PARAMS ((bfd *, bfd *))) bfd_true)
988 #define srec_bfd_is_local_label bfd_generic_is_local_label
989 #define srec_bfd_free_cached_info bfd_true
990
991 bfd_target srec_vec =
992 {
993 "srec", /* name */
994 bfd_target_srec_flavour,
995 true, /* target byte order */
996 true, /* target headers byte order */
997 (HAS_RELOC | EXEC_P | /* object flags */
998 HAS_LINENO | HAS_DEBUG |
999 HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
1000 (SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
1001 | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
1002 0, /* leading underscore */
1003 ' ', /* ar_pad_char */
1004 16, /* ar_max_namelen */
1005 1, /* minimum alignment */
1006 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
1007 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
1008 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
1009 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
1010 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
1011 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
1012
1013 {
1014 _bfd_dummy_target,
1015 srec_object_p, /* bfd_check_format */
1016 (struct bfd_target * (*)()) bfd_nullvoidptr,
1017 (struct bfd_target * (*)()) bfd_nullvoidptr,
1018 },
1019 {
1020 bfd_false,
1021 srec_mkobject,
1022 _bfd_generic_mkarchive,
1023 bfd_false,
1024 },
1025 { /* bfd_write_contents */
1026 bfd_false,
1027 srec_write_object_contents,
1028 _bfd_write_archive_contents,
1029 bfd_false,
1030 },
1031 JUMP_TABLE (srec)
1032 };
1033
1034
1035
1036 bfd_target symbolsrec_vec =
1037 {
1038 "symbolsrec", /* name */
1039 bfd_target_srec_flavour,
1040 true, /* target byte order */
1041 true, /* target headers byte order */
1042 (HAS_RELOC | EXEC_P | /* object flags */
1043 HAS_LINENO | HAS_DEBUG |
1044 HAS_SYMS | HAS_LOCALS | WP_TEXT | D_PAGED),
1045 (SEC_CODE | SEC_DATA | SEC_ROM | SEC_HAS_CONTENTS
1046 | SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
1047 0, /* leading underscore */
1048 ' ', /* ar_pad_char */
1049 16, /* ar_max_namelen */
1050 1, /* minimum alignment */
1051 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
1052 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
1053 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* data */
1054 bfd_getb64, bfd_getb_signed_64, bfd_putb64,
1055 bfd_getb32, bfd_getb_signed_32, bfd_putb32,
1056 bfd_getb16, bfd_getb_signed_16, bfd_putb16, /* hdrs */
1057
1058 {
1059 _bfd_dummy_target,
1060 symbolsrec_object_p, /* bfd_check_format */
1061 (struct bfd_target * (*)()) bfd_nullvoidptr,
1062 (struct bfd_target * (*)()) bfd_nullvoidptr,
1063 },
1064 {
1065 bfd_false,
1066 srec_mkobject,
1067 _bfd_generic_mkarchive,
1068 bfd_false,
1069 },
1070 { /* bfd_write_contents */
1071 bfd_false,
1072 symbolsrec_write_object_contents,
1073 _bfd_write_archive_contents,
1074 bfd_false,
1075 },
1076 JUMP_TABLE (srec),
1077 (PTR) 0
1078 };
This page took 0.075682 seconds and 5 git commands to generate.