scc

simple C compiler
git clone git://git.2f30.org/scc
Log | Files | Refs | README | LICENSE

commit e8664d759323eb1ec776615a8806470f8e95b6d9
parent d53555e55c3592a1331b3c3d2a3b0fbced35fcf5
Author: Roberto E. Vargas Caballero <k0ga@shike2.com>
Date:   Fri,  8 Sep 2017 18:31:47 +0200

[as] Add address overflow check

Diffstat:
as/as.h | 1+
as/main.c | 16++++++++++++++++
as/target/i386/ins.c | 2++
3 files changed, 19 insertions(+), 0 deletions(-)

diff --git a/as/as.h b/as/as.h @@ -55,3 +55,4 @@ extern int nr_ins; extern Ins instab[]; extern Op optab[]; extern int pass; +extern TUINT maxaddr; diff --git a/as/main.c b/as/main.c @@ -50,6 +50,7 @@ as(char *text, char *xargs) Ins *ins; Op *op, *lim; Arg *args; + TUINT pc, curpc; ins = bsearch(text, instab, nr_ins, sizeof(Ins), cmp); @@ -69,10 +70,25 @@ as(char *text, char *xargs) return; } (*op->format)(op, args); + + pc = cursec->pc; + curpc = cursec->curpc; + cursec->curpc += op->size; cursec->pc += op->size; + + if (pass == 2) + return; + if (cursec->pc > cursec->max) cursec->max = cursec->pc; + + if (pc > cursec->pc || + curpc > cursec->curpc || + cursec->curpc > maxaddr || + cursec->pc > maxaddr) { + die("address overflow"); + } } int diff --git a/as/target/i386/ins.c b/as/target/i386/ins.c @@ -3,6 +3,8 @@ #include "../../as.h" #include "ins.h" +TUINT maxaddr = ((TUINT) 1 << 32) -1; + void direct(Op *op, Arg *args) {