Now full of documentation. Yum Yum.
[deliverable/binutils-gdb.git] / bfd / ieee.c
CommitLineData
ce3f6d51 1/* bfd back-end for ieee-695 objects.
d0ec7a8e 2
ce3f6d51 3 IEEE 695 format is a stream of records, which we parse using a simple one-
9b4641a6
JG
4 token (which is one byte in this lexicon) lookahead recursive decent
5 parser. */
87f86b4e 6
9b4641a6 7/* Copyright (C) 1990, 1991 Free Software Foundation, Inc.
87f86b4e 8
9b4641a6 9This file is part of BFD, the Binary File Diddler.
87f86b4e 10
9b4641a6
JG
11BFD is free software; you can redistribute it and/or modify
12it under the terms of the GNU General Public License as published by
13the Free Software Foundation; either version 1, or (at your option)
14any later version.
87f86b4e 15
9b4641a6
JG
16BFD is distributed in the hope that it will be useful,
17but WITHOUT ANY WARRANTY; without even the implied warranty of
18MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19GNU General Public License for more details.
87f86b4e 20
9b4641a6
JG
21You should have received a copy of the GNU General Public License
22along with BFD; see the file COPYING. If not, write to
23the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
87f86b4e 24
d0ec7a8e 25
7ed4093a 26#include <sysdep.h>
87f86b4e
DHW
27#include "bfd.h"
28#include "libbfd.h"
87f86b4e
DHW
29#include "ieee.h"
30#include "libieee.h"
31
ce3f6d51
JG
32/* Functions for writing to ieee files in the strange way that the
33 standard requires. */
87f86b4e
DHW
34
35static void
301dfc71
SC
36DEFUN(ieee_write_byte,(abfd, byte),
37 bfd *abfd AND
38 bfd_byte byte)
87f86b4e 39{
d0ec7a8e 40 bfd_write((PTR)&byte, 1, 1, abfd);
87f86b4e
DHW
41}
42
43
44static void
301dfc71
SC
45DEFUN(ieee_write_2bytes,(abfd, bytes),
46 bfd *abfd AND
47 int bytes)
87f86b4e
DHW
48{
49 bfd_byte buffer[2];
50 buffer[0] = bytes >> 8;
51 buffer[1] = bytes & 0xff;
52
d0ec7a8e 53 bfd_write((PTR)buffer, 1, 2, abfd);
87f86b4e
DHW
54}
55
56static void
301dfc71
SC
57DEFUN(ieee_write_int,(abfd, value),
58 bfd *abfd AND
59 bfd_vma value)
87f86b4e
DHW
60{
61 if (value >= 0 && value <= 127) {
62 ieee_write_byte(abfd, value);
63 }
64 else {
65 unsigned int length;
66 /* How many significant bytes ? */
67 /* FIXME FOR LONGER INTS */
68 if (value & 0xff000000) {
69 length = 4;
70 }
71 else if (value & 0x00ff0000) {
72 length = 3;
73 }
74 else if (value & 0x0000ff00) {
75 length = 2;
76 }
77 else length = 1;
78
ce3f6d51 79 ieee_write_byte(abfd, (int)ieee_number_repeat_start_enum + length);
87f86b4e
DHW
80 switch (length) {
81 case 4:
82 ieee_write_byte(abfd, value >> 24);
83 case 3:
84 ieee_write_byte(abfd, value >> 16);
85 case 2:
86 ieee_write_byte(abfd, value >> 8);
87 case 1:
88 ieee_write_byte(abfd, value);
89 }
90 }
91}
92
93static void
301dfc71
SC
94DEFUN(ieee_write_id,(abfd, id),
95 bfd *abfd AND
96 CONST char *id)
87f86b4e
DHW
97{
98 size_t length = strlen(id);
99 if (length >= 0 && length <= 127) {
100 ieee_write_byte(abfd, length);
101 }
102 else if (length < 255) {
103 ieee_write_byte(abfd, ieee_extension_length_1_enum);
104 ieee_write_byte(abfd, length);
105 }
106 else if (length < 65535) {
107 ieee_write_byte(abfd, ieee_extension_length_2_enum);
108 ieee_write_byte(abfd, length >> 8);
109 ieee_write_byte(abfd, length & 0xff);
110 }
111 else {
112 BFD_FAIL();
113 }
d0ec7a8e 114 bfd_write((PTR)id, 1, length, abfd);
87f86b4e
DHW
115}
116/***************************************************************************
117Functions for reading from ieee files in the strange way that the
118standard requires:
119*/
87f86b4e 120
d0ec7a8e 121
6f715d66
SC
122#define this_byte(ieee) *((ieee)->input_p)
123#define next_byte(ieee) ((ieee)->input_p++)
124#define this_byte_and_next(ieee) (*((ieee)->input_p++))
87f86b4e
DHW
125
126
301dfc71 127static unsigned short
d0ec7a8e 128DEFUN(read_2bytes,(ieee),
6f715d66 129 common_header_type *ieee)
87f86b4e 130{
d0ec7a8e
SC
131 unsigned char c1 = this_byte_and_next(ieee);
132 unsigned char c2 = this_byte_and_next(ieee);
87f86b4e
DHW
133 return (c1<<8 ) | c2;
134
135}
136
137static void
d0ec7a8e 138DEFUN(bfd_get_string,(ieee, string, length),
6f715d66 139 common_header_type *ieee AND
301dfc71
SC
140 char *string AND
141 size_t length)
87f86b4e
DHW
142{
143 size_t i;
144 for (i= 0; i < length; i++) {
d0ec7a8e 145 string[i] = this_byte_and_next(ieee);
87f86b4e
DHW
146 }
147}
148
301dfc71 149static char *
d0ec7a8e 150DEFUN(read_id,(ieee),
6f715d66 151 common_header_type *ieee)
87f86b4e
DHW
152{
153 size_t length;
154 char *string;
d0ec7a8e 155 length = this_byte_and_next(ieee);
87f86b4e
DHW
156 if (length >= 0x00 && length <= 0x7f) {
157 /* Simple string of length 0 to 127 */
158 }
159 else if (length == 0xde) {
160 /* Length is next byte, allowing 0..255 */
d0ec7a8e 161 length = this_byte_and_next(ieee);
87f86b4e
DHW
162 }
163 else if (length == 0xdf) {
164 /* Length is next two bytes, allowing 0..65535 */
d0ec7a8e
SC
165 length = this_byte_and_next(ieee) ;
166 length = (length * 256) + this_byte_and_next(ieee);
87f86b4e
DHW
167 }
168 /* Buy memory and read string */
d0ec7a8e
SC
169 string = bfd_alloc(ieee->abfd, length+1);
170 bfd_get_string(ieee, string, length);
87f86b4e
DHW
171 string[length] = 0;
172 return string;
173}
174
175static void
d0ec7a8e 176DEFUN(ieee_write_expression,(abfd, value, section, symbol, pcrel, index),
301dfc71
SC
177 bfd*abfd AND
178 bfd_vma value AND
179 asection *section AND
d0ec7a8e
SC
180 asymbol *symbol AND
181 boolean pcrel AND
182 unsigned int index)
87f86b4e
DHW
183{
184 unsigned int plus_count = 0;
185 ieee_write_int(abfd, value);
186 if (section != (asection *)NULL) {
187 plus_count++;
188 ieee_write_byte(abfd, ieee_variable_L_enum);
189 ieee_write_byte(abfd, section->index +IEEE_SECTION_NUMBER_BASE);
190 }
191
d0ec7a8e
SC
192
193
87f86b4e
DHW
194 if (symbol != (asymbol *)NULL) {
195 plus_count++;
196 if ((symbol->flags & BSF_UNDEFINED ) ||
197 (symbol->flags & BSF_FORT_COMM)) {
198 ieee_write_byte(abfd, ieee_variable_X_enum);
199 ieee_write_int(abfd, symbol->value);
200 }
201 else if (symbol->flags & BSF_GLOBAL) {
202 ieee_write_byte(abfd, ieee_variable_I_enum);
203 ieee_write_int(abfd, symbol->value);
204 }
301dfc71
SC
205 else if (symbol->flags & BSF_LOCAL) {
206 /* This is a reference to a defined local symbol,
207 We can easily do a local as a section+offset */
208 if (symbol->section != (asection *)NULL) {
209 /* If this symbol is not absolute, add the base of it */
210 ieee_write_byte(abfd, ieee_variable_L_enum);
211 ieee_write_byte(abfd, symbol->section->index +
212 IEEE_SECTION_NUMBER_BASE);
213 plus_count++;
214 }
215
216 ieee_write_int(abfd, symbol->value);
217 }
87f86b4e 218 else {
301dfc71 219
87f86b4e
DHW
220 BFD_FAIL();
221 }
222 }
223
d0ec7a8e
SC
224 if(pcrel) {
225 /* subtract the pc from here by asking for PC of this section*/
226 ieee_write_byte(abfd, ieee_variable_P_enum);
227 ieee_write_byte(abfd, index +IEEE_SECTION_NUMBER_BASE);
228 ieee_write_byte(abfd, ieee_function_minus_enum);
229 }
230
231 while (plus_count > 0) {
87f86b4e
DHW
232 ieee_write_byte(abfd, ieee_function_plus_enum);
233 plus_count--;
234 }
235
236}
237
238
239
240
241
242
243
244
245
246/*****************************************************************************/
247
248/*
249writes any integer into the buffer supplied and always takes 5 bytes
250*/
251static void
301dfc71
SC
252DEFUN(ieee_write_int5,(buffer, value),
253 bfd_byte*buffer AND
254 bfd_vma value )
87f86b4e
DHW
255{
256 buffer[0] = ieee_number_repeat_4_enum;
257 buffer[1] = (value >> 24 ) & 0xff;
258 buffer[2] = (value >> 16 ) & 0xff;
259 buffer[3] = (value >> 8 ) & 0xff;
301dfc71
SC
260 buffer[4] = (value >> 0 ) & 0xff;
261}
262static void
263DEFUN(ieee_write_int5_out, (abfd, value),
264 bfd *abfd AND
265 bfd_vma value)
266{
d0ec7a8e 267 bfd_byte b[5];
301dfc71 268 ieee_write_int5(b, value);
d0ec7a8e 269 bfd_write((PTR)b,1,5,abfd);
87f86b4e 270}
87f86b4e
DHW
271
272
273static boolean
d0ec7a8e 274DEFUN(parse_int,(ieee, value_ptr),
6f715d66 275 common_header_type *ieee AND
301dfc71 276 bfd_vma *value_ptr)
87f86b4e 277{
d0ec7a8e 278 int value = this_byte(ieee);
87f86b4e
DHW
279 int result;
280 if (value >= 0 && value <= 127) {
281 *value_ptr = value;
d0ec7a8e 282 next_byte(ieee);
87f86b4e
DHW
283 return true;
284 }
285 else if (value >= 0x80 && value <= 0x88) {
286 unsigned int count = value & 0xf;
287 result = 0;
d0ec7a8e 288 next_byte(ieee);
87f86b4e 289 while (count) {
d0ec7a8e 290 result =(result << 8) | this_byte_and_next(ieee);
87f86b4e
DHW
291 count--;
292 }
293 *value_ptr = result;
294 return true;
295 }
296 return false;
297}
301dfc71 298static int
d0ec7a8e 299DEFUN(parse_i,(ieee, ok),
6f715d66 300 common_header_type *ieee AND
301dfc71 301 boolean *ok)
87f86b4e
DHW
302{
303 bfd_vma x;
d0ec7a8e 304 *ok = parse_int(ieee, &x);
87f86b4e
DHW
305 return x;
306}
307
301dfc71 308static bfd_vma
d0ec7a8e 309DEFUN(must_parse_int,(ieee),
6f715d66 310 common_header_type *ieee)
87f86b4e
DHW
311{
312 bfd_vma result;
d0ec7a8e 313 BFD_ASSERT(parse_int(ieee, &result) == true);
87f86b4e
DHW
314 return result;
315}
316
317typedef struct
318{
319 bfd_vma value;
320 asection *section;
321 ieee_symbol_index_type symbol;
322} ieee_value_type;
323
324
325static
326reloc_howto_type abs32_howto
d0ec7a8e 327 = HOWTO(1,0,2,32,0,0,0,true,0,"abs32",true,0xffffffff, 0xffffffff,false);
87f86b4e
DHW
328static
329reloc_howto_type abs16_howto
d0ec7a8e
SC
330 = HOWTO(1,0,1,16,0,0,0,true,0,"abs16",true,0x0000ffff, 0x0000ffff,false);
331
332static
333reloc_howto_type rel32_howto
334 = HOWTO(1,0,2,32,1,0,0,true,0,"rel32",true,0xffffffff, 0xffffffff,false);
335static
336reloc_howto_type rel16_howto
337 = HOWTO(1,0,1,16,1,0,0,true,0,"rel16",true,0x0000ffff, 0x0000ffff,false);
87f86b4e
DHW
338
339static ieee_symbol_index_type NOSYMBOL = { 0, 0};
340
341
301dfc71 342static void
d0ec7a8e
SC
343DEFUN(parse_expression,(ieee, value, section, symbol, pcrel, extra),
344 ieee_data_type *ieee AND
301dfc71
SC
345 bfd_vma *value AND
346 asection **section AND
347 ieee_symbol_index_type *symbol AND
348 boolean *pcrel AND
349 unsigned int *extra)
d0ec7a8e 350
87f86b4e
DHW
351{
352#define POS sp[1]
353#define TOS sp[0]
354#define NOS sp[-1]
355#define INC sp++;
356#define DEC sp--;
357
358 boolean loop = true;
359 ieee_value_type stack[10];
360
361 /* The stack pointer always points to the next unused location */
362#define PUSH(x,y,z) TOS.symbol=x;TOS.section=y;TOS.value=z;INC;
363#define POP(x,y,z) DEC;x=TOS.symbol;y=TOS.section;z=TOS.value;
364 ieee_value_type *sp = stack;
365
366 while (loop) {
6f715d66 367 switch (this_byte(&(ieee->h)))
87f86b4e 368 {
d0ec7a8e
SC
369 case ieee_variable_P_enum:
370 /* P variable, current program counter for section n */
371 {
372 int section_n ;
6f715d66 373 next_byte(&(ieee->h));
d0ec7a8e 374 *pcrel = true;
6f715d66 375 section_n = must_parse_int(&(ieee->h));
d0ec7a8e
SC
376 PUSH(NOSYMBOL, 0,
377 TOS.value = ieee->section_table[section_n]->vma +
378 ieee_per_section(ieee->section_table[section_n])->pc);
379 break;
380 }
381 case ieee_variable_L_enum:
382 /* L variable address of section N */
6f715d66
SC
383 next_byte(&(ieee->h));
384 PUSH(NOSYMBOL,ieee->section_table[must_parse_int(&(ieee->h))],0);
d0ec7a8e
SC
385 break;
386 case ieee_variable_R_enum:
387 /* R variable, logical address of section module */
388 /* FIXME, this should be different to L */
6f715d66
SC
389 next_byte(&(ieee->h));
390 PUSH(NOSYMBOL,ieee->section_table[must_parse_int(&(ieee->h))],0);
d0ec7a8e
SC
391 break;
392 case ieee_variable_S_enum:
393 /* S variable, size in MAUS of section module */
6f715d66 394 next_byte(&(ieee->h));
d0ec7a8e
SC
395 PUSH(NOSYMBOL,
396 0,
6f715d66 397 ieee->section_table[must_parse_int(&(ieee->h))]->size);
87f86b4e 398 break;
87f86b4e 399
d0ec7a8e
SC
400 case ieee_variable_X_enum:
401 /* Push the address of external variable n */
402 {
403 ieee_symbol_index_type sy;
6f715d66
SC
404 next_byte(&(ieee->h));
405 sy.index = (int)(must_parse_int(&(ieee->h))) ;
d0ec7a8e 406 sy.letter = 'X';
87f86b4e 407
d0ec7a8e
SC
408 PUSH(sy, 0, 0);
409 }
410 break;
411 case ieee_function_minus_enum:
87f86b4e 412 {
d0ec7a8e
SC
413 bfd_vma value1, value2;
414 asection *section1, *section_dummy;
415 ieee_symbol_index_type sy;
6f715d66 416 next_byte(&(ieee->h));
d0ec7a8e
SC
417
418 POP(sy, section1, value1);
419 POP(sy, section_dummy, value2);
420 PUSH(sy, section1, value1-value2);
87f86b4e 421 }
d0ec7a8e
SC
422 break;
423 case ieee_function_plus_enum:
424 {
425 bfd_vma value1, value2;
426 asection *section1;
427 asection *section2;
428 ieee_symbol_index_type sy1;
429 ieee_symbol_index_type sy2;
6f715d66 430 next_byte(&(ieee->h));
d0ec7a8e
SC
431
432 POP(sy1, section1, value1);
433 POP(sy2, section2, value2);
434 PUSH(sy1.letter ? sy1 : sy2, section1 ? section1: section2, value1+value2);
87f86b4e 435 }
d0ec7a8e
SC
436 break;
437 default:
438 {
439 bfd_vma va;
6f715d66
SC
440 BFD_ASSERT(this_byte(&(ieee->h)) < (int)ieee_variable_A_enum
441 || this_byte(&(ieee->h)) > (int)ieee_variable_Z_enum);
442 if (parse_int(&(ieee->h), &va))
d0ec7a8e
SC
443 {
444 PUSH(NOSYMBOL,0, va);
445 }
446 else {
447 /*
448 Thats all that we can understand. As far as I can see
449 there is a bug in the Microtec IEEE output which I'm
450 using to scan, whereby the comma operator is ommited
451 sometimes in an expression, giving expressions with too
452 many terms. We can tell if that's the case by ensuring
453 that sp == stack here. If not, then we've pushed
454 something too far, so we keep adding
455 */
456
457 while (sp != stack+1) {
458 asection *section1;
459 ieee_symbol_index_type sy1;
460 POP(sy1, section1, *extra);
461 }
462
463 POP(*symbol, *section, *value);
464 loop = false;
465 }
87f86b4e 466 }
87f86b4e 467
d0ec7a8e 468 }
87f86b4e
DHW
469 }
470}
471
301dfc71
SC
472
473
474#define ieee_seek(abfd, offset) \
6f715d66
SC
475 ieee_data(abfd)->h.input_p = ieee_data(abfd)->h.first_byte + offset
476
477#define ieee_pos(abfd) ieee_data(abfd)->h.input_p -ieee_data(abfd)->h.first_byte
87f86b4e
DHW
478
479static void
301dfc71
SC
480DEFUN(ieee_slurp_external_symbols,(abfd),
481 bfd *abfd)
87f86b4e
DHW
482{
483 ieee_data_type *ieee = ieee_data(abfd);
484 file_ptr offset = ieee->w.r.external_part;
485
486 ieee_symbol_type **prev_symbols_ptr = &ieee->external_symbols;
487 ieee_symbol_type **prev_reference_ptr = &ieee->external_reference;
488 ieee_symbol_type *symbol;
489 unsigned int symbol_count = 0;
490 boolean loop = true;
491
492 ieee->symbol_table_full = true;
493
301dfc71 494 ieee_seek(abfd, offset );
87f86b4e
DHW
495
496 while (loop) {
6f715d66 497 switch (this_byte(&(ieee->h))) {
87f86b4e 498 case ieee_external_symbol_enum:
6f715d66
SC
499 next_byte(&(ieee->h));
500 symbol = (ieee_symbol_type *)bfd_alloc(ieee->h.abfd, sizeof(ieee_symbol_type));
87f86b4e
DHW
501
502 *prev_symbols_ptr = symbol;
503 prev_symbols_ptr= &symbol->next;
6f715d66 504 symbol->index = must_parse_int(&(ieee->h));
87f86b4e
DHW
505 if (symbol->index > ieee->external_symbol_max_index) {
506 ieee->external_symbol_max_index = symbol->index;
507 }
508 BFD_ASSERT (symbol->index >= ieee->external_symbol_min_index);
509 symbol_count++;
510 symbol->symbol.the_bfd = abfd;
6f715d66 511 symbol->symbol.name = read_id(&(ieee->h));
d0ec7a8e 512 symbol->symbol.udata = (PTR)NULL;
87f86b4e
DHW
513 symbol->symbol.flags = BSF_NO_FLAGS;
514 break;
515 case ieee_attribute_record_enum >> 8:
516 {
517 unsigned int symbol_name_index;
518 unsigned int symbol_type_index;
519 unsigned int symbol_attribute_def;
520 bfd_vma value;
6f715d66
SC
521 next_byte(&(ieee->h)); /* Skip prefix */
522 next_byte(&(ieee->h));
523 symbol_name_index = must_parse_int(&(ieee->h));
524 symbol_type_index = must_parse_int(&(ieee->h));
525 symbol_attribute_def = must_parse_int(&(ieee->h));
87f86b4e 526
6f715d66 527 parse_int(&(ieee->h),&value);
87f86b4e
DHW
528
529 }
530 break;
531 case ieee_value_record_enum >> 8:
532 {
533 unsigned int symbol_name_index;
534 ieee_symbol_index_type symbol_ignore;
301dfc71 535 boolean pcrel_ignore;
d0ec7a8e 536 unsigned int extra;
6f715d66
SC
537 next_byte(&(ieee->h));
538 next_byte(&(ieee->h));
87f86b4e 539
6f715d66 540 symbol_name_index = must_parse_int(&(ieee->h));
d0ec7a8e 541 parse_expression(ieee,
87f86b4e
DHW
542 &symbol->symbol.value,
543 &symbol->symbol.section,
544 &symbol_ignore,
d0ec7a8e
SC
545 &pcrel_ignore,
546 &extra);
87f86b4e
DHW
547 if (symbol->symbol.section != (asection *)NULL) {
548 symbol->symbol.flags = BSF_GLOBAL | BSF_EXPORT;
549 }
550 else {
551 symbol->symbol.flags = BSF_GLOBAL | BSF_EXPORT | BSF_ABSOLUTE;
552 }
553 }
554 break;
555 case ieee_weak_external_reference_enum:
556 { bfd_vma size;
557 bfd_vma value ;
6f715d66 558 next_byte(&(ieee->h));
87f86b4e 559 /* Throw away the external reference index */
6f715d66 560 (void)must_parse_int(&(ieee->h));
87f86b4e 561 /* Fetch the default size if not resolved */
6f715d66 562 size = must_parse_int(&(ieee->h));
87f86b4e 563 /* Fetch the defautlt value if available */
6f715d66 564 if ( parse_int(&(ieee->h), &value) == false) {
87f86b4e
DHW
565 value = 0;
566 }
567 /* This turns into a common */
568 symbol->symbol.flags = BSF_FORT_COMM;
569 symbol->symbol.value = size;
570 }
571 break;
572
573 case ieee_external_reference_enum:
6f715d66
SC
574 next_byte(&(ieee->h));
575 symbol = (ieee_symbol_type *)bfd_alloc(ieee->h.abfd, sizeof(ieee_symbol_type));
87f86b4e
DHW
576 symbol_count++;
577 *prev_reference_ptr = symbol;
578 prev_reference_ptr = &symbol->next;
6f715d66 579 symbol->index = must_parse_int(&(ieee->h));
87f86b4e 580 symbol->symbol.the_bfd = abfd;
6f715d66 581 symbol->symbol.name = read_id(&(ieee->h));
d0ec7a8e 582 symbol->symbol.udata = (PTR)NULL;
87f86b4e
DHW
583 symbol->symbol.section = (asection *)NULL;
584 symbol->symbol.value = (bfd_vma)0;
585 symbol->symbol.flags = BSF_UNDEFINED;
586 if (symbol->index > ieee->external_reference_max_index) {
587 ieee->external_reference_max_index = symbol->index;
588 }
589 BFD_ASSERT (symbol->index >= ieee->external_reference_min_index);
590 break;
591
592 default:
593 loop = false;
594 }
595 }
596
597 if (ieee->external_symbol_max_index != 0) {
598 ieee->external_symbol_count =
599 ieee->external_symbol_max_index -
600 ieee->external_symbol_min_index + 1 ;
601 }
602 else {
603 ieee->external_symbol_count = 0;
604 }
605
606
607 if(ieee->external_reference_max_index != 0) {
608 ieee->external_reference_count =
609 ieee->external_reference_max_index -
610 ieee->external_reference_min_index + 1;
611 }
612 else {
613 ieee->external_reference_count = 0;
614 }
615
616 abfd->symcount =
617 ieee->external_reference_count + ieee->external_symbol_count;
618
619 if (symbol_count != abfd->symcount) {
620 /* There are gaps in the table -- */
621 ieee->symbol_table_full = false;
622 }
623 *prev_symbols_ptr = (ieee_symbol_type *)NULL;
624 *prev_reference_ptr = (ieee_symbol_type *)NULL;
625}
626
627static void
301dfc71
SC
628DEFUN(ieee_slurp_symbol_table,(abfd),
629 bfd *abfd)
87f86b4e
DHW
630{
631 if (ieee_data(abfd)->read_symbols == false) {
632 ieee_slurp_external_symbols(abfd);
633 ieee_data(abfd)->read_symbols= true;
634 }
635}
636
d0ec7a8e 637unsigned int
301dfc71
SC
638DEFUN(ieee_get_symtab_upper_bound,(abfd),
639 bfd *abfd)
87f86b4e
DHW
640{
641 ieee_slurp_symbol_table (abfd);
642
643 return (abfd->symcount != 0) ?
644 (abfd->symcount+1) * (sizeof (ieee_symbol_type *)) : 0;
645}
646
647/*
648Move from our internal lists to the canon table, and insert in
649symbol index order
650*/
651
652extern bfd_target ieee_vec;
653unsigned int
301dfc71
SC
654DEFUN(ieee_get_symtab,(abfd, location),
655 bfd *abfd AND
656 asymbol **location)
87f86b4e
DHW
657{
658 ieee_symbol_type *symp;
659 static bfd dummy_bfd;
660 static asymbol empty_symbol =
d0ec7a8e
SC
661 { &dummy_bfd," ieee empty",(symvalue)0,BSF_DEBUGGING | BSF_ABSOLUTE};
662
87f86b4e
DHW
663
664 ieee_data_type *ieee = ieee_data(abfd);
665 dummy_bfd.xvec= &ieee_vec;
666 ieee_slurp_symbol_table(abfd);
667
668 if (ieee->symbol_table_full == false) {
669 /* Arrgh - there are gaps in the table, run through and fill them */
670 /* up with pointers to a null place */
671 unsigned int i;
672 for (i= 0; i < abfd->symcount; i++) {
673 location[i] = &empty_symbol;
674 }
675 }
676
677
678 ieee->external_symbol_base_offset= - ieee->external_symbol_min_index;
679 for (symp = ieee_data(abfd)->external_symbols;
680 symp != (ieee_symbol_type *)NULL;
681 symp = symp->next) {
682 /* Place into table at correct index locations */
683 location[symp->index + ieee->external_symbol_base_offset] = &symp->symbol;
684
685 }
686
687 /* The external refs are indexed in a bit */
688 ieee->external_reference_base_offset =
689 - ieee->external_reference_min_index +ieee->external_symbol_count ;
690
691 for (symp = ieee_data(abfd)->external_reference;
692 symp != (ieee_symbol_type *)NULL;
693 symp = symp->next) {
694 location[symp->index + ieee->external_reference_base_offset] =
695 &symp->symbol;
696
697 }
698
699
700
701 location[abfd->symcount] = (asymbol *)NULL;
702
703 return abfd->symcount;
704}
705
706
707static void
301dfc71
SC
708DEFUN(ieee_slurp_sections,(abfd),
709 bfd *abfd)
87f86b4e
DHW
710{
711 ieee_data_type *ieee = ieee_data(abfd);
712 file_ptr offset = ieee->w.r.section_part;
713
714 asection *section = (asection *)NULL;
715
716 if (offset != 0) {
717 bfd_byte section_type[3];
301dfc71 718 ieee_seek(abfd, offset);
87f86b4e 719 while (true) {
6f715d66 720 switch (this_byte(&(ieee->h))) {
87f86b4e
DHW
721 case ieee_section_type_enum:
722 {
723 unsigned int section_index ;
6f715d66
SC
724 next_byte(&(ieee->h));
725 section_index = must_parse_int(&(ieee->h));
87f86b4e
DHW
726 /* Fixme to be nice about a silly number of sections */
727 BFD_ASSERT(section_index < NSECTIONS);
728
729 section = bfd_make_section(abfd, " tempname");
730 ieee->section_table[section_index] = section;
731 section->flags = SEC_NO_FLAGS;
732 section->target_index = section_index;
6f715d66 733 section_type[0] = this_byte_and_next(&(ieee->h));
87f86b4e
DHW
734 switch (section_type[0]) {
735 case 0xC3:
6f715d66
SC
736 section_type[1] = this_byte(&(ieee->h));
737 section->flags = SEC_LOAD | SEC_ALLOC | SEC_HAS_CONTENTS;
87f86b4e
DHW
738 switch (section_type[1]) {
739 case 0xD0:
740 /* Normal code */
6f715d66 741 next_byte(&(ieee->h));
87f86b4e
DHW
742 section->flags |= SEC_LOAD | SEC_CODE;
743 break;
744 case 0xC4:
6f715d66 745 next_byte(&(ieee->h));
87f86b4e
DHW
746 section->flags |= SEC_LOAD | SEC_DATA;
747 /* Normal data */
748 break;
749 case 0xD2:
6f715d66 750 next_byte(&(ieee->h));
87f86b4e
DHW
751 /* Normal rom data */
752 section->flags |= SEC_LOAD | SEC_ROM | SEC_DATA;
753 break;
754 default:
755 break;
756 }
757 }
6f715d66 758 section->name = read_id(&(ieee->h));
87f86b4e 759 { bfd_vma parent, brother, context;
6f715d66
SC
760 parse_int(&(ieee->h), &parent);
761 parse_int(&(ieee->h), &brother);
762 parse_int(&(ieee->h), &context);
87f86b4e
DHW
763 }
764
765
766 }
767 break;
768 case ieee_section_alignment_enum:
769 {
770 unsigned int section_index;
771 bfd_vma value;
6f715d66
SC
772 next_byte(&(ieee->h));
773 section_index = must_parse_int(&ieee->h);
87f86b4e
DHW
774 if (section_index > ieee->section_count) {
775 ieee->section_count = section_index;
776 }
777 ieee->section_table[section_index]->alignment_power =
6f715d66
SC
778 bfd_log2(must_parse_int(&ieee->h));
779 (void)parse_int(&(ieee->h), & value);
87f86b4e
DHW
780 }
781 break;
782 case ieee_e2_first_byte_enum:
783 {
6f715d66 784 ieee_record_enum_type t = read_2bytes(&(ieee->h));
87f86b4e
DHW
785 switch (t) {
786 case ieee_section_size_enum:
6f715d66
SC
787 section = ieee->section_table[must_parse_int(&(ieee->h))];
788 section->size = must_parse_int(&(ieee->h));
87f86b4e
DHW
789 break;
790 case ieee_physical_region_size_enum:
6f715d66
SC
791 section = ieee->section_table[must_parse_int(&(ieee->h))];
792 section->size = must_parse_int(&(ieee->h));
87f86b4e
DHW
793 break;
794 case ieee_region_base_address_enum:
6f715d66
SC
795 section = ieee->section_table[must_parse_int(&(ieee->h))];
796 section->vma = must_parse_int(&(ieee->h));
87f86b4e
DHW
797 break;
798 case ieee_mau_size_enum:
6f715d66
SC
799 must_parse_int(&(ieee->h));
800 must_parse_int(&(ieee->h));
87f86b4e
DHW
801 break;
802 case ieee_m_value_enum:
6f715d66
SC
803 must_parse_int(&(ieee->h));
804 must_parse_int(&(ieee->h));
87f86b4e
DHW
805 break;
806 case ieee_section_base_address_enum:
6f715d66
SC
807 section = ieee->section_table[must_parse_int(&(ieee->h))];
808 section->vma = must_parse_int(&(ieee->h));
87f86b4e
DHW
809 break;
810 case ieee_section_offset_enum:
6f715d66
SC
811 (void) must_parse_int(&(ieee->h));
812 (void) must_parse_int(&(ieee->h));
87f86b4e
DHW
813 break;
814 default:
815 return;
816 }
817 }
818 break;
819 default:
820 return;
821 }
822 }
823 }
824}
825
826/***********************************************************************
827* archive stuff
828*/
829bfd_target *
301dfc71
SC
830DEFUN(ieee_archive_p,(abfd),
831 bfd *abfd)
87f86b4e
DHW
832{
833 char *library;
834 boolean loop;
6f715d66 835
87f86b4e 836 unsigned int i;
6f715d66
SC
837uint8e_type buffer[512];
838 int buffer_i = 0;
839 int buffer_offset = 0;
840 ieee_ar_data_type *save = ieee_ar_data(abfd);
841 ieee_ar_data_type *ieee ;
842 set_tdata(abfd, bfd_alloc(abfd, sizeof(ieee_ar_data_type)));
843 ieee= ieee_ar_data(abfd);
844
845
846 bfd_read((PTR)buffer, 1, sizeof(buffer), abfd);
d0ec7a8e 847
6f715d66
SC
848 ieee->h.first_byte = buffer;
849 ieee->h.input_p = buffer;
d0ec7a8e 850
6f715d66
SC
851 ieee->h.abfd = abfd;
852
853 if (this_byte(&(ieee->h)) != Module_Beginning) return (bfd_target*)NULL;
854
855 next_byte(&(ieee->h));
856 library= read_id(&(ieee->h));
87f86b4e 857 if (strcmp(library , "LIBRARY") != 0) {
6f715d66
SC
858 bfd_release(abfd, ieee);
859 ieee_ar_data(abfd)= save;
87f86b4e
DHW
860 return (bfd_target *)NULL;
861 }
862 /* Throw away the filename */
6f715d66 863 free( read_id(&(ieee->h)));
87f86b4e
DHW
864 /* This must be an IEEE archive, so we'll buy some space to do
865 things */
6f715d66
SC
866 ieee->element_count = 0;
867 ieee->element_index = 0;
87f86b4e 868
6f715d66
SC
869 next_byte(&(ieee->h)); /* Drop the ad part */
870 must_parse_int(&(ieee->h)); /* And the two dummy numbers */
871 must_parse_int(&(ieee->h));
87f86b4e
DHW
872
873 loop = true;
874 /* Read the index of the BB table */
875 while (loop) {
876 ieee_ar_obstack_type t;
6f715d66 877 int rec =read_2bytes(&(ieee->h));
87f86b4e 878 if (rec ==ieee_assign_value_to_variable_enum) {
6f715d66
SC
879 int record_number = must_parse_int(&(ieee->h));
880 t.file_offset = must_parse_int(&(ieee->h));
87f86b4e 881 t.abfd = (bfd *)NULL;
6f715d66
SC
882 ieee->element_count++;
883 bfd_alloc_grow(abfd, (PTR)&t, sizeof(t));
884
885 /* Make sure that we don't go over the end of the buffer */
886
887 if (ieee_pos(abfd) > sizeof(buffer)/2) {
888 /* Past half way, reseek and reprime */
889 buffer_offset += ieee_pos(abfd);
890 bfd_seek(abfd, buffer_offset, SEEK_SET);
891 bfd_read(buffer, 1, sizeof(buffer), abfd);
892 ieee->h.first_byte = buffer;
893 ieee->h.input_p = buffer;
894 }
87f86b4e
DHW
895 }
896 else loop = false;
897 }
6f715d66
SC
898
899 ieee->elements = (ieee_ar_obstack_type *)bfd_alloc_finish(abfd);
87f86b4e
DHW
900
901 /* Now scan the area again, and replace BB offsets with file */
902 /* offsets */
903
904
6f715d66
SC
905 for (i = 2; i < ieee->element_count; i++) {
906 bfd_seek(abfd, ieee->elements[i].file_offset, SEEK_SET);
907 bfd_read(buffer, 1, sizeof(buffer), abfd);
908 ieee->h.first_byte = buffer;
909 ieee->h.input_p = buffer;
910
911 next_byte(&(ieee->h)); /* Drop F8 */
912 next_byte(&(ieee->h)); /* Drop 14 */
913 must_parse_int(&(ieee->h)); /* Drop size of block */
914 if (must_parse_int(&(ieee->h)) != 0) {
87f86b4e 915 /* This object has been deleted */
6f715d66 916 ieee->elements[i].file_offset = 0;
87f86b4e
DHW
917 }
918 else {
6f715d66 919 ieee->elements[i].file_offset = must_parse_int(&(ieee->h));
87f86b4e
DHW
920 }
921 }
922
87f86b4e 923 return abfd->xvec;
6f715d66 924
87f86b4e
DHW
925}
926
301dfc71
SC
927static boolean
928DEFUN(ieee_mkobject,(abfd),
929 bfd *abfd)
6f715d66
SC
930{
931 set_tdata (abfd, bfd_zalloc(abfd,sizeof(ieee_data_type)));
932
933
301dfc71
SC
934 return true;
935}
936
87f86b4e 937bfd_target *
301dfc71
SC
938DEFUN(ieee_object_p,(abfd),
939 bfd *abfd)
87f86b4e
DHW
940{
941 char *processor;
942 unsigned int part;
301dfc71 943 ieee_data_type *ieee;
d0ec7a8e
SC
944 uint8e_type buffer[300];
945 ieee_data_type *save = ieee_data(abfd);
9b4641a6 946 set_tdata (abfd, 0);
301dfc71
SC
947 ieee_mkobject(abfd);
948 ieee = ieee_data(abfd);
949
950 /* Read the first few bytes in to see if it makes sense */
d0ec7a8e 951 bfd_read((PTR)buffer, 1, sizeof(buffer), abfd);
301dfc71 952
6f715d66
SC
953 ieee->h.input_p = buffer;
954 if (this_byte_and_next(&(ieee->h)) != Module_Beginning) goto fail;
301dfc71
SC
955
956 ieee->read_symbols= false;
957 ieee->read_data= false;
958 ieee->section_count = 0;
959 ieee->external_symbol_max_index = 0;
960 ieee->external_symbol_min_index = IEEE_PUBLIC_BASE;
961 ieee->external_reference_min_index =IEEE_REFERENCE_BASE;
962 ieee->external_reference_max_index = 0;
6f715d66 963 ieee->h.abfd = abfd;
301dfc71
SC
964 memset((PTR)ieee->section_table, 0, sizeof(ieee->section_table));
965
6f715d66 966 processor = ieee->mb.processor = read_id(&(ieee->h));
301dfc71 967 if (strcmp(processor,"LIBRARY") == 0) goto fail;
6f715d66 968 ieee->mb.module_name = read_id(&(ieee->h));
87f86b4e 969 if (abfd->filename == (char *)NULL) {
301dfc71 970 abfd->filename = ieee->mb.module_name;
87f86b4e
DHW
971 }
972 /* Determine the architecture and machine type of the object file. */
973 bfd_scan_arch_mach(processor, &abfd->obj_arch, &abfd->obj_machine);
974
6f715d66 975 if (this_byte(&(ieee->h)) != ieee_address_descriptor_enum) {
301dfc71 976 goto fail;
87f86b4e 977 }
6f715d66 978 next_byte(&(ieee->h));
87f86b4e 979
6f715d66 980 if (parse_int(&(ieee->h), &ieee->ad.number_of_bits_mau) == false) {
301dfc71 981 goto fail;
87f86b4e 982 }
6f715d66 983 if(parse_int(&(ieee->h), &ieee->ad.number_of_maus_in_address) == false) {
301dfc71 984 goto fail;
87f86b4e
DHW
985 }
986
987 /* If there is a byte order info, take it */
6f715d66
SC
988 if (this_byte(&(ieee->h)) == ieee_variable_L_enum ||
989 this_byte(&(ieee->h)) == ieee_variable_M_enum)
990 next_byte(&(ieee->h));
87f86b4e
DHW
991
992
993 for (part = 0; part < N_W_VARIABLES; part++) {
994 boolean ok;
6f715d66 995 if (read_2bytes(&(ieee->h)) != ieee_assign_value_to_variable_enum) {
301dfc71 996 goto fail;
87f86b4e 997 }
6f715d66 998 if (this_byte_and_next(&(ieee->h)) != part) {
301dfc71 999 goto fail;
87f86b4e
DHW
1000 }
1001
6f715d66 1002 ieee->w.offset[part] = parse_i(&(ieee->h), &ok);
87f86b4e 1003 if (ok==false) {
301dfc71 1004 goto fail;
87f86b4e
DHW
1005 }
1006
1007 }
1008 abfd->flags = HAS_SYMS;
1009
301dfc71
SC
1010/* By now we know that this is a real IEEE file, we're going to read
1011 the whole thing into memory so that we can run up and down it
1012 quickly. We can work out how big the file is from the trailer
1013 record */
1014
6f715d66 1015 ieee_data(abfd)->h.first_byte = (uint8e_type *) bfd_alloc(ieee->h.abfd, ieee->w.r.me_record
301dfc71
SC
1016 + 50);
1017 bfd_seek(abfd, 0, 0);
6f715d66 1018 bfd_read((PTR)(ieee_data(abfd)->h.first_byte), 1, ieee->w.r.me_record+50, abfd);
301dfc71 1019
87f86b4e
DHW
1020 ieee_slurp_sections(abfd);
1021 return abfd->xvec;
301dfc71 1022 fail:
d0ec7a8e 1023 (void) bfd_release(abfd, ieee);
c0e5039e 1024 set_tdata (abfd, save);
301dfc71 1025 return (bfd_target *)NULL;
87f86b4e
DHW
1026}
1027
1028
1029void
2b1d8a50 1030DEFUN(ieee_print_symbol,(ignore_abfd, afile, symbol, how),
301dfc71 1031 bfd *ignore_abfd AND
2b1d8a50 1032 PTR afile AND
301dfc71
SC
1033 asymbol *symbol AND
1034 bfd_print_symbol_enum_type how)
87f86b4e 1035{
2b1d8a50
JG
1036 FILE *file = (FILE *)afile;
1037
87f86b4e
DHW
1038 switch (how) {
1039 case bfd_print_symbol_name_enum:
1040 fprintf(file,"%s", symbol->name);
1041 break;
1042 case bfd_print_symbol_type_enum:
1043#if 0
1044 fprintf(file,"%4x %2x",aout_symbol(symbol)->desc & 0xffff,
1045 aout_symbol(symbol)->other & 0xff);
1046#endif
1047 BFD_FAIL();
1048 break;
1049 case bfd_print_symbol_all_enum:
301dfc71
SC
1050 {
1051 CONST char *section_name = symbol->section == (asection *)NULL ?
1052 "*abs" : symbol->section->name;
d0ec7a8e
SC
1053 if (symbol->name[0] == ' ') {
1054 fprintf(file,"* empty table entry ");
1055 }
1056 else {
1057 bfd_print_symbol_vandf((PTR)file,symbol);
301dfc71 1058
d0ec7a8e
SC
1059 fprintf(file," %-5s %04x %02x %s",
1060 section_name,
1061 (unsigned) ieee_symbol(symbol)->index,
1062 (unsigned) 0, /*
301dfc71
SC
1063 aout_symbol(symbol)->desc & 0xffff,
1064 aout_symbol(symbol)->other & 0xff,*/
d0ec7a8e
SC
1065 symbol->name);
1066 }
301dfc71 1067 }
87f86b4e
DHW
1068 break;
1069 }
1070}
1071
1072
7ed4093a 1073static void
7564d3d7
SC
1074DEFUN(do_one,(ieee, current_map, location_ptr,s),
1075 ieee_data_type *ieee AND
1076 ieee_per_section_type *current_map AND
1077 uint8e_type *location_ptr AND
1078 asection *s)
1079{
6f715d66 1080 switch (this_byte(&(ieee->h)))
7564d3d7
SC
1081 {
1082 case ieee_load_constant_bytes_enum:
1083 {
1084 unsigned int number_of_maus;
1085 unsigned int i;
6f715d66
SC
1086 next_byte(&(ieee->h));
1087 number_of_maus = must_parse_int(&(ieee->h));
7564d3d7
SC
1088
1089 for (i = 0; i < number_of_maus; i++) {
6f715d66
SC
1090 location_ptr[current_map->pc++]= this_byte(&(ieee->h));
1091 next_byte(&(ieee->h));
7564d3d7
SC
1092 }
1093 }
1094 break;
1095
1096 case ieee_load_with_relocation_enum:
1097 {
1098 boolean loop = true;
6f715d66 1099 next_byte(&(ieee->h));
7564d3d7
SC
1100 while (loop)
1101 {
6f715d66 1102 switch (this_byte(&(ieee->h)))
7564d3d7
SC
1103 {
1104 case ieee_variable_R_enum:
1105
1106 case ieee_function_signed_open_b_enum:
1107 case ieee_function_unsigned_open_b_enum:
1108 case ieee_function_either_open_b_enum:
1109 {
1110 unsigned int extra = 4;
1111 boolean pcrel = false;
1112
1113 ieee_reloc_type *r =
6f715d66 1114 (ieee_reloc_type *) bfd_alloc(ieee->h.abfd,
7564d3d7
SC
1115 sizeof(ieee_reloc_type));
1116
1117 *(current_map->reloc_tail_ptr) = r;
1118 current_map->reloc_tail_ptr= &r->next;
1119 r->next = (ieee_reloc_type *)NULL;
6f715d66 1120 next_byte(&(ieee->h));
7564d3d7
SC
1121 parse_expression(ieee,
1122 &r->relent.addend,
1123 &r->relent.section,
1124 &r->symbol,
1125 &pcrel, &extra);
1126 r->relent.address = current_map->pc;
1127 s->reloc_count++;
6f715d66 1128 switch (this_byte(&(ieee->h))) {
7564d3d7 1129 case ieee_function_signed_close_b_enum:
6f715d66 1130 next_byte(&(ieee->h));
7564d3d7
SC
1131 break;
1132 case ieee_function_unsigned_close_b_enum:
6f715d66 1133 next_byte(&(ieee->h));
7564d3d7
SC
1134 break;
1135 case ieee_function_either_close_b_enum:
6f715d66 1136 next_byte(&(ieee->h));
7564d3d7
SC
1137 break;
1138 default:
1139 break;
1140 }
1141 /* Build a relocation entry for this type */
6f715d66
SC
1142 if (this_byte(&(ieee->h)) == ieee_comma) {
1143 next_byte(&(ieee->h));
7564d3d7 1144 /* Fetch number of bytes to pad */
6f715d66 1145 extra = must_parse_int(&(ieee->h));
7564d3d7
SC
1146 };
1147
1148 /* If pc rel then stick -ve pc into instruction
1149 and take out of reloc*/
1150
1151 switch (extra)
1152 {
1153 case 0:
1154 case 4:
1155 if (pcrel == true)
1156 {
6f715d66 1157 bfd_put_32(ieee->h.abfd, -current_map->pc, location_ptr +
7564d3d7
SC
1158 current_map->pc);
1159 r->relent.howto = &rel32_howto;
1160 r->relent.addend -= current_map->pc;
1161 }
1162 else
1163 {
6f715d66 1164 bfd_put_32(ieee->h.abfd, 0, location_ptr +
7564d3d7
SC
1165 current_map->pc);
1166 r->relent.howto = &abs32_howto;
1167 }
1168 current_map->pc +=4;
1169 break;
1170 case 2:
1171 if (pcrel == true) {
6f715d66 1172 bfd_put_16(ieee->h.abfd, (int)(-current_map->pc), location_ptr +current_map->pc);
7564d3d7
SC
1173 r->relent.addend -= current_map->pc;
1174 r->relent.howto = &rel16_howto;
1175 }
1176 else {
6f715d66 1177 bfd_put_16(ieee->h.abfd, 0, location_ptr +current_map->pc);
7564d3d7
SC
1178 r->relent.howto = &abs16_howto;
1179 }
1180 current_map->pc +=2;
1181 break;
1182
1183 default:
1184 BFD_FAIL();
1185 break;
1186 }
1187 }
1188 break;
1189 default:
1190 {
1191 bfd_vma this_size ;
6f715d66 1192 if (parse_int(&(ieee->h), &this_size) == true) {
7564d3d7
SC
1193 unsigned int i;
1194 for (i = 0; i < this_size; i++) {
6f715d66
SC
1195 location_ptr[current_map->pc ++] = this_byte(&(ieee->h));
1196 next_byte(&(ieee->h));
7564d3d7
SC
1197 }
1198 }
1199 else {
1200 loop = false;
1201 }
1202 }
1203 }
1204 }
1205 }
1206 }
1207}
87f86b4e 1208
6f715d66 1209/* Read in all the section data and relocation stuff too */
301dfc71
SC
1210static boolean
1211DEFUN(ieee_slurp_section_data,(abfd),
1212 bfd *abfd)
87f86b4e
DHW
1213{
1214 bfd_byte *location_ptr ;
1215 ieee_data_type *ieee = ieee_data(abfd);
1216 unsigned int section_number ;
1217
1218 ieee_per_section_type *current_map;
1219 asection *s;
1220 /* Seek to the start of the data area */
1221 if (ieee->read_data== true) return true;
1222 ieee->read_data = true;
301dfc71 1223 ieee_seek(abfd, ieee->w.r.data_part);
87f86b4e
DHW
1224
1225 /* Allocate enough space for all the section contents */
1226
1227
1228 for (s = abfd->sections; s != (asection *)NULL; s = s->next) {
a6dab071 1229 ieee_per_section_type *per = (ieee_per_section_type *) s->used_by_bfd;
6f715d66 1230 per->data = (bfd_byte *) bfd_alloc(ieee->h.abfd, s->size);
87f86b4e 1231 /*SUPPRESS 68*/
87f86b4e
DHW
1232 per->reloc_tail_ptr =
1233 (ieee_reloc_type **)&(s->relocation);
1234 }
1235
1236
1237
1238 while (true) {
6f715d66 1239 switch (this_byte(&(ieee->h)))
87f86b4e 1240 {
7564d3d7
SC
1241 /* IF we see anything strange then quit */
1242 default:
1243 return true;
87f86b4e 1244
7564d3d7 1245 case ieee_set_current_section_enum:
6f715d66
SC
1246 next_byte(&(ieee->h));
1247 section_number = must_parse_int(&(ieee->h));
7564d3d7
SC
1248 s = ieee->section_table[section_number];
1249 current_map = (ieee_per_section_type *) s->used_by_bfd;
1250 location_ptr = current_map->data - s->vma;
1251 /* The document I have says that Microtec's compilers reset */
1252 /* this after a sec section, even though the standard says not */
1253 /* to. SO .. */
1254 current_map->pc =s->vma;
1255 break;
87f86b4e 1256
87f86b4e 1257
7564d3d7 1258 case ieee_e2_first_byte_enum:
6f715d66
SC
1259 next_byte(&(ieee->h));
1260 switch (this_byte(&(ieee->h)))
7564d3d7
SC
1261 {
1262 case ieee_set_current_pc_enum & 0xff:
87f86b4e 1263 {
7564d3d7
SC
1264 bfd_vma value;
1265 asection *dsection;
1266 ieee_symbol_index_type symbol;
1267 unsigned int extra;
1268 boolean pcrel;
6f715d66
SC
1269 next_byte(&(ieee->h));
1270 must_parse_int(&(ieee->h)); /* Thow away section #*/
7564d3d7 1271 parse_expression(ieee, &value, &dsection, &symbol,
d0ec7a8e 1272 &pcrel, &extra);
7564d3d7
SC
1273 current_map->pc = value;
1274 BFD_ASSERT((unsigned)(value - s->vma) <= s->size);
87f86b4e 1275 }
7564d3d7
SC
1276 break;
1277
1278 case ieee_value_starting_address_enum & 0xff:
1279 /* We've got to the end of the data now - */
1280 return true;
1281 default:
1282 BFD_FAIL();
1283 return true;
1284 }
1285 break;
1286 case ieee_repeat_data_enum:
1287 {
1288 /* Repeat the following LD or LR n times - we do this by
1289 remembering the stream pointer before running it and
6f715d66
SC
1290 resetting it and running it n times. We special case
1291 the repetition of a repeat_data/load_constant
7564d3d7
SC
1292 */
1293
1294 unsigned int iterations ;
1295 uint8e_type *start ;
6f715d66
SC
1296 next_byte(&(ieee->h));
1297 iterations = must_parse_int(&(ieee->h));
1298 start = ieee->h.input_p;
1299 if (start[0] == ieee_load_constant_bytes_enum &&
1300 start[1] == 1) {
1301 while (iterations != 0) {
1302 location_ptr[current_map->pc++] = start[2];
1303 iterations--;
1304 }
1305 next_byte(&(ieee->h));
1306 next_byte(&(ieee->h));
1307 next_byte(&(ieee->h));
1308 }
1309 else {
1310 while (iterations != 0) {
1311 ieee->h.input_p = start;
1312 do_one(ieee, current_map, location_ptr,s);
1313 iterations --;
1314 }
7564d3d7
SC
1315 }
1316 }
1317 break;
1318 case ieee_load_constant_bytes_enum:
1319 case ieee_load_with_relocation_enum:
1320 {
1321 do_one(ieee, current_map, location_ptr,s);
87f86b4e
DHW
1322 }
1323 }
87f86b4e
DHW
1324 }
1325}
1326
1327
1328
7564d3d7
SC
1329
1330
87f86b4e 1331boolean
301dfc71
SC
1332DEFUN(ieee_new_section_hook,(abfd, newsect),
1333 bfd *abfd AND
1334 asection *newsect)
87f86b4e 1335{
a6dab071 1336 newsect->used_by_bfd = (PTR)
d0ec7a8e 1337 bfd_alloc(abfd, sizeof(ieee_per_section_type));
87f86b4e
DHW
1338 ieee_per_section( newsect)->data = (bfd_byte *)NULL;
1339 ieee_per_section(newsect)->section = newsect;
1340 return true;
1341}
1342
1343
1344unsigned int
301dfc71
SC
1345DEFUN(ieee_get_reloc_upper_bound,(abfd, asect),
1346 bfd *abfd AND
1347 sec_ptr asect)
87f86b4e
DHW
1348{
1349 ieee_slurp_section_data(abfd);
1350 return (asect->reloc_count+1) * sizeof(arelent *);
1351}
1352
1353static boolean
301dfc71
SC
1354DEFUN(ieee_get_section_contents,(abfd, section, location, offset, count),
1355 bfd *abfd AND
1356 sec_ptr section AND
d0ec7a8e 1357 PTR location AND
301dfc71 1358 file_ptr offset AND
7ed4093a 1359 bfd_size_type count)
87f86b4e 1360{
a6dab071 1361 ieee_per_section_type *p = (ieee_per_section_type *) section->used_by_bfd;
87f86b4e 1362 ieee_slurp_section_data(abfd);
7ed4093a 1363 (void) memcpy(location, p->data + offset, (unsigned)count);
87f86b4e
DHW
1364 return true;
1365}
1366
1367
1368unsigned int
301dfc71
SC
1369DEFUN(ieee_canonicalize_reloc,(abfd, section, relptr, symbols),
1370 bfd *abfd AND
1371 sec_ptr section AND
1372 arelent **relptr AND
1373 asymbol **symbols)
87f86b4e 1374{
d0ec7a8e 1375/* ieee_per_section_type *p = (ieee_per_section_type *) section->used_by_bfd;*/
87f86b4e
DHW
1376 ieee_reloc_type *src = (ieee_reloc_type *)(section->relocation);
1377 ieee_data_type *ieee = ieee_data(abfd);
1378
1379 while (src != (ieee_reloc_type *)NULL) {
1380 /* Work out which symbol to attatch it this reloc to */
1381 switch (src->symbol.letter) {
1382 case 'X':
1383 src->relent.sym_ptr_ptr =
1384 symbols + src->symbol.index + ieee->external_reference_base_offset;
1385 break;
1386 case 0:
1387 src->relent.sym_ptr_ptr = (asymbol **)NULL;
1388 break;
1389 default:
1390
1391 BFD_FAIL();
1392 }
1393 *relptr++ = &src->relent;
1394 src = src->next;
1395 }
1396 *relptr = (arelent *)NULL;
1397 return section->reloc_count;
1398}
1399
1400boolean
301dfc71
SC
1401DEFUN(ieee_set_arch_mach,(abfd, arch, machine),
1402 bfd *abfd AND
1403 enum bfd_architecture arch AND
1404 unsigned long machine)
87f86b4e
DHW
1405{
1406 abfd->obj_arch = arch;
1407 abfd->obj_machine = machine;
1408 return true;
1409}
1410
87f86b4e 1411
301dfc71
SC
1412static int
1413DEFUN(comp,(ap, bp),
39a2ce33
SC
1414 CONST PTR ap AND
1415 CONST PTR bp)
87f86b4e 1416{
9872a49c
SC
1417 arelent *a = *((arelent **)ap);
1418 arelent *b = *((arelent **)bp);
87f86b4e
DHW
1419 return a->address - b->address;
1420}
9872a49c 1421
87f86b4e
DHW
1422/*
1423Write the section headers
1424*/
1425
1426static void
301dfc71
SC
1427DEFUN(ieee_write_section_part,(abfd),
1428 bfd *abfd)
87f86b4e
DHW
1429{
1430 ieee_data_type *ieee = ieee_data(abfd);
1431 asection *s;
1432 ieee->w.r.section_part = bfd_tell(abfd);
1433 for (s = abfd->sections; s != (asection *)NULL; s=s->next) {
1434 ieee_write_byte(abfd, ieee_section_type_enum);
1435 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1436
6f715d66
SC
1437 if (abfd->flags & EXEC_P)
1438 {
1439 /* This image is executable, so output absolute sections */
1440 ieee_write_byte(abfd, ieee_variable_A_enum);
1441 ieee_write_byte(abfd, ieee_variable_S_enum);
1442 }
1443 else
1444 {
1445 ieee_write_byte(abfd, ieee_variable_C_enum);
1446 }
1447
1448 switch (s->flags &(SEC_CODE | SEC_DATA | SEC_ROM))
1449 {
1450 case SEC_CODE | SEC_LOAD:
1451 case SEC_CODE:
1452 ieee_write_byte(abfd, ieee_variable_P_enum);
1453 break;
1454 case SEC_DATA:
1455 default:
1456 ieee_write_byte(abfd, ieee_variable_D_enum);
1457 break;
1458 case SEC_ROM:
1459 case SEC_ROM | SEC_DATA:
1460 case SEC_ROM | SEC_LOAD:
1461 case SEC_ROM | SEC_DATA | SEC_LOAD:
1462
1463 ieee_write_byte(abfd, ieee_variable_R_enum);
1464 }
1465
87f86b4e
DHW
1466
1467 ieee_write_id(abfd, s->name);
6f715d66 1468#if 0
87f86b4e
DHW
1469 ieee_write_int(abfd, 0); /* Parent */
1470 ieee_write_int(abfd, 0); /* Brother */
1471 ieee_write_int(abfd, 0); /* Context */
6f715d66 1472#endif
87f86b4e
DHW
1473 /* Alignment */
1474 ieee_write_byte(abfd, ieee_section_alignment_enum);
1475 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1476 ieee_write_int(abfd, 1 << s->alignment_power);
1477
1478 /* Size */
1479 ieee_write_2bytes(abfd, ieee_section_size_enum);
1480 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1481 ieee_write_int(abfd, s->size);
1482
1483 /* Vma */
6f715d66 1484 ieee_write_2bytes(abfd, ieee_section_base_address_enum);
87f86b4e
DHW
1485 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1486 ieee_write_int(abfd, s->vma);
1487
1488 }
1489}
1490
1491
1492
6f715d66
SC
1493static void
1494DEFUN(do_with_relocs,(abfd, s),
1495 bfd *abfd AND
1496 asection *s)
87f86b4e 1497{
6f715d66
SC
1498 unsigned int relocs_to_go = s->reloc_count;
1499 bfd_byte header[11];
1500
1501 bfd_byte *stream = ieee_per_section(s)->data;
1502 arelent **p = s->orelocation;
1503
1504 bfd_size_type current_byte_index = 0;
1505
1506 qsort(s->orelocation,
1507 relocs_to_go,
1508 sizeof(arelent **),
1509 comp);
1510
1511
1512
1513 /* Output the section preheader */
1514 header[0] =ieee_set_current_section_enum;
1515 header[1] = s->index + IEEE_SECTION_NUMBER_BASE;
1516
1517 header[2] = ieee_set_current_pc_enum >> 8;
1518 header[3]= ieee_set_current_pc_enum & 0xff;
1519 header[4] = s->index + IEEE_SECTION_NUMBER_BASE;
1520 ieee_write_int5(header+5, s->vma );
1521 header[10] = ieee_load_with_relocation_enum;
1522 bfd_write((PTR)header, 1, sizeof(header), abfd);
1523
1524 /* Output the data stream as the longest sequence of bytes
1525 possible, allowing for the a reasonable packet size and
1526 relocation stuffs */
1527
1528 if ((PTR)stream == (PTR)NULL) {
1529 /* Outputting a section without data, fill it up */
1530 stream = (uint8e_type *)(bfd_alloc(abfd, s->size));
1531 memset((PTR)stream, 0, s->size);
1532 }
1533 while (current_byte_index < s->size) {
1534 bfd_size_type run;
1535 unsigned int MAXRUN = 32;
1536 if (relocs_to_go) {
1537 run = (*p)->address - current_byte_index;
1538 }
1539 else {
1540 run = MAXRUN;
1541 }
1542 if (run > s->size - current_byte_index) {
1543 run = s->size - current_byte_index;
1544 }
1545
1546 if (run != 0) {
1547 /* Output a stream of bytes */
1548 ieee_write_int(abfd, run);
1549 bfd_write((PTR)(stream + current_byte_index),
1550 1,
1551 run,
1552 abfd);
1553 current_byte_index += run;
1554 }
1555 /* Output any relocations here */
1556 if (relocs_to_go && (*p) && (*p)->address == current_byte_index) {
1557 while (relocs_to_go && (*p) && (*p)->address == current_byte_index) {
1558
1559 arelent *r = *p;
1560 bfd_vma ov;
1561 if (r->howto->pc_relative) {
1562 r->addend += current_byte_index;
1563 }
1564
1565 switch (r->howto->size) {
1566 case 2:
1567
1568 ov = bfd_get_32(abfd,
1569 stream+current_byte_index);
1570 current_byte_index +=4;
1571 break;
1572 case 1:
1573 ov = bfd_get_16(abfd,
1574 stream+current_byte_index);
1575 current_byte_index +=2;
1576 break;
1577 default:
1578 BFD_FAIL();
1579 }
1580 ieee_write_byte(abfd, ieee_function_either_open_b_enum);
1581
1582 if (r->sym_ptr_ptr != (asymbol **)NULL) {
1583 ieee_write_expression(abfd, r->addend + ov,
1584 r->section,
1585 *(r->sym_ptr_ptr),
1586 r->howto->pc_relative, s->target_index);
1587 }
1588 else {
1589 ieee_write_expression(abfd, r->addend + ov,
1590 r->section,
1591 (asymbol *)NULL,
1592 r->howto->pc_relative, s->target_index);
1593 }
1594 ieee_write_byte(abfd,
1595 ieee_function_either_close_b_enum);
1596 if (r->howto->size != 2) {
1597 ieee_write_byte(abfd, ieee_comma);
1598 ieee_write_int(abfd, 1<< r->howto->size);
1599 }
1600
1601 relocs_to_go --;
1602 p++;
1603 }
1604
1605 }
1606 }
1607}
1608
1609/* If there are no relocations in the output section then we can
1610be clever about how we write. We block items up into a max of 127
1611bytes */
1612
1613static void
1614DEFUN(do_as_repeat, (abfd, s),
1615 bfd *abfd AND
1616 asection *s)
1617{
1618 ieee_write_byte(abfd, ieee_set_current_section_enum);
1619 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1620 ieee_write_byte(abfd, ieee_set_current_pc_enum >> 8);
1621 ieee_write_byte(abfd, ieee_set_current_pc_enum & 0xff);
1622 ieee_write_byte(abfd, s->index + IEEE_SECTION_NUMBER_BASE);
1623 ieee_write_int(abfd, s->vma );
1624
1625 ieee_write_byte(abfd,ieee_repeat_data_enum);
1626 ieee_write_int(abfd, s->size);
1627 ieee_write_byte(abfd, ieee_load_constant_bytes_enum);
1628 ieee_write_byte(abfd, 1);
1629 ieee_write_byte(abfd, 0);
1630}
1631
1632static void
1633DEFUN(do_without_relocs, (abfd, s),
1634 bfd *abfd AND
1635 asection *s)
1636{
1637 bfd_byte *stream = ieee_per_section(s)->data;
1638
1639 if (stream == 0 || ((s->flags & SEC_LOAD) == 0))
301dfc71 1640 {
6f715d66
SC
1641 do_as_repeat(abfd, s);
1642 }
1643 else
1644 {
1645 unsigned int i;
1646 for (i = 0; i < s->size; i++) {
1647 if (stream[i] != 0) {
1648 do_with_relocs(abfd, s);
1649 return;
1650 }
1651 }
1652 do_as_repeat(abfd, s);
1653 }
1654
1655}
301dfc71 1656
6f715d66
SC
1657
1658static unsigned char *output_ptr_start;
1659static unsigned char *output_ptr;
1660static unsigned char *output_ptr_end;
1661static unsigned char *input_ptr_start;
1662static unsigned char *input_ptr;
1663static unsigned char *input_ptr_end;
1664static bfd *input_bfd;
1665static bfd *output_bfd;
1666static int output_buffer;
1667
1668static void fill()
1669{
1670 bfd_read(input_ptr_start, 1, input_ptr_end - input_ptr_start, input_bfd);
1671 input_ptr = input_ptr_start;
1672}
1673static void flush()
1674{
1675 bfd_write(output_ptr_start,1,output_ptr - output_ptr_start, output_bfd);
1676 output_ptr = output_ptr_start;
1677 output_buffer++;
1678}
1679
1680#define THIS() ( *input_ptr )
1681#define NEXT() { input_ptr++; if (input_ptr == input_ptr_end) fill(); }
1682#define OUT(x) { *output_ptr++ = (x); if(output_ptr == output_ptr_end) flush(); }
1683
1684static void write_int(value)
1685int value;
1686{
1687 if (value >= 0 && value <= 127) {
1688 OUT(value);
1689 }
1690 else {
1691 unsigned int length;
1692 /* How many significant bytes ? */
1693 /* FIXME FOR LONGER INTS */
1694 if (value & 0xff000000) {
1695 length = 4;
1696 }
1697 else if (value & 0x00ff0000) {
1698 length = 3;
1699 }
1700 else if (value & 0x0000ff00) {
1701 length = 2;
1702 }
1703 else length = 1;
1704
1705 OUT((int)ieee_number_repeat_start_enum + length);
1706 switch (length) {
1707 case 4:
1708 OUT( value >> 24);
1709 case 3:
1710 OUT( value >> 16);
1711 case 2:
1712 OUT( value >> 8);
1713 case 1:
1714 OUT( value);
1715 }
1716
1717 }
1718}
1719static void copy_id()
1720{
1721 int length = THIS();
1722 char ch;
1723 OUT(length);
1724 NEXT();
1725 while (length--) {
1726 ch = THIS();
1727 OUT(ch);
1728 NEXT();
1729 }
1730}
1731#define VAR(x) ((x | 0x80))
1732static void copy_expression()
1733{
1734 int stack[10];
1735 int *tos = stack;
1736 int value = 0;
1737 while (1) {
1738 switch (THIS()) {
1739 case 0x84:
1740 NEXT();
1741 value = THIS(); NEXT();
1742 value = (value << 8) | THIS(); NEXT();
1743 value = (value << 8) | THIS(); NEXT();
1744 value = (value << 8) | THIS(); NEXT();
1745 *tos ++ = value;
1746 break;
1747 case 0x83:
1748 NEXT();
1749 value = THIS(); NEXT();
1750 value = (value << 8) | THIS(); NEXT();
1751 value = (value << 8) | THIS(); NEXT();
1752 *tos ++ = value;
1753 break;
1754 case 0x82:
1755 NEXT();
1756 value = THIS(); NEXT();
1757 value = (value << 8) | THIS(); NEXT();
1758 *tos ++ = value;
1759 break;
1760 case 0x81:
1761 NEXT();
1762 value = THIS(); NEXT();
1763 *tos ++ = value;
1764 break;
1765 case 0x80:
1766 NEXT();
1767 *tos ++ = 0;
1768 break;
1769 default:
1770 if (THIS() >0x84) {
1771 /* Not a number, just bug out with the answer */
1772 write_int(*(--tos));
1773 return;
1774 }
1775 *tos++ = THIS();
1776NEXT();
1777 value = 0;
1778 break;
1779 case 0xa5:
1780 /* PLUS anything */
1781 {
1782 int value = *(--tos);
1783 value += *(--tos);
1784 *tos++ = value;
1785 NEXT();
301dfc71 1786 }
6f715d66
SC
1787 break;
1788 case VAR('R') :
1789 {
1790 int section_number ;
1791 ieee_data_type *ieee;
1792 asection *s;
1793 NEXT();
1794 section_number = THIS();
1795
1796 NEXT();
1797 ieee= ieee_data(input_bfd);
1798 s = ieee->section_table[section_number];
1799 if (s->output_section) {
1800 value = s->output_section->vma ;
1801 } else { value = 0; }
1802 value += s->output_offset;
1803 *tos++ = value;
1804 value = 0;
1805 }
1806 break;
1807 case 0x90:
1808 {
1809 NEXT();
1810 write_int(*(--tos));
1811 OUT(0x90);
1812 return;
87f86b4e 1813
6f715d66
SC
1814 }
1815 }
1816 }
1817
1818}
87f86b4e 1819
6f715d66
SC
1820/* Drop the int in the buffer, and copy a null into the gap, which we
1821 will overwrite later */
87f86b4e 1822
6f715d66
SC
1823struct output_buffer_struct {
1824unsigned char *ptrp;
1825 int buffer;
1826} ;
87f86b4e 1827
6f715d66
SC
1828static void
1829DEFUN(fill_int,(buf),
1830 struct output_buffer_struct *buf)
1831{
1832 if (buf->buffer == output_buffer) {
1833 /* Still a chance to output the size */
1834 int value = output_ptr - buf->ptrp + 3;
1835 buf->ptrp[0] = value >> 24;
1836 buf->ptrp[1] = value >> 16;
1837 buf->ptrp[2] = value >> 8;
1838 buf->ptrp[3] = value >> 0;
1839 }
87f86b4e 1840
6f715d66
SC
1841}
1842static void
1843DEFUN(drop_int,(buf),
1844 struct output_buffer_struct *buf)
1845{
1846 int type = THIS();
1847 int ch;
1848 if (type <= 0x84) {
1849 NEXT();
1850 switch(type) {
1851 case 0x84: ch = THIS(); NEXT();
1852 case 0x83: ch = THIS(); NEXT();
1853 case 0x82: ch = THIS(); NEXT();
1854 case 0x81: ch = THIS(); NEXT();
1855 case 0x80: break;
1856 }
1857 }
1858 OUT(0x84);
1859 buf->ptrp = output_ptr;
1860 buf->buffer = output_buffer;
1861 OUT(0);OUT(0);OUT(0);OUT(0);
1862}
1863
1864static void copy_int()
1865{
1866 int type = THIS();
1867 int ch;
1868 if (type <= 0x84) {
1869 OUT(type);
1870 NEXT();
1871 switch(type) {
1872 case 0x84: ch = THIS(); NEXT(); OUT(ch);
1873 case 0x83: ch = THIS(); NEXT(); OUT(ch);
1874 case 0x82: ch = THIS(); NEXT(); OUT(ch);
1875 case 0x81: ch = THIS(); NEXT(); OUT(ch);
1876 case 0x80: break;
1877 }
1878 }
1879}
1880
1881#define ID copy_id()
1882#define INT copy_int()
1883#define EXP copy_expression()
1884static void copy_till_end();
1885#define INTn(q) copy_int()
1886#define EXPn(q) copy_expression()
1887static void f1_record()
1888{
1889 int ch;
1890 /* ATN record */
1891 NEXT();
1892 ch = THIS();
1893 switch (ch)
1894 {
1895 default:
1896 OUT(0xf1); OUT(ch);
1897 break;
1898 case 0xc9:
1899 NEXT();
1900 OUT(0xf1); OUT(0xc9);
1901 INT; INT; ch = THIS();
1902 switch (ch)
1903 {
1904 case 0x16: NEXT();break;
1905 case 0x01: NEXT();break;
1906 case 0x00: NEXT(); INT; break;
1907 case 0x03: NEXT(); INT; break;
1908 case 0x13: EXPn(instruction address); break;
1909 default:
1910 break;
1911 }
1912 break;
1913 case 0xd8:
1914 /* EXternal ref */
1915 NEXT();
1916 OUT(0xf1); OUT(0xd8);
1917 EXP ; EXP; EXP; EXP;
1918 break;
1919 case 0xce:
1920 NEXT();
1921 OUT(0xf1);OUT(0xce); INT; INT; ch = THIS(); INT;
1922 switch (ch) {
1923 case 0x01:
1924 INT; INT; break;
1925 case 0x02:
1926 INT; break;
1927 case 0x04:
1928 EXPn(external function); break;
1929 case 0x05:
1930 break;
1931 case 0x07: INTn(line number); INT;
1932 case 0x08: break;
1933 case 0x0a: INTn(locked register); INT; break;
1934 case 0x3f: copy_till_end(); break;
1935 case 0x3e: copy_till_end(); break;
1936 case 0x40: copy_till_end(); break;
1937 case 0x41: ID; break;
87f86b4e 1938 }
6f715d66
SC
1939 }
1940
1941}
1942static void f0_record()
1943{
1944 /* Attribute record */
1945 NEXT();
1946 OUT(0xf0);
1947 INTn(Symbol name );
1948 ID;
1949}
1950static void copy_till_end()
1951{
1952 int ch = THIS();
1953 while (1) {
1954 while (ch <= 0x80)
1955 {
1956 OUT(ch);
1957 NEXT();
1958 ch = THIS();
1959 }
1960 switch (ch) {
1961 case 0x84:
1962 OUT(THIS());
1963 NEXT();
1964 case 0x83:
1965 OUT(THIS());
1966 NEXT();
1967 case 0x82:
1968 OUT(THIS());
1969 NEXT();
1970 case 0x81:
1971 OUT(THIS());
1972 NEXT();
1973 OUT(THIS());
1974 NEXT();
1975
1976 ch = THIS();
1977 break;
1978 default:
1979 return;
1980 }
1981 }
1982
1983}
1984
1985static void f2_record()
1986{
1987 int ch;
1988 NEXT();
1989 OUT(0xf2);
1990 INT ;
1991 NEXT();
1992 OUT(0xce);
1993 INT ;
1994copy_till_end();
1995}
1996
1997
1998static void block();
1999static void f8_record()
2000{
2001 int ch;
2002 NEXT();
2003 ch = THIS();
2004 switch (ch)
2005 {
2006 case 0x01:
2007 case 0x02:
2008 case 0x03:
2009 /* Unique typedefs for module */
2010 /* GLobal typedefs */
2011 /* High level module scope beginning */
2012 {
2013 struct output_buffer_struct ob;
2014 NEXT();
2015 OUT(0xf8); OUT(ch);
2016 drop_int(&ob); ID ;
2017
2018 block();
2019
2020 NEXT();
2021 fill_int(&ob);
2022 OUT(0xf9);
301dfc71 2023 }
6f715d66
SC
2024 break;
2025 case 0x04:
2026 /* Global function */
2027 {
2028 struct output_buffer_struct ob;
2029 NEXT();
2030 OUT(0xf8); OUT(0x04);
2031 drop_int(&ob); ID ; INTn(stack size); INTn(ret val);
2032 EXPn(offset);
2033
2034 block();
2035
2036 NEXT();
2037 OUT(0xf9);
2038 EXPn(size of block);
2039 fill_int(&ob);
301dfc71 2040 }
6f715d66 2041 break;
301dfc71 2042
6f715d66
SC
2043 case 0x05:
2044 /* File name for source line numbers */
2045 {
2046 struct output_buffer_struct ob;
2047 NEXT();
2048 OUT(0xf8); OUT(0x05);
2049 drop_int(&ob);
2050 ID; INTn(year); INTn(month); INTn(day);
2051 INTn(hour); INTn(monute); INTn(second);
2052 block();
2053 NEXT();
2054 OUT(0xf9);
2055 fill_int(&ob);
301dfc71 2056 }
6f715d66
SC
2057 break;
2058
2059 case 0x06:
2060 /* Local function */
2061 { struct output_buffer_struct ob;
2062 NEXT(); OUT(0xf8); OUT(0x06);
2063 drop_int(&ob);
2064 ID; INTn(stack size); INTn(type return);
2065 EXPn(offset);
2066 block();
2067 NEXT();
2068 OUT(0xf9);
2069 EXPn(size);
2070 fill_int(&ob);
2071 }
2072 break;
2073
2074 case 0x0a:
2075 /* Assembler module scope beginning -*/
2076 { struct output_buffer_struct ob;
d0ec7a8e 2077
6f715d66
SC
2078 NEXT();
2079 OUT(0xf8); OUT(0x0a);
2080 drop_int(&ob);
2081 ID; ID; INT; ID; INT; INT; INT; INT; INT; INT;
d0ec7a8e 2082
6f715d66 2083 block();
d0ec7a8e 2084
6f715d66
SC
2085 NEXT();
2086 OUT(0xf9);
2087 fill_int(&ob);
2088 }
2089 break;
2090 case 0x0b:
2091 {
2092 struct output_buffer_struct ob;
2093 NEXT();
2094 OUT(0xf8); OUT(0x0b);
2095 drop_int(&ob); ID ; INT; INTn(section index); EXPn(offset); INTn(stuff);
d0ec7a8e 2096
6f715d66 2097 block();
d0ec7a8e 2098
6f715d66
SC
2099 OUT(0xf9);
2100 NEXT();
2101 EXPn(Size in Maus);
2102 fill_int(&ob);
87f86b4e 2103 }
6f715d66 2104 break;
87f86b4e 2105 }
6f715d66 2106}
87f86b4e 2107
6f715d66
SC
2108static void e2_record()
2109{
2110 OUT(0xe2);
2111 NEXT();
2112 OUT(0xce);
2113 NEXT();
2114 INT;
2115 EXP;
2116}
2117
2118static void DEFUN_VOID(block)
2119{
2120 int ch ;
2121 while (1) {
2122 ch = THIS();
2123 switch (ch) {
2124 case 0xe1:
2125 case 0xe5:
2126 return;
2127 case 0xf9:
2128 return;
2129 case 0xf0:
2130 f0_record();
2131 break;
2132 case 0xf1:
2133 f1_record();
2134 break;
2135 case 0xf2:
2136 f2_record();
2137 break;
2138 case 0xf8:
2139 f8_record();
2140 break;
2141 case 0xe2:
2142 e2_record();
2143 break;
2144
2145 }
2146 }
2147}
2148
2149
2150
2151/* relocate_debug,
2152 moves all the debug information from the source bfd to the output
2153 bfd, and relocates any expressions it finds
2154*/
2155
2156static void
2157DEFUN(relocate_debug,(output, input),
2158 bfd *output AND
2159 bfd *input)
2160{
2161#define IBS 400
2162#define OBS 400
2163 unsigned char input_buffer[IBS];
2164
2165 input_ptr_start = input_ptr = input_buffer;
2166 input_ptr_end = input_buffer + IBS;
2167 input_bfd = input;
2168 bfd_read(input_ptr_start, 1, IBS, input);
2169 block();
2170}
2171/*
2172 During linking, we we told about the bfds which made up our
2173 contents, we have a list of them. They will still be open, so go to
2174 the debug info in each, and copy it out, relocating it as we go.
2175*/
2176
2177static void
2178DEFUN(ieee_write_debug_part, (abfd),
2179 bfd *abfd)
2180{
2181 ieee_data_type *ieee = ieee_data(abfd);
2182 bfd_chain_type *chain = ieee->chain_root;
2183 unsigned char output_buffer[OBS];
2184 output_ptr_start = output_ptr = output_buffer ;
2185 output_ptr_end = output_buffer + OBS;
2186 output_ptr = output_buffer;
2187 output_bfd = abfd;
2188 ieee->w.r.debug_information_part = bfd_tell(abfd);
2189 while (chain != (bfd_chain_type *)NULL) {
2190 bfd *entry = chain->this;
2191 ieee_data_type *entry_ieee = ieee_data(entry);
2192 if (entry_ieee->w.r.debug_information_part) {
2193 bfd_seek(entry, entry_ieee->w.r.debug_information_part, SEEK_SET);
2194 relocate_debug(abfd, entry);
2195 }
2196
2197 chain = chain->next;
2198 }
2199
2200 flush();
2201
2202}
2203/* write the data in an ieee way */
2204static void
2205DEFUN(ieee_write_data_part,(abfd),
2206 bfd *abfd)
2207{
2208 asection *s;
2209 ieee_data_type *ieee = ieee_data(abfd);
2210 ieee->w.r.data_part = bfd_tell(abfd);
2211 for (s = abfd->sections; s != (asection *)NULL; s = s->next)
2212 {
2213 /* Sort the reloc records so we can insert them in the correct
2214 places */
2215 if (s->reloc_count != 0)
2216 {
2217 do_with_relocs(abfd, s);
2218 }
2219 else
2220 {
2221 do_without_relocs(abfd, s);
2222 }
2223 }
301dfc71 2224}
87f86b4e
DHW
2225
2226
2227
2228static void
301dfc71
SC
2229DEFUN(init_for_output,(abfd),
2230 bfd *abfd)
87f86b4e
DHW
2231{
2232 asection *s;
2233 for (s = abfd->sections; s != (asection *)NULL; s = s->next) {
2234 if (s->size != 0) {
d0ec7a8e 2235 ieee_per_section(s)->data = (bfd_byte *)(bfd_alloc(abfd, s->size));
87f86b4e
DHW
2236 }
2237 }
2238}
2239
2240/** exec and core file sections */
2241
2242/* set section contents is complicated with IEEE since the format is
2243* not a byte image, but a record stream.
2244*/
2245boolean
301dfc71
SC
2246DEFUN(ieee_set_section_contents,(abfd, section, location, offset, count),
2247 bfd *abfd AND
2248 sec_ptr section AND
d0ec7a8e 2249 PTR location AND
301dfc71 2250 file_ptr offset AND
7ed4093a 2251 bfd_size_type count)
87f86b4e
DHW
2252{
2253 if (ieee_per_section(section)->data == (bfd_byte *)NULL) {
2254 init_for_output(abfd);
2255 }
7ed4093a
SC
2256 (void) memcpy(ieee_per_section(section)->data + offset,
2257 location,
2258 (unsigned int)count);
87f86b4e
DHW
2259 return true;
2260}
2261
2262/*
2263write the external symbols of a file, IEEE considers two sorts of
2264external symbols, public, and referenced. It uses to internal forms
2265to index them as well. When we write them out we turn their symbol
2266values into indexes from the right base.
2267*/
2268static void
301dfc71
SC
2269DEFUN(ieee_write_external_part,(abfd),
2270 bfd *abfd)
87f86b4e
DHW
2271{
2272 asymbol **q;
2273 ieee_data_type *ieee = ieee_data(abfd);
2274
2275 unsigned int reference_index = IEEE_REFERENCE_BASE;
2276 unsigned int public_index = IEEE_PUBLIC_BASE;
2277 ieee->w.r.external_part = bfd_tell(abfd);
2278 if (abfd->outsymbols != (asymbol **)NULL) {
2279 for (q = abfd->outsymbols; *q != (asymbol *)NULL; q++) {
2280 asymbol *p = *q;
2281 if (p->flags & BSF_UNDEFINED) {
2282 /* This must be a symbol reference .. */
2283 ieee_write_byte(abfd, ieee_external_reference_enum);
2284 ieee_write_int(abfd, reference_index);
2285 ieee_write_id(abfd, p->name);
2286 p->value = reference_index;
2287 reference_index++;
2288 }
2289 else if(p->flags & BSF_FORT_COMM) {
2290 /* This is a weak reference */
2291 ieee_write_byte(abfd, ieee_external_reference_enum);
2292 ieee_write_int(abfd, reference_index);
2293 ieee_write_id(abfd, p->name);
2294 ieee_write_byte(abfd, ieee_weak_external_reference_enum);
2295 ieee_write_int(abfd, reference_index);
2296 ieee_write_int(abfd, p->value);
2297 ieee_write_int(abfd, BFD_FORT_COMM_DEFAULT_VALUE);
2298 p->value = reference_index;
2299 reference_index++;
2300 }
2301 else if(p->flags & BSF_GLOBAL) {
2302 /* This must be a symbol definition */
2303
2304 ieee_write_byte(abfd, ieee_external_symbol_enum);
2305 ieee_write_int(abfd, public_index );
2306 ieee_write_id(abfd, p->name);
2307
2308 /* Write out the value */
2309 ieee_write_2bytes(abfd, ieee_value_record_enum);
2310 ieee_write_int(abfd, public_index);
2311 if (p->section != (asection *)NULL)
2312 {
6f715d66
SC
2313 if (abfd->flags & EXEC_P)
2314 {
2315 /* If fully linked, then output all symbols
2316 relocated */
2317 ieee_write_int(abfd,
2318 p->value + p->section->output_offset+ p->section->output_section->vma);
2319
2320 }
2321 else {
2322 ieee_write_expression(abfd,
2323 p->value + p->section->output_offset,
2324 p->section->output_section,
2325 (asymbol *)NULL, false, 0);
2326 }
87f86b4e
DHW
2327 }
2328 else
2329 {
2330 ieee_write_expression(abfd,
2331 p->value,
2332 (asection *)NULL,
d0ec7a8e 2333 (asymbol *)NULL, false, 0);
87f86b4e
DHW
2334 }
2335 p->value = public_index;
2336 public_index++;
2337 }
2338 else {
2339 /* This can happen - when there are gaps in the symbols read */
2340 /* from an input ieee file */
2341 }
2342 }
2343 }
2344
2345}
2346
2347static
301dfc71
SC
2348void
2349DEFUN(ieee_write_me_part,(abfd),
2350 bfd *abfd)
87f86b4e
DHW
2351{
2352 ieee_data_type *ieee= ieee_data(abfd);
2353 ieee->w.r.me_record = bfd_tell(abfd);
2354
2355 ieee_write_2bytes(abfd, ieee_value_starting_address_enum);
2356 ieee_write_int(abfd, abfd->start_address);
2357 ieee_write_byte(abfd, ieee_module_end_enum);
2358
2359}
2360boolean
301dfc71
SC
2361DEFUN(ieee_write_object_contents,(abfd),
2362 bfd *abfd)
87f86b4e
DHW
2363{
2364 ieee_data_type *ieee = ieee_data(abfd);
2365 unsigned int i;
301dfc71
SC
2366 file_ptr old;
2367 /* Fast forward over the header area */
2368 bfd_seek(abfd, 0, 0);
2369 ieee_write_byte(abfd, ieee_module_beginning_enum);
2370
2371 ieee_write_id(abfd, bfd_printable_arch_mach(abfd->obj_arch,
2372 abfd->obj_machine));
2373 ieee_write_id(abfd, abfd->filename);
6f715d66
SC
2374
2375
2376
2377
2378 /* Fast forward over the variable bits */
2379
2380
2381
301dfc71
SC
2382 ieee_write_byte(abfd, ieee_address_descriptor_enum);
2383 ieee_write_byte(abfd, 8); /* Bits per MAU */
2384 ieee_write_byte(abfd, 4); /* MAU's per address */
2385
301dfc71
SC
2386 old = bfd_tell(abfd);
2387 bfd_seek(abfd, 8 * N_W_VARIABLES, 1);
87f86b4e 2388
6f715d66
SC
2389
2390 ieee->w.r.extension_record = bfd_tell(abfd);
2391 ieee->w.r.environmental_record = bfd_tell(abfd);
2392 ieee_write_byte(abfd, 0xf0);
2393 ieee_write_byte(abfd, 0x20);
2394 ieee_write_byte(abfd, 0x00);
2395 ieee_write_byte(abfd, 0xf1);
2396 ieee_write_byte(abfd, 0xce);
2397 ieee_write_byte(abfd, 0x20);
2398 ieee_write_byte(abfd, 0x00);
2399 ieee_write_byte(abfd, 0x55);
2400 ieee_write_id(abfd,"built using BFD");
2401
2402
2403
87f86b4e 2404 /*
301dfc71
SC
2405 First write the symbols, this changes their values into table
2406 indeces so we cant use it after this point
2407 */
87f86b4e
DHW
2408 ieee_write_external_part(abfd);
2409 ieee_write_byte(abfd, ieee_record_seperator_enum);
2410
2411 ieee_write_section_part(abfd);
2412 ieee_write_byte(abfd, ieee_record_seperator_enum);
6f715d66
SC
2413
2414
2415 /*
2416 Write any debugs we have been told about
2417 */
2418ieee_write_debug_part(abfd);
2419
87f86b4e 2420 /*
301dfc71
SC
2421 Can only write the data once the symbols have been written since
2422 the data contains relocation information which points to the
2423 symbols
2424 */
87f86b4e
DHW
2425 ieee_write_data_part(abfd);
2426 ieee_write_byte(abfd, ieee_record_seperator_enum);
2427
2428 /*
301dfc71
SC
2429 At the end we put the end !
2430 */
87f86b4e 2431 ieee_write_me_part(abfd);
87f86b4e 2432
87f86b4e 2433
301dfc71
SC
2434 /* Generate the header */
2435 bfd_seek(abfd, old, false);
87f86b4e
DHW
2436
2437 for (i= 0; i < N_W_VARIABLES; i++) {
2438 ieee_write_2bytes(abfd,ieee_assign_value_to_variable_enum);
2439 ieee_write_byte(abfd, i);
301dfc71 2440 ieee_write_int5_out(abfd, ieee->w.offset[i]);
87f86b4e
DHW
2441 }
2442 return true;
2443}
2444
2445
2446
2447\f
2448/* Native-level interface to symbols. */
2449
2450/* We read the symbols into a buffer, which is discarded when this
2451function exits. We read the strings into a buffer large enough to
2452hold them all plus all the cached symbol entries. */
2453
2454asymbol *
301dfc71
SC
2455DEFUN(ieee_make_empty_symbol,(abfd),
2456 bfd *abfd)
87f86b4e
DHW
2457{
2458
2459 ieee_symbol_type *new =
2460 (ieee_symbol_type *)zalloc (sizeof (ieee_symbol_type));
2461 new->symbol.the_bfd = abfd;
2462 return &new->symbol;
2463
2464}
2465
87f86b4e 2466static bfd *
6f715d66
SC
2467DEFUN(ieee_openr_next_archived_file,(arch, prev),
2468 bfd *arch AND
2469 bfd *prev)
87f86b4e
DHW
2470{
2471 ieee_ar_data_type *ar = ieee_ar_data(arch);
2472 /* take the next one from the arch state, or reset */
2473 if (prev == (bfd *)NULL) {
2474 /* Reset the index - the first two entries are bogus*/
2475 ar->element_index = 2;
2476 }
2477 while (true) {
2478 ieee_ar_obstack_type *p = ar->elements + ar->element_index;
2479 ar->element_index++;
2480 if (ar->element_index <= ar->element_count) {
2481 if (p->file_offset != (file_ptr)0) {
2482 if (p->abfd == (bfd *)NULL) {
2483 p->abfd = _bfd_create_empty_archive_element_shell(arch);
2484 p->abfd->origin = p->file_offset;
2485 }
2486 return p->abfd;
2487 }
2488 }
2489 else {
6f715d66 2490 bfd_error = no_more_archived_files;
87f86b4e
DHW
2491 return (bfd *)NULL;
2492 }
2493
2494 }
2495}
2496
2497static boolean
2498ieee_find_nearest_line(abfd,
2499 section,
2500 symbols,
2501 offset,
2502 filename_ptr,
2503 functionname_ptr,
2504 line_ptr)
2505bfd *abfd;
2506asection *section;
2507asymbol **symbols;
2508bfd_vma offset;
2509char **filename_ptr;
2510char **functionname_ptr;
d0ec7a8e 2511int *line_ptr;
87f86b4e
DHW
2512{
2513 return false;
87f86b4e 2514}
301dfc71
SC
2515
2516
2517static int
9872a49c 2518ieee_generic_stat_arch_elt(abfd, buf)
301dfc71
SC
2519bfd *abfd;
2520struct stat *buf;
2521{
2522 ieee_ar_data_type *ar = ieee_ar_data(abfd);
2523 if (ar == (ieee_ar_data_type *)NULL) {
2524 bfd_error = invalid_operation;
2525 return -1;
2526 }
2527 else {
2528 buf->st_size = 0x1;
2529 buf->st_mode = 0666;
2530 return 0;
2531 }
2532}
39a2ce33 2533static int
d0ec7a8e
SC
2534DEFUN(ieee_sizeof_headers,(abfd, x),
2535 bfd *abfd AND
2536 boolean x)
39a2ce33 2537{
d0ec7a8e 2538 return 0;
39a2ce33
SC
2539}
2540
6f715d66
SC
2541
2542
2543static void
2544DEFUN(ieee_bfd_debug_info_start,(abfd),
2545 bfd *abfd)
2546 {
2547
2548 }
2549
2550static void
2551DEFUN(ieee_bfd_debug_info_end,(abfd),
2552 bfd *abfd)
2553 {
2554
2555 }
2556
2557
2558/* Add this section to the list of sections we have debug info for, to
2559 be ready to output it at close time
2560 */
2561static void
2562DEFUN(ieee_bfd_debug_info_accumulate,(abfd, section),
2563 bfd *abfd AND
2564 asection *section)
2565{
2566 ieee_data_type *ieee = ieee_data(section->owner);
2567 ieee_data_type *output_ieee = ieee_data(abfd);
2568 /* can only accumulate data from other ieee bfds */
2569 if (section->owner->xvec != abfd->xvec)
2570 return;
2571 /* Only bother once per bfd */
2572 if (ieee->done_debug == true)
2573 return;
2574 ieee->done_debug = true;
2575
2576 /* Don't bother if there is no debug info */
2577 if (ieee->w.r.debug_information_part == 0)
2578 return;
2579
2580
2581 /* Add to chain */
2582 {
2583 bfd_chain_type *n = (bfd_chain_type *) bfd_alloc(abfd, sizeof(bfd_chain_type));
2584 n->this = section->owner;
2585 n->next = (bfd_chain_type *)NULL;
2586
2587 if (output_ieee->chain_head) {
2588 output_ieee->chain_head->next = n;
2589 }
2590 else {
2591 output_ieee->chain_root = n;
2592
2593 }
2594 output_ieee->chain_head = n;
2595 }
2596}
2597
2598
2599
2600
2601
2602
2603#define FOO PROTO
d0ec7a8e
SC
2604#define ieee_core_file_failing_command (char *(*)())(bfd_nullvoidptr)
2605#define ieee_core_file_failing_signal (int (*)())bfd_0
6f715d66 2606#define ieee_core_file_matches_executable_p ( FOO(boolean, (*),(bfd *, bfd *)))bfd_false
9872a49c
SC
2607#define ieee_slurp_armap bfd_true
2608#define ieee_slurp_extended_name_table bfd_true
d0ec7a8e 2609#define ieee_truncate_arname (void (*)())bfd_nullvoidptr
6f715d66 2610#define ieee_write_armap (FOO( boolean, (*),(bfd *, unsigned int, struct orl *, int, int))) bfd_nullvoidptr
d0ec7a8e 2611#define ieee_get_lineno (struct lineno_cache_entry *(*)())bfd_nullvoidptr
2b1d8a50 2612#define ieee_close_and_cleanup bfd_generic_close_and_cleanup
9872a49c 2613
301dfc71 2614
87f86b4e
DHW
2615/*SUPPRESS 460 */
2616bfd_target ieee_vec =
2617{
2618 "ieee", /* name */
2619 bfd_target_ieee_flavour_enum,
2620 true, /* target byte order */
2621 true, /* target headers byte order */
2622 (HAS_RELOC | EXEC_P | /* object flags */
2623 HAS_LINENO | HAS_DEBUG |
2624 HAS_SYMS | HAS_LOCALS | DYNAMIC | WP_TEXT | D_PAGED),
f61d204a 2625 (SEC_CODE|SEC_DATA|SEC_ROM|SEC_HAS_CONTENTS
87f86b4e 2626 |SEC_ALLOC | SEC_LOAD | SEC_RELOC), /* section flags */
87f86b4e
DHW
2627 ' ', /* ar_pad_char */
2628 16, /* ar_max_namelen */
6f715d66 2629 1, /* minimum alignment */
7ed4093a
SC
2630_do_getb64, _do_putb64, _do_getb32, _do_putb32, _do_getb16, _do_putb16, /* data */
2631_do_getb64, _do_putb64, _do_getb32, _do_putb32, _do_getb16, _do_putb16, /* hdrs */
87f86b4e 2632
d0ec7a8e 2633 { _bfd_dummy_target,
87f86b4e
DHW
2634 ieee_object_p, /* bfd_check_format */
2635 ieee_archive_p,
d0ec7a8e 2636 _bfd_dummy_target,
87f86b4e
DHW
2637 },
2638 {
2639 bfd_false,
2640 ieee_mkobject,
2641 _bfd_generic_mkarchive,
2642 bfd_false
2643 },
2b1d8a50
JG
2644 {
2645 bfd_false,
2646 ieee_write_object_contents,
2647 _bfd_write_archive_contents,
2648 bfd_false,
2649 },
2650 JUMP_TABLE(ieee)
87f86b4e 2651};
This page took 0.148724 seconds and 4 git commands to generate.