From 666e88ee2a66366a81497b4e927b02c69f18a165 Mon Sep 17 00:00:00 2001 From: herman ten brugge Date: Tue, 29 Jul 2025 08:26:57 +0200 Subject: [PATCH] Update for clang -fsanitize I tried to fix all remaining warnings/errors reported by -fsanitize. The riscv64-gen.c is a bit large because it contained a lot of warnings. I forgot some arm-link.c changes in last commit. The other changes are all small fixes to avoid warnings/errors. --- arm-gen.c | 4 +- arm-link.c | 20 +++++----- include/stddef.h | 2 +- riscv64-gen.c | 100 +++++++++++++++++++++-------------------------- riscv64-link.c | 2 +- tccelf.c | 9 +++-- tccgen.c | 2 +- x86_64-gen.c | 3 ++ 8 files changed, 68 insertions(+), 74 deletions(-) diff --git a/arm-gen.c b/arm-gen.c index a74fa90e..882b0986 100644 --- a/arm-gen.c +++ b/arm-gen.c @@ -310,7 +310,7 @@ static uint32_t stuff_const(uint32_t op, uint32_t c) if(c<256) /* catch undefined <<32 */ return op|c; for(i=2;i<32;i+=2) { - m=(0xff>>i)|(0xff<<(32-i)); + m=(0xffu>>i)|(0xffu<<(32-i)); if(!(c&~m)) return op|(i<<7)|(c<>(32-i)); } @@ -593,7 +593,7 @@ void load(int r, SValue *sv) sign=0; else { sign=1; - fc=-fc; + fc=-(unsigned)fc; } v = fr & VT_VALMASK; diff --git a/arm-link.c b/arm-link.c index 3e78db92..4a35559c 100644 --- a/arm-link.c +++ b/arm-link.c @@ -201,10 +201,10 @@ ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, write32le(ptr, read32le(ptr) & 0xff000000); if (x & 0x800000) x -= 0x1000000; - x <<= 2; + x = (unsigned) x << 2; blx_avail = (CONFIG_TCC_CPUVER >= 5); is_thumb = val & 1; - is_bl = (*(unsigned *) ptr) >> 24 == 0xeb; + is_bl = ((unsigned) read32le(ptr)) >> 24 == 0xeb; is_call = (type == R_ARM_CALL || (type == R_ARM_PC24 && is_bl)); x += val - addr; #ifdef DEBUG_RELOC @@ -241,8 +241,8 @@ ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, return; /* Get initial offset */ - hi = (*(uint16_t *)ptr); - lo = (*(uint16_t *)(ptr+2)); + hi = (uint16_t) read16le(ptr); + lo = (uint16_t) read16le(ptr+2); s = (hi >> 10) & 1; j1 = (lo >> 13) & 1; j2 = (lo >> 11) & 1; @@ -313,11 +313,11 @@ ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, j2 = s ^ (i2 ^ 1); imm10 = (x >> 12) & 0x3ff; imm11 = (x >> 1) & 0x7ff; - (*(uint16_t *)ptr) = (uint16_t) ((hi & 0xf800) | - (s << 10) | imm10); - (*(uint16_t *)(ptr+2)) = (uint16_t) ((lo & 0xc000) | - (j1 << 13) | blx_bit | (j2 << 11) | - imm11); + write16le(ptr, (uint16_t) ((hi & 0xf800) | + (s << 10) | imm10)); + write16le(ptr+2, (uint16_t) ((lo & 0xc000) | + (j1 << 13) | blx_bit | (j2 << 11) | + imm11)); } return; case R_ARM_MOVT_ABS: @@ -422,7 +422,7 @@ ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, return; case R_ARM_GLOB_DAT: case R_ARM_JUMP_SLOT: - *(addr_t *)ptr = val; + write32le(ptr, val); return; case R_ARM_NONE: /* Nothing to do. Normally used to indicate a dependency diff --git a/include/stddef.h b/include/stddef.h index da9b9e0d..3d328daa 100644 --- a/include/stddef.h +++ b/include/stddef.h @@ -17,7 +17,7 @@ typedef union { long long __ll; long double __ld; } max_align_t; #endif #undef offsetof -#define offsetof(type, field) ((size_t)&((type *)0)->field) +#define offsetof(type, field) __builtin_offsetof(type, field) #if defined __i386__ || defined __x86_64__ void *alloca(size_t size); diff --git a/riscv64-gen.c b/riscv64-gen.c index a7aa4a7b..a3705666 100644 --- a/riscv64-gen.c +++ b/riscv64-gen.c @@ -35,6 +35,10 @@ #include "tcc.h" #include +#define UPPER(x) (((unsigned)(x) + 0x800u) & 0xfffff000) +#define SIGN7(x) ((((x) & 0xff) ^ 0x80) - 0x80) +#define SIGN11(x) ((((x) & 0xfff) ^ 0x800) - 0x800) + ST_DATA const char * const target_machine_defs = "__riscv\0" "__riscv_xlen 64\0" @@ -163,7 +167,7 @@ ST_FUNC void gsym_addr(int t_, int a_) } } -static int load_symofs(int r, SValue *sv, int forstore) +static int load_symofs(int r, SValue *sv, int forstore, int *new_fc) { int rr, doload = 0, large_addend = 0; int fc = sv->c.i, v = sv->r & VT_VALMASK; @@ -173,7 +177,7 @@ static int load_symofs(int r, SValue *sv, int forstore) if (sv->sym->type.t & VT_STATIC) { // XXX do this per linker relax greloca(cur_text_section, sv->sym, ind, R_RISCV_PCREL_HI20, sv->c.i); - sv->c.i = 0; + *new_fc = 0; } else { if (((unsigned)fc + (1 << 11)) >> 12){ large_addend = 1; @@ -193,9 +197,9 @@ static int load_symofs(int r, SValue *sv, int forstore) if (doload) { EI(0x03, 3, rr, rr, 0); // ld RR, 0(RR) if (large_addend) { - o(0x37 | (6 << 7) | ((0x800 + fc) & 0xfffff000)); //lui t1, high(fc) + o(0x37 | (6 << 7) | UPPER(fc)); //lui t1, high(fc) ER(0x33, 0, rr, rr, 6, 0); // add RR, RR, t1 - sv->c.i = fc << 20 >> 20; + *new_fc = SIGN11(fc); } } } else if (v == VT_LOCAL || v == VT_LLOCAL) { @@ -204,9 +208,9 @@ static int load_symofs(int r, SValue *sv, int forstore) tcc_error("unimp: store(giant local off) (0x%lx)", (long)sv->c.i); if (((unsigned)fc + (1 << 11)) >> 12) { rr = is_ireg(r) ? ireg(r) : 5; // t0 - o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) + o(0x37 | (rr << 7) | UPPER(fc)); //lui RR, upper(fc) ER(0x33, 0, rr, rr, 8, 0); // add RR, RR, s0 - sv->c.i = fc << 20 >> 20; + *new_fc = SIGN11(fc); } } else tcc_error("uhh"); @@ -217,13 +221,12 @@ static void load_large_constant(int rr, int fc, uint32_t pi) { if (fc < 0) pi++; - o(0x37 | (rr << 7) | (((pi + 0x800) & 0xfffff000))); // lui RR, up(up(fc)) - EI(0x13, 0, rr, rr, (int)pi << 20 >> 20); // addi RR, RR, lo(up(fc)) + o(0x37 | (rr << 7) | UPPER(pi)); // lui RR, up(up(fc)) + EI(0x13, 0, rr, rr, SIGN11(pi)); // addi RR, RR, lo(up(fc)) EI(0x13, 1, rr, rr, 12); // slli RR, RR, 12 - EI(0x13, 0, rr, rr, (fc + (1 << 19)) >> 20); // addi RR, RR, up(lo(fc)) + EI(0x13, 0, rr, rr, SIGN11(((unsigned)fc + (1 << 19)) >> 20)); // addi RR, RR, up(lo(fc)) EI(0x13, 1, rr, rr, 12); // slli RR, RR, 12 - fc = (fc + (1 << 7)) << 12 >> 12; - EI(0x13, 0, rr, rr, fc >> 8); // addi RR, RR, lo1(lo(fc)) + EI(0x13, 0, rr, rr, SIGN11(((unsigned)fc + (1 << 7)) >> 8)); // addi RR, RR, lo1(lo(fc)) EI(0x13, 1, rr, rr, 8); // slli RR, RR, 8 } @@ -233,7 +236,6 @@ ST_FUNC void load(int r, SValue *sv) int v = fr & VT_VALMASK; int rr = is_ireg(r) ? ireg(r) : freg(r); int fc = sv->c.i; - uint64_t save_fc = sv->c.i; int bt = sv->type.t & VT_BTYPE; int align, size; if (fr & VT_LVAL) { @@ -246,16 +248,14 @@ ST_FUNC void load(int r, SValue *sv) if (size < 4 && !is_float(sv->type.t) && (sv->type.t & VT_UNSIGNED)) func3 |= 4; if (v == VT_LOCAL || (fr & VT_SYM)) { - br = load_symofs(r, sv, 0); - fc = sv->c.i; + br = load_symofs(r, sv, 0, &fc); } else if (v < VT_CONST) { br = ireg(v); /*if (((unsigned)fc + (1 << 11)) >> 12) tcc_error("unimp: load(large addend) (0x%x)", fc);*/ fc = 0; // XXX store ofs in LVAL(reg) } else if (v == VT_LLOCAL) { - br = load_symofs(r, sv, 0); - fc = sv->c.i; + br = load_symofs(r, sv, 0, &fc); EI(0x03, 3, rr, br, fc); // ld RR, fc(BR) br = rr; fc = 0; @@ -264,10 +264,10 @@ ST_FUNC void load(int r, SValue *sv) si >>= 32; if (si != 0) { load_large_constant(rr, fc, si); - fc = fc << 24 >> 24; + fc = SIGN7(fc); } else { - o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) - fc = fc << 20 >> 20; + o(0x37 | (rr << 7) | UPPER(fc)); //lui RR, upper(fc) + fc = SIGN11(fc); } br = rr; } else { @@ -278,18 +278,17 @@ ST_FUNC void load(int r, SValue *sv) int rb = 0, do32bit = 8, zext = 0; assert((!is_float(sv->type.t) && is_ireg(r)) || bt == VT_LDOUBLE); if (fr & VT_SYM) { - rb = load_symofs(r, sv, 0); - fc = sv->c.i; + rb = load_symofs(r, sv, 0, &fc); do32bit = 0; } if (is_float(sv->type.t) && bt != VT_LDOUBLE) tcc_error("unimp: load(float)"); - if (fc != sv->c.i) { + if (do32bit && fc != sv->c.i) { int64_t si = sv->c.i; si >>= 32; if (si != 0) { load_large_constant(rr, fc, si); - fc = fc << 24 >> 24; + fc = SIGN7(fc); rb = rr; do32bit = 0; } else if (bt == VT_LLONG) { @@ -299,17 +298,16 @@ ST_FUNC void load(int r, SValue *sv) } } if (((unsigned)fc + (1 << 11)) >> 12) - o(0x37 | (rr << 7) | ((0x800 + fc) & 0xfffff000)), rb = rr; //lui RR, upper(fc) + o(0x37 | (rr << 7) | UPPER(fc)), rb = rr; //lui RR, upper(fc) if (fc || (rr != rb) || do32bit || (fr & VT_SYM)) - EI(0x13 | do32bit, 0, rr, rb, fc << 20 >> 20); // addi[w] R, x0|R, FC + EI(0x13 | do32bit, 0, rr, rb, SIGN11(fc)); // addi[w] R, x0|R, FC if (zext) { EI(0x13, 1, rr, rr, 32); // slli RR, RR, 32 EI(0x13, 5, rr, rr, 32); // srli RR, RR, 32 } } else if (v == VT_LOCAL) { - int br = load_symofs(r, sv, 0); + int br = load_symofs(r, sv, 0, &fc); assert(is_ireg(r)); - fc = sv->c.i; EI(0x13, 0, rr, br, fc); // addi R, s0, FC } else if (v < VT_CONST) { /* reg-reg */ //assert(!fc); XXX support offseted regs @@ -324,7 +322,7 @@ ST_FUNC void load(int r, SValue *sv) func7 |= 1; assert(size == 4 || size == 8); o(0x53 | (rr << 7) | ((is_freg(v) ? freg(v) : ireg(v)) << 15) - | (func7 << 25)); // fmv.{w.x, x.w, d.x, x.d} RR, VR + | ((unsigned)func7 << 25)); // fmv.{w.x, x.w, d.x, x.d} RR, VR } } else if (v == VT_CMP) { int op = vtop->cmp_op; @@ -371,7 +369,6 @@ ST_FUNC void load(int r, SValue *sv) EI(0x13, 0, rr, 0, t ^ 1); // addi RR, x0, !t } else tcc_error("unimp: load(non-const)"); - sv->c.i = save_fc; } ST_FUNC void store(int r, SValue *sv) @@ -379,7 +376,6 @@ ST_FUNC void store(int r, SValue *sv) int fr = sv->r & VT_VALMASK; int rr = is_ireg(r) ? ireg(r) : freg(r), ptrreg; int fc = sv->c.i; - uint64_t save_fc = sv->c.i; int bt = sv->type.t & VT_BTYPE; int align, size = type_size(&sv->type, &align); assert(!is_float(bt) || is_freg(r) || bt == VT_LDOUBLE); @@ -393,8 +389,7 @@ ST_FUNC void store(int r, SValue *sv) tcc_error("unimp: large sized store"); assert(sv->r & VT_LVAL); if (fr == VT_LOCAL || (sv->r & VT_SYM)) { - ptrreg = load_symofs(-1, sv, 1); - fc = sv->c.i; + ptrreg = load_symofs(-1, sv, 1, &fc); } else if (fr < VT_CONST) { ptrreg = ireg(fr); /*if (((unsigned)fc + (1 << 11)) >> 12) @@ -406,17 +401,16 @@ ST_FUNC void store(int r, SValue *sv) si >>= 32; if (si != 0) { load_large_constant(ptrreg, fc, si); - fc = fc << 24 >> 24; + fc = SIGN7(fc); } else { - o(0x37 | (ptrreg << 7) | ((0x800 + fc) & 0xfffff000)); //lui RR, upper(fc) - fc = fc << 20 >> 20; + o(0x37 | (ptrreg << 7) | UPPER(fc)); //lui RR, upper(fc) + fc = SIGN11(fc); } } else tcc_error("implement me: %s(!local)", __FUNCTION__); ES(is_freg(r) ? 0x27 : 0x23, // fs... | s... size == 1 ? 0 : size == 2 ? 1 : size == 4 ? 2 : 3, // ... [wd] | [bhwd] ptrreg, rr, fc); // RR, fc(base) - sv->c.i = save_fc; } static void gcall_or_jmp(int docall) @@ -634,11 +628,8 @@ ST_FUNC void gfunc_call(int nb_args) if (stack_add) { if (stack_add >= 0x800) { - unsigned int bit11 = (((unsigned int)-stack_add) >> 11) & 1; - o(0x37 | (5 << 7) | - ((-stack_add + (bit11 << 12)) & 0xfffff000)); //lui t0, upper(v) - EI(0x13, 0, 5, 5, ((-stack_add & 0xfff) - bit11 * (1 << 12))); - // addi t0, t0, lo(v) + o(0x37 | (5 << 7) | UPPER(-stack_add)); //lui t0, upper(v) + EI(0x13, 0, 5, 5, SIGN11(-stack_add)); // addi t0, t0, lo(v) ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 } else @@ -766,11 +757,8 @@ done: vtop -= nb_args + 1; if (stack_add) { if (stack_add >= 0x800) { - unsigned int bit11 = ((unsigned int)stack_add >> 11) & 1; - o(0x37 | (5 << 7) | - ((stack_add + (bit11 << 12)) & 0xfffff000)); //lui t0, upper(v) - EI(0x13, 0, 5, 5, (stack_add & 0xfff) - bit11 * (1 << 12)); - // addi t0, t0, lo(v) + o(0x37 | (5 << 7) | UPPER(stack_add)); //lui t0, upper(v) + EI(0x13, 0, 5, 5, SIGN11(stack_add)); // addi t0, t0, lo(v) ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 } else @@ -911,8 +899,8 @@ ST_FUNC void gfunc_epilog(void) if (v >= (1 << 11)) { d = 16; - o(0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) - EI(0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) + o(0x37 | (5 << 7) | UPPER(v-16)); //lui t0, upper(v) + EI(0x13, 0, 5, 5, SIGN11(v-16)); // addi t0, t0, lo(v) ER(0x33, 0, 2, 2, 5, 0); // add sp, sp, t0 } EI(0x03, 3, 1, 2, d - 8 - num_va_regs * 8); // ld ra, v-8(sp) @@ -922,8 +910,8 @@ ST_FUNC void gfunc_epilog(void) large_ofs_ind = ind; if (v >= (1 << 11)) { EI(0x13, 0, 8, 2, d - num_va_regs * 8); // addi s0, sp, d - o(0x37 | (5 << 7) | ((0x800 + (v-16)) & 0xfffff000)); //lui t0, upper(v) - EI(0x13, 0, 5, 5, (v-16) << 20 >> 20); // addi t0, t0, lo(v) + o(0x37 | (5 << 7) | UPPER(v-16)); //lui t0, upper(v) + EI(0x13, 0, 5, 5, SIGN11(v-16)); // addi t0, t0, lo(v) ER(0x33, 0, 2, 2, 5, 0x20); // sub sp, sp, t0 gjmp_addr(func_sub_sp_offset + 5*4); } @@ -972,8 +960,8 @@ ST_FUNC void gjmp_addr(int a) { uint32_t r = a - ind, imm; if ((r + (1 << 21)) & ~((1U << 22) - 2)) { - o(0x17 | (5 << 7) | (((r + 0x800) & 0xfffff000))); // lui RR, up(r) - r = (int)r << 20 >> 20; + o(0x17 | (5 << 7) | UPPER(r)); // lui RR, up(r) + r = SIGN11(r); EI(0x67, 0, 0, 5, r); // jalr x0, r(t0) } else { imm = (((r >> 12) & 0xff) << 12) @@ -1394,9 +1382,9 @@ ST_FUNC void ggoto(void) ST_FUNC void gen_vla_sp_save(int addr) { if (((unsigned)addr + (1 << 11)) >> 12) { - o(0x37 | (5 << 7) | ((0x800 + addr) & 0xfffff000)); //lui t0,upper(addr) + o(0x37 | (5 << 7) | UPPER(addr)); //lui t0,upper(addr) ER(0x33, 0, 5, 5, 8, 0); // add t0, t0, s0 - ES(0x23, 3, 5, 2, (int)addr << 20 >> 20); // sd sp, fc(t0) + ES(0x23, 3, 5, 2, SIGN11(addr)); // sd sp, fc(t0) } else ES(0x23, 3, 8, 2, addr); // sd sp, fc(s0) @@ -1405,9 +1393,9 @@ ST_FUNC void gen_vla_sp_save(int addr) ST_FUNC void gen_vla_sp_restore(int addr) { if (((unsigned)addr + (1 << 11)) >> 12) { - o(0x37 | (5 << 7) | ((0x800 + addr) & 0xfffff000)); //lui t0,upper(addr) + o(0x37 | (5 << 7) | UPPER(addr)); //lui t0,upper(addr) ER(0x33, 0, 5, 5, 8, 0); // add t0, t0, s0 - EI(0x03, 3, 2, 5, (int)addr << 20 >> 20); // ld sp, fc(t0) + EI(0x03, 3, 2, 5, SIGN11(addr)); // ld sp, fc(t0) } else EI(0x03, 3, 2, 8, addr); // ld sp, fc(s0) diff --git a/riscv64-link.c b/riscv64-link.c index 6a843387..bdc8c242 100644 --- a/riscv64-link.c +++ b/riscv64-link.c @@ -347,7 +347,7 @@ ST_FUNC void relocate(TCCState *s1, ElfW_Rel *rel, int type, unsigned char *ptr, *ptr = (*ptr & ~0xff) | (val & 0xff); return; case R_RISCV_SET16: - write16le(ptr, (read16le(ptr) & ~0xffff) | (val & 0xffff)); + write16le(ptr, val); return; case R_RISCV_SUB6: *ptr = (*ptr & ~0x3f) | ((*ptr - val) & 0x3f); diff --git a/tccelf.c b/tccelf.c index 3e23cf7b..06d47658 100644 --- a/tccelf.c +++ b/tccelf.c @@ -1129,6 +1129,7 @@ static void relocate_section(TCCState *s1, Section *s, Section *sr) qrel = (ElfW_Rel *)sr->data; for_each_elem(sr, 0, rel, ElfW_Rel) { + if (s->data == NULL) continue; /* bss */ ptr = s->data + rel->r_offset; sym_index = ELFW(R_SYM)(rel->r_info); sym = &((ElfW(Sym) *)symtab_section->data)[sym_index]; @@ -1595,7 +1596,8 @@ ST_FUNC void tcc_add_btstub(TCCState *s1) s = data_section; /* Align to PTR_SIZE */ - section_ptr_add(s, -s->data_offset & (PTR_SIZE - 1)); + if (s->data_offset) + section_ptr_add(s, -s->data_offset & (PTR_SIZE - 1)); o = s->data_offset; /* create a struct rt_context (see tccrun.c) */ if (s1->dwarf) { @@ -3257,7 +3259,7 @@ invalid: sm_table[i].s = s; /* concatenate sections */ size = sh->sh_size; - if (sh->sh_type != SHT_NOBITS) { + if (sh->sh_type != SHT_NOBITS && size) { unsigned char *ptr; lseek(fd, file_offset + sh->sh_offset, SEEK_SET); ptr = section_ptr_add(s, size); @@ -3308,6 +3310,7 @@ invalid: /* resolve symbols */ old_to_new_syms = tcc_mallocz(nb_syms * sizeof(int)); + if (nb_syms == 0) goto skip; sym = symtab + 1; for(i = 1; i < nb_syms; i++, sym++) { if (sym->st_shndx != SHN_UNDEF && @@ -3340,7 +3343,7 @@ invalid: sym->st_shndx, name); old_to_new_syms[i] = sym_index; } - +skip: /* third pass to patch relocation entries */ for(i = 1; i < ehdr.e_shnum; i++) { s = sm_table[i].s; diff --git a/tccgen.c b/tccgen.c index 6d949dc5..c25a2243 100644 --- a/tccgen.c +++ b/tccgen.c @@ -4562,7 +4562,7 @@ do_decl: } else { type1.t = (type1.t & ~VT_STRUCT_MASK) | VT_BITFIELD - | (bit_size << (VT_STRUCT_SHIFT + 6)); + | ((unsigned)bit_size << (VT_STRUCT_SHIFT + 6)); } } if (v != 0 || (type1.t & VT_BTYPE) == VT_STRUCT) { diff --git a/x86_64-gen.c b/x86_64-gen.c index 5609bedf..ce521141 100644 --- a/x86_64-gen.c +++ b/x86_64-gen.c @@ -409,6 +409,7 @@ void load(int r, SValue *sv) v1.type.t = VT_LLONG; v1.r = VT_CONST; v1.c.i = sv->c.i; + v1.sym = NULL; fr = r; if (!(reg_classes[fr] & (RC_INT|RC_R11))) fr = get_reg(RC_INT); @@ -1938,6 +1939,7 @@ void gen_opf(int op) v1.type.t = VT_PTR; v1.r = VT_LOCAL | VT_LVAL; v1.c.i = fc; + v1.sym = NULL; load(r, &v1); fc = 0; vtop->r = r = r | VT_LVAL; @@ -2006,6 +2008,7 @@ void gen_opf(int op) v1.type.t = VT_PTR; v1.r = VT_LOCAL | VT_LVAL; v1.c.i = fc; + v1.sym = NULL; load(r, &v1); fc = 0; vtop->r = r = r | VT_LVAL;