shithub: riscv

Download patch

ref: 0d59a2358a2a1f93fb28cd7f47f8420fbf06a9af
parent: e24bfa4941679fafc7578f542acc08acd18fff99
author: cinap_lenrek <cinap_lenrek@felloff.net>
date: Sun Apr 19 19:37:05 EDT 2020

?a, cc: fix buffer overflows in built-in preprocessor (macbody)

add a buffer size argument to macexpand() and check for
overflow.

check for overflow when parsing #include directives.

--- a/sys/src/cmd/1a/a.h
+++ b/sys/src/cmd/1a/a.h
@@ -156,7 +156,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/2a/a.h
+++ b/sys/src/cmd/2a/a.h
@@ -157,7 +157,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/5a/a.h
+++ b/sys/src/cmd/5a/a.h
@@ -137,7 +137,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	maclin(void);
 void	macprag(void);
--- a/sys/src/cmd/6a/a.h
+++ b/sys/src/cmd/6a/a.h
@@ -151,7 +151,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/7a/a.h
+++ b/sys/src/cmd/7a/a.h
@@ -143,7 +143,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	maclin(void);
 void	macprag(void);
--- a/sys/src/cmd/8a/a.h
+++ b/sys/src/cmd/8a/a.h
@@ -152,7 +152,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/cc/lex.c
+++ b/sys/src/cmd/cc/lex.c
@@ -760,7 +760,7 @@
 	if(s->macro) {
 		newio();
 		cp = ionext->b;
-		macexpand(s, cp);
+		macexpand(s, cp, sizeof(ionext->b));
 		pushio();
 		ionext->link = iostack;
 		iostack = ionext;
--- a/sys/src/cmd/cc/lexbody
+++ b/sys/src/cmd/cc/lexbody
@@ -238,7 +238,7 @@
 		if(s->macro) {
 			newio();
 			cp = ionext->b;
-			macexpand(s, cp);
+			macexpand(s, cp, sizeof(ionext->b));
 			pushio();
 			ionext->link = iostack;
 			iostack = ionext;
--- a/sys/src/cmd/cc/macbody
+++ b/sys/src/cmd/cc/macbody
@@ -128,7 +128,11 @@
 	char *p;
 	long l;
 
-	strcpy(symb, cp);
+	strncpy(symb, cp, NSYMB);
+	if(symb[NSYMB-1] != '\0'){
+		yyerror("macro too long: %s", cp);
+		symb[NSYMB-1] = 0;
+	}
 	p = strchr(symb, '=');
 	if(p) {
 		*p++ = 0;
@@ -376,15 +380,14 @@
 }
 
 void
-macexpand(Sym *s, char *b)
+macexpand(Sym *s, char *b, int blen)
 {
 	char buf[2000];
 	int n, l, c, nargs;
-	char *arg[NARG], *cp, *ob, *ecp, dots;
+	char *arg[NARG], *cp, *ob, *eb, *ecp, dots;
 
-	ob = b;
 	if(*s->macro == 0) {
-		strcpy(b, s->macro+1);
+		strncpy(b, s->macro+1, blen);
 		if(debug['m'])
 			print("#expand %s %s\n", s->name, ob);
 		return;
@@ -493,8 +496,12 @@
 		*b = 0;
 		return;
 	}
+	ob = b;
+	eb = b + blen-1;
 	cp = s->macro+1;
 	for(;;) {
+		if(b >= eb)
+			goto toobig;
 		c = *cp++;
 		if(c == '\n')
 			c = ' ';
@@ -514,8 +521,11 @@
 		c -= 'a';
 		if(c < 0 || c >= n)
 			continue;
-		strcpy(b, arg[c]);
-		b += strlen(arg[c]);
+		l = strlen(arg[c]);
+		if(b+l > eb)
+			goto toobig;
+		memmove(b, arg[c], l);
+		b += l;
 	}
 	*b = 0;
 	if(debug['m'])
@@ -551,6 +561,10 @@
 			break;
 		if(c == '\n')
 			goto bad;
+		if(hp >= &str[STRINGSZ-1]){
+			yyerror("name too long for #include");
+			break;
+		}
 		*hp++ = c;
 	}
 	*hp = 0;
@@ -558,29 +572,28 @@
 	c = getcom();
 	if(c != '\n')
 		goto bad;
-
 	f = -1;
+	c = 0;
 	for(i=0; i<ninclude; i++) {
 		if(i == 0 && c0 == '>')
 			continue;
-		strcpy(symb, include[i]);
-		strcat(symb, "/");
-		if(strcmp(symb, "./") == 0)
-			symb[0] = 0;
-		strcat(symb, str);
+		c = snprint(symb, NSYMB, "%s/%s", include[i], str)+1;
+		if(strncmp(symb, "./", 2) == 0){
+			c -= 2;
+			memmove(symb, symb+2, c);
+		}
 		f = open(symb, 0);
 		if(f >= 0)
 			break;
 	}
 	if(f < 0)
-		strcpy(symb, str);
-	c = strlen(symb) + 1;
+		c = snprint(symb, NSYMB, "%s", str)+1;
 	while(c & 3)
 		c++;
 	while(nhunk < c)
 		gethunk();
 	hp = hunk;
-	memcpy(hunk, symb, c);
+	memmove(hunk, symb, c);
 	nhunk -= c;
 	hunk += c;
 	newio();
--- a/sys/src/cmd/ka/a.h
+++ b/sys/src/cmd/ka/a.h
@@ -136,7 +136,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/qa/a.h
+++ b/sys/src/cmd/qa/a.h
@@ -138,7 +138,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	macprag(void);
 void	maclin(void);
--- a/sys/src/cmd/va/a.h
+++ b/sys/src/cmd/va/a.h
@@ -136,7 +136,7 @@
 void	domacro(void);
 void	macund(void);
 void	macdef(void);
-void	macexpand(Sym*, char*);
+void	macexpand(Sym*, char*, int);
 void	macinc(void);
 void	maclin(void);
 void	macprag(void);