3bf0e754cab21f1e7ed092bc57b02614811d0be0
[deliverable/binutils-gdb.git] / gas / config / obj-coff.c
1 /* coff object file format
2 Copyright (C) 1989, 1990, 1991, 1992 Free Software Foundation, Inc.
3
4 This file is part of GAS.
5
6 GAS is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 2, or (at your option)
9 any later version.
10
11 GAS is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GAS; see the file COPYING. If not, write to
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
19
20 #include "as.h"
21
22 #include "obstack.h"
23
24 #ifndef BFD_ASSEMBLER
25 lineno *lineno_rootP;
26
27 const short seg_N_TYPE[] =
28 { /* in: segT out: N_TYPE bits */
29 C_ABS_SECTION,
30 C_TEXT_SECTION,
31 C_DATA_SECTION,
32 C_BSS_SECTION,
33 C_UNDEF_SECTION, /* SEG_UNKNOWN */
34 C_UNDEF_SECTION, /* SEG_ABSENT */
35 C_UNDEF_SECTION, /* SEG_PASS1 */
36 C_UNDEF_SECTION, /* SEG_GOOF */
37 C_UNDEF_SECTION, /* SEG_BIG */
38 C_UNDEF_SECTION, /* SEG_DIFFERENCE */
39 C_DEBUG_SECTION, /* SEG_DEBUG */
40 C_NTV_SECTION, /* SEG_NTV */
41 C_PTV_SECTION, /* SEG_PTV */
42 C_REGISTER_SECTION, /* SEG_REGISTER */
43 };
44
45
46 /* Add 4 to the real value to get the index and compensate the negatives */
47
48 const segT N_TYPE_seg[32] =
49 {
50 SEG_PTV, /* C_PTV_SECTION == -4 */
51 SEG_NTV, /* C_NTV_SECTION == -3 */
52 SEG_DEBUG, /* C_DEBUG_SECTION == -2 */
53 SEG_ABSOLUTE, /* C_ABS_SECTION == -1 */
54 SEG_UNKNOWN, /* C_UNDEF_SECTION == 0 */
55 SEG_TEXT, /* C_TEXT_SECTION == 1 */
56 SEG_DATA, /* C_DATA_SECTION == 2 */
57 SEG_BSS, /* C_BSS_SECTION == 3 */
58 SEG_REGISTER, /* C_REGISTER_SECTION == 4 */
59 SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF,
60 SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF,
61 SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF, SEG_GOOF
62 };
63 #endif
64
65 char *s_get_name PARAMS ((symbolS * s));
66 static symbolS *tag_find_or_make PARAMS ((char *name));
67 static symbolS *tag_find PARAMS ((char *name));
68 #ifdef BFD_HEADERS
69 static void obj_coff_section_header_append PARAMS ((char **where, struct internal_scnhdr * header));
70 #else
71 static void obj_coff_section_header_append PARAMS ((char **where, SCNHDR * header));
72 #endif
73 static void obj_coff_def PARAMS ((int what));
74 static void obj_coff_dim PARAMS ((void));
75 static void obj_coff_endef PARAMS ((void));
76 static void obj_coff_line PARAMS ((void));
77 static void obj_coff_ln PARAMS ((int));
78 static void obj_coff_scl PARAMS ((void));
79 static void obj_coff_size PARAMS ((void));
80 static void obj_coff_stab PARAMS ((int what));
81 static void obj_coff_tag PARAMS ((void));
82 static void obj_coff_type PARAMS ((void));
83 static void obj_coff_val PARAMS ((void));
84 static void tag_init PARAMS ((void));
85 static void tag_insert PARAMS ((char *name, symbolS * symbolP));
86
87 #ifdef BFD_ASSEMBLER
88 static void SA_SET_SYM_ENDNDX PARAMS ((symbolS *, symbolS *));
89 static void SA_SET_SYM_TAGNDX PARAMS ((symbolS *, symbolS *));
90 #endif
91
92 int line_base;
93
94 static struct hash_control *tag_hash;
95 static symbolS *def_symbol_in_progress;
96
97 const pseudo_typeS obj_pseudo_table[] =
98 {
99 #ifndef IGNORE_DEBUG
100 {"def", obj_coff_def, 0},
101 {"dim", obj_coff_dim, 0},
102 {"endef", obj_coff_endef, 0},
103 {"line", obj_coff_line, 0},
104 {"ln", obj_coff_ln, 0},
105 {"appline", obj_coff_ln, 1},
106 {"scl", obj_coff_scl, 0},
107 {"size", obj_coff_size, 0},
108 {"tag", obj_coff_tag, 0},
109 {"type", obj_coff_type, 0},
110 {"val", obj_coff_val, 0},
111 #else
112 {"def", s_ignore, 0},
113 {"dim", s_ignore, 0},
114 {"endef", s_ignore, 0},
115 {"line", s_ignore, 0},
116 {"ln", s_ignore, 0},
117 {"scl", s_ignore, 0},
118 {"size", s_ignore, 0},
119 {"tag", s_ignore, 0},
120 {"type", s_ignore, 0},
121 {"val", s_ignore, 0},
122 #endif /* ignore debug */
123
124 {"ident", s_ignore, 0}, /* we don't yet handle this. */
125
126
127 /* stabs aka a.out aka b.out directives for debug symbols.
128 Currently ignored silently. Except for .line at which
129 we guess from context. */
130 {"desc", s_ignore, 0}, /* def */
131 {"stabd", obj_coff_stab, 'd'},/* stabs */
132 {"stabn", obj_coff_stab, 'n'},/* stabs */
133 {"stabs", obj_coff_stab, 's'},/* stabs */
134
135 /* stabs-in-coff (?) debug pseudos (ignored) */
136 {"optim", s_ignore, 0}, /* For sun386i cc (?) */
137 /* other stuff */
138 {"ABORT", s_abort, 0},
139
140 {NULL} /* end sentinel */
141 }; /* obj_pseudo_table */
142
143 #ifdef BFD_ASSEMBLER
144 struct line_no {
145 struct line_no *next;
146 fragS *frag;
147 alent l;
148 };
149 #endif
150
151 #define GET_FILENAME_STRING(X) \
152 ((char*)(&((X)->sy_symbol.ost_auxent->x_file.x_n.x_offset))[1])
153
154 /* obj dependant output values */
155 #ifndef BFD_ASSEMBLER
156 #ifdef BFD_HEADERS
157 static struct internal_scnhdr bss_section_header;
158 struct internal_scnhdr data_section_header;
159 struct internal_scnhdr text_section_header;
160 #else
161 static SCNHDR bss_section_header;
162 SCNHDR data_section_header;
163 SCNHDR text_section_header;
164 #endif
165 #endif
166
167 #ifdef BFD_ASSEMBLER
168
169 /* @@ Ick. */
170 static segT
171 fetch_coff_debug_section ()
172 {
173 static segT debug_section;
174 if (!debug_section)
175 {
176 CONST asymbol *s;
177 s = bfd_make_debug_symbol (stdoutput, (char *) 0, 0);
178 assert (s != 0);
179 debug_section = s->section;
180 }
181 return debug_section;
182 }
183
184 static void
185 SA_SET_SYM_ENDNDX (sym, val)
186 symbolS *sym;
187 symbolS *val;
188 {
189 combined_entry_type *entry, *p;
190
191 entry = &coffsymbol (sym->bsym)->native[1];
192 p = coffsymbol (val->bsym)->native;
193 entry->u.auxent.x_sym.x_fcnary.x_fcn.x_endndx.p = p;
194 entry->fix_end = 1;
195 }
196
197 static void
198 SA_SET_SYM_TAGNDX (sym, val)
199 symbolS *sym;
200 symbolS *val;
201 {
202 combined_entry_type *entry, *p;
203
204 entry = &coffsymbol (sym->bsym)->native[1];
205 p = coffsymbol (val->bsym)->native;
206 entry->u.auxent.x_sym.x_tagndx.p = p;
207 entry->fix_tag = 1;
208 }
209
210 #else /* ! BFD_ASSEMBLER */
211
212 /* Relocation. */
213
214 static int
215 reloc_compare (p1, p2)
216 #ifdef BFD_HEADERS
217 struct internal_reloc *p1, *p2;
218 #else
219 RELOC *p1, *p2;
220 #endif
221 {
222 return (int) (p1->r_vaddr - p2->r_vaddr);
223 }
224
225 /*
226 * emit_relocations()
227 *
228 * Crawl along a fixS chain. Emit the segment's relocations.
229 */
230
231 void
232 obj_emit_relocations (where, fixP, segment_address_in_file)
233 char **where;
234 fixS *fixP; /* Fixup chain for this segment. */
235 relax_addressT segment_address_in_file;
236 {
237 #ifdef BFD_HEADERS
238 struct internal_reloc *ri_table;
239 #else
240 RELOC *ri_table;
241 #endif
242 #ifdef TC_I960
243 char *callj_table;
244 #endif
245 symbolS *symbolP;
246 int i, count;
247 fixS *p;
248
249 for (count = 0, p = fixP; p; p = p->fx_next)
250 if (p->fx_addsy)
251 count++;
252 if (!count)
253 return;
254
255 #ifdef BFD_HEADERS
256 ri_table = (struct internal_reloc *) calloc (sizeof (*ri_table), count);
257 #else
258 ri_table = (RELOC *) calloc (sizeof (*ri_table), count);
259 #endif
260 if (!ri_table)
261 as_fatal ("obj_emit_relocations: Could not malloc relocation table");
262
263 #ifdef TC_I960
264 callj_table = (char *) malloc (sizeof (char) * count);
265 if (!callj_table)
266 as_fatal ("obj_emit_relocations: Could not malloc callj table");
267 #endif
268
269 for (i = 0; fixP; fixP = fixP->fx_next)
270 {
271 if (symbolP = fixP->fx_addsy)
272 {
273 int rtype_ok = 0;
274 #if defined(TC_M68K)
275 ri_table[i].r_type = (fixP->fx_pcrel ?
276 (fixP->fx_size == 1 ? R_PCRBYTE :
277 fixP->fx_size == 2 ? R_PCRWORD :
278 R_PCRLONG) :
279 (fixP->fx_size == 1 ? R_RELBYTE :
280 fixP->fx_size == 2 ? R_RELWORD :
281 R_RELLONG));
282 rtype_ok = 1;
283 #endif
284 #if defined(TC_I386)
285 /* FIXME-SOON R_OFF8 & R_DIR16 are a vague guess, completly
286 untested. */
287 ri_table[i].r_type = (fixP->fx_pcrel ?
288 (fixP->fx_size == 1 ? R_PCRBYTE :
289 fixP->fx_size == 2 ? R_PCRWORD :
290 R_PCRLONG) :
291 (fixP->fx_size == 1 ? R_OFF8 :
292 fixP->fx_size == 2 ? R_DIR16 :
293 R_DIR32));
294 rtype_ok = 1;
295 #endif
296 #if defined(TC_I960)
297 ri_table[i].r_type = (fixP->fx_pcrel
298 ? R_IPRMED
299 : R_RELLONG);
300 callj_table[i] = fixP->fx_callj ? 1 : 0;
301 rtype_ok = 1;
302 #endif
303 #if defined(TC_A29K)
304 ri_table[i].r_type = tc_coff_fix2rtype (fixP);
305 rtype_ok = 1;
306 #endif
307 if (!rtype_ok)
308 abort ();
309 ri_table[i].r_vaddr = (fixP->fx_frag->fr_address
310 + fixP->fx_where);
311 /* If symbol associated to relocation entry is a bss symbol
312 or undefined symbol just remember the index of the symbol.
313 Otherwise store the index of the symbol describing the
314 section the symbol belong to. This heuristic speeds up ld.
315 */
316 /* Local symbols can generate relocation information. In case
317 of structure return for instance. But they have no symbol
318 number because they won't be emitted in the final object.
319 In the case where they are in the BSS section, this leads
320 to an incorrect r_symndx.
321 Under bsd the loader do not care if the symbol reference
322 is incorrect. But the SYS V ld complains about this. To
323 avoid this we associate the symbol to the associated
324 section, *even* if it is the BSS section. */
325 /* If someone can tell me why the other symbols of the bss
326 section are not associated with the .bss section entry,
327 I'd be gratefull. I guess that it has to do with the special
328 nature of the .bss section. Or maybe this is because the
329 bss symbols are declared in the common section and can
330 be resized later. Can it break code some where ? */
331 ri_table[i].r_symndx = (S_GET_SEGMENT (symbolP) == SEG_TEXT
332 ? dot_text_symbol->sy_number
333 : (S_GET_SEGMENT (symbolP) == SEG_DATA
334 ? dot_data_symbol->sy_number
335 : ((SF_GET_LOCAL (symbolP)
336 ? dot_bss_symbol->sy_number
337 : symbolP->sy_number)))); /* bss or undefined */
338
339 /* md_ri_to_chars((char *) &ri, ri); *//* Last step : write md f */
340
341 i++;
342 } /* if there's a symbol */
343 } /* for each fixP */
344
345 /* AIX ld prefer to have the reloc table with r_vaddr sorted.
346 But sorting it should not hurt any other ld. */
347 qsort (ri_table, count, sizeof (*ri_table), reloc_compare);
348
349 for (i = 0; i < count; i++)
350 {
351 #ifdef BFD_HEADERS
352 *where += bfd_coff_swap_reloc_out (stdoutput, &ri_table[i], *where);
353 # ifdef TC_A29K
354 /* The 29k has a special kludge for the high 16 bit reloc.
355 Two relocations are emmited, R_IHIHALF, and R_IHCONST.
356 The second one doesn't contain a symbol, but uses the
357 value for offset */
358 if (ri_table[i].r_type == R_IHIHALF)
359 {
360 /* now emit the second bit */
361 ri_table[i].r_type = R_IHCONST;
362 ri_table[i].r_symndx = fixP->fx_addnumber;
363 *where += bfd_coff_swap_reloc_out (stdoutput, &ri_table[i],
364 *where);
365 }
366 # endif /* TC_A29K */
367
368 #else /* not BFD_HEADERS */
369 append (where, (char *) &ri_table[i], RELSZ);
370 #endif /* not BFD_HEADERS */
371
372 #ifdef TC_I960
373 if (callj_table[i])
374 {
375 ri_table[i].r_type = R_OPTCALL;
376 # ifdef BFD_HEADERS
377 *where += bfd_coff_swap_reloc_out (stdoutput, &ri_table[i],
378 *where);
379 # else
380 append (where, (char *) &ri_table[i], (unsigned long) RELSZ);
381 # endif /* BFD_HEADERS */
382 } /* if it's a callj, do it again for the opcode */
383 #endif /* TC_I960 */
384 }
385
386 free (ri_table);
387 #ifdef TC_I960
388 free (callj_table);
389 #endif
390
391 return;
392 } /* obj_emit_relocations() */
393
394 /* Coff file generation & utilities */
395
396 #ifdef BFD_HEADERS
397 void
398 obj_header_append (where, headers)
399 char **where;
400 object_headers *headers;
401 {
402 tc_headers_hook (headers);
403 *where += bfd_coff_swap_filehdr_out (stdoutput, &(headers->filehdr), *where);
404 #ifndef OBJ_COFF_OMIT_OPTIONAL_HEADER
405 *where += bfd_coff_swap_aouthdr_out (stdoutput, &(headers->aouthdr), *where);
406 #endif
407 obj_coff_section_header_append (where, &text_section_header);
408 obj_coff_section_header_append (where, &data_section_header);
409 obj_coff_section_header_append (where, &bss_section_header);
410 }
411
412 #else /* ! BFD_HEADERS */
413
414 void
415 obj_header_append (where, headers)
416 char **where;
417 object_headers *headers;
418 {
419 tc_headers_hook (headers);
420
421 #ifdef CROSS_COMPILE
422 /* Eventually swap bytes for cross compilation for file header */
423 md_number_to_chars (*where, headers->filehdr.f_magic, sizeof (headers->filehdr.f_magic));
424 *where += sizeof (headers->filehdr.f_magic);
425 md_number_to_chars (*where, headers->filehdr.f_nscns, sizeof (headers->filehdr.f_nscns));
426 *where += sizeof (headers->filehdr.f_nscns);
427 md_number_to_chars (*where, headers->filehdr.f_timdat, sizeof (headers->filehdr.f_timdat));
428 *where += sizeof (headers->filehdr.f_timdat);
429 md_number_to_chars (*where, headers->filehdr.f_symptr, sizeof (headers->filehdr.f_symptr));
430 *where += sizeof (headers->filehdr.f_symptr);
431 md_number_to_chars (*where, headers->filehdr.f_nsyms, sizeof (headers->filehdr.f_nsyms));
432 *where += sizeof (headers->filehdr.f_nsyms);
433 md_number_to_chars (*where, headers->filehdr.f_opthdr, sizeof (headers->filehdr.f_opthdr));
434 *where += sizeof (headers->filehdr.f_opthdr);
435 md_number_to_chars (*where, headers->filehdr.f_flags, sizeof (headers->filehdr.f_flags));
436 *where += sizeof (headers->filehdr.f_flags);
437
438 #ifndef OBJ_COFF_OMIT_OPTIONAL_HEADER
439 /* Eventually swap bytes for cross compilation for a.out header */
440 md_number_to_chars (*where, headers->aouthdr.magic, sizeof (headers->aouthdr.magic));
441 *where += sizeof (headers->aouthdr.magic);
442 md_number_to_chars (*where, headers->aouthdr.vstamp, sizeof (headers->aouthdr.vstamp));
443 *where += sizeof (headers->aouthdr.vstamp);
444 md_number_to_chars (*where, headers->aouthdr.tsize, sizeof (headers->aouthdr.tsize));
445 *where += sizeof (headers->aouthdr.tsize);
446 md_number_to_chars (*where, headers->aouthdr.dsize, sizeof (headers->aouthdr.dsize));
447 *where += sizeof (headers->aouthdr.dsize);
448 md_number_to_chars (*where, headers->aouthdr.bsize, sizeof (headers->aouthdr.bsize));
449 *where += sizeof (headers->aouthdr.bsize);
450 md_number_to_chars (*where, headers->aouthdr.entry, sizeof (headers->aouthdr.entry));
451 *where += sizeof (headers->aouthdr.entry);
452 md_number_to_chars (*where, headers->aouthdr.text_start, sizeof (headers->aouthdr.text_start));
453 *where += sizeof (headers->aouthdr.text_start);
454 md_number_to_chars (*where, headers->aouthdr.data_start, sizeof (headers->aouthdr.data_start));
455 *where += sizeof (headers->aouthdr.data_start);
456 md_number_to_chars (*where, headers->aouthdr.tagentries, sizeof (headers->aouthdr.tagentries));
457 *where += sizeof (headers->aouthdr.tagentries);
458 #endif /* OBJ_COFF_OMIT_OPTIONAL_HEADER */
459
460 #else /* CROSS_COMPILE */
461
462 append (where, (char *) &headers->filehdr, sizeof (headers->filehdr));
463 #ifndef OBJ_COFF_OMIT_OPTIONAL_HEADER
464 append (where, (char *) &headers->aouthdr, sizeof (headers->aouthdr));
465 #endif /* OBJ_COFF_OMIT_OPTIONAL_HEADER */
466
467 #endif /* CROSS_COMPILE */
468
469 /* Output the section headers */
470 obj_coff_section_header_append (where, &text_section_header);
471 obj_coff_section_header_append (where, &data_section_header);
472 obj_coff_section_header_append (where, &bss_section_header);
473
474 return;
475 } /* obj_header_append() */
476
477 #endif /* ! BFD_HEADERS */
478
479 void
480 obj_symbol_to_chars (where, symbolP)
481 char **where;
482 symbolS *symbolP;
483 {
484 /* Move the value into the COFF symbol itself. */
485 symbolP->sy_symbol.ost_entry.n_value = S_GET_VALUE (symbolP);
486
487 #ifdef BFD_HEADERS
488 unsigned int numaux = symbolP->sy_symbol.ost_entry.n_numaux;
489 unsigned int i;
490
491 if (S_GET_SEGMENT (symbolP) == SEG_REGISTER)
492 {
493 S_SET_SEGMENT (symbolP, SEG_ABSOLUTE);
494 }
495 *where += bfd_coff_swap_sym_out (stdoutput, &symbolP->sy_symbol.ost_entry,
496 *where);
497
498 for (i = 0; i < numaux; i++)
499 {
500 *where += bfd_coff_swap_aux_out (stdoutput,
501 &symbolP->sy_symbol.ost_auxent[i],
502 S_GET_DATA_TYPE (symbolP),
503 S_GET_STORAGE_CLASS (symbolP),
504 *where);
505 }
506
507 #else /* BFD_HEADERS */
508 SYMENT *syment = &symbolP->sy_symbol.ost_entry;
509 int i;
510 char numaux = syment->n_numaux;
511 unsigned short type = S_GET_DATA_TYPE (symbolP);
512
513 #ifdef CROSS_COMPILE
514 md_number_to_chars (*where, syment->n_value, sizeof (syment->n_value));
515 *where += sizeof (syment->n_value);
516 md_number_to_chars (*where, syment->n_scnum, sizeof (syment->n_scnum));
517 *where += sizeof (syment->n_scnum);
518 md_number_to_chars (*where, 0, sizeof (short)); /* pad n_flags */
519 *where += sizeof (short);
520 md_number_to_chars (*where, syment->n_type, sizeof (syment->n_type));
521 *where += sizeof (syment->n_type);
522 md_number_to_chars (*where, syment->n_sclass, sizeof (syment->n_sclass));
523 *where += sizeof (syment->n_sclass);
524 md_number_to_chars (*where, syment->n_numaux, sizeof (syment->n_numaux));
525 *where += sizeof (syment->n_numaux);
526 #else /* CROSS_COMPILE */
527 append (where, (char *) syment, sizeof (*syment));
528 #endif /* CROSS_COMPILE */
529
530 /* Should do the following:
531 if (.file entry) MD(..)... else if (static entry) MD(..) */
532 if (numaux > OBJ_COFF_MAX_AUXENTRIES)
533 {
534 as_bad ("Internal error? too many auxents for symbol");
535 } /* too many auxents */
536
537 for (i = 0; i < numaux; ++i)
538 {
539 #ifdef CROSS_COMPILE
540 #if 0 /* This code has never been tested */
541 /* The most common case, x_sym entry. */
542 if ((SF_GET (symbolP) & (SF_FILE | SF_STATICS)) == 0)
543 {
544 md_number_to_chars (*where, auxP->x_sym.x_tagndx, sizeof (auxP->x_sym.x_tagndx));
545 *where += sizeof (auxP->x_sym.x_tagndx);
546 if (ISFCN (type))
547 {
548 md_number_to_chars (*where, auxP->x_sym.x_misc.x_fsize, sizeof (auxP->x_sym.x_misc.x_fsize));
549 *where += sizeof (auxP->x_sym.x_misc.x_fsize);
550 }
551 else
552 {
553 md_number_to_chars (*where, auxP->x_sym.x_misc.x_lnno, sizeof (auxP->x_sym.x_misc.x_lnno));
554 *where += sizeof (auxP->x_sym.x_misc.x_lnno);
555 md_number_to_chars (*where, auxP->x_sym.x_misc.x_size, sizeof (auxP->x_sym.x_misc.x_size));
556 *where += sizeof (auxP->x_sym.x_misc.x_size);
557 }
558 if (ISARY (type))
559 {
560 register int index;
561 for (index = 0; index < DIMNUM; index++)
562 md_number_to_chars (*where, auxP->x_sym.x_fcnary.x_ary.x_dimen[index], sizeof (auxP->x_sym.x_fcnary.x_ary.x_dimen[index]));
563 *where += sizeof (auxP->x_sym.x_fcnary.x_ary.x_dimen[index]);
564 }
565 else
566 {
567 md_number_to_chars (*where, auxP->x_sym.x_fcnary.x_fcn.x_lnnoptr, sizeof (auxP->x_sym.x_fcnary.x_fcn.x_lnnoptr));
568 *where += sizeof (auxP->x_sym.x_fcnary.x_fcn.x_lnnoptr);
569 md_number_to_chars (*where, auxP->x_sym.x_fcnary.x_fcn.x_endndx, sizeof (auxP->x_sym.x_fcnary.x_fcn.x_endndx));
570 *where += sizeof (auxP->x_sym.x_fcnary.x_fcn.x_endndx);
571 }
572 md_number_to_chars (*where, auxP->x_sym.x_tvndx, sizeof (auxP->x_sym.x_tvndx));
573 *where += sizeof (auxP->x_sym.x_tvndx);
574 }
575 else if (SF_GET_FILE (symbolP))
576 { /* .file */
577 ;
578 }
579 else if (SF_GET_STATICS (symbolP))
580 { /* .text, .data, .bss symbols */
581 md_number_to_chars (*where, auxP->x_scn.x_scnlen, sizeof (auxP->x_scn.x_scnlen));
582 *where += sizeof (auxP->x_scn.x_scnlen);
583 md_number_to_chars (*where, auxP->x_scn.x_nreloc, sizeof (auxP->x_scn.x_nreloc));
584 *where += sizeof (auxP->x_scn.x_nreloc);
585 md_number_to_chars (*where, auxP->x_scn.x_nlinno, sizeof (auxP->x_scn.x_nlinno));
586 *where += sizeof (auxP->x_scn.x_nlinno);
587 }
588 #endif /* 0 */
589 #else /* CROSS_COMPILE */
590 append (where, (char *) &symbolP->sy_symbol.ost_auxent[i], sizeof (symbolP->sy_symbol.ost_auxent[i]));
591 #endif /* CROSS_COMPILE */
592
593 }; /* for each aux in use */
594 #endif /* BFD_HEADERS */
595 return;
596 } /* obj_symbol_to_chars() */
597
598 #ifdef BFD_HEADERS
599 static void
600 obj_coff_section_header_append (where, header)
601 char **where;
602 struct internal_scnhdr *header;
603 {
604 *where += bfd_coff_swap_scnhdr_out (stdoutput, header, *where);
605 }
606
607 #else
608 static void
609 obj_coff_section_header_append (where, header)
610 char **where;
611 SCNHDR *header;
612 {
613 #ifdef CROSS_COMPILE
614 memcpy (*where, header->s_name, sizeof (header->s_name));
615 *where += sizeof (header->s_name);
616
617 md_number_to_chars (*where, header->s_paddr, sizeof (header->s_paddr));
618 *where += sizeof (header->s_paddr);
619
620 md_number_to_chars (*where, header->s_vaddr, sizeof (header->s_vaddr));
621 *where += sizeof (header->s_vaddr);
622
623 md_number_to_chars (*where, header->s_size, sizeof (header->s_size));
624 *where += sizeof (header->s_size);
625
626 md_number_to_chars (*where, header->s_scnptr, sizeof (header->s_scnptr));
627 *where += sizeof (header->s_scnptr);
628
629 md_number_to_chars (*where, header->s_relptr, sizeof (header->s_relptr));
630 *where += sizeof (header->s_relptr);
631
632 md_number_to_chars (*where, header->s_lnnoptr, sizeof (header->s_lnnoptr));
633 *where += sizeof (header->s_lnnoptr);
634
635 md_number_to_chars (*where, header->s_nreloc, sizeof (header->s_nreloc));
636 *where += sizeof (header->s_nreloc);
637
638 md_number_to_chars (*where, header->s_nlnno, sizeof (header->s_nlnno));
639 *where += sizeof (header->s_nlnno);
640
641 md_number_to_chars (*where, header->s_flags, sizeof (header->s_flags));
642 *where += sizeof (header->s_flags);
643
644 #ifdef TC_I960
645 md_number_to_chars (*where, header->s_align, sizeof (header->s_align));
646 *where += sizeof (header->s_align);
647 #endif /* TC_I960 */
648
649 #else /* CROSS_COMPILE */
650
651 append (where, (char *) header, sizeof (*header));
652
653 #endif /* CROSS_COMPILE */
654
655 return;
656 } /* obj_coff_section_header_append() */
657
658 #endif
659 void
660 obj_emit_symbols (where, symbol_rootP)
661 char **where;
662 symbolS *symbol_rootP;
663 {
664 symbolS *symbolP;
665 /*
666 * Emit all symbols left in the symbol chain.
667 */
668 for (symbolP = symbol_rootP; symbolP; symbolP = symbol_next (symbolP))
669 {
670 /* Used to save the offset of the name. It is used to point
671 to the string in memory but must be a file offset. */
672 register char *temp;
673
674 tc_coff_symbol_emit_hook (symbolP);
675
676 temp = S_GET_NAME (symbolP);
677 if (SF_GET_STRING (symbolP))
678 {
679 S_SET_OFFSET (symbolP, symbolP->sy_name_offset);
680 S_SET_ZEROES (symbolP, 0);
681 }
682 else
683 {
684 memset (symbolP->sy_symbol.ost_entry.n_name, '\0', SYMNMLEN);
685 strncpy (symbolP->sy_symbol.ost_entry.n_name, temp, SYMNMLEN);
686 }
687 obj_symbol_to_chars (where, symbolP);
688 S_SET_NAME (symbolP, temp);
689 }
690 } /* obj_emit_symbols() */
691
692 #endif /* ! BFD_ASSEMBLER */
693
694 /* Merge a debug symbol containing debug information into a normal symbol. */
695
696 void
697 c_symbol_merge (debug, normal)
698 symbolS *debug;
699 symbolS *normal;
700 {
701 S_SET_DATA_TYPE (normal, S_GET_DATA_TYPE (debug));
702 S_SET_STORAGE_CLASS (normal, S_GET_STORAGE_CLASS (debug));
703
704 if (S_GET_NUMBER_AUXILIARY (debug) > S_GET_NUMBER_AUXILIARY (normal))
705 /* take the most we have */
706 S_SET_NUMBER_AUXILIARY (normal, S_GET_NUMBER_AUXILIARY (debug));
707
708 if (S_GET_NUMBER_AUXILIARY (debug) > 0)
709 {
710 /* Move all the auxiliary information. */
711 #ifdef BFD_ASSEMBLER
712 /* @@ How many fields do we want to preserve? Would it make more
713 sense to pick and choose those we want to copy? Should look
714 into this further.... [raeburn:19920512.2209EST] */
715 alent *linenos;
716 linenos = coffsymbol (normal->bsym)->lineno;
717 memcpy ((char *) &coffsymbol (normal->bsym)->native,
718 (char *) &coffsymbol (debug->bsym)->native,
719 S_GET_NUMBER_AUXILIARY(debug) * AUXESZ);
720 coffsymbol (normal->bsym)->lineno = linenos;
721 #else
722 memcpy ((char *) &normal->sy_symbol.ost_auxent[0],
723 (char *) &debug->sy_symbol.ost_auxent[0],
724 S_GET_NUMBER_AUXILIARY (debug) * AUXESZ);
725 #endif
726 }
727
728 /* Move the debug flags. */
729 SF_SET_DEBUG_FIELD (normal, SF_GET_DEBUG_FIELD (debug));
730 } /* c_symbol_merge() */
731
732 static symbolS *previous_file_symbol;
733 void
734 c_dot_file_symbol (filename)
735 char *filename;
736 {
737 symbolS *symbolP;
738
739 #ifdef BFD_ASSEMBLER
740 symbolP = symbol_new (filename, &bfd_abs_section, 0,
741 &zero_address_frag);
742 #else
743 symbolP = symbol_new (".file",
744 SEG_DEBUG,
745 0,
746 &zero_address_frag);
747 #endif
748
749 S_SET_STORAGE_CLASS (symbolP, C_FILE);
750 S_SET_NUMBER_AUXILIARY (symbolP, 1);
751
752 #ifdef BFD_ASSEMBLER
753 symbolP->bsym->flags = BSF_DEBUGGING;
754 #else
755 if (strlen(filename) > 14)
756 {
757 /* This won't fit into a 14 char space, it will go into the string
758 table. */
759 symbolP->sy_symbol.ost_auxent->x_file.x_n.x_zeroes = 0;
760 (&(symbolP->sy_symbol.ost_auxent->x_file.x_n.x_offset))[0] = string_byte_count;
761 (&(symbolP->sy_symbol.ost_auxent->x_file.x_n.x_offset))[1] = (int)filename;
762 }
763 else
764 {
765 SA_SET_FILE_FNAME (symbolP, filename);
766 }
767 SF_SET_DEBUG (symbolP);
768 #endif
769
770 #ifndef NO_LISTING
771 {
772 extern int listing;
773 if (listing)
774 {
775 listing_source_file (filename);
776 }
777 }
778 #endif
779
780 S_SET_VALUE (symbolP, (long) previous_file_symbol);
781
782 previous_file_symbol = symbolP;
783
784 /* Make sure that the symbol is first on the symbol chain */
785 if (symbol_rootP != symbolP)
786 {
787 if (symbolP == symbol_lastP)
788 {
789 symbol_lastP = symbol_lastP->sy_previous;
790 } /* if it was the last thing on the list */
791
792 symbol_remove (symbolP, &symbol_rootP, &symbol_lastP);
793 symbol_insert (symbolP, symbol_rootP, &symbol_rootP, &symbol_lastP);
794 symbol_rootP = symbolP;
795 } /* if not first on the list */
796 }
797
798 /*
799 * Build a 'section static' symbol.
800 */
801
802 char *
803 c_section_symbol (name, value, length, nreloc, nlnno)
804 char *name;
805 long value;
806 long length;
807 unsigned short nreloc;
808 unsigned short nlnno;
809 {
810 symbolS *symbolP;
811
812 symbolP = symbol_new (name,
813 (name[1] == 't'
814 ? text_section
815 : name[1] == 'd'
816 ? data_section
817 : bss_section),
818 value,
819 &zero_address_frag);
820
821 S_SET_STORAGE_CLASS (symbolP, C_STAT);
822 S_SET_NUMBER_AUXILIARY (symbolP, 1);
823
824 SA_SET_SCN_SCNLEN (symbolP, length);
825 SA_SET_SCN_NRELOC (symbolP, nreloc);
826 SA_SET_SCN_NLINNO (symbolP, nlnno);
827
828 SF_SET_STATICS (symbolP);
829
830 return (char *) symbolP;
831 } /* c_section_symbol() */
832
833 void
834 c_section_header (header,
835 name,
836 core_address,
837 size,
838 data_ptr,
839 reloc_ptr,
840 lineno_ptr,
841 reloc_number,
842 lineno_number,
843 alignment)
844 #ifdef BFD_HEADERS
845 struct internal_scnhdr *header;
846 #else
847 SCNHDR *header;
848 #endif
849 char *name;
850 long core_address;
851 long size;
852 long data_ptr;
853 long reloc_ptr;
854 long lineno_ptr;
855 long reloc_number;
856 long lineno_number;
857 long alignment;
858 {
859 strncpy (header->s_name, name, 8);
860 header->s_paddr = header->s_vaddr = core_address;
861 header->s_scnptr = ((header->s_size = size) != 0) ? data_ptr : 0;
862 header->s_relptr = reloc_ptr;
863 header->s_lnnoptr = lineno_ptr;
864 header->s_nreloc = reloc_number;
865 header->s_nlnno = lineno_number;
866
867 #ifdef OBJ_COFF_SECTION_HEADER_HAS_ALIGNMENT
868 #ifdef OBJ_COFF_BROKEN_ALIGNMENT
869 header->s_align = ((name[1] == 'b' || (size > 0)) ? 16 : 0);
870 #else
871 header->s_align = ((alignment == 0)
872 ? 0
873 : (1 << alignment));
874 #endif /* OBJ_COFF_BROKEN_ALIGNMENT */
875 #endif /* OBJ_COFF_SECTION_HEADER_HAS_ALIGNMENT */
876
877 header->s_flags = STYP_REG | (name[1] == 't'
878 ? STYP_TEXT
879 : name[1] == 'd'
880 ? STYP_DATA
881 : name[1] == 'b'
882 ? STYP_BSS
883 : STYP_INFO);
884 }
885
886 /* Line number handling */
887
888 #ifdef BFD_ASSEMBLER
889
890 /* Symbol of last function, which we should hang line#s off of. */
891 symbolS *function_lineoff;
892
893 #else
894
895 /* Offset in line#s where the last function started (the odd entry for
896 line #0). */
897 int function_lineoff = -1;
898
899 int text_lineno_number;
900
901 /* We use this to build pointers from .bf's into the linetable. It
902 should match exactly the values that are later assigned in
903 text_lineno_number by write.c. */
904 int our_lineno_number;
905
906 lineno *lineno_lastP;
907 #endif
908
909 #ifndef BFD_ASSEMBLER
910 int
911 c_line_new (paddr, line_number, frag)
912 long paddr;
913 unsigned short line_number;
914 fragS *frag;
915 {
916 lineno *new_line = (lineno *) xmalloc (sizeof (lineno));
917
918 new_line->line.l_addr.l_paddr = paddr;
919 new_line->line.l_lnno = line_number;
920 new_line->frag = (char *) frag;
921 new_line->next = (lineno *) 0;
922
923 if (lineno_rootP == (lineno *) 0)
924 lineno_rootP = new_line;
925 else
926 lineno_lastP->next = new_line;
927 lineno_lastP = new_line;
928 return LINESZ * our_lineno_number++;
929 }
930 #endif
931
932 void
933 obj_emit_lineno (where, line, file_start)
934 char **where;
935 #ifndef BFD_ASSEMBLER /* sigh */
936 lineno *line;
937 #endif
938 char *file_start;
939 {
940 #ifndef BFD_ASSEMBLER
941 #ifdef BFD_HEADERS
942 struct bfd_internal_lineno *line_entry;
943 #else
944 LINENO *line_entry;
945 #endif
946 for (; line; line = line->next)
947 {
948 line_entry = &line->line;
949
950 /* FIXME-SOMEDAY Resolving the sy_number of function linno's used to be
951 done in write_object_file() but their symbols need a fileptr to the
952 lnno, so I moved this resolution check here. xoxorich. */
953
954 if (line_entry->l_lnno == 0)
955 {
956 /* There is a good chance that the symbol pointed to
957 is not the one that will be emitted and that the
958 sy_number is not accurate. */
959 symbolS *symbolP;
960
961 symbolP = (symbolS *) line_entry->l_addr.l_symndx;
962
963 line_entry->l_addr.l_symndx = symbolP->sy_number;
964 symbolP->sy_symbol.ost_auxent[0].x_sym.x_fcnary.x_fcn.x_lnnoptr = *where - file_start;
965
966 } /* if this is a function linno */
967 #ifdef BFD_HEADERS
968 *where += bfd_coff_swap_lineno_out (stdoutput, line_entry, *where);
969 #else
970 /* No matter which member of the union we process, they are
971 both long. */
972 #ifdef CROSS_COMPILE
973 md_number_to_chars (*where, line_entry->l_addr.l_paddr, sizeof (line_entry->l_addr.l_paddr));
974 *where += sizeof (line_entry->l_addr.l_paddr);
975
976 md_number_to_chars (*where, line_entry->l_lnno, sizeof (line_entry->l_lnno));
977 *where += sizeof (line_entry->l_lnno);
978
979 #ifdef TC_I960
980 **where = '0';
981 ++*where;
982 **where = '0';
983 ++*where;
984 #endif /* TC_I960 */
985
986 #else /* CROSS_COMPILE */
987 append (where, (char *) line_entry, LINESZ);
988 #endif /* CROSS_COMPILE */
989 #endif /* BFD_HEADERS */
990 } /* for each line number */
991 #else /* BFD_ASSEMBLER */
992 abort ();
993 #endif /* BFD_ASSEMBLER */
994 }
995
996 void
997 obj_symbol_new_hook (symbolP)
998 symbolS *symbolP;
999 {
1000 char underscore = 0; /* Symbol has leading _ */
1001
1002 #ifdef BFD_ASSEMBLER
1003 {
1004 long sz = (OBJ_COFF_MAX_AUXENTRIES + 1) * sizeof (combined_entry_type);
1005 char *s = (char *) bfd_alloc_by_size_t (stdoutput, sz);
1006 memset (s, 0, sz);
1007 coffsymbol (symbolP->bsym)->native = (combined_entry_type *) s;
1008 }
1009 #else
1010 /* Effective symbol */
1011 /* Store the pointer in the offset. */
1012 S_SET_ZEROES (symbolP, 0L);
1013 /* Additional information */
1014 symbolP->sy_symbol.ost_flags = 0;
1015 /* Auxiliary entries */
1016 memset ((char *) &symbolP->sy_symbol.ost_auxent[0], '\0', AUXESZ);
1017 #endif
1018 S_SET_DATA_TYPE (symbolP, T_NULL);
1019 S_SET_STORAGE_CLASS (symbolP, 0);
1020 S_SET_NUMBER_AUXILIARY (symbolP, 0);
1021
1022 #ifdef STRIP_UNDERSCORE
1023 /* Remove leading underscore at the beginning of the symbol.
1024 This is to be compatible with the standard librairies. */
1025 if (*S_GET_NAME (symbolP) == '_')
1026 {
1027 underscore = 1;
1028 S_SET_NAME (symbolP, S_GET_NAME (symbolP) + 1);
1029 }
1030 #endif /* STRIP_UNDERSCORE */
1031
1032 if (S_IS_STRING (symbolP))
1033 SF_SET_STRING (symbolP);
1034 if (!underscore && S_IS_LOCAL (symbolP))
1035 SF_SET_LOCAL (symbolP);
1036 }
1037
1038 /* stack stuff */
1039 stack *
1040 stack_init (chunk_size, element_size)
1041 unsigned long chunk_size;
1042 unsigned long element_size;
1043 {
1044 stack *st;
1045
1046 st = (stack *) malloc (sizeof (stack));
1047 if (!st)
1048 return 0;
1049 st->data = malloc (chunk_size);
1050 if (!st->data)
1051 {
1052 free (st);
1053 return 0;
1054 }
1055 st->pointer = 0;
1056 st->size = chunk_size;
1057 st->chunk_size = chunk_size;
1058 st->element_size = element_size;
1059 return st;
1060 }
1061
1062 void
1063 stack_delete (st)
1064 stack *st;
1065 {
1066 free (st->data);
1067 free (st);
1068 }
1069
1070 char *
1071 stack_push (st, element)
1072 stack *st;
1073 char *element;
1074 {
1075 if (st->pointer + st->element_size >= st->size)
1076 {
1077 st->size += st->chunk_size;
1078 if ((st->data = xrealloc (st->data, st->size)) == (char *) 0)
1079 return (char *) 0;
1080 }
1081 memcpy (st->data + st->pointer, element, st->element_size);
1082 st->pointer += st->element_size;
1083 return st->data + st->pointer;
1084 } /* stack_push() */
1085
1086 char *
1087 stack_pop (st)
1088 stack *st;
1089 {
1090 if ((st->pointer -= st->element_size) < 0)
1091 {
1092 st->pointer = 0;
1093 return (char *) 0;
1094 }
1095 return st->data + st->pointer;
1096 }
1097
1098 char *
1099 stack_top (st)
1100 stack *st;
1101 {
1102 return st->data + st->pointer - st->element_size;
1103 }
1104
1105
1106 /*
1107 * Handle .ln directives.
1108 */
1109
1110 #ifdef BFD_ASSEMBLER
1111 static symbolS *current_lineno_sym;
1112 static struct line_no *line_nos;
1113
1114 static void
1115 add_lineno (frag, offset, num)
1116 fragS *frag;
1117 int offset;
1118 int num;
1119 {
1120 struct line_no *new_line = (struct line_no *) bfd_alloc_by_size_t (stdoutput,
1121 sizeof (struct line_no));
1122 if (!current_lineno_sym)
1123 {
1124 abort ();
1125 }
1126 new_line->next = line_nos;
1127 new_line->frag = frag;
1128 new_line->l.line_number = num;
1129 new_line->l.u.offset = offset;
1130 line_nos = new_line;
1131 }
1132
1133 static void
1134 add_linesym (sym)
1135 symbolS *sym;
1136 {
1137 if (line_nos)
1138 {
1139 add_lineno (0, 0, 0);
1140 coffsymbol (current_lineno_sym->bsym)->lineno = (alent *) line_nos;
1141 line_nos = 0;
1142 }
1143 current_lineno_sym = sym;
1144 }
1145 #endif
1146
1147 static void
1148 obj_coff_ln (appline)
1149 int appline;
1150 {
1151 int l;
1152
1153 if (! appline && def_symbol_in_progress != NULL)
1154 {
1155 as_warn (".ln pseudo-op inside .def/.endef: ignored.");
1156 demand_empty_rest_of_line ();
1157 return;
1158 }
1159
1160 l = get_absolute_expression ();
1161 #ifdef BFD_ASSEMBLER
1162 add_lineno (frag_now, frag_now_fix (), l);
1163 #else
1164 c_line_new (frag_now_fix (), l, frag_now);
1165 #endif
1166
1167 #ifndef NO_LISTING
1168 {
1169 extern int listing;
1170
1171 if (listing)
1172 {
1173 if (! appline)
1174 l += line_base - 1;
1175 listing_source_line (l);
1176 }
1177 }
1178 #endif
1179
1180 demand_empty_rest_of_line ();
1181 } /* obj_coff_ln() */
1182
1183 /*
1184 * def()
1185 *
1186 * Handle .def directives.
1187 *
1188 * One might ask : why can't we symbol_new if the symbol does not
1189 * already exist and fill it with debug information. Because of
1190 * the C_EFCN special symbol. It would clobber the value of the
1191 * function symbol before we have a chance to notice that it is
1192 * a C_EFCN. And a second reason is that the code is more clear this
1193 * way. (at least I think it is :-).
1194 *
1195 */
1196
1197 #define SKIP_SEMI_COLON() while (*input_line_pointer++ != ';')
1198 #define SKIP_WHITESPACES() while (*input_line_pointer == ' ' || \
1199 *input_line_pointer == '\t') \
1200 input_line_pointer++;
1201
1202 static void
1203 obj_coff_def (what)
1204 int what;
1205 {
1206 char name_end; /* Char after the end of name */
1207 char *symbol_name; /* Name of the debug symbol */
1208 char *symbol_name_copy; /* Temporary copy of the name */
1209 unsigned int symbol_name_length;
1210
1211 if (def_symbol_in_progress != NULL)
1212 {
1213 as_warn (".def pseudo-op used inside of .def/.endef: ignored.");
1214 demand_empty_rest_of_line ();
1215 return;
1216 } /* if not inside .def/.endef */
1217
1218 SKIP_WHITESPACES ();
1219
1220 symbol_name = input_line_pointer;
1221 #ifdef STRIP_UNDERSCORE
1222 if (symbol_name[0] == '_' && symbol_name[1] != 0)
1223 symbol_name++;
1224 #endif /* STRIP_UNDERSCORE */
1225
1226 name_end = get_symbol_end ();
1227 symbol_name_length = strlen (symbol_name);
1228 symbol_name_copy = xmalloc (symbol_name_length + 1);
1229 strcpy (symbol_name_copy, symbol_name);
1230
1231 /* Initialize the new symbol */
1232 #ifdef BFD_ASSEMBLER
1233 def_symbol_in_progress = symbol_make (symbol_name_copy);
1234 #else
1235 def_symbol_in_progress = (symbolS *) obstack_alloc (&notes, sizeof (*def_symbol_in_progress));
1236 memset (def_symbol_in_progress, '\0', sizeof (*def_symbol_in_progress));
1237
1238 S_SET_NAME (def_symbol_in_progress, symbol_name_copy);
1239 def_symbol_in_progress->sy_name_offset = ~0;
1240 def_symbol_in_progress->sy_number = ~0;
1241 #endif
1242
1243 def_symbol_in_progress->sy_frag = &zero_address_frag;
1244
1245 if (S_IS_STRING (def_symbol_in_progress))
1246 SF_SET_STRING (def_symbol_in_progress);
1247
1248 *input_line_pointer = name_end;
1249
1250 demand_empty_rest_of_line ();
1251 }
1252
1253 unsigned int dim_index;
1254 static void
1255 obj_coff_endef ()
1256 {
1257 symbolS *symbolP;
1258 /* DIM BUG FIX sac@cygnus.com */
1259 dim_index = 0;
1260 if (def_symbol_in_progress == NULL)
1261 {
1262 as_warn (".endef pseudo-op used outside of .def/.endef: ignored.");
1263 demand_empty_rest_of_line ();
1264 return;
1265 } /* if not inside .def/.endef */
1266
1267 /* Set the section number according to storage class. */
1268 switch (S_GET_STORAGE_CLASS (def_symbol_in_progress))
1269 {
1270 case C_STRTAG:
1271 case C_ENTAG:
1272 case C_UNTAG:
1273 SF_SET_TAG (def_symbol_in_progress);
1274 /* intentional fallthrough */
1275 case C_FILE:
1276 case C_TPDEF:
1277 SF_SET_DEBUG (def_symbol_in_progress);
1278 #ifdef BFD_ASSEMBLER
1279 S_SET_SEGMENT (def_symbol_in_progress, fetch_coff_debug_section ());
1280 #else
1281 S_SET_SEGMENT (def_symbol_in_progress, SEG_DEBUG);
1282 #endif
1283 break;
1284
1285 case C_EFCN:
1286 SF_SET_LOCAL (def_symbol_in_progress); /* Do not emit this symbol. */
1287 /* intentional fallthrough */
1288 case C_BLOCK:
1289 SF_SET_PROCESS (def_symbol_in_progress); /* Will need processing before writing */
1290 /* intentional fallthrough */
1291 case C_FCN:
1292 {
1293 CONST char *name;
1294 S_SET_SEGMENT (def_symbol_in_progress, text_section);
1295
1296 #ifdef BFD_ASSEMBLER
1297 name = bfd_asymbol_name (def_symbol_in_progress->bsym);
1298 #else
1299 name = def_symbol_in_progress->sy_symbol.ost_entry._n._n_nptr[1];
1300 #endif
1301 if (name[1] == 'b' && name[2] == 'f')
1302 {
1303 if (function_lineoff < 0)
1304 as_warn ("`%s' symbol without preceding function", name);
1305 #ifdef BFD_ASSEMBLER
1306 abort ();
1307 #else
1308 SA_GET_SYM_LNNOPTR (def_symbol_in_progress) = function_lineoff;
1309 #endif
1310 /* Will need relocating */
1311 SF_SET_PROCESS (def_symbol_in_progress);
1312 #ifdef BFD_ASSEMBLER
1313 function_lineoff = 0;
1314 #else
1315 function_lineoff = -1;
1316 #endif
1317 }
1318 }
1319 break;
1320
1321 #ifdef C_AUTOARG
1322 case C_AUTOARG:
1323 #endif /* C_AUTOARG */
1324 case C_AUTO:
1325 case C_REG:
1326 case C_MOS:
1327 case C_MOE:
1328 case C_MOU:
1329 case C_ARG:
1330 case C_REGPARM:
1331 case C_FIELD:
1332 case C_EOS:
1333 SF_SET_DEBUG (def_symbol_in_progress);
1334 S_SET_SEGMENT (def_symbol_in_progress, absolute_section);
1335 break;
1336
1337 case C_EXT:
1338 case C_STAT:
1339 case C_LABEL:
1340 /* Valid but set somewhere else (s_comm, s_lcomm, colon) */
1341 break;
1342
1343 case C_USTATIC:
1344 case C_EXTDEF:
1345 case C_ULABEL:
1346 as_warn ("unexpected storage class %d",
1347 S_GET_STORAGE_CLASS (def_symbol_in_progress));
1348 break;
1349 } /* switch on storage class */
1350
1351 /* Now that we have built a debug symbol, try to find if we should
1352 merge with an existing symbol or not. If a symbol is C_EFCN or
1353 SEG_ABSOLUTE or untagged SEG_DEBUG it never merges. */
1354
1355 /* Two cases for functions. Either debug followed by definition or
1356 definition followed by debug. For definition first, we will
1357 merge the debug symbol into the definition. For debug first, the
1358 lineno entry MUST point to the definition function or else it
1359 will point off into space when obj_crawl_symbol_chain() merges
1360 the debug symbol into the real symbol. Therefor, let's presume
1361 the debug symbol is a real function reference. */
1362
1363 /* FIXME-SOON If for some reason the definition label/symbol is
1364 never seen, this will probably leave an undefined symbol at link
1365 time. */
1366
1367 if (S_GET_STORAGE_CLASS (def_symbol_in_progress) == C_EFCN
1368 #ifdef BFD_ASSEMBLER
1369 || (!strcmp (bfd_get_section_name (stdoutput,
1370 S_GET_SEGMENT (def_symbol_in_progress)),
1371 "*DEBUG*")
1372 && !SF_GET_TAG (def_symbol_in_progress))
1373 #else
1374 || (S_GET_SEGMENT (def_symbol_in_progress) == SEG_DEBUG
1375 && !SF_GET_TAG (def_symbol_in_progress))
1376 #endif
1377 || S_GET_SEGMENT (def_symbol_in_progress) == absolute_section
1378 || (symbolP = symbol_find_base (S_GET_NAME (def_symbol_in_progress), DO_NOT_STRIP)) == NULL)
1379 {
1380 #ifdef BFD_ASSEMBLER
1381 if (def_symbol_in_progress != symbol_lastP)
1382 symbol_append (def_symbol_in_progress, symbol_lastP, &symbol_rootP,
1383 &symbol_lastP);
1384 #else
1385 symbol_append (def_symbol_in_progress, symbol_lastP, &symbol_rootP,
1386 &symbol_lastP);
1387 #endif
1388 }
1389 else
1390 {
1391 /* This symbol already exists, merge the newly created symbol
1392 into the old one. This is not mandatory. The linker can
1393 handle duplicate symbols correctly. But I guess that it save
1394 a *lot* of space if the assembly file defines a lot of
1395 symbols. [loic] */
1396
1397 /* The debug entry (def_symbol_in_progress) is merged into the
1398 previous definition. */
1399
1400 c_symbol_merge (def_symbol_in_progress, symbolP);
1401 /* FIXME-SOON Should *def_symbol_in_progress be free'd? xoxorich. */
1402 def_symbol_in_progress = symbolP;
1403
1404 if (SF_GET_FUNCTION (def_symbol_in_progress)
1405 || SF_GET_TAG (def_symbol_in_progress))
1406 {
1407 /* For functions, and tags, the symbol *must* be where the
1408 debug symbol appears. Move the existing symbol to the
1409 current place. */
1410 /* If it already is at the end of the symbol list, do nothing */
1411 if (def_symbol_in_progress != symbol_lastP)
1412 {
1413 symbol_remove (def_symbol_in_progress, &symbol_rootP, &symbol_lastP);
1414 symbol_append (def_symbol_in_progress, symbol_lastP, &symbol_rootP, &symbol_lastP);
1415 }
1416 }
1417 }
1418
1419 if (SF_GET_TAG (def_symbol_in_progress)
1420 && symbol_find_base (S_GET_NAME (def_symbol_in_progress), DO_NOT_STRIP) == NULL)
1421 {
1422 tag_insert (S_GET_NAME (def_symbol_in_progress), def_symbol_in_progress);
1423 }
1424
1425 if (SF_GET_FUNCTION (def_symbol_in_progress))
1426 {
1427 know (sizeof (def_symbol_in_progress) <= sizeof (long));
1428 #ifdef BFD_ASSEMBLER
1429 function_lineoff = def_symbol_in_progress;
1430 add_linesym (def_symbol_in_progress);
1431 #else
1432 function_lineoff = c_line_new ((long) def_symbol_in_progress, 0,
1433 &zero_address_frag);
1434 #endif
1435 SF_SET_PROCESS (def_symbol_in_progress);
1436
1437 if (symbolP == NULL)
1438 {
1439 /* That is, if this is the first time we've seen the
1440 function... */
1441 symbol_table_insert (def_symbol_in_progress);
1442 } /* definition follows debug */
1443 } /* Create the line number entry pointing to the function being defined */
1444
1445 def_symbol_in_progress = NULL;
1446 demand_empty_rest_of_line ();
1447 return;
1448 }
1449
1450 static void
1451 obj_coff_dim ()
1452 {
1453 register int dim_index;
1454
1455 if (def_symbol_in_progress == NULL)
1456 {
1457 as_warn (".dim pseudo-op used outside of .def/.endef: ignored.");
1458 demand_empty_rest_of_line ();
1459 return;
1460 } /* if not inside .def/.endef */
1461
1462 S_SET_NUMBER_AUXILIARY (def_symbol_in_progress, 1);
1463
1464 for (dim_index = 0; dim_index < DIMNUM; dim_index++)
1465 {
1466 SKIP_WHITESPACES ();
1467 SA_SET_SYM_DIMEN (def_symbol_in_progress, dim_index, get_absolute_expression ());
1468
1469 switch (*input_line_pointer)
1470 {
1471
1472 case ',':
1473 input_line_pointer++;
1474 break;
1475
1476 default:
1477 as_warn ("badly formed .dim directive ignored");
1478 /* intentional fallthrough */
1479 case '\n':
1480 case ';':
1481 dim_index = DIMNUM;
1482 break;
1483 } /* switch on following character */
1484 } /* for each dimension */
1485
1486 demand_empty_rest_of_line ();
1487 return;
1488 } /* obj_coff_dim() */
1489
1490 static void
1491 obj_coff_line ()
1492 {
1493 int this_base;
1494
1495 if (def_symbol_in_progress == NULL)
1496 {
1497 obj_coff_ln (0);
1498 return;
1499 } /* if it looks like a stabs style line */
1500
1501 this_base = get_absolute_expression ();
1502 if (this_base > line_base)
1503 {
1504 line_base = this_base;
1505 }
1506
1507
1508 S_SET_NUMBER_AUXILIARY (def_symbol_in_progress, 1);
1509 SA_SET_SYM_LNNO (def_symbol_in_progress, line_base);
1510
1511 demand_empty_rest_of_line ();
1512 return;
1513 } /* obj_coff_line() */
1514
1515 static void
1516 obj_coff_size ()
1517 {
1518 if (def_symbol_in_progress == NULL)
1519 {
1520 as_warn (".size pseudo-op used outside of .def/.endef ignored.");
1521 demand_empty_rest_of_line ();
1522 return;
1523 } /* if not inside .def/.endef */
1524
1525 S_SET_NUMBER_AUXILIARY (def_symbol_in_progress, 1);
1526 SA_SET_SYM_SIZE (def_symbol_in_progress, get_absolute_expression ());
1527 demand_empty_rest_of_line ();
1528 return;
1529 } /* obj_coff_size() */
1530
1531 static void
1532 obj_coff_scl ()
1533 {
1534 if (def_symbol_in_progress == NULL)
1535 {
1536 as_warn (".scl pseudo-op used outside of .def/.endef ignored.");
1537 demand_empty_rest_of_line ();
1538 return;
1539 } /* if not inside .def/.endef */
1540
1541 S_SET_STORAGE_CLASS (def_symbol_in_progress, get_absolute_expression ());
1542 demand_empty_rest_of_line ();
1543 return;
1544 } /* obj_coff_scl() */
1545
1546 static void
1547 obj_coff_tag ()
1548 {
1549 char *symbol_name;
1550 char name_end;
1551
1552 if (def_symbol_in_progress == NULL)
1553 {
1554 as_warn (".tag pseudo-op used outside of .def/.endef ignored.");
1555 demand_empty_rest_of_line ();
1556 return;
1557 } /* if not inside .def/.endef */
1558
1559 S_SET_NUMBER_AUXILIARY (def_symbol_in_progress, 1);
1560 symbol_name = input_line_pointer;
1561 name_end = get_symbol_end ();
1562
1563 /* Assume that the symbol referred to by .tag is always defined. */
1564 /* This was a bad assumption. I've added find_or_make. xoxorich. */
1565 SA_SET_SYM_TAGNDX (def_symbol_in_progress,
1566 (long) tag_find_or_make (symbol_name));
1567 if (SA_GET_SYM_TAGNDX (def_symbol_in_progress) == 0L)
1568 {
1569 as_warn ("tag not found for .tag %s", symbol_name);
1570 } /* not defined */
1571
1572 SF_SET_TAGGED (def_symbol_in_progress);
1573 *input_line_pointer = name_end;
1574
1575 demand_empty_rest_of_line ();
1576 } /* obj_coff_tag() */
1577
1578 static void
1579 obj_coff_type ()
1580 {
1581 if (def_symbol_in_progress == NULL)
1582 {
1583 as_warn (".type pseudo-op used outside of .def/.endef ignored.");
1584 demand_empty_rest_of_line ();
1585 return;
1586 } /* if not inside .def/.endef */
1587
1588 S_SET_DATA_TYPE (def_symbol_in_progress, get_absolute_expression ());
1589
1590 if (ISFCN (S_GET_DATA_TYPE (def_symbol_in_progress)) &&
1591 S_GET_STORAGE_CLASS (def_symbol_in_progress) != C_TPDEF)
1592 {
1593 SF_SET_FUNCTION (def_symbol_in_progress);
1594 } /* is a function */
1595
1596 demand_empty_rest_of_line ();
1597 return;
1598 } /* obj_coff_type() */
1599
1600 static void
1601 obj_coff_val ()
1602 {
1603 if (def_symbol_in_progress == NULL)
1604 {
1605 as_warn (".val pseudo-op used outside of .def/.endef ignored.");
1606 demand_empty_rest_of_line ();
1607 return;
1608 } /* if not inside .def/.endef */
1609
1610 if (is_name_beginner (*input_line_pointer))
1611 {
1612 char *symbol_name = input_line_pointer;
1613 char name_end = get_symbol_end ();
1614
1615 if (!strcmp (symbol_name, "."))
1616 {
1617 def_symbol_in_progress->sy_frag = frag_now;
1618 S_SET_VALUE (def_symbol_in_progress, obstack_next_free (&frags) - frag_now->fr_literal);
1619 /* If the .val is != from the .def (e.g. statics) */
1620 }
1621 else if (strcmp (S_GET_NAME (def_symbol_in_progress), symbol_name))
1622 {
1623 def_symbol_in_progress->sy_forward = symbol_find_or_make (symbol_name);
1624
1625 /* If the segment is undefined when the forward
1626 reference is solved, then copy the segment id
1627 from the forward symbol. */
1628 SF_SET_GET_SEGMENT (def_symbol_in_progress);
1629 }
1630 /* Otherwise, it is the name of a non debug symbol and its value will be calculated later. */
1631 *input_line_pointer = name_end;
1632 }
1633 else
1634 {
1635 S_SET_VALUE (def_symbol_in_progress, get_absolute_expression ());
1636 } /* if symbol based */
1637
1638 demand_empty_rest_of_line ();
1639 return;
1640 } /* obj_coff_val() */
1641
1642 /*
1643 * Maintain a list of the tagnames of the structres.
1644 */
1645
1646 static void
1647 tag_init ()
1648 {
1649 tag_hash = hash_new ();
1650 return;
1651 } /* tag_init() */
1652
1653 static void
1654 tag_insert (name, symbolP)
1655 CONST char *name;
1656 symbolS *symbolP;
1657 {
1658 register char *error_string;
1659
1660 if (*(error_string = hash_jam (tag_hash, name, (char *) symbolP)))
1661 {
1662 as_fatal ("Inserting \"%s\" into structure table failed: %s",
1663 name, error_string);
1664 }
1665 return;
1666 } /* tag_insert() */
1667
1668 static symbolS *
1669 tag_find_or_make (name)
1670 char *name;
1671 {
1672 symbolS *symbolP;
1673
1674 if ((symbolP = tag_find (name)) == NULL)
1675 {
1676 symbolP = symbol_new (name, undefined_section,
1677 0, &zero_address_frag);
1678
1679 tag_insert (S_GET_NAME (symbolP), symbolP);
1680 symbol_table_insert (symbolP);
1681 } /* not found */
1682
1683 return (symbolP);
1684 } /* tag_find_or_make() */
1685
1686 static symbolS *
1687 tag_find (name)
1688 char *name;
1689 {
1690 #ifdef STRIP_UNDERSCORE
1691 if (*name == '_')
1692 name++;
1693 #endif /* STRIP_UNDERSCORE */
1694 return ((symbolS *) hash_find (tag_hash, name));
1695 } /* tag_find() */
1696
1697 void
1698 obj_read_begin_hook ()
1699 {
1700 /* These had better be the same. Usually 18 bytes. */
1701 #ifndef BFD_HEADERS
1702 know (sizeof (SYMENT) == sizeof (AUXENT));
1703 know (SYMESZ == AUXESZ);
1704 #endif
1705 tag_init ();
1706 }
1707
1708 void
1709 obj_crawl_symbol_chain (headers)
1710 object_headers *headers;
1711 {
1712 int symbol_number = 0;
1713 lineno *lineP;
1714 symbolS *last_functionP = NULL;
1715 symbolS *last_tagP;
1716 symbolS *symbolP;
1717 symbolS *symbol_externP = NULL;
1718 symbolS *symbol_extern_lastP = NULL;
1719
1720 /* Initialize the stack used to keep track of the matching .bb .be */
1721 stack *block_stack = stack_init (512, sizeof (symbolS *));
1722
1723 /* JF deal with forward references first... */
1724 for (symbolP = symbol_rootP; symbolP; symbolP = symbol_next (symbolP))
1725 {
1726
1727 if (symbolP->sy_forward)
1728 {
1729 S_SET_VALUE (symbolP, (S_GET_VALUE (symbolP)
1730 + S_GET_VALUE (symbolP->sy_forward)
1731 + symbolP->sy_forward->sy_frag->fr_address));
1732
1733 if (
1734 #ifndef TE_I386AIX
1735 SF_GET_GET_SEGMENT (symbolP)
1736 #else
1737 SF_GET_GET_SEGMENT (symbolP)
1738 && S_GET_SEGMENT (symbolP) == SEG_UNKNOWN
1739 #endif /* TE_I386AIX */
1740 )
1741 {
1742 S_SET_SEGMENT (symbolP, S_GET_SEGMENT (symbolP->sy_forward));
1743 } /* forward segment also */
1744
1745 symbolP->sy_forward = 0;
1746 } /* if it has a forward reference */
1747 } /* walk the symbol chain */
1748
1749 tc_crawl_symbol_chain (headers);
1750
1751 /* The symbol list should be ordered according to the following sequence
1752 * order :
1753 * . .file symbol
1754 * . debug entries for functions
1755 * . fake symbols for .text .data and .bss
1756 * . defined symbols
1757 * . undefined symbols
1758 * But this is not mandatory. The only important point is to put the
1759 * undefined symbols at the end of the list.
1760 */
1761
1762 if (symbol_rootP == NULL
1763 || S_GET_STORAGE_CLASS (symbol_rootP) != C_FILE)
1764 {
1765 know (!previous_file_symbol);
1766 c_dot_file_symbol ("fake");
1767 } /* Is there a .file symbol ? If not insert one at the beginning. */
1768
1769 /*
1770 * Build up static symbols for .text, .data and .bss
1771 */
1772 dot_text_symbol = (symbolS *)
1773 c_section_symbol (".text",
1774 0,
1775 H_GET_TEXT_SIZE (headers),
1776 0 /*text_relocation_number */ ,
1777 0 /*text_lineno_number */ );
1778 #ifdef TE_I386AIX
1779 symbol_remove (dot_text_symbol, &symbol_rootP, &symbol_lastP);
1780 symbol_append (dot_text_symbol, previous_file_symbol,
1781 &symbol_rootP, &symbol_lastP);
1782 #endif /* TE_I386AIX */
1783
1784 dot_data_symbol = (symbolS *)
1785 c_section_symbol (".data",
1786 H_GET_TEXT_SIZE (headers),
1787 H_GET_DATA_SIZE (headers),
1788 0 /*data_relocation_number */ ,
1789 0); /* There are no data lineno entries */
1790 #ifdef TE_I386AIX
1791 symbol_remove (dot_data_symbol, &symbol_rootP, &symbol_lastP);
1792 symbol_append (dot_data_symbol, dot_text_symbol,
1793 &symbol_rootP, &symbol_lastP);
1794 #endif /* TE_I386AIX */
1795
1796 dot_bss_symbol = (symbolS *)
1797 c_section_symbol (".bss",
1798 H_GET_TEXT_SIZE (headers) + H_GET_DATA_SIZE (headers),
1799 H_GET_BSS_SIZE (headers),
1800 0, /* No relocation for a bss section. */
1801 0); /* There are no bss lineno entries */
1802 #ifdef TE_I386AIX
1803 symbol_remove (dot_bss_symbol, &symbol_rootP, &symbol_lastP);
1804 symbol_append (dot_bss_symbol, dot_data_symbol,
1805 &symbol_rootP, &symbol_lastP);
1806 #endif /* TE_I386AIX */
1807
1808 #if defined(DEBUG)
1809 verify_symbol_chain (symbol_rootP, symbol_lastP);
1810 #endif /* DEBUG */
1811
1812 /* Three traversals of symbol chains here. The
1813 first traversal yanks externals into a temporary
1814 chain, removing the externals from the global
1815 chain, numbers symbols, and does some other guck.
1816 The second traversal is on the temporary chain of
1817 externals and just appends them to the global
1818 chain again, numbering them as we go. The third
1819 traversal patches pointers to symbols (using sym
1820 indexes). The last traversal was once done as
1821 part of the first pass, but that fails when a
1822 reference preceeds a definition as the definition
1823 has no number at the time we process the
1824 reference. */
1825
1826 /* Note that symbolP will be NULL at the end of a loop
1827 if an external was at the beginning of the list (it
1828 gets moved off the list). Hence the weird check in
1829 the loop control.
1830 */
1831 for (symbolP = symbol_rootP;
1832 symbolP;
1833 symbolP = symbolP ? symbol_next (symbolP) : symbol_rootP)
1834 {
1835 if (!SF_GET_DEBUG (symbolP))
1836 {
1837 /* Debug symbols do not need all this rubbish */
1838 symbolS *real_symbolP;
1839
1840 /* L* and C_EFCN symbols never merge. */
1841 if (!SF_GET_LOCAL (symbolP)
1842 && (real_symbolP = symbol_find_base (S_GET_NAME (symbolP), DO_NOT_STRIP))
1843 && real_symbolP != symbolP)
1844 {
1845 /* FIXME-SOON: where do dups come from? Maybe tag references before definitions? xoxorich. */
1846 /* Move the debug data from the debug symbol to the
1847 real symbol. Do NOT do the oposite (i.e. move from
1848 real symbol to debug symbol and remove real symbol from the
1849 list.) Because some pointers refer to the real symbol
1850 whereas no pointers refer to the debug symbol. */
1851 c_symbol_merge (symbolP, real_symbolP);
1852 /* Replace the current symbol by the real one */
1853 /* The symbols will never be the last or the first
1854 because : 1st symbol is .file and 3 last symbols are
1855 .text, .data, .bss */
1856 symbol_remove (real_symbolP, &symbol_rootP, &symbol_lastP);
1857 symbol_insert (real_symbolP, symbolP, &symbol_rootP, &symbol_lastP);
1858 symbol_remove (symbolP, &symbol_rootP, &symbol_lastP);
1859 symbolP = real_symbolP;
1860 } /* if not local but dup'd */
1861
1862 if (flagseen['R'] && (S_GET_SEGMENT (symbolP) == SEG_DATA))
1863 {
1864 S_SET_SEGMENT (symbolP, SEG_TEXT);
1865 } /* push data into text */
1866
1867 S_SET_VALUE (symbolP, S_GET_VALUE (symbolP) + symbolP->sy_frag->fr_address);
1868
1869 if (!S_IS_DEFINED (symbolP) && !SF_GET_LOCAL (symbolP))
1870 {
1871 S_SET_EXTERNAL (symbolP);
1872 }
1873 else if (S_GET_STORAGE_CLASS (symbolP) == C_NULL)
1874 {
1875 if (S_GET_SEGMENT (symbolP) == SEG_TEXT)
1876 {
1877 S_SET_STORAGE_CLASS (symbolP, C_LABEL);
1878 }
1879 else
1880 {
1881 S_SET_STORAGE_CLASS (symbolP, C_STAT);
1882 }
1883 } /* no storage class yet */
1884
1885 /* Mainly to speed up if not -g */
1886 if (SF_GET_PROCESS (symbolP))
1887 {
1888 /* Handle the nested blocks auxiliary info. */
1889 if (S_GET_STORAGE_CLASS (symbolP) == C_BLOCK)
1890 {
1891 if (!strcmp (S_GET_NAME (symbolP), ".bb"))
1892 stack_push (block_stack, (char *) &symbolP);
1893 else
1894 { /* .eb */
1895 register symbolS *begin_symbolP;
1896 begin_symbolP = *(symbolS **) stack_pop (block_stack);
1897 if (begin_symbolP == (symbolS *) 0)
1898 as_warn ("mismatched .eb");
1899 else
1900 SA_SET_SYM_ENDNDX (begin_symbolP, symbol_number + 2);
1901 }
1902 }
1903 /* If we are able to identify the type of a function, and we
1904 are out of a function (last_functionP == 0) then, the
1905 function symbol will be associated with an auxiliary
1906 entry. */
1907 if (last_functionP == (symbolS *) 0 &&
1908 SF_GET_FUNCTION (symbolP))
1909 {
1910 last_functionP = symbolP;
1911
1912 if (S_GET_NUMBER_AUXILIARY (symbolP) < 1)
1913 {
1914 S_SET_NUMBER_AUXILIARY (symbolP, 1);
1915 } /* make it at least 1 */
1916
1917 /* Clobber possible stale .dim information. */
1918 memset (symbolP->sy_symbol.ost_auxent[0].x_sym.x_fcnary.x_ary.x_dimen,
1919 '\0', sizeof (symbolP->sy_symbol.ost_auxent[0].x_sym.x_fcnary.x_ary.x_dimen));
1920 }
1921 /* The C_FCN doesn't need any additional information.
1922 I don't even know if this is needed for sdb. But the
1923 standard assembler generates it, so...
1924 */
1925 if (S_GET_STORAGE_CLASS (symbolP) == C_EFCN)
1926 {
1927 if (last_functionP == (symbolS *) 0)
1928 as_fatal ("C_EFCN symbol out of scope");
1929 SA_SET_SYM_FSIZE (last_functionP,
1930 (long) (S_GET_VALUE (symbolP) -
1931 S_GET_VALUE (last_functionP)));
1932 SA_SET_SYM_ENDNDX (last_functionP, symbol_number);
1933 last_functionP = (symbolS *) 0;
1934 }
1935 }
1936 }
1937 else if (SF_GET_TAG (symbolP))
1938 {
1939 /* First descriptor of a structure must point to
1940 the first slot after the structure description. */
1941 last_tagP = symbolP;
1942
1943 }
1944 else if (S_GET_STORAGE_CLASS (symbolP) == C_EOS)
1945 {
1946 /* +2 take in account the current symbol */
1947 SA_SET_SYM_ENDNDX (last_tagP, symbol_number + 2);
1948 }
1949 else if (S_GET_STORAGE_CLASS (symbolP) == C_FILE)
1950 {
1951 if (symbolP->sy_symbol.ost_auxent->x_file.x_n.x_zeroes == 0)
1952 {
1953 symbolP->sy_symbol.ost_auxent->x_file.x_n.x_offset = string_byte_count;
1954 string_byte_count +=
1955 strlen(GET_FILENAME_STRING(symbolP)) + 1;
1956
1957
1958 }
1959
1960 if (S_GET_VALUE (symbolP))
1961 {
1962 S_SET_VALUE ((symbolS *) S_GET_VALUE (symbolP), symbol_number);
1963 S_SET_VALUE (symbolP, 0);
1964 } /* no one points at the first .file symbol */
1965 } /* if debug or tag or eos or file */
1966
1967 /* We must put the external symbols apart. The loader
1968 does not bomb if we do not. But the references in
1969 the endndx field for a .bb symbol are not corrected
1970 if an external symbol is removed between .bb and .be.
1971 I.e in the following case :
1972 [20] .bb endndx = 22
1973 [21] foo external
1974 [22] .be
1975 ld will move the symbol 21 to the end of the list but
1976 endndx will still be 22 instead of 21. */
1977
1978 if (SF_GET_LOCAL (symbolP))
1979 {
1980 /* remove C_EFCN and LOCAL (L...) symbols */
1981 /* next pointer remains valid */
1982 symbol_remove (symbolP, &symbol_rootP, &symbol_lastP);
1983
1984 }
1985 else if (
1986 #ifdef TE_I386AIX
1987 S_GET_STORAGE_CLASS (symbolP) == C_EXT
1988 && !SF_GET_FUNCTION (symbolP)
1989 #else /* not TE_I386AIX */
1990 !S_IS_DEFINED (symbolP)
1991 && !S_IS_DEBUG (symbolP)
1992 && !SF_GET_STATICS (symbolP)
1993 #endif /* not TE_I386AIX */
1994 )
1995 {
1996 /* if external, Remove from the list */
1997 symbolS *hold = symbol_previous (symbolP);
1998
1999 symbol_remove (symbolP, &symbol_rootP, &symbol_lastP);
2000 symbol_clear_list_pointers (symbolP);
2001 symbol_append (symbolP, symbol_extern_lastP, &symbol_externP, &symbol_extern_lastP);
2002 symbolP = hold;
2003 }
2004 else
2005 {
2006 if (SF_GET_STRING (symbolP))
2007 {
2008 symbolP->sy_name_offset = string_byte_count;
2009 string_byte_count += strlen (S_GET_NAME (symbolP)) + 1;
2010 }
2011 else
2012 {
2013 symbolP->sy_name_offset = 0;
2014 } /* fix "long" names */
2015
2016 symbolP->sy_number = symbol_number;
2017 symbol_number += 1 + S_GET_NUMBER_AUXILIARY (symbolP);
2018 } /* if local symbol */
2019 } /* traverse the symbol list */
2020
2021 for (symbolP = symbol_externP; symbol_externP;)
2022 {
2023 symbolS *tmp = symbol_externP;
2024
2025 /* append */
2026 symbol_remove (tmp, &symbol_externP, &symbol_extern_lastP);
2027 symbol_append (tmp, symbol_lastP, &symbol_rootP, &symbol_lastP);
2028
2029 /* and process */
2030 if (SF_GET_STRING (tmp))
2031 {
2032 tmp->sy_name_offset = string_byte_count;
2033 string_byte_count += strlen (S_GET_NAME (tmp)) + 1;
2034 }
2035 else
2036 {
2037 tmp->sy_name_offset = 0;
2038 } /* fix "long" names */
2039
2040 tmp->sy_number = symbol_number;
2041 symbol_number += 1 + S_GET_NUMBER_AUXILIARY (tmp);
2042 } /* append the entire extern chain */
2043
2044 /* When a tag reference preceeds the tag definition, the definition
2045 will not have a number at the time we process the reference
2046 during the first traversal. Thus, a second traversal. */
2047
2048 for (symbolP = symbol_rootP; symbolP; symbolP = symbol_next (symbolP))
2049 {
2050 if (SF_GET_TAGGED (symbolP))
2051 {
2052 SA_SET_SYM_TAGNDX (symbolP, ((symbolS *) SA_GET_SYM_TAGNDX (symbolP))->sy_number);
2053 }
2054 }
2055
2056 know (symbol_externP == NULL);
2057 know (symbol_extern_lastP == NULL);
2058
2059 /* FIXME-SOMEDAY I'm counting line no's here so we know what to put
2060 in the section headers, and I'm resolving the addresses since I'm
2061 not sure how to do it later. I am NOT resolving the linno's
2062 representing functions. Their symbols need a fileptr pointing to
2063 this linno when emitted. Thus, I resolve them on emit.
2064 xoxorich. */
2065
2066 for (lineP = lineno_rootP; lineP; lineP = lineP->next)
2067 {
2068 if (lineP->line.l_lnno > 0)
2069 {
2070 lineP->line.l_addr.l_paddr += ((fragS *) lineP->frag)->fr_address;
2071 }
2072 else
2073 {
2074 ;
2075 }
2076 text_lineno_number++;
2077 } /* for each line number */
2078
2079 H_SET_SYMBOL_TABLE_SIZE (headers, symbol_number);
2080
2081 return;
2082 }
2083
2084 /*
2085 * Find strings by crawling along symbol table chain.
2086 */
2087
2088 void
2089 obj_emit_strings (where)
2090 char **where;
2091 {
2092 symbolS *symbolP;
2093
2094 #ifdef CROSS_COMPILE
2095 /* Gotta do md_ byte-ordering stuff for string_byte_count first - KWK */
2096 md_number_to_chars (*where, string_byte_count, sizeof (string_byte_count));
2097 *where += sizeof (string_byte_count);
2098 #else /* CROSS_COMPILE */
2099 append (where, (char *) &string_byte_count, (unsigned long) sizeof (string_byte_count));
2100 #endif /* CROSS_COMPILE */
2101
2102 for (symbolP = symbol_rootP; symbolP; symbolP = symbol_next (symbolP))
2103 {
2104 if (S_GET_STORAGE_CLASS(symbolP) == C_FILE)
2105 {
2106 /* May need special treatment for this auxent */
2107 if (symbolP->sy_symbol.ost_auxent->x_file.x_n.x_zeroes == 0)
2108 {
2109 char *p = GET_FILENAME_STRING(symbolP);
2110 append
2111 (where,p, strlen(p)+1);
2112 }
2113 }
2114 if (SF_GET_STRING (symbolP))
2115 {
2116 append (where, S_GET_NAME (symbolP),
2117 (unsigned long) (strlen (S_GET_NAME (symbolP)) + 1));
2118 } /* if it has a string */
2119 } /* walk the symbol chain */
2120 }
2121
2122 void
2123 obj_pre_write_hook (headers)
2124 object_headers *headers;
2125 {
2126 register int text_relocation_number = 0;
2127 register int data_relocation_number = 0;
2128 register fixS *fixP;
2129
2130 /* FIXME-SOMEDAY this should be done at fixup_segment time but I'm
2131 going to wait until I do multiple segments. xoxorich. */
2132 /* Count the number of relocation entries for text and data */
2133 for (fixP = text_fix_root; fixP; fixP = fixP->fx_next)
2134 {
2135 if (fixP->fx_addsy)
2136 {
2137 ++text_relocation_number;
2138 #ifdef TC_I960
2139 /* two relocs per callj under coff. */
2140 if (fixP->fx_callj)
2141 {
2142 ++text_relocation_number;
2143 } /* if callj and not already fixed. */
2144 #endif /* TC_I960 */
2145 #ifdef TC_A29K
2146 /* Count 2 for a constH */
2147 if (fixP->fx_r_type == RELOC_CONSTH)
2148 {
2149 ++text_relocation_number;
2150 }
2151 #endif
2152
2153 } /* if not yet fixed */
2154 } /* for each fix */
2155
2156 SA_SET_SCN_NRELOC (dot_text_symbol, text_relocation_number);
2157 /* Assign the number of line number entries for the text section */
2158 SA_SET_SCN_NLINNO (dot_text_symbol, text_lineno_number);
2159 /* Assign the size of the section */
2160 SA_SET_SCN_SCNLEN (dot_text_symbol, H_GET_TEXT_SIZE (headers));
2161
2162 for (fixP = data_fix_root; fixP; fixP = fixP->fx_next)
2163 {
2164 if (fixP->fx_addsy)
2165 {
2166 ++data_relocation_number;
2167 } /* if still relocatable */
2168 #ifdef TC_A29K
2169 /* Count 2 for a constH */
2170 if (fixP->fx_r_type == RELOC_CONSTH)
2171 {
2172 ++data_relocation_number;
2173 }
2174 #endif
2175
2176 } /* for each fix */
2177
2178
2179 SA_SET_SCN_NRELOC (dot_data_symbol, data_relocation_number);
2180 /* Assign the size of the section */
2181 SA_SET_SCN_SCNLEN (dot_data_symbol, H_GET_DATA_SIZE (headers));
2182
2183 /* Assign the size of the section */
2184 SA_SET_SCN_SCNLEN (dot_bss_symbol, H_GET_BSS_SIZE (headers));
2185
2186 /* pre write hook can add relocs (for 960 and 29k coff) so */
2187 headers->relocation_size = text_relocation_number * RELSZ +
2188 data_relocation_number * RELSZ;
2189
2190
2191
2192 /* Fill in extra coff fields */
2193
2194 /* Initialize general line number information. */
2195 H_SET_LINENO_SIZE (headers, text_lineno_number * LINESZ);
2196
2197 /* filehdr */
2198 H_SET_FILE_MAGIC_NUMBER (headers, FILE_HEADER_MAGIC);
2199 H_SET_NUMBER_OF_SECTIONS (headers, 3); /* text+data+bss */
2200 #ifndef OBJ_COFF_OMIT_TIMESTAMP
2201 H_SET_TIME_STAMP (headers, (long) time ((long *) 0));
2202 #else /* OBJ_COFF_OMIT_TIMESTAMP */
2203 H_SET_TIME_STAMP (headers, 0);
2204 #endif /* OBJ_COFF_OMIT_TIMESTAMP */
2205 H_SET_SYMBOL_TABLE_POINTER (headers, H_GET_SYMBOL_TABLE_FILE_OFFSET (headers));
2206 #if 0
2207 printf ("FILHSZ %x\n", FILHSZ);
2208 printf ("OBJ_COFF_AOUTHDRSZ %x\n", OBJ_COFF_AOUTHDRSZ);
2209 printf ("section headers %x\n", H_GET_NUMBER_OF_SECTIONS (headers) * SCNHSZ);
2210 printf ("get text size %x\n", H_GET_TEXT_SIZE (headers));
2211 printf ("get data size %x\n", H_GET_DATA_SIZE (headers));
2212 printf ("get relocation size %x\n", H_GET_RELOCATION_SIZE (headers));
2213 printf ("get lineno size %x\n", H_GET_LINENO_SIZE (headers));
2214 #endif
2215 /* symbol table size allready set */
2216 H_SET_SIZEOF_OPTIONAL_HEADER (headers, OBJ_COFF_AOUTHDRSZ);
2217
2218 /* do not added the F_RELFLG for the standard COFF.
2219 * The AIX linker complain on file with relocation info striped flag.
2220 */
2221 #ifdef KEEP_RELOC_INFO
2222 H_SET_FLAGS (headers, (text_lineno_number == 0 ? F_LNNO : 0)
2223 | BYTE_ORDERING);
2224 #else
2225 H_SET_FLAGS (headers, (text_lineno_number == 0 ? F_LNNO : 0)
2226 | ((text_relocation_number + data_relocation_number) ? 0 : F_RELFLG)
2227 | BYTE_ORDERING);
2228 #endif
2229 /* aouthdr */
2230 /* magic number allready set */
2231 H_SET_VERSION_STAMP (headers, 0);
2232 /* Text, data, bss size; entry point; text_start and data_start are already set */
2233
2234 /* Build section headers */
2235
2236 c_section_header (&text_section_header,
2237 ".text",
2238 0,
2239 H_GET_TEXT_SIZE (headers),
2240 H_GET_TEXT_FILE_OFFSET (headers),
2241 (SA_GET_SCN_NRELOC (dot_text_symbol)
2242 ? H_GET_RELOCATION_FILE_OFFSET (headers)
2243 : 0),
2244 (text_lineno_number
2245 ? H_GET_LINENO_FILE_OFFSET (headers)
2246 : 0),
2247 SA_GET_SCN_NRELOC (dot_text_symbol),
2248 text_lineno_number,
2249 section_alignment[(int) SEG_TEXT]);
2250
2251 c_section_header (&data_section_header,
2252 ".data",
2253 H_GET_TEXT_SIZE (headers),
2254 H_GET_DATA_SIZE (headers),
2255 (H_GET_DATA_SIZE (headers)
2256 ? H_GET_DATA_FILE_OFFSET (headers)
2257 : 0),
2258 (SA_GET_SCN_NRELOC (dot_data_symbol)
2259 ? (H_GET_RELOCATION_FILE_OFFSET (headers)
2260 + text_section_header.s_nreloc * RELSZ)
2261 : 0),
2262 0, /* No line number information */
2263 SA_GET_SCN_NRELOC (dot_data_symbol),
2264 0, /* No line number information */
2265 section_alignment[(int) SEG_DATA]);
2266
2267 c_section_header (&bss_section_header,
2268 ".bss",
2269 H_GET_TEXT_SIZE (headers) + H_GET_DATA_SIZE (headers),
2270 H_GET_BSS_SIZE (headers),
2271 0, /* No file offset */
2272 0, /* No relocation information */
2273 0, /* No line number information */
2274 0, /* No relocation information */
2275 0, /* No line number information */
2276 section_alignment[(int) SEG_BSS]);
2277 }
2278
2279 /* This is a copy from aout. All I do is neglect to actually build the symbol. */
2280
2281 static void
2282 obj_coff_stab (what)
2283 int what;
2284 {
2285 char *string;
2286 expressionS e;
2287 int goof = 0; /* TRUE if we have aborted. */
2288 int length;
2289 int saved_type = 0;
2290 long longint;
2291 symbolS *symbolP = 0;
2292
2293 if (what == 's')
2294 {
2295 string = demand_copy_C_string (&length);
2296 SKIP_WHITESPACE ();
2297
2298 if (*input_line_pointer == ',')
2299 {
2300 input_line_pointer++;
2301 }
2302 else
2303 {
2304 as_bad ("I need a comma after symbol's name");
2305 goof = 1;
2306 } /* better be a comma */
2307 } /* skip the string */
2308
2309 /*
2310 * Input_line_pointer->after ','. String->symbol name.
2311 */
2312 if (!goof)
2313 {
2314 if (get_absolute_expression_and_terminator (&longint) != ',')
2315 {
2316 as_bad ("I want a comma after the n_type expression");
2317 goof = 1;
2318 input_line_pointer--; /* Backup over a non-',' char. */
2319 } /* on error */
2320 } /* no error */
2321
2322 if (!goof)
2323 {
2324 if (get_absolute_expression_and_terminator (&longint) != ',')
2325 {
2326 as_bad ("I want a comma after the n_other expression");
2327 goof = 1;
2328 input_line_pointer--; /* Backup over a non-',' char. */
2329 } /* on error */
2330 } /* no error */
2331
2332 if (!goof)
2333 {
2334 get_absolute_expression ();
2335
2336 if (what == 's' || what == 'n')
2337 {
2338 if (*input_line_pointer != ',')
2339 {
2340 as_bad ("I want a comma after the n_desc expression");
2341 goof = 1;
2342 }
2343 else
2344 {
2345 input_line_pointer++;
2346 } /* on goof */
2347 } /* not stabd */
2348 } /* no error */
2349
2350 expression (&e);
2351
2352 if (goof)
2353 {
2354 ignore_rest_of_line ();
2355 }
2356 else
2357 {
2358 demand_empty_rest_of_line ();
2359 } /* on error */
2360 } /* obj_coff_stab() */
2361
2362 #ifdef BFD_ASSEMBLER
2363 static
2364 unsigned long
2365 align (val, exp)
2366 {
2367 int n = (1 << exp) - 1;
2368 printf ("align (%x, %x)\n", val, exp);
2369 val = (val + n) & ~n;
2370 return val;
2371 }
2372
2373 void
2374 coff_check_file_symbols (symp, punt)
2375 symbolS *symp;
2376 int *punt;
2377 {
2378 static symbolS *last_functionP, *last_tagP;
2379 static stack *block_stack;
2380
2381 if (!block_stack)
2382 block_stack = stack_init (512, sizeof (symbolS*));
2383
2384 #if 1
2385 if (!S_IS_DEFINED (symp) && S_GET_STORAGE_CLASS (symp) != C_STAT)
2386 S_SET_STORAGE_CLASS (symp, C_EXT);
2387 #endif
2388
2389 if (!SF_GET_DEBUG (symp))
2390 {
2391 symbolS *real;
2392 if (!SF_GET_LOCAL (symp)
2393 && (real = symbol_find_base (S_GET_NAME (symp), DO_NOT_STRIP))
2394 && real != symp)
2395 {
2396 c_symbol_merge (symp, real);
2397 *punt = 1;
2398 }
2399 if (!S_IS_DEFINED (symp) && !SF_GET_LOCAL (symp))
2400 {
2401 assert (S_GET_VALUE (symp) == 0);
2402 S_SET_EXTERNAL (symp);
2403 }
2404 else if (S_GET_STORAGE_CLASS (symp) == C_NULL)
2405 {
2406 if (S_GET_SEGMENT (symp) == text_section)
2407 S_SET_STORAGE_CLASS (symp, C_LABEL);
2408 else
2409 S_SET_STORAGE_CLASS (symp, C_STAT);
2410 }
2411 if (SF_GET_PROCESS (symp))
2412 {
2413 if (S_GET_STORAGE_CLASS (symp) == C_BLOCK)
2414 {
2415 if (!strcmp (S_GET_NAME (symp), ".bb"))
2416 stack_push (block_stack, (char *) &symp);
2417 else
2418 {
2419 symbolS *begin;
2420 begin = *(symbolS **) stack_pop (block_stack);
2421 if (begin == 0)
2422 as_warn ("mismatched .eb");
2423 else
2424 SA_SET_SYM_ENDNDX (begin, begin);
2425 }
2426 }
2427 if (last_functionP == 0 && SF_GET_FUNCTION (symp))
2428 {
2429 union internal_auxent *auxp;
2430 last_functionP = symp;
2431 if (S_GET_NUMBER_AUXILIARY (symp) < 1)
2432 S_SET_NUMBER_AUXILIARY (symp, 1);
2433 auxp = &coffsymbol (symp->bsym)->native[1].u.auxent;
2434 memset (auxp->x_sym.x_fcnary.x_ary.x_dimen, 0,
2435 sizeof (auxp->x_sym.x_fcnary.x_ary.x_dimen));
2436 }
2437 if (S_GET_STORAGE_CLASS (symp) == C_EFCN)
2438 {
2439 if (last_functionP == 0)
2440 as_fatal ("C_EFCN symbol out of scope");
2441 SA_SET_SYM_FSIZE (last_functionP,
2442 (long) (S_GET_VALUE (symp)
2443 - S_GET_VALUE (last_functionP)));
2444 SA_SET_SYM_ENDNDX (last_functionP, symp);
2445 last_functionP = 0;
2446 }
2447 }
2448 else if (SF_GET_TAG (symp))
2449 last_tagP = symp;
2450 else if (S_GET_STORAGE_CLASS (symp) == C_EOS)
2451 SA_SET_SYM_ENDNDX (last_tagP, symp);
2452 else if (S_GET_STORAGE_CLASS (symp) == C_FILE)
2453 {
2454 if (S_GET_VALUE (symp))
2455 {
2456 S_SET_VALUE ((symbolS *) S_GET_VALUE (symp), 0xdeadbeef);
2457 S_SET_VALUE (symp, 0);
2458 }
2459 }
2460 if (SF_GET_LOCAL (symp))
2461 *punt = 1;
2462 /* more ... */
2463 }
2464 if (coffsymbol (symp->bsym)->lineno)
2465 {
2466 int i, n;
2467 struct line_no *lptr;
2468 alent *l;
2469
2470 lptr = (struct line_no *) coffsymbol (symp->bsym)->lineno;
2471 for (i = 0; lptr; lptr = lptr->next)
2472 i++;
2473 n = i + 1;
2474 lptr = (struct line_no *) coffsymbol (symp->bsym)->lineno;
2475 l = (alent *) bfd_alloc_by_size_t (stdoutput, n * sizeof (alent));
2476 coffsymbol (symp->bsym)->lineno = l;
2477 for (i = n - 1; i > 0; i--)
2478 {
2479 if (lptr->frag)
2480 lptr->l.u.offset += lptr->frag->fr_address;
2481 l[i] = lptr->l;
2482 lptr = lptr->next;
2483 }
2484 }
2485 }
2486
2487 void
2488 DEFUN_VOID(obj_coff_section)
2489 {
2490 /* Strip out the section name */
2491 char *section_name ;
2492 char *section_name_end;
2493 char c;
2494
2495 unsigned int len;
2496 unsigned int exp;
2497
2498 section_name = input_line_pointer;
2499 c = get_symbol_end();
2500 section_name_end = input_line_pointer;
2501
2502 len = section_name_end - section_name ;
2503 input_line_pointer++;
2504 SKIP_WHITESPACE();
2505 if (c == ',')
2506 exp = get_absolute_expression();
2507 else if (*input_line_pointer == ',')
2508 {
2509 input_line_pointer++;
2510 exp = get_absolute_expression();
2511 }
2512 else
2513 {
2514 exp = 0;
2515 }
2516
2517 printf ("change_to_section(`%s',%d,%x)\n", section_name, len,exp);
2518 *section_name_end = c;
2519 }
2520
2521 void
2522 coff_frob_file ()
2523 {
2524 if (symbol_rootP == NULL
2525 || S_GET_STORAGE_CLASS (symbol_rootP) != C_FILE)
2526 {
2527 assert (previous_file_symbol == 0);
2528 c_dot_file_symbol ("fake");
2529 }
2530 if (current_lineno_sym)
2531 add_linesym ((symbolS *) 0);
2532 }
2533 #endif /* BFD_ASSEMBLER */
2534
2535 #ifdef DEBUG
2536 /* for debugging */
2537 CONST char *
2538 s_get_name (s)
2539 symbolS *s;
2540 {
2541 return ((s == NULL) ? "(NULL)" : S_GET_NAME (s));
2542 } /* s_get_name() */
2543
2544 void
2545 symbol_dump ()
2546 {
2547 symbolS *symbolP;
2548
2549 for (symbolP = symbol_rootP; symbolP; symbolP = symbol_next (symbolP))
2550 {
2551 #ifdef BFD_ASSEMBLER
2552 printf("0x%lx: \"%s\" type = %ld, class = %d, segment = %d\n",
2553 (unsigned long) symbolP,
2554 S_GET_NAME(symbolP),
2555 (long) S_GET_DATA_TYPE(symbolP),
2556 S_GET_STORAGE_CLASS(symbolP),
2557 (int) S_GET_SEGMENT(symbolP));
2558 #else
2559 printf ("%3ld: 0x%lx \"%s\" type = %ld, class = %d, segment = %d\n",
2560 symbolP->sy_number,
2561 (unsigned long) symbolP,
2562 S_GET_NAME (symbolP),
2563 (long) S_GET_DATA_TYPE (symbolP),
2564 S_GET_STORAGE_CLASS (symbolP),
2565 (int) S_GET_SEGMENT (symbolP));
2566 #endif
2567 }
2568 }
2569
2570 #endif /* DEBUG */
2571
2572 /* end of obj-coff.c */
This page took 0.136573 seconds and 3 git commands to generate.