소스 검색

bug fix with #include in argument
save #pragma's until they can be printed

eck 34 년 전
부모
커밋
ae2eddb822
6개의 변경된 파일99개의 추가작업 그리고 41개의 파일을 삭제
  1. 1 1
      lang/cem/cpp.ansi/Makefile
  2. 1 2
      lang/cem/cpp.ansi/class.h
  3. 5 7
      lang/cem/cpp.ansi/domacro.c
  4. 1 1
      lang/cem/cpp.ansi/main.c
  5. 75 16
      lang/cem/cpp.ansi/preprocess.c
  6. 16 14
      lang/cem/cpp.ansi/replace.c

+ 1 - 1
lang/cem/cpp.ansi/Makefile

@@ -77,7 +77,7 @@ GENERATED = tokenfile.g Lpars.h LLfiles LL.output lint.out \
 all:	cc
 
 cc:	cfiles
-	make "EMHOME="$(EMHOME) "CC="$(CC) ncpp
+	make "EMHOME="$(EMHOME) "CC=$(CC)" ncpp
 
 hfiles: Parameters char.c
 	./make.hfiles Parameters

+ 1 - 2
lang/cem/cpp.ansi/class.h

@@ -41,8 +41,7 @@
 #define	is_oct(ch)	(isoct[ch])
 #define	is_dig(ch)	(isdig[ch])
 #define	is_hex(ch)	(ishex[ch])
-#define	is_suf(ch)	(issuf[ch])
 #define	is_wsp(ch)	(iswsp[ch])
 
 extern char tkclass[];
-extern char inidf[], isoct[], isdig[], ishex[], issuf[], iswsp[];
+extern char inidf[], isoct[], isdig[], ishex[], iswsp[];

+ 5 - 7
lang/cem/cpp.ansi/domacro.c

@@ -67,12 +67,10 @@ GetIdentifier(skiponerr)
 	The token appearing directly after the '#' is obtained by calling
 	the basic lexical analyzing function GetToken() and is interpreted
 	to perform the action belonging to that token.
-	An error message is produced when the token is not recognized,
-	i.e. it is not one of "define" .. "undef" , integer or newline.
-	Return 1 if the preprocessing directive is done. This is to leave
-	pragma's in the input.
+	An error message is produced when the token is not recognized.
+	Pragma's are handled by do_pragma(). They are passed on to the
+	compiler.
 */
-int
 domacro()
 {
 	struct token tk;	/* the token itself			*/
@@ -132,7 +130,8 @@ domacro()
 			do_error();
 			break;
 		case K_PRAGMA:				/* "pragma"	*/
-			return 0;	/* this is for the compiler */
+			do_pragma();
+			break;
 		case K_UNDEF:				/* "undef"	*/
 			do_undef();
 			break;
@@ -151,7 +150,6 @@ domacro()
 		error("illegal # line");
 		SkipToNewLine();
 	}
-	return 1;
 }
 
 skip_block(to_endif)

+ 1 - 1
lang/cem/cpp.ansi/main.c

@@ -33,7 +33,7 @@ main(argc, argv)
 
 	inctable = (char **) Malloc(10 * sizeof(char *));
 	inc_max = 10;
-	inc_total = 2;
+	inc_total = 3;
 	inctable[0] = ".";
 	inctable[1] = "/usr/include";
 	init_pp();	/* initialise the preprocessor macros	*/

+ 75 - 16
lang/cem/cpp.ansi/preprocess.c

@@ -6,6 +6,7 @@
 /* PREPROCESSOR DRIVER */
 
 #include	<system.h>
+#include	<alloc.h>
 #include	"input.h"
 #include	"obufsize.h"
 #include	"arith.h"
@@ -16,6 +17,7 @@
 #include	"idfsize.h"
 #include	"bits.h"
 #include	"line_prefix.h"
+#include	"textsize.h"
 
 char	_obuf[OBUFSIZE];
 #ifdef DOBITS
@@ -31,6 +33,46 @@ Xflush()
 static char *SkipComment();
 extern char options[];
 
+/* #pragma directives are saved here and passed to the compiler later on.
+ */
+struct prag_info {
+	int	pr_linnr;
+	char	*pr_fil;
+	char	*pr_text;
+};
+static struct prag_info *pragma_tab;
+static int pragma_nr;
+
+do_pragma()
+{
+	register int size = ITEXTSIZE;
+	char *cur_line = Malloc(size);
+	register char *c_ptr = cur_line;
+	register int c = GetChar();
+
+	*c_ptr = '\0';
+	while(c != '\n') {
+		if (c_ptr + 1 - cur_line == size) {
+			cur_line = Realloc(cur_line, size + ITEXTSIZE);
+			c_ptr = cur_line + size - 1;
+		}
+		*c_ptr++ = c;
+		c = GetChar();
+	}
+	*c_ptr = '\0';
+	if (!pragma_nr) {
+		pragma_tab = (struct prag_info *)Malloc(sizeof(struct prag_info));
+	} else {
+		pragma_tab = (struct prag_info *)Realloc(pragma_tab
+				    , sizeof(struct prag_info) * (pragma_nr+1));
+	}
+	pragma_tab[pragma_nr].pr_linnr = LineNumber;
+	pragma_tab[pragma_nr].pr_fil = FileName;
+	pragma_tab[pragma_nr].pr_text = cur_line;
+	pragma_nr++;
+	LineNumber++;
+}
+
 preprocess(fn)
 	char *fn;
 {
@@ -58,7 +100,8 @@ preprocess(fn)
 			echo(*p++);
 		}
 	}
-#define	do_line(lineno, fn)						\
+
+#define	do_line_dir(lineno, fn)						\
 		if (lineno != LineNumber || fn != FileName) {		\
 			fn = FileName;					\
 			lineno = LineNumber;				\
@@ -81,6 +124,34 @@ preprocess(fn)
 		startline = 1;
 		c = GetChar();
 		while (startline) {
+		    /* first flush the saved pragma's */
+		    if (pragma_nr) {
+			register int i = 0;
+			int LiNo = LineNumber;
+			char *FiNam = FileName;
+
+			while (i < pragma_nr) {
+			    register char *c_ptr = "#pragma";
+
+			    LineNumber = pragma_tab[i].pr_linnr;
+			    FileName = pragma_tab[i].pr_fil;
+			    do_line_dir(lineno, fn);
+			    while (*c_ptr) { echo(*c_ptr++); }
+			    c_ptr = pragma_tab[i].pr_text;
+			    while (*c_ptr) { echo(*c_ptr++); }
+			    newline(); lineno++;
+			    free(pragma_tab[i].pr_text);
+			    i++;
+			}
+			free(pragma_tab);
+			pragma_tab = (struct prag_info *)0;
+			pragma_nr = 0;
+			LineNumber = LiNo;
+			FileName = FiNam;
+			do_line_dir(lineno, fn);
+		    }
+
+
 		    while (class(c) == STSKIP || c == '/') {
 			if (c == '/') {
 			    if (!InputLevel) {
@@ -102,25 +173,13 @@ preprocess(fn)
 		    }
 
 		    if (c == '#') {
-			if (!domacro()) {	/* pass pragma's to compiler */
-			    register char *p = "#pragma";
-
-			    do_line(lineno, fn);
-
-			    while(*p) {
-				echo(*p++);
-			    }
-			    while ((c = GetChar()) != EOI) {
-				if (class(c) == STNL) break;
-				echo(c);
-			    }
-			}
+			domacro();
 			lineno++;
 			newline();
 			c = GetChar();
 		    } else startline = 0;
 		}
-		do_line(lineno, fn);
+		do_line_dir(lineno, fn);
 		for (;;) {
 
 			/* illegal character */
@@ -205,7 +264,7 @@ preprocess(fn)
 						continue;
 					} else if (!is_dig(c)) {
 						continue;
-					}
+					} else echo(c);
 				}
 				c = GetChar();
 				while (in_idf(c) || c == '.') {

+ 16 - 14
lang/cem/cpp.ansi/replace.c

@@ -277,13 +277,13 @@ struct repl *repl;
 		/* stash arguments */
 		register int i;
 
-		*args->a_rawptr++ = '(';
 		for (i = 0; ap->a_rawvec[i] != (char *)0; i++) {
+			if (i == 0) stash(repl, '(', -1);
+			else stash(repl, ',', -1);
 			for (p = ap->a_rawvec[i]; *p != '\0'; p++)
 				 stash(repl, *p, -1);
-			stash(repl, ',', -1);
 		}
-		*(args->a_rawptr-1) = ')';	/* delete last ',' */
+		stash(repl, ')', -1);
 	}
 }
 
@@ -373,16 +373,14 @@ actual(repl)
 				}
 			}
 			UnGetChar();
-		} else if (ch == '(' || ch == '[' || ch == '{') {
-			/* a comma may occur within these constructions ???
-			 */
+		} else if (ch == '(') {
+			/* a comma may occur within parentheses */
 			level++;
 			stash(repl, ch, !nostashraw);
-		} else if (ch == ')' || ch == ']' || ch == '}') {
+		} else if (ch == ')') {
 			level--;
-			/* clossing parenthesis of macro call */
-			if (ch == ')' && level < 0)
-				return ')';
+			/* test on closing parenthesis of macro call */
+			if (level < 0) return ')';
 			stash(repl, ch, !nostashraw);
 		} else if (ch == ',') {
 			if (level <= 0) { /* comma separator for next argument */
@@ -406,7 +404,7 @@ actual(repl)
 				interpreted as such.
 			*/
 
-			ch = GetChar();
+a_new_line:		ch = GetChar();
 			while (class(ch) == STSKIP || ch == '/') {
 			    if (ch == '/') {
 				    if ((ch = GetChar()) == '*' && !InputLevel) {
@@ -423,9 +421,10 @@ actual(repl)
 			    } else ch = GetChar();
 			}
 
-			if (ch == '#')
+			if (ch == '#') {
 				domacro();
-			else if (ch == EOI) {
+				goto a_new_line;
+			} else if (ch == EOI) {
 				error("unterminated macro call");
 				return ')';
 			}
@@ -726,7 +725,8 @@ add2repl(repl, ch)
 {
 	register int index = repl->r_ptr - repl->r_text;
  
-	if (index + 1 >= repl->r_size) {
+	assert(index < repl->r_size);
+	if (index + 2 >= repl->r_size) {
 		repl->r_text = Realloc(repl->r_text, repl->r_size <<= 1);
 		repl->r_ptr = repl->r_text + index;
 	}
@@ -749,6 +749,7 @@ stash(repl, ch, stashraw)
 	register int index = args->a_expptr - args->a_expbuf;
  
 	if (stashraw >= 0) {
+		assert(index < args->a_expsize);
 		if (index + 1 >= args->a_expsize) {
 			args->a_expbuf = Realloc(args->a_expbuf,
 						    args->a_expsize <<= 1);
@@ -759,6 +760,7 @@ stash(repl, ch, stashraw)
  
 	if (stashraw) {
 		index = args->a_rawptr - args->a_rawbuf;
+		assert(index < args->a_rawsize);
 		if (index + 1 >= args->a_rawsize) {
 			args->a_rawbuf = Realloc(args->a_rawbuf,
 						    args->a_rawsize <<= 1);