scc

simple c99 compiler
git clone git://git.simple-cc.org/scc
Log | Files | Refs | Submodules | README | LICENSE

commit ad3d0dac54f11b7b789b7a8932977ecbadf6380e
parent a77ab9891df84fa7e6286b10087692e267532469
Author: Roberto E. Vargas Caballero <k0ga@shike2.com>
Date:   Sat, 30 Oct 2021 10:58:33 +0200

libmach/coff: Fix use of section flags

Section flags in coff are actually identifiers and not flags.
It means that we have to check against actual values and not
doing and operations. Additional values of flags are added.

Diffstat:
Minclude/scc/scc/coff32/scnhdr.h | 29+++++++++++++++++------------
Msrc/libmach/coff32/coff32getsec.c | 74+++++++++++++++++++++++++++++++++++++++++++++++---------------------------
Msrc/libmach/coff32/coff32getsym.c | 39++++++++++++++++++---------------------
Mtests/nm/execute/0001-z80.sh | 3+++
Mtests/nm/execute/0004-z80-v.sh | 3+++
Mtests/nm/execute/0005-z80-A.sh | 9+++++++++
Mtests/nm/execute/0006-z80-o.sh | 3+++
Mtests/nm/execute/0007-z80-d.sh | 3+++
Mtests/nm/execute/0008-z80-x.sh | 3+++
Mtests/nm/execute/0009-z80-P-o.sh | 3+++
Mtests/nm/execute/0010-z80-P-d.sh | 3+++
Mtests/nm/execute/0011-z80-P-x.sh | 3+++
12 files changed, 115 insertions(+), 60 deletions(-)

diff --git a/include/scc/scc/coff32/scnhdr.h b/include/scc/scc/coff32/scnhdr.h @@ -18,15 +18,20 @@ struct scnhdr { #define SCNHDR struct scnhdr #define SCNHSZ 40 -#define STYP_REG 0 -#define STYP_DSECT (1 << 0) -#define STYP_NOLOAD (1 << 1) -#define STYP_GROUP (1 << 2) -#define STYP_PAD (1 << 3) -#define STYP_COPY (1 << 4) -#define STYP_TEXT (1 << 5) -#define STYP_DATA (1 << 6) -#define STYP_BSS (1 << 7) -#define STYP_INFO (1 << 9) -#define STYP_OVER (1 << 11) -#define STYP_LIB (1 << 12) + +#define STYP_REG 0x00 +#define STYP_DSECT 0x01 +#define STYP_NOLOAD 0x02 +#define STYP_GROUP 0x04 +#define STYP_PAD 0x08 +#define STYP_COPY 0x10 +#define STYP_TEXT 0x20 +#define STYP_DATA 0x40 +#define STYP_BSS 0x80 +#define STYP_RDATA 0x100 +#define STYP_INFO 0x200 +#define STYP_OVER 0x400 +#define STYP_LIB 0x800 +#define STYP_MERGE 0x2000 +#define TYP_REVERSE_PAD 0x4000 +#define STYP_LIT 0x8020 diff --git a/src/libmach/coff32/coff32getsec.c b/src/libmach/coff32/coff32getsec.c @@ -11,7 +11,6 @@ coff32getsec(Obj *obj, int *idx, Section *sec) long n = *idx; int type; unsigned sflags; - unsigned long flags; SCNHDR *scn; Coff32 *coff = obj->data; FILHDR *hdr = &coff->hdr; @@ -20,48 +19,69 @@ coff32getsec(Obj *obj, int *idx, Section *sec) return NULL; scn = &coff->scns[n]; - flags = scn->s_flags; - - if (flags & STYP_TEXT) { + switch (scn->s_flags) { + case STYP_REG: + type = 'D'; + sflags = SALLOC | SRELOC | SLOAD | SWRITE | SREAD; + break; + case STYP_DSECT: + type = '?'; + sflags = SRELOC; + break; + case STYP_NOLOAD: + type = 'D'; + sflags = SALLOC | SREAD | SWRITE; + break; + case TYP_REVERSE_PAD: + case STYP_PAD: + type = '?'; + sflags = SLOAD; + break; + case STYP_COPY: + type = '?'; + sflags |= SLOAD | SRELOC; + break; + case STYP_TEXT: type = 'T'; sflags = SALLOC | SRELOC | SLOAD | SEXEC | SREAD; - if (flags & STYP_NOLOAD) - sflags |= SSHARED; - } else if (flags & STYP_DATA) { + break; + case STYP_DATA: type = 'D'; sflags = SALLOC | SRELOC | SLOAD | SWRITE | SREAD; - if (flags & STYP_NOLOAD) - sflags |= SSHARED; - } else if (flags & STYP_BSS) { + break; + case STYP_BSS: type = 'B'; sflags = SALLOC | SREAD | SWRITE; - } else if (flags & STYP_INFO) { + break; + case STYP_LIT: + case STYP_RDATA: + type = 'D'; + sflags = SALLOC | SRELOC | SLOAD | SWRITE | SREAD; + break; + case STYP_LIB: + case STYP_INFO: type = 'N'; sflags = 0; - } else if (flags & STYP_LIB) { - type = 'T'; - sflags = SRELOC; - } else if (flags & STYP_DSECT) { - type = 'D'; + break; + case STYP_OVER: + type = '?'; sflags = SRELOC; - } else if (flags & STYP_PAD) { - type = 'D'; - sflags = SLOAD; - } else { - type = 'D'; /* We assume that STYP_REG is data */ - sflags = SALLOC | SRELOC | SLOAD | SWRITE | SREAD; + break; + case STYP_GROUP: + case STYP_MERGE: + default: + type = '?'; + sflags = 0; + break; } - if (flags & STYP_NOLOAD) - sflags &= ~SLOAD; - sec->name = scn->s_name; sec->index = n; sec->size = scn->s_size; - sec->base = 0; /* TODO: Check what is the actual value */ + sec->base = scn->s_vaddr; sec->type = type; sec->flags = sflags; - sec->align = 4; /* TODO: Check how align is defined in coff */ + sec->align = 16; return sec; } diff --git a/src/libmach/coff32/coff32getsym.c b/src/libmach/coff32/coff32getsym.c @@ -12,7 +12,6 @@ typeof(Coff32 *coff, SYMENT *ent, char *name) { int c; SCNHDR *scn; - long flags; switch (ent->n_scnum) { case N_DEBUG: @@ -26,16 +25,27 @@ typeof(Coff32 *coff, SYMENT *ent, char *name) break; default: scn = &coff->scns[ent->n_scnum-1]; - flags = scn->s_flags; - if (flags & STYP_TEXT) + + switch (scn->s_flags) { + case STYP_TEXT: c = 't'; - else if (flags & STYP_DATA) + break; + case STYP_DATA: c = 'd'; - else if (flags & STYP_BSS) + break; + case STYP_BSS: c = 'b'; - else + break; + case STYP_INFO: + c = 'N'; + break; + case STYP_LIT: + c = 'r'; + break; + default: c = '?'; - break; + break; + } } if (ent->n_sclass == C_EXT) @@ -44,19 +54,6 @@ typeof(Coff32 *coff, SYMENT *ent, char *name) return c; } -static int -stypeof(char *name) -{ - if (strcmp(name, ".text") == 0 - || strcmp(name, ".data") == 0 - || strcmp(name, ".bss") == 0 - || strcmp(name, ".rdata") == 0) { - return SYMSECTION; - } else { - return SYMOBJECT; - } -} - static char * symname(Coff32 *coff, SYMENT *ent) { @@ -80,7 +77,7 @@ coff32getsym(Obj *obj, int *idx, Symbol *sym) ent = &coff->ents[n]; sym->name = symname(coff, ent); sym->type = typeof(coff, ent, sym->name); - sym->stype = stypeof(sym->name); + sym->stype = SYMOBJECT; sym->value = ent->n_value; sym->size = (sym->type == 'C') ? ent->n_value : 0; sym->index = n; diff --git a/tests/nm/execute/0001-z80.sh b/tests/nm/execute/0001-z80.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm z80.out > $tmp1 cat <<! > $tmp2 +0000000000000000 b .bss +0000000000000000 d .data +0000000000000000 t .text 0000000000000001 B averylongbss 0000000000000001 D averylongdata 0000000000000001 T averylongtext diff --git a/tests/nm/execute/0004-z80-v.sh b/tests/nm/execute/0004-z80-v.sh @@ -10,6 +10,9 @@ nm -v z80.out > $tmp1 cat <<! > $tmp2 U text6 +0000000000000000 t .text +0000000000000000 d .data +0000000000000000 b .bss 0000000000000000 T text1 0000000000000000 D data1 0000000000000000 B bss1 diff --git a/tests/nm/execute/0005-z80-A.sh b/tests/nm/execute/0005-z80-A.sh @@ -13,6 +13,9 @@ ar -qv f.a f.out nm -A f.a z80.out > $tmp1 cat <<! > $tmp2 +f.a[z80.out]: 0000000000000000 b .bss +f.a[z80.out]: 0000000000000000 d .data +f.a[z80.out]: 0000000000000000 t .text f.a[z80.out]: 0000000000000001 B averylongbss f.a[z80.out]: 0000000000000001 D averylongdata f.a[z80.out]: 0000000000000001 T averylongtext @@ -29,6 +32,9 @@ f.a[z80.out]: 0000000000000002 t text3 f.a[z80.out]: 000000000000000a C text4 f.a[z80.out]: 0000000000000012 C text5 f.a[z80.out]: U text6 +f.a[f.out]: 0000000000000000 b .bss +f.a[f.out]: 0000000000000000 d .data +f.a[f.out]: 0000000000000000 t .text f.a[f.out]: 0000000000000001 B averylongbss f.a[f.out]: 0000000000000001 D averylongdata f.a[f.out]: 0000000000000001 T averylongtext @@ -45,6 +51,9 @@ f.a[f.out]: 0000000000000002 t text3 f.a[f.out]: 000000000000000a C text4 f.a[f.out]: 0000000000000012 C text5 f.a[f.out]: U text6 +z80.out: 0000000000000000 b .bss +z80.out: 0000000000000000 d .data +z80.out: 0000000000000000 t .text z80.out: 0000000000000001 B averylongbss z80.out: 0000000000000001 D averylongdata z80.out: 0000000000000001 T averylongtext diff --git a/tests/nm/execute/0006-z80-o.sh b/tests/nm/execute/0006-z80-o.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -t o z80.out > $tmp1 cat <<! > $tmp2 +0000000000000000 b .bss +0000000000000000 d .data +0000000000000000 t .text 0000000000000001 B averylongbss 0000000000000001 D averylongdata 0000000000000001 T averylongtext diff --git a/tests/nm/execute/0007-z80-d.sh b/tests/nm/execute/0007-z80-d.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -t d z80.out > $tmp1 cat <<! > $tmp2 +0000000000000000 b .bss +0000000000000000 d .data +0000000000000000 t .text 0000000000000001 B averylongbss 0000000000000001 D averylongdata 0000000000000001 T averylongtext diff --git a/tests/nm/execute/0008-z80-x.sh b/tests/nm/execute/0008-z80-x.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -t x z80.out > $tmp1 cat <<! > $tmp2 +0000000000000000 b .bss +0000000000000000 d .data +0000000000000000 t .text 0000000000000001 B averylongbss 0000000000000001 D averylongdata 0000000000000001 T averylongtext diff --git a/tests/nm/execute/0009-z80-P-o.sh b/tests/nm/execute/0009-z80-P-o.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -P -t o z80.out > $tmp1 cat <<! > $tmp2 +.bss b 0000000000000000 0 +.data d 0000000000000000 0 +.text t 0000000000000000 0 averylongbss B 0000000000000001 0 averylongdata D 0000000000000001 0 averylongtext T 0000000000000001 0 diff --git a/tests/nm/execute/0010-z80-P-d.sh b/tests/nm/execute/0010-z80-P-d.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -P -t x z80.out > $tmp1 cat <<! > $tmp2 +.bss b 0000000000000000 0 +.data d 0000000000000000 0 +.text t 0000000000000000 0 averylongbss B 0000000000000001 0 averylongdata D 0000000000000001 0 averylongtext T 0000000000000001 0 diff --git a/tests/nm/execute/0011-z80-P-x.sh b/tests/nm/execute/0011-z80-P-x.sh @@ -9,6 +9,9 @@ trap "rm -f $tmp1 $tmp2; exit" 0 2 3 nm -P -t x z80.out > $tmp1 cat <<! > $tmp2 +.bss b 0000000000000000 0 +.data d 0000000000000000 0 +.text t 0000000000000000 0 averylongbss B 0000000000000001 0 averylongdata D 0000000000000001 0 averylongtext T 0000000000000001 0