tccelf: cleanup sort_sections() & etc. fixes
with -Wl,-oformat=binary, executable code should come first. (for linux kernel image for example) Also: - simplify RELRO sections: create them as readonly, but add SHF_WRITE flag later when needed (i.e. relocations do exist) - tcc.h etc: exclude eh_frames on non-elf platforms - tccelf.c:tcc_load_object_file(): don't load debug sections when linking without -g (special dwarf case in relocate_section() wont work when dwlo/hi were not initialized). - tcc.c: avoid loop if something fails (ret < 0) without message (while failing without message should not happen either) - tccelf.c:tcc_load_alacarte: give message - tccpp.c: treat '# 123xyz' in asm file as comment - lib/Makefile: cleanup - libtcc.c: tcc_add_library(): fallback to try filename as is (also remove tcc_add_library_err())
This commit is contained in:
parent
3eb6352c52
commit
dd2e5f8b06
9 changed files with 141 additions and 125 deletions
71
lib/Makefile
71
lib/Makefile
|
@ -7,6 +7,8 @@ include $(TOP)/Makefile
|
|||
VPATH = $(TOPSRC)/lib $(TOPSRC)/win32/lib
|
||||
T = $(or $(CROSS_TARGET),$(NATIVE_TARGET),unknown)
|
||||
X = $(if $(CROSS_TARGET),$(CROSS_TARGET)-)
|
||||
XCFG = $(or $(findstring -win,$T),-unx)
|
||||
S = $(if $(findstring yes,$(SILENT)),@$(info * $@))
|
||||
|
||||
TCC = $(TOP)/$(X)tcc$(EXESUF)
|
||||
XTCC ?= $(TOP)/$(X)tcc$(EXESUF)
|
||||
|
@ -16,8 +18,6 @@ XFLAGS-unx = -B$(TOPSRC)
|
|||
XFLAGS-win = -B$(TOPSRC)/win32 -I$(TOPSRC)/include
|
||||
XFLAGS = $(XFLAGS$(XCFG)) -I$(TOP)
|
||||
BFLAGS = -bt
|
||||
XCFG = $(or $(findstring -win,$T),-unx)
|
||||
S = $(if $(findstring yes,$(SILENT)),@$(info * $@))
|
||||
|
||||
# in order to use gcc, type: make <target>-libtcc1-usegcc=yes
|
||||
arm-libtcc1-usegcc ?= no
|
||||
|
@ -29,47 +29,48 @@ arm-libtcc1-usegcc ?= no
|
|||
ifeq "$($(T)-libtcc1-usegcc)" "yes"
|
||||
XCC = $(CC)
|
||||
XAR = $(AR)
|
||||
XFLAGS = $(CFLAGS) -fPIC -gdwarf -fno-omit-frame-pointer -Wno-unused-function -Wno-unused-variable
|
||||
BFLAGS = -g
|
||||
XFLAGS = $(CFLAGS) -fPIC -fno-omit-frame-pointer -Wno-unused-function -Wno-unused-variable
|
||||
BFLAGS = $(if $(CONFIG_dwarf),-gdwarf,-gstabs)
|
||||
endif
|
||||
|
||||
ifneq ($(CONFIG_backtrace),no)
|
||||
# only for native compiler
|
||||
ifneq ($(CONFIG_bcheck),no)
|
||||
$(X)BCHECK_O = bcheck.o
|
||||
endif
|
||||
$(X)BT_O = bt-exe.o bt-log.o
|
||||
$(X)B_O = $(BCHECK_O) bt-exe.o bt-log.o bt-dll.o
|
||||
endif
|
||||
$(X)BT_O += runmain.o tcov.o
|
||||
I386_O = libtcc1.o alloca.o alloca-bt.o $(COMMON_O)
|
||||
X86_64_O = libtcc1.o alloca.o alloca-bt.o $(COMMON_O)
|
||||
ARM_O = libtcc1.o armeabi.o alloca.o armflush.o $(COMMON_O)
|
||||
ARM64_O = lib-arm64.o $(COMMON_O)
|
||||
RISCV64_O = lib-arm64.o $(COMMON_O)
|
||||
COMMON_O = stdatomic.o atomic.o builtin.o
|
||||
WIN_O = crt1.o crt1w.o wincrt1.o wincrt1w.o dllcrt1.o dllmain.o
|
||||
LIN_O = dsohandle.o
|
||||
OSX_O =
|
||||
|
||||
DSO_O = dsohandle.o
|
||||
# backtrace/bcheck/run only for native compiler
|
||||
Nat = $(if $X,no,)
|
||||
Cbt = $(Nat)$(subst yes,,$(CONFIG_backtrace))
|
||||
Cbc = $(Cbt)$(subst yes,,$(CONFIG_bcheck))
|
||||
|
||||
$(Nat)COMMON_O += runmain.o tcov.o
|
||||
$(Cbt)COMMON_O += bt-exe.o bt-log.o
|
||||
$(Cbt)WIN_O += bt-dll.o
|
||||
$(Cbc)COMMON_O += bcheck.o
|
||||
|
||||
# not in libtcc1.a
|
||||
EXTRA_O = runmain.o bt-exe.o bt-dll.o bt-log.o bcheck.o
|
||||
|
||||
I386_O = libtcc1.o alloca.o alloca-bt.o stdatomic.o atomic.o builtin.o $(BT_O)
|
||||
X86_64_O = libtcc1.o alloca.o alloca-bt.o stdatomic.o atomic.o builtin.o $(BT_O)
|
||||
ARM_O = libtcc1.o armeabi.o alloca.o armflush.o stdatomic.o atomic.o builtin.o $(BT_O)
|
||||
ARM64_O = lib-arm64.o stdatomic.o atomic.o builtin.o $(BT_O)
|
||||
RISCV64_O = lib-arm64.o stdatomic.o atomic.o builtin.o $(BT_O)
|
||||
WIN_O = crt1.o crt1w.o wincrt1.o wincrt1w.o dllcrt1.o dllmain.o
|
||||
|
||||
OBJ-i386 = $(I386_O) $(BCHECK_O) $(DSO_O)
|
||||
OBJ-x86_64 = $(X86_64_O) va_list.o $(BCHECK_O) $(DSO_O)
|
||||
OBJ-x86_64-osx = $(X86_64_O) va_list.o $(BCHECK_O)
|
||||
OBJ-i386-win32 = $(I386_O) chkstk.o $(B_O) $(WIN_O)
|
||||
OBJ-x86_64-win32 = $(X86_64_O) chkstk.o $(B_O) $(WIN_O)
|
||||
OBJ-arm64 = $(ARM64_O) $(BCHECK_O) $(DSO_O)
|
||||
OBJ-arm64-osx = $(ARM64_O) $(BCHECK_O)
|
||||
OBJ-arm = $(ARM_O) $(BCHECK_O) $(DSO_O)
|
||||
OBJ-arm-fpa = $(ARM_O) $(DSO_O)
|
||||
OBJ-arm-fpa-ld = $(ARM_O) $(DSO_O)
|
||||
OBJ-arm-vfp = $(ARM_O) $(DSO_O)
|
||||
OBJ-arm-eabi = $(ARM_O) $(DSO_O)
|
||||
OBJ-arm-eabihf = $(ARM_O) $(DSO_O)
|
||||
OBJ-i386 = $(I386_O) $(LIN_O)
|
||||
OBJ-x86_64 = $(X86_64_O) va_list.o $(LIN_O)
|
||||
OBJ-x86_64-osx = $(X86_64_O) va_list.o $(OSX_O)
|
||||
OBJ-i386-win32 = $(I386_O) chkstk.o $(WIN_O)
|
||||
OBJ-x86_64-win32 = $(X86_64_O) chkstk.o $(WIN_O)
|
||||
OBJ-arm64 = $(ARM64_O) $(LIN_O)
|
||||
OBJ-arm64-osx = $(ARM64_O) $(OSX_O)
|
||||
OBJ-arm = $(ARM_O) $(LIN_O)
|
||||
OBJ-arm-fpa = $(OBJ-arm)
|
||||
OBJ-arm-fpa-ld = $(OBJ-arm)
|
||||
OBJ-arm-vfp = $(OBJ-arm)
|
||||
OBJ-arm-eabi = $(OBJ-arm)
|
||||
OBJ-arm-eabihf = $(OBJ-arm)
|
||||
OBJ-arm-wince = $(ARM_O) $(WIN_O)
|
||||
OBJ-riscv64 = $(RISCV64_O) $(BCHECK_O) $(DSO_O)
|
||||
OBJ-riscv64 = $(RISCV64_O) $(LIN_O)
|
||||
|
||||
OBJ-extra = $(filter $(EXTRA_O),$(OBJ-$T))
|
||||
OBJ-libtcc1 = $(addprefix $(X),$(filter-out $(OBJ-extra),$(OBJ-$T)))
|
||||
|
|
34
libtcc.c
34
libtcc.c
|
@ -1004,6 +1004,8 @@ static int tcc_glob_so(TCCState *s1, const char *pattern, char *buf, int size)
|
|||
}
|
||||
#endif
|
||||
|
||||
static int guess_filetype(const char *filename);
|
||||
|
||||
ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags)
|
||||
{
|
||||
int fd, ret = -1;
|
||||
|
@ -1014,6 +1016,9 @@ ST_FUNC int tcc_add_file_internal(TCCState *s1, const char *filename, int flags)
|
|||
filename = buf;
|
||||
#endif
|
||||
|
||||
if (0 == (flags & AFF_TYPE_MASK))
|
||||
flags |= guess_filetype(filename);
|
||||
|
||||
/* ignore binary files with -E */
|
||||
if (s1->output_type == TCC_OUTPUT_PREPROCESS
|
||||
&& (flags & AFF_TYPE_BIN))
|
||||
|
@ -1123,10 +1128,10 @@ check_success:
|
|||
return ret;
|
||||
}
|
||||
|
||||
LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename)
|
||||
static int guess_filetype(const char *filename)
|
||||
{
|
||||
int filetype = s->filetype;
|
||||
if (0 == (filetype & AFF_TYPE_MASK)) {
|
||||
int filetype = 0;
|
||||
if (1) {
|
||||
/* use a file extension to detect a filetype */
|
||||
const char *ext = tcc_fileextension(filename);
|
||||
if (ext[0]) {
|
||||
|
@ -1145,7 +1150,12 @@ LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename)
|
|||
filetype = AFF_TYPE_C;
|
||||
}
|
||||
}
|
||||
return tcc_add_file_internal(s, filename, filetype | AFF_PRINT_ERROR);
|
||||
return filetype;
|
||||
}
|
||||
|
||||
LIBTCCAPI int tcc_add_file(TCCState *s, const char *filename)
|
||||
{
|
||||
return tcc_add_file_internal(s, filename, s->filetype | AFF_PRINT_ERROR);
|
||||
}
|
||||
|
||||
LIBTCCAPI int tcc_add_library_path(TCCState *s, const char *pathname)
|
||||
|
@ -1162,12 +1172,12 @@ static int tcc_add_library_internal(TCCState *s1, const char *fmt,
|
|||
|
||||
for(i = 0; i < nb_paths; i++) {
|
||||
snprintf(buf, sizeof(buf), fmt, paths[i], filename);
|
||||
ret = tcc_add_file_internal(s1, buf, (flags & ~AFF_PRINT_ERROR) | AFF_TYPE_BIN);
|
||||
ret = tcc_add_file_internal(s1, buf, flags & ~AFF_PRINT_ERROR);
|
||||
if (ret != FILE_NOT_FOUND)
|
||||
return ret;
|
||||
}
|
||||
if (flags & AFF_PRINT_ERROR)
|
||||
tcc_error_noabort("file '%s' not found", filename);
|
||||
tcc_error_noabort("library '%s' not found", filename);
|
||||
return FILE_NOT_FOUND;
|
||||
}
|
||||
|
||||
|
@ -1219,15 +1229,7 @@ LIBTCCAPI int tcc_add_library(TCCState *s, const char *libraryname)
|
|||
return ret;
|
||||
++pp;
|
||||
}
|
||||
return FILE_NOT_FOUND;
|
||||
}
|
||||
|
||||
PUB_FUNC int tcc_add_library_err(TCCState *s1, const char *libname)
|
||||
{
|
||||
int ret = tcc_add_library(s1, libname);
|
||||
if (ret == FILE_NOT_FOUND)
|
||||
tcc_error_noabort("library '%s' not found", libname);
|
||||
return ret;
|
||||
return tcc_add_dll(s, libraryname, AFF_PRINT_ERROR);
|
||||
}
|
||||
|
||||
/* handle #pragma comment(lib,) */
|
||||
|
@ -1235,7 +1237,7 @@ ST_FUNC void tcc_add_pragma_libs(TCCState *s1)
|
|||
{
|
||||
int i;
|
||||
for (i = 0; i < s1->nb_pragma_libs; i++)
|
||||
tcc_add_library_err(s1, s1->pragma_libs[i]);
|
||||
tcc_add_library(s1, s1->pragma_libs[i]);
|
||||
}
|
||||
|
||||
LIBTCCAPI int tcc_add_symbol(TCCState *s1, const char *name, const void *val)
|
||||
|
|
10
tcc.c
10
tcc.c
|
@ -366,7 +366,7 @@ redo:
|
|||
struct filespec *f = s->files[n];
|
||||
s->filetype = f->type;
|
||||
if (f->type & AFF_TYPE_LIB) {
|
||||
ret = tcc_add_library_err(s, f->name);
|
||||
ret = tcc_add_library(s, f->name);
|
||||
} else {
|
||||
if (1 == s->verbose)
|
||||
printf("-> %s\n", f->name);
|
||||
|
@ -392,9 +392,9 @@ redo:
|
|||
} else {
|
||||
if (!s->outfile)
|
||||
s->outfile = default_outputfile(s, first_file);
|
||||
if (!s->just_deps && tcc_output_file(s, s->outfile))
|
||||
;
|
||||
else if (s->gen_deps)
|
||||
if (!s->just_deps)
|
||||
ret = tcc_output_file(s, s->outfile);
|
||||
if (!ret && s->gen_deps)
|
||||
gen_makedeps(s, s->outfile, s->deps_outfile);
|
||||
}
|
||||
}
|
||||
|
@ -402,7 +402,7 @@ redo:
|
|||
done = 1;
|
||||
if (t)
|
||||
done = 0; /* run more tests with -dt -run */
|
||||
else if (s->nb_errors)
|
||||
else if (ret)
|
||||
ret = 1;
|
||||
else if (n < s->nb_files)
|
||||
done = 0; /* compile more files with -c */
|
||||
|
|
13
tcc.h
13
tcc.h
|
@ -974,8 +974,6 @@ struct TCCState {
|
|||
int uw_sym;
|
||||
unsigned uw_offs;
|
||||
# endif
|
||||
#else
|
||||
unsigned shf_RELRO; /* section flags for RELRO sections */
|
||||
#endif
|
||||
|
||||
#if defined TCC_TARGET_MACHO
|
||||
|
@ -1874,10 +1872,6 @@ ST_FUNC int gen_makedeps(TCCState *s, const char *target, const char *filename);
|
|||
|
||||
/* ------------ tccdbg.c ------------ */
|
||||
|
||||
ST_FUNC void tcc_eh_frame_start(TCCState *s1);
|
||||
ST_FUNC void tcc_eh_frame_end(TCCState *s1);
|
||||
ST_FUNC void tcc_eh_frame_hdr(TCCState *s1, int final);
|
||||
|
||||
ST_FUNC void tcc_debug_new(TCCState *s);
|
||||
|
||||
ST_FUNC void tcc_debug_start(TCCState *s1);
|
||||
|
@ -1896,6 +1890,13 @@ ST_FUNC void tcc_debug_typedef(TCCState *s1, Sym *sym);
|
|||
ST_FUNC void tcc_debug_stabn(TCCState *s1, int type, int value);
|
||||
ST_FUNC void tcc_debug_fix_anon(TCCState *s1, CType *t);
|
||||
|
||||
#if !(defined ELF_OBJ_ONLY || defined TCC_TARGET_ARM || defined TARGETOS_BSD)
|
||||
ST_FUNC void tcc_eh_frame_start(TCCState *s1);
|
||||
ST_FUNC void tcc_eh_frame_end(TCCState *s1);
|
||||
ST_FUNC void tcc_eh_frame_hdr(TCCState *s1, int final);
|
||||
#define TCC_EH_FRAME 1
|
||||
#endif
|
||||
|
||||
ST_FUNC void tcc_tcov_start(TCCState *s1);
|
||||
ST_FUNC void tcc_tcov_end(TCCState *s1);
|
||||
ST_FUNC void tcc_tcov_check_line(TCCState *s1, int start);
|
||||
|
|
11
tccdbg.c
11
tccdbg.c
|
@ -424,7 +424,7 @@ ST_FUNC void tcc_debug_new(TCCState *s1)
|
|||
if (s1->do_debug && s1->output_type == TCC_OUTPUT_MEMORY)
|
||||
s1->do_backtrace = 1;
|
||||
if (s1->do_backtrace)
|
||||
shf = SHF_ALLOC | SHF_WRITE; // SHF_WRITE needed for musl/SELINUX
|
||||
shf = SHF_ALLOC; /* have debug data available at runtime */
|
||||
#endif
|
||||
|
||||
if (s1->dwarf) {
|
||||
|
@ -511,7 +511,7 @@ static void put_stabn(TCCState *s1, int type, int other, int desc, int value)
|
|||
|
||||
/* ------------------------------------------------------------------------- */
|
||||
#define dwarf_data1(s,data) \
|
||||
{ unsigned char *p = section_ptr_add((s), 1); *p = (data); }
|
||||
(*(uint8_t*)section_ptr_add((s), 1) = (data))
|
||||
#define dwarf_data2(s,data) \
|
||||
write16le(section_ptr_add((s), 2), (data))
|
||||
#define dwarf_data4(s,data) \
|
||||
|
@ -712,10 +712,9 @@ static void dwarf_sleb128_op (TCCState *s1, long long value)
|
|||
} while (more);
|
||||
}
|
||||
|
||||
#if TCC_EH_FRAME
|
||||
ST_FUNC void tcc_eh_frame_start(TCCState *s1)
|
||||
{
|
||||
#if !(defined _WIN32 || defined __APPLE__ || defined TCC_TARGET_ARM || \
|
||||
defined TARGETOS_BSD)
|
||||
if (!s1->unwind_tables)
|
||||
return;
|
||||
eh_frame_section = new_section(s1, ".eh_frame", SHT_PROGBITS, SHF_ALLOC);
|
||||
|
@ -784,7 +783,6 @@ ST_FUNC void tcc_eh_frame_start(TCCState *s1)
|
|||
dwarf_data1(eh_frame_section, DW_CFA_nop);
|
||||
write32le(eh_frame_section->data + s1->eh_start, // length
|
||||
eh_frame_section->data_offset - s1->eh_start - 4);
|
||||
#endif
|
||||
}
|
||||
|
||||
static void tcc_debug_frame_end(TCCState *s1, int size)
|
||||
|
@ -1006,6 +1004,7 @@ next:
|
|||
qsort(eh_frame_hdr_section->data + tab_offset, count,
|
||||
sizeof(struct eh_search_table), sort_eh_table);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* start of translation unit info */
|
||||
ST_FUNC void tcc_debug_start(TCCState *s1)
|
||||
|
@ -2172,7 +2171,9 @@ ST_FUNC void tcc_debug_funcend(TCCState *s1, int size)
|
|||
/* lldb does not like function end and next function start at same pc */
|
||||
int min_instr_len;
|
||||
|
||||
#if TCC_EH_FRAME
|
||||
tcc_debug_frame_end(s1, size);
|
||||
#endif
|
||||
if (!s1->do_debug)
|
||||
return;
|
||||
min_instr_len = dwarf_line.last_pc == ind ? 0 : DWARF_MIN_INSTR_LEN;
|
||||
|
|
96
tccelf.c
96
tccelf.c
|
@ -51,7 +51,7 @@ struct sym_version {
|
|||
#define shf_RELRO SHF_ALLOC
|
||||
static const char rdata[] = ".rdata";
|
||||
#else
|
||||
#define shf_RELRO s1->shf_RELRO
|
||||
#define shf_RELRO SHF_ALLOC /* eventually made SHF_WRITE in sort_sections() */
|
||||
static const char rdata[] = ".data.ro";
|
||||
#endif
|
||||
|
||||
|
@ -61,12 +61,6 @@ ST_FUNC void tccelf_new(TCCState *s)
|
|||
{
|
||||
TCCState *s1 = s;
|
||||
|
||||
#ifndef TCC_TARGET_PE
|
||||
shf_RELRO = SHF_ALLOC;
|
||||
if (s1->output_type != TCC_OUTPUT_MEMORY)
|
||||
shf_RELRO |= SHF_WRITE; /* the ELF loader will set it to RO at runtime */
|
||||
#endif
|
||||
|
||||
/* no section zero */
|
||||
dynarray_add(&s->sections, &s->nb_sections, NULL);
|
||||
|
||||
|
@ -95,7 +89,9 @@ ST_FUNC void tccelf_new(TCCState *s)
|
|||
tcc_debug_new(s);
|
||||
}
|
||||
|
||||
#if TCC_EH_FRAME
|
||||
tcc_eh_frame_start(s);
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_TCC_BCHECK
|
||||
if (s->do_bounds_check) {
|
||||
|
@ -1126,8 +1122,8 @@ static void relocate_section(TCCState *s1, Section *s, Section *sr)
|
|||
r = 0; /* cannot apply 64bit relocation to 32bit value */
|
||||
sr->data_offset = sr->sh_size = r;
|
||||
#ifdef CONFIG_TCC_PIE
|
||||
if (r && 0 == (s->sh_flags & SHF_WRITE))
|
||||
tcc_warning("%d relocations to ro-section %s", (unsigned)(r / sizeof *qrel), s->name);
|
||||
if (r && (s->sh_flags & SHF_EXECINSTR))
|
||||
tcc_warning("%d relocations to %s", (unsigned)(r / sizeof *qrel), s->name);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
@ -1758,7 +1754,7 @@ ST_FUNC void tcc_add_runtime(TCCState *s1)
|
|||
if (s1->do_bounds_check && s1->output_type != TCC_OUTPUT_DLL) {
|
||||
tcc_add_support(s1, "bcheck.o");
|
||||
# if !(TARGETOS_OpenBSD || TARGETOS_NetBSD)
|
||||
tcc_add_library_err(s1, "dl");
|
||||
tcc_add_library(s1, "dl");
|
||||
# endif
|
||||
lpthread = 1;
|
||||
}
|
||||
|
@ -1774,8 +1770,8 @@ ST_FUNC void tcc_add_runtime(TCCState *s1)
|
|||
}
|
||||
#endif
|
||||
if (lpthread)
|
||||
tcc_add_library_err(s1, "pthread");
|
||||
tcc_add_library_err(s1, "c");
|
||||
tcc_add_library(s1, "pthread");
|
||||
tcc_add_library(s1, "c");
|
||||
#ifdef TCC_LIBGCC
|
||||
if (!s1->static_link) {
|
||||
if (TCC_LIBGCC[0] == '/')
|
||||
|
@ -1785,7 +1781,7 @@ ST_FUNC void tcc_add_runtime(TCCState *s1)
|
|||
}
|
||||
#endif
|
||||
#if defined TCC_TARGET_ARM && TARGETOS_FreeBSD
|
||||
tcc_add_library_err(s1, "gcc_s"); // unwind code
|
||||
tcc_add_library(s1, "gcc_s"); // unwind code
|
||||
#endif
|
||||
if (TCC_LIBTCC1[0])
|
||||
tcc_add_support(s1, TCC_LIBTCC1);
|
||||
|
@ -2091,7 +2087,7 @@ static int set_sec_sizes(TCCState *s1)
|
|||
/* allocate the section */
|
||||
s->sh_flags |= SHF_ALLOC;
|
||||
s->sh_size = count * sizeof(ElfW_Rel);
|
||||
if (!(s1->sections[s->sh_info]->sh_flags & SHF_WRITE))
|
||||
if (s1->sections[s->sh_info]->sh_flags & SHF_EXECINSTR)
|
||||
textrel += count;
|
||||
}
|
||||
}
|
||||
|
@ -2161,47 +2157,58 @@ static int sort_sections(TCCState *s1, int *sec_order, struct dyn_inf *d)
|
|||
} else {
|
||||
j = 0x700;
|
||||
}
|
||||
if (s1->output_format != TCC_OUTPUT_FORMAT_ELF) {
|
||||
if (j >= 0x700 || 0 == strncmp(s->name, ".eh_frame", 9))
|
||||
s->sh_size = 0, j = 0x900;
|
||||
}
|
||||
|
||||
if (s->sh_type == SHT_SYMTAB || s->sh_type == SHT_DYNSYM) {
|
||||
k = 0x10;
|
||||
} else if (s->sh_type == SHT_STRTAB && strcmp(s->name, ".stabstr")) {
|
||||
k = 0x11;
|
||||
if (i == nb_sections - 1) /* ".shstrtab" assumed to remain last */
|
||||
if (i == nb_sections - 1) /* ".shstrtab" assumed to stay last */
|
||||
k = 0xff;
|
||||
} else if (s->sh_type == SHT_HASH || s->sh_type == SHT_GNU_HASH) {
|
||||
k = 0x12;
|
||||
} else if (s->sh_type == SHT_GNU_verdef
|
||||
|| s->sh_type == SHT_GNU_verneed
|
||||
|| s->sh_type == SHT_GNU_versym) {
|
||||
k = 0x13;
|
||||
} else if (s->sh_type == SHT_RELX) {
|
||||
k = 0x20;
|
||||
if (s1->plt && s == s1->plt->reloc)
|
||||
k = 0x21;
|
||||
} else if (s->sh_flags & SHF_EXECINSTR) {
|
||||
k = 0x30;
|
||||
/* RELRO sections --> */
|
||||
} else if (s->sh_type == SHT_PREINIT_ARRAY) {
|
||||
k = 0x41;
|
||||
} else if (s->sh_type == SHT_INIT_ARRAY) {
|
||||
k = 0x42;
|
||||
} else if (s->sh_type == SHT_FINI_ARRAY) {
|
||||
k = 0x43;
|
||||
#ifdef CONFIG_TCC_BCHECK
|
||||
} else if (s == bounds_section || s == lbounds_section) {
|
||||
k = 0x44;
|
||||
#endif
|
||||
} else if (s == rodata_section || 0 == strcmp(s->name, ".data.rel.ro")) {
|
||||
k = 0x45;
|
||||
} else if (s->sh_type == SHT_DYNAMIC) {
|
||||
k = 0x46;
|
||||
} else if (s == s1->got) {
|
||||
k = 0x47; /* .got as RELRO needs BIND_NOW in DT_FLAGS */
|
||||
} else if (s->reloc && (s->reloc->sh_flags & SHF_ALLOC) && j == 0x100) {
|
||||
k = 0x44;
|
||||
/* <-- */
|
||||
} else if (s->sh_type == SHT_NOTE) {
|
||||
k = 0x60;
|
||||
} else if (s->sh_type == SHT_NOBITS) {
|
||||
k = 0x70; /* bss */
|
||||
} else if (s == d->interp) {
|
||||
k = 0x00;
|
||||
} else {
|
||||
k = 0x50;
|
||||
if (s->sh_type == SHT_NOTE)
|
||||
k = 0x60;
|
||||
if (s->sh_flags & SHF_EXECINSTR)
|
||||
k = 0x70;
|
||||
if (s->sh_type == SHT_NOBITS)
|
||||
k = 0x80;
|
||||
if (s == d->interp)
|
||||
k = 0x00;
|
||||
k = 0x50; /* data */
|
||||
}
|
||||
k += j;
|
||||
|
||||
if ((k & 0xfff0) == 0x140) {
|
||||
/* make RELRO section writable */
|
||||
k += 0x100, s->sh_flags |= SHF_WRITE;
|
||||
}
|
||||
for (n = i; n > 1 && k < (f = sec_cls[n - 1]); --n)
|
||||
sec_cls[n] = f, sec_order[n] = sec_order[n - 1];
|
||||
sec_cls[n] = k, sec_order[n] = i;
|
||||
|
@ -2233,7 +2240,7 @@ static int sort_sections(TCCState *s1, int *sec_order, struct dyn_inf *d)
|
|||
f0 = f, ++n, f |= 1<<8;
|
||||
}
|
||||
sec_cls[i] = f;
|
||||
//printf("ph %d sec %02d : %3X %3X %8.2X %04X %s\n", (f>0) * n, i, f, k, s->sh_type, s->sh_size, s->name);
|
||||
//printf("ph %d sec %02d : %3X %3X %8.2X %04X %s\n", (f>0) * n, i, f, k, s->sh_type, (int)s->sh_size, s->name);
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
@ -2395,12 +2402,8 @@ static int layout_sections(TCCState *s1, int *sec_order, struct dyn_inf *d)
|
|||
fill_phdr(++ph, PT_NOTE, d->note);
|
||||
if (d->dynamic)
|
||||
fill_phdr(++ph, PT_DYNAMIC, d->dynamic)->p_flags |= PF_W;
|
||||
if (eh_frame_hdr_section) {
|
||||
add32le(eh_frame_hdr_section->data + 4,
|
||||
eh_frame_section->sh_offset -
|
||||
eh_frame_hdr_section->sh_offset - 4);
|
||||
if (eh_frame_hdr_section)
|
||||
fill_phdr(++ph, PT_GNU_EH_FRAME, eh_frame_hdr_section);
|
||||
}
|
||||
if (d->roinf)
|
||||
fill_phdr(++ph, PT_GNU_RELRO, d->roinf)->p_flags |= PF_W;
|
||||
if (d->interp)
|
||||
|
@ -2869,10 +2872,10 @@ static int elf_output_file(TCCState *s1, const char *filename)
|
|||
/* shared library case: simply export all global symbols */
|
||||
export_global_syms(s1);
|
||||
}
|
||||
|
||||
#if TCC_EH_FRAME
|
||||
/* fill with initial data */
|
||||
tcc_eh_frame_hdr(s1, 0);
|
||||
|
||||
#endif
|
||||
dyninf.gnu_hash = create_gnu_hash(s1);
|
||||
} else {
|
||||
build_got_entries(s1, 0);
|
||||
|
@ -2956,10 +2959,10 @@ static int elf_output_file(TCCState *s1, const char *filename)
|
|||
update_gnu_hash(s1, dyninf.gnu_hash);
|
||||
|
||||
reorder_sections(s1, sec_order);
|
||||
|
||||
#if TCC_EH_FRAME
|
||||
/* fill with final data */
|
||||
tcc_eh_frame_hdr(s1, 1);
|
||||
|
||||
#endif
|
||||
/* Create the ELF file with name 'filename' */
|
||||
ret = tcc_write_elf_file(s1, filename, dyninf.phnum, dyninf.phdr);
|
||||
the_end:
|
||||
|
@ -3146,6 +3149,11 @@ invalid:
|
|||
if (sh->sh_type == SHT_RELX)
|
||||
sh = &shdr[sh->sh_info];
|
||||
/* ignore sections types we do not handle (plus relocs to those) */
|
||||
if (0 == strncmp(strsec + sh->sh_name, ".debug_", 7)
|
||||
|| 0 == strncmp(strsec + sh->sh_name, ".stab", 5)) {
|
||||
if (!s1->do_debug || seencompressed)
|
||||
continue;
|
||||
} else
|
||||
if (sh->sh_type != SHT_PROGBITS &&
|
||||
#ifdef TCC_ARM_EABI
|
||||
sh->sh_type != SHT_ARM_EXIDX &&
|
||||
|
@ -3157,12 +3165,9 @@ invalid:
|
|||
sh->sh_type != SHT_NOBITS &&
|
||||
sh->sh_type != SHT_PREINIT_ARRAY &&
|
||||
sh->sh_type != SHT_INIT_ARRAY &&
|
||||
sh->sh_type != SHT_FINI_ARRAY &&
|
||||
strcmp(strsec + sh->sh_name, ".stabstr")
|
||||
sh->sh_type != SHT_FINI_ARRAY
|
||||
)
|
||||
continue;
|
||||
if (seencompressed && 0 == strncmp(strsec + sh->sh_name, ".debug_", 7))
|
||||
continue;
|
||||
|
||||
sh = &shdr[i];
|
||||
sh_name = strsec + sh->sh_name;
|
||||
|
@ -3414,7 +3419,7 @@ static int tcc_load_alacarte(TCCState *s1, int fd, int size, int entrysize)
|
|||
|
||||
data = tcc_malloc(size);
|
||||
if (full_read(fd, data, size) != size)
|
||||
goto the_end;
|
||||
goto invalid;
|
||||
nsyms = get_be(data, entrysize);
|
||||
ar_index = data + entrysize;
|
||||
ar_names = (char *) ar_index + nsyms * entrysize;
|
||||
|
@ -3432,6 +3437,7 @@ static int tcc_load_alacarte(TCCState *s1, int fd, int size, int entrysize)
|
|||
off = get_be(ar_index + i * entrysize, entrysize);
|
||||
len = read_ar_header(fd, off, &hdr);
|
||||
if (len <= 0 || memcmp(hdr.ar_fmag, ARFMAG, 2)) {
|
||||
invalid:
|
||||
tcc_error_noabort("invalid archive");
|
||||
goto the_end;
|
||||
}
|
||||
|
|
2
tccgen.c
2
tccgen.c
|
@ -401,7 +401,9 @@ ST_FUNC int tccgen_compile(TCCState *s1)
|
|||
gen_inline_functions(s1);
|
||||
check_vstack();
|
||||
/* end of translation unit info */
|
||||
#if TCC_EH_FRAME
|
||||
tcc_eh_frame_end(s1);
|
||||
#endif
|
||||
tcc_debug_end(s1);
|
||||
tcc_tcov_end(s1);
|
||||
return 0;
|
||||
|
|
10
tccpe.c
10
tccpe.c
|
@ -845,7 +845,7 @@ found_dll:
|
|||
return s;
|
||||
}
|
||||
|
||||
void pe_free_imports(struct pe_info *pe)
|
||||
static void pe_free_imports(struct pe_info *pe)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < pe->imp_count; ++i) {
|
||||
|
@ -1133,9 +1133,7 @@ static int pe_section_class(Section *s)
|
|||
name = s->name;
|
||||
|
||||
if (0 == memcmp(name, ".stab", 5) || 0 == memcmp(name, ".debug_", 7)) {
|
||||
if (s->s1->do_debug)
|
||||
return sec_debug;
|
||||
|
||||
return sec_debug;
|
||||
} else if (flags & SHF_ALLOC) {
|
||||
if (type == SHT_PROGBITS
|
||||
|| type == SHT_INIT_ARRAY
|
||||
|
@ -1995,7 +1993,7 @@ static void pe_add_runtime(TCCState *s1, struct pe_info *pe)
|
|||
tcc_add_support(s1, TCC_LIBTCC1);
|
||||
for (pp = libs; 0 != (p = *pp); ++pp) {
|
||||
if (*p)
|
||||
tcc_add_library_err(s1, p);
|
||||
tcc_add_library(s1, p);
|
||||
else if (PE_DLL != pe_type && PE_GUI != pe_type)
|
||||
break;
|
||||
}
|
||||
|
@ -2068,8 +2066,8 @@ ST_FUNC int pe_output_file(TCCState *s1, const char *filename)
|
|||
#ifdef CONFIG_TCC_BCHECK
|
||||
tcc_add_bcheck(s1);
|
||||
#endif
|
||||
pe_add_runtime(s1, &pe);
|
||||
tcc_add_pragma_libs(s1);
|
||||
pe_add_runtime(s1, &pe);
|
||||
resolve_common_syms(s1);
|
||||
pe_set_options(s1, &pe);
|
||||
pe_check_symbols(&pe);
|
||||
|
|
19
tccpp.c
19
tccpp.c
|
@ -1929,23 +1929,28 @@ ST_FUNC void preprocess(int is_bof)
|
|||
break;
|
||||
case TOK_LINE:
|
||||
next_nomacro();
|
||||
if (tok != TOK_PPNUM)
|
||||
if (tok != TOK_PPNUM) {
|
||||
_line_err:
|
||||
if (parse_flags & PARSE_FLAG_ASM_FILE)
|
||||
goto ignore;
|
||||
tcc_error("wrong #line format");
|
||||
}
|
||||
case TOK_PPNUM:
|
||||
parse_number(tokc.str.data);
|
||||
n = tokc.i;
|
||||
for (n = 0, q = tokc.str.data; *q; ++q) {
|
||||
if (!isnum(*q))
|
||||
goto _line_err;
|
||||
n = n * 10 + *q - '0';
|
||||
}
|
||||
next_nomacro();
|
||||
if (tok != TOK_LINEFEED) {
|
||||
if (tok == TOK_PPSTR && tokc.str.data[0] == '"') {
|
||||
tokc.str.data[tokc.str.size - 2] = 0;
|
||||
tccpp_putfile(tokc.str.data + 1);
|
||||
} else if (parse_flags & PARSE_FLAG_ASM_FILE)
|
||||
goto ignore;
|
||||
else
|
||||
} else
|
||||
goto _line_err;
|
||||
next_nomacro();
|
||||
}
|
||||
} else if (parse_flags & PARSE_FLAG_ASM_FILE)
|
||||
goto ignore;
|
||||
if (file->fd > 0)
|
||||
total_lines += file->line_num - n;
|
||||
file->line_num = n;
|
||||
|
|
Loading…
Add table
Reference in a new issue