2 * COFF file handling for TCC
4 * Copyright (c) 2003, 2004 TK
5 * Copyright (c) 2004 Fabrice Bellard
7 * This library is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU Lesser General Public
9 * License as published by the Free Software Foundation; either
10 * version 2 of the License, or (at your option) any later version.
12 * This library is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * Lesser General Public License for more details.
17 * You should have received a copy of the GNU Lesser General Public
18 * License along with this library; if not, write to the Free Software
19 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 #define MAXNSCNS 255 /* MAXIMUM NUMBER OF SECTIONS */
25 #define MAX_STR_TABLE 1000000
26 AOUTHDR o_filehdr
; /* OPTIONAL (A.OUT) FILE HEADER */
28 SCNHDR section_header
[MAXNSCNS
];
30 #define MAX_FUNCS 1000
31 #define MAX_FUNC_NAME_LENGTH 128
34 char Func
[MAX_FUNCS
][MAX_FUNC_NAME_LENGTH
];
35 char AssociatedFile
[MAX_FUNCS
][MAX_FUNC_NAME_LENGTH
];
36 int LineNoFilePtr
[MAX_FUNCS
];
37 int EndAddress
[MAX_FUNCS
];
38 int LastLineNo
[MAX_FUNCS
];
39 int FuncEntries
[MAX_FUNCS
];
41 int OutputTheSection(Section
* sect
);
42 short int GetCoffFlags(const char* s
);
43 void SortSymbolTable(void);
44 Section
* FindSection(TCCState
* s1
, const char* sname
);
46 int C67_main_entry_point
;
48 int FindCoffSymbolIndex(const char* func_name
);
61 unsigned short lineno
;
62 unsigned short nentries
;
70 unsigned short lineno
;
71 unsigned short dummy1
;
74 unsigned short dummy4
;
77 ST_FUNC
int tcc_output_coff(TCCState
* s1
, FILE* f
)
82 char* Coff_str_table
, *pCoff_str_table
;
83 int CoffTextSectionNo
, coff_nb_syms
;
84 FILHDR file_hdr
; /* FILE HEADER STRUCTURE */
85 Section
* stext
, *sdata
, *sbss
;
86 int i
, NSectionsToOutput
= 0;
88 Coff_str_table
= pCoff_str_table
= NULL
;
90 stext
= FindSection(s1
, ".text");
91 sdata
= FindSection(s1
, ".data");
92 sbss
= FindSection(s1
, ".bss");
94 nb_syms
= symtab_section
->data_offset
/ sizeof(Elf32_Sym
);
95 coff_nb_syms
= FindCoffSymbolIndex("XXXXXXXXXX1");
97 file_hdr
.f_magic
= COFF_C67_MAGIC
; /* magic number */
98 file_hdr
.f_timdat
= 0; /* time & date stamp */
99 file_hdr
.f_opthdr
= sizeof(AOUTHDR
); /* sizeof(optional hdr) */
100 file_hdr
.f_flags
= 0x1143; /* flags (copied from what code composer does) */
101 file_hdr
.f_TargetID
= 0x99; /* for C6x = 0x0099 */
103 o_filehdr
.magic
= 0x0108; /* see magic.h */
104 o_filehdr
.vstamp
= 0x0190; /* version stamp */
106 stext
->data_offset
; /* text size in bytes, padded to FW bdry */
107 o_filehdr
.dsize
= sdata
->data_offset
; /* initialized data " " */
108 o_filehdr
.bsize
= sbss
->data_offset
; /* uninitialized data " " */
109 o_filehdr
.entrypt
= C67_main_entry_point
; /* entry pt. */
110 o_filehdr
.text_start
= stext
->sh_addr
; /* base of text used for this file */
111 o_filehdr
.data_start
= sdata
->sh_addr
; /* base of data used for this file */
113 // create all the section headers
115 file_pointer
= FILHSZ
+ sizeof(AOUTHDR
);
117 CoffTextSectionNo
= -1;
119 for (i
= 1; i
< s1
->nb_sections
; i
++) {
120 coff_sec
= §ion_header
[i
];
121 tcc_sect
= s1
->sections
[i
];
123 if (OutputTheSection(tcc_sect
)) {
126 if (CoffTextSectionNo
== -1 && tcc_sect
== stext
)
127 CoffTextSectionNo
= NSectionsToOutput
; // rem which coff sect
128 // number the .text sect
131 strcpy(coff_sec
->s_name
, tcc_sect
->name
); /* section name */
133 coff_sec
->s_paddr
= tcc_sect
->sh_addr
; /* physical address */
134 coff_sec
->s_vaddr
= tcc_sect
->sh_addr
; /* virtual address */
135 coff_sec
->s_size
= tcc_sect
->data_offset
; /* section size */
136 coff_sec
->s_scnptr
= 0; /* file ptr to raw data for section */
137 coff_sec
->s_relptr
= 0; /* file ptr to relocation */
138 coff_sec
->s_lnnoptr
= 0; /* file ptr to line numbers */
139 coff_sec
->s_nreloc
= 0; /* number of relocation entries */
140 coff_sec
->s_flags
= GetCoffFlags(coff_sec
->s_name
); /* flags */
141 coff_sec
->s_reserved
= 0; /* reserved byte */
142 coff_sec
->s_page
= 0; /* memory page id */
144 file_pointer
+= sizeof(SCNHDR
);
148 file_hdr
.f_nscns
= NSectionsToOutput
; /* number of sections */
150 // now loop through and determine file pointer locations
153 for (i
= 1; i
< s1
->nb_sections
; i
++) {
154 coff_sec
= §ion_header
[i
];
155 tcc_sect
= s1
->sections
[i
];
157 if (OutputTheSection(tcc_sect
)) {
160 file_pointer
; /* file ptr to raw data for section */
161 file_pointer
+= coff_sec
->s_size
;
165 // now loop through and determine file pointer locations
166 // for the relocation data
168 for (i
= 1; i
< s1
->nb_sections
; i
++) {
169 coff_sec
= §ion_header
[i
];
170 tcc_sect
= s1
->sections
[i
];
172 if (OutputTheSection(tcc_sect
)) {
173 // put relocations data
174 if (coff_sec
->s_nreloc
> 0) {
175 coff_sec
->s_relptr
= file_pointer
; /* file ptr to relocation */
176 file_pointer
+= coff_sec
->s_nreloc
* sizeof(struct reloc
);
181 // now loop through and determine file pointer locations
182 // for the line number data
184 for (i
= 1; i
< s1
->nb_sections
; i
++) {
185 coff_sec
= §ion_header
[i
];
186 tcc_sect
= s1
->sections
[i
];
188 coff_sec
->s_nlnno
= 0;
189 coff_sec
->s_lnnoptr
= 0;
191 if (s1
->do_debug
&& tcc_sect
== stext
) {
192 // count how many line nos data
194 // also find association between source file name and function
195 // so we can sort the symbol table
197 Stab_Sym
* sym
, *sym_end
;
198 char func_name
[MAX_FUNC_NAME_LENGTH
],
199 last_func_name
[MAX_FUNC_NAME_LENGTH
];
200 unsigned long func_addr
, last_pc
, pc
;
201 const char* incl_files
[INCLUDE_STACK_SIZE
];
202 int incl_index
, len
, last_line_num
;
205 coff_sec
->s_lnnoptr
= file_pointer
; /* file ptr to linno */
210 last_func_name
[0] = '\0';
211 last_pc
= 0xffffffff;
213 sym
= (Stab_Sym
*)stab_section
->data
+ 1;
215 (Stab_Sym
*)(stab_section
->data
+ stab_section
->data_offset
);
218 while (sym
< sym_end
) {
219 switch (sym
->n_type
) {
220 /* function start or end */
222 if (sym
->n_strx
== 0) {
226 file_pointer
+= LINESZ
;
228 pc
= sym
->n_value
+ func_addr
;
231 EndAddress
[nFuncs
] = pc
;
232 FuncEntries
[nFuncs
] =
233 (file_pointer
- LineNoFilePtr
[nFuncs
]) / LINESZ
- 1;
234 LastLineNo
[nFuncs
++] = last_line_num
+ 1;
236 // beginning of function
238 LineNoFilePtr
[nFuncs
] = file_pointer
;
240 file_pointer
+= LINESZ
;
242 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
244 p
= strchr(str
, ':');
246 pstrcpy(func_name
, sizeof(func_name
), str
);
247 pstrcpy(Func
[nFuncs
], sizeof(func_name
), str
);
250 if (len
> sizeof(func_name
) - 1)
251 len
= sizeof(func_name
) - 1;
252 memcpy(func_name
, str
, len
);
253 memcpy(Func
[nFuncs
], str
, len
);
254 func_name
[len
] = '\0';
257 // save the file that it came in so we can sort later
258 pstrcpy(AssociatedFile
[nFuncs
], sizeof(func_name
),
259 incl_files
[incl_index
- 1]);
261 func_addr
= sym
->n_value
;
265 /* line number info */
267 pc
= sym
->n_value
+ func_addr
;
270 last_line_num
= sym
->n_desc
;
273 strcpy(last_func_name
, func_name
);
276 file_pointer
+= LINESZ
;
280 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
282 if (incl_index
< INCLUDE_STACK_SIZE
) {
283 incl_files
[incl_index
++] = str
;
291 if (sym
->n_strx
== 0) {
292 incl_index
= 0; /* end of translation unit */
294 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
295 /* do not add path */
297 if (len
> 0 && str
[len
- 1] != '/')
307 file_hdr
.f_symptr
= file_pointer
; /* file pointer to symtab */
310 file_hdr
.f_nsyms
= coff_nb_syms
; /* number of symtab entries */
312 file_hdr
.f_nsyms
= 0;
314 file_pointer
+= file_hdr
.f_nsyms
* SYMNMLEN
;
316 // OK now we are all set to write the file
318 fwrite(&file_hdr
, FILHSZ
, 1, f
);
319 fwrite(&o_filehdr
, sizeof(o_filehdr
), 1, f
);
321 // write section headers
322 for (i
= 1; i
< s1
->nb_sections
; i
++) {
323 coff_sec
= §ion_header
[i
];
324 tcc_sect
= s1
->sections
[i
];
326 if (OutputTheSection(tcc_sect
)) {
327 fwrite(coff_sec
, sizeof(SCNHDR
), 1, f
);
332 for (i
= 1; i
< s1
->nb_sections
; i
++) {
333 coff_sec
= §ion_header
[i
];
334 tcc_sect
= s1
->sections
[i
];
336 if (OutputTheSection(tcc_sect
)) {
337 fwrite(tcc_sect
->data
, tcc_sect
->data_offset
, 1, f
);
341 // write relocation data
342 for (i
= 1; i
< s1
->nb_sections
; i
++) {
343 coff_sec
= §ion_header
[i
];
344 tcc_sect
= s1
->sections
[i
];
346 if (OutputTheSection(tcc_sect
)) {
347 // put relocations data
348 if (coff_sec
->s_nreloc
> 0) {
349 fwrite(tcc_sect
->reloc
,
350 coff_sec
->s_nreloc
* sizeof(struct reloc
), 1, f
);
355 // group the symbols in order of filename, func1, func2, etc
356 // finally global symbols
361 // write line no data
363 for (i
= 1; i
< s1
->nb_sections
; i
++) {
364 coff_sec
= §ion_header
[i
];
365 tcc_sect
= s1
->sections
[i
];
367 if (s1
->do_debug
&& tcc_sect
== stext
) {
368 // count how many line nos data
370 Stab_Sym
* sym
, *sym_end
;
371 char func_name
[128], last_func_name
[128];
372 unsigned long func_addr
, last_pc
, pc
;
373 const char* incl_files
[INCLUDE_STACK_SIZE
];
374 int incl_index
, len
, last_line_num
;
382 last_func_name
[0] = '\0';
385 sym
= (Stab_Sym
*)stab_section
->data
+ 1;
387 (Stab_Sym
*)(stab_section
->data
+ stab_section
->data_offset
);
389 while (sym
< sym_end
) {
390 switch (sym
->n_type
) {
391 /* function start or end */
393 if (sym
->n_strx
== 0) {
396 CoffLineNo
.l_addr
.l_paddr
= last_pc
;
397 CoffLineNo
.l_lnno
= last_line_num
+ 1;
398 fwrite(&CoffLineNo
, 6, 1, f
);
400 pc
= sym
->n_value
+ func_addr
;
404 // beginning of function
406 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
408 p
= strchr(str
, ':');
410 pstrcpy(func_name
, sizeof(func_name
), str
);
413 if (len
> sizeof(func_name
) - 1)
414 len
= sizeof(func_name
) - 1;
415 memcpy(func_name
, str
, len
);
416 func_name
[len
] = '\0';
418 func_addr
= sym
->n_value
;
422 // output a function begin
424 CoffLineNo
.l_addr
.l_symndx
=
425 FindCoffSymbolIndex(func_name
);
426 CoffLineNo
.l_lnno
= 0;
428 fwrite(&CoffLineNo
, 6, 1, f
);
432 /* line number info */
434 pc
= sym
->n_value
+ func_addr
;
437 strcpy(last_func_name
, func_name
);
439 // output a line reference
441 CoffLineNo
.l_addr
.l_paddr
= last_pc
;
443 if (last_line_num
== -1) {
444 CoffLineNo
.l_lnno
= sym
->n_desc
;
446 CoffLineNo
.l_lnno
= last_line_num
+ 1;
449 fwrite(&CoffLineNo
, 6, 1, f
);
452 last_line_num
= sym
->n_desc
;
458 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
460 if (incl_index
< INCLUDE_STACK_SIZE
) {
461 incl_files
[incl_index
++] = str
;
469 if (sym
->n_strx
== 0) {
470 incl_index
= 0; /* end of translation unit */
472 str
= (const char*)stabstr_section
->data
+ sym
->n_strx
;
473 /* do not add path */
475 if (len
> 0 && str
[len
- 1] != '/')
485 // write symbol table
498 Coff_str_table
= (char*)tcc_malloc(MAX_STR_TABLE
);
499 pCoff_str_table
= Coff_str_table
;
502 p
= (Elf32_Sym
*)symtab_section
->data
;
504 for (i
= 0; i
< nb_syms
; i
++) {
506 name
= symtab_section
->link
->data
+ p
->st_name
;
508 for (k
= 0; k
< 8; k
++)
509 csym
._n
._n_name
[k
] = 0;
511 if (strlen(name
) <= 8) {
512 strcpy(csym
._n
._n_name
, name
);
514 if (pCoff_str_table
- Coff_str_table
+ strlen(name
) >
516 tcc_error("String table too large");
518 csym
._n
._n_n
._n_zeroes
= 0;
519 csym
._n
._n_n
._n_offset
= pCoff_str_table
- Coff_str_table
+ 4;
521 strcpy(pCoff_str_table
, name
);
522 pCoff_str_table
+= strlen(name
) + 1; // skip over null
526 if (p
->st_info
== 4) {
527 // put a filename symbol
528 csym
.n_value
= 33; // ?????
529 csym
.n_scnum
= N_DEBUG
;
531 csym
.n_sclass
= C_FILE
;
533 fwrite(&csym
, 18, 1, f
);
536 } else if (p
->st_info
== 0x12) {
537 // find the function data
539 for (k
= 0; k
< nFuncs
; k
++) {
540 if (strcmp(name
, Func
[k
]) == 0)
545 tcc_error("debug info can't find function: %s", name
);
547 // put a Function Name
549 csym
.n_value
= p
->st_value
; // physical address
550 csym
.n_scnum
= CoffTextSectionNo
;
551 csym
.n_type
= MKTYPE(T_INT
, DT_FCN
, 0, 0, 0, 0, 0);
552 csym
.n_sclass
= C_EXT
;
554 fwrite(&csym
, 18, 1, f
);
559 auxfunc
.size
= EndAddress
[k
] - p
->st_value
;
560 auxfunc
.fileptr
= LineNoFilePtr
[k
];
561 auxfunc
.nextsym
= n
+ 6; // tktk
563 fwrite(&auxfunc
, 18, 1, f
);
567 strcpy(csym
._n
._n_name
, ".bf");
568 csym
.n_value
= p
->st_value
; // physical address
569 csym
.n_scnum
= CoffTextSectionNo
;
571 csym
.n_sclass
= C_FCN
;
573 fwrite(&csym
, 18, 1, f
);
579 auxbf
.nentries
= FuncEntries
[k
];
580 auxbf
.localframe
= 0;
581 auxbf
.nextentry
= n
+ 6;
583 fwrite(&auxbf
, 18, 1, f
);
587 strcpy(csym
._n
._n_name
, ".ef");
588 csym
.n_value
= EndAddress
[k
]; // physical address
589 csym
.n_scnum
= CoffTextSectionNo
;
591 csym
.n_sclass
= C_FCN
;
593 fwrite(&csym
, 18, 1, f
);
598 auxef
.lineno
= LastLineNo
[k
];
603 fwrite(&auxef
, 18, 1, f
);
608 // try an put some type info
610 if ((p
->st_other
& VT_BTYPE
) == VT_DOUBLE
) {
611 csym
.n_type
= T_DOUBLE
; // int
612 csym
.n_sclass
= C_EXT
;
613 } else if ((p
->st_other
& VT_BTYPE
) == VT_FLOAT
) {
614 csym
.n_type
= T_FLOAT
;
615 csym
.n_sclass
= C_EXT
;
616 } else if ((p
->st_other
& VT_BTYPE
) == VT_INT
) {
617 csym
.n_type
= T_INT
; // int
618 csym
.n_sclass
= C_EXT
;
619 } else if ((p
->st_other
& VT_BTYPE
) == VT_SHORT
) {
620 csym
.n_type
= T_SHORT
;
621 csym
.n_sclass
= C_EXT
;
622 } else if ((p
->st_other
& VT_BTYPE
) == VT_BYTE
) {
623 csym
.n_type
= T_CHAR
;
624 csym
.n_sclass
= C_EXT
;
626 csym
.n_type
= T_INT
; // just mark as a label
627 csym
.n_sclass
= C_LABEL
;
630 csym
.n_value
= p
->st_value
;
633 fwrite(&csym
, 18, 1, f
);
640 fwrite(&auxfunc
, 18, 1, f
);
650 // write string table
652 // first write the size
653 i
= pCoff_str_table
- Coff_str_table
;
656 // then write the strings
657 fwrite(Coff_str_table
, i
, 1, f
);
659 tcc_free(Coff_str_table
);
665 // group the symbols in order of filename, func1, func2, etc
666 // finally global symbols
668 void SortSymbolTable(void)
671 Elf32_Sym
* p
, *p2
, *NewTable
;
674 NewTable
= (Elf32_Sym
*)tcc_malloc(nb_syms
* sizeof(Elf32_Sym
));
676 p
= (Elf32_Sym
*)symtab_section
->data
;
678 // find a file symbol, copy it over
679 // then scan the whole symbol list and copy any function
680 // symbols that match the file association
682 for (i
= 0; i
< nb_syms
; i
++) {
683 if (p
->st_info
== 4) {
684 name
= (char*)symtab_section
->link
->data
+ p
->st_name
;
686 // this is a file symbol, copy it over
690 p2
= (Elf32_Sym
*)symtab_section
->data
;
692 for (j
= 0; j
< nb_syms
; j
++) {
693 if (p2
->st_info
== 0x12) {
694 // this is a func symbol
696 name2
= (char*)symtab_section
->link
->data
+ p2
->st_name
;
698 // find the function data index
700 for (k
= 0; k
< nFuncs
; k
++) {
701 if (strcmp(name2
, Func
[k
]) == 0)
706 tcc_error("debug (sort) info can't find function: %s",
710 if (strcmp(AssociatedFile
[k
], name
) == 0) {
711 // yes they match copy it over
722 // now all the filename and func symbols should have been copied over
723 // copy all the rest over (all except file and funcs)
725 p
= (Elf32_Sym
*)symtab_section
->data
;
726 for (i
= 0; i
< nb_syms
; i
++) {
727 if (p
->st_info
!= 4 && p
->st_info
!= 0x12) {
734 tcc_error("Internal Compiler error, debug info");
738 p
= (Elf32_Sym
*)symtab_section
->data
;
739 for (i
= 0; i
< nb_syms
; i
++) {
746 int FindCoffSymbolIndex(const char* func_name
)
752 p
= (Elf32_Sym
*)symtab_section
->data
;
754 for (i
= 0; i
< nb_syms
; i
++) {
756 name
= (char*)symtab_section
->link
->data
+ p
->st_name
;
758 if (p
->st_info
== 4) {
759 // put a filename symbol
761 } else if (p
->st_info
== 0x12) {
763 if (strcmp(func_name
, name
) == 0)
768 // put a Function Name
787 return n
; // total number of symbols
790 int OutputTheSection(Section
* sect
)
792 const char* s
= sect
->name
;
794 if (!strcmp(s
, ".text"))
796 else if (!strcmp(s
, ".data"))
802 short int GetCoffFlags(const char* s
)
804 if (!strcmp(s
, ".text"))
805 return STYP_TEXT
| STYP_DATA
| STYP_ALIGN
| 0x400;
806 else if (!strcmp(s
, ".data"))
808 else if (!strcmp(s
, ".bss"))
810 else if (!strcmp(s
, ".stack"))
811 return STYP_BSS
| STYP_ALIGN
| 0x200;
812 else if (!strcmp(s
, ".cinit"))
813 return STYP_COPY
| STYP_DATA
| STYP_ALIGN
| 0x200;
818 Section
* FindSection(TCCState
* s1
, const char* sname
)
823 for (i
= 1; i
< s1
->nb_sections
; i
++) {
826 if (!strcmp(sname
, s
->name
))
830 tcc_error("could not find section %s", sname
);
834 ST_FUNC
int tcc_load_coff(TCCState
* s1
, int fd
)
836 // tktk TokenSym *ts;
839 unsigned int str_size
;
840 char* Coff_str_table
, *name
;
844 FILHDR file_hdr
; /* FILE HEADER STRUCTURE */
846 f
= fdopen(fd
, "rb");
848 tcc_error("Unable to open .out file for input");
851 if (fread(&file_hdr
, FILHSZ
, 1, f
) != 1)
852 tcc_error("error reading .out file for input");
854 if (fread(&o_filehdr
, sizeof(o_filehdr
), 1, f
) != 1)
855 tcc_error("error reading .out file for input");
857 // first read the string table
859 if (fseek(f
, file_hdr
.f_symptr
+ file_hdr
.f_nsyms
* SYMESZ
, SEEK_SET
))
860 tcc_error("error reading .out file for input");
862 if (fread(&str_size
, sizeof(int), 1, f
) != 1)
863 tcc_error("error reading .out file for input");
865 Coff_str_table
= (char*)tcc_malloc(str_size
);
867 if (fread(Coff_str_table
, str_size
- 4, 1, f
) != 1)
868 tcc_error("error reading .out file for input");
870 // read/process all the symbols
872 // seek back to symbols
874 if (fseek(f
, file_hdr
.f_symptr
, SEEK_SET
))
875 tcc_error("error reading .out file for input");
877 for (i
= 0; i
< file_hdr
.f_nsyms
; i
++) {
878 if (fread(&csym
, SYMESZ
, 1, f
) != 1)
879 tcc_error("error reading .out file for input");
881 if (csym
._n
._n_n
._n_zeroes
== 0) {
882 name
= Coff_str_table
+ csym
._n
._n_n
._n_offset
- 4;
884 name
= csym
._n
._n_name
;
887 for (k
= 0; k
< 8; k
++)
895 // if (strcmp("_DAC_Buffer",name)==0) // tktk
898 if (((csym
.n_type
& 0x30) == 0x20 && csym
.n_sclass
== 0x2) ||
899 ((csym
.n_type
& 0x30) == 0x30 && csym
.n_sclass
== 0x2) ||
900 (csym
.n_type
== 0x4 && csym
.n_sclass
== 0x2) ||
901 (csym
.n_type
== 0x8 && csym
.n_sclass
== 0x2) || // structures
902 (csym
.n_type
== 0x18 &&
903 csym
.n_sclass
== 0x2) || // pointer to structure
904 (csym
.n_type
== 0x7 && csym
.n_sclass
== 0x2) || // doubles
905 (csym
.n_type
== 0x6 && csym
.n_sclass
== 0x2)) // floats
907 // strip off any leading underscore (except for other main routine)
909 if (name
[0] == '_' && strcmp(name
, "_main") != 0)
912 tcc_add_symbol(s1
, name
, (void*)(uintptr_t)csym
.n_value
);
914 // skip any aux records
916 if (csym
.n_numaux
== 1) {
917 if (fread(&csym
, SYMESZ
, 1, f
) != 1)
918 tcc_error("error reading .out file for input");