aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorPer Bothner <bothner@gcc.gnu.org>1997-07-29 15:40:30 -0700
committerPer Bothner <bothner@gcc.gnu.org>1997-07-29 15:40:30 -0700
commite3d1fd3263e5c0c5aa66bef848d829139029dc77 (patch)
treef72535174d01e86fc9e15923b22fdb881128d053 /gcc
parentb4294351090fb3fd736b6f1b8cb0861971818079 (diff)
downloadgcc-e3d1fd3263e5c0c5aa66bef848d829139029dc77.zip
gcc-e3d1fd3263e5c0c5aa66bef848d829139029dc77.tar.gz
gcc-e3d1fd3263e5c0c5aa66bef848d829139029dc77.tar.bz2
Patches to use cpplib with cc1 #if USE_CPPLIB.
From-SVN: r14557
Diffstat (limited to 'gcc')
-rw-r--r--gcc/c-lex.c366
-rw-r--r--gcc/toplev.c13
2 files changed, 278 insertions, 101 deletions
diff --git a/gcc/c-lex.c b/gcc/c-lex.c
index b9c2190..c3c4d0e 100644
--- a/gcc/c-lex.c
+++ b/gcc/c-lex.c
@@ -44,6 +44,13 @@ Boston, MA 02111-1307, USA. */
extern int errno;
#endif
+#if USE_CPPLIB
+#include "cpplib.h"
+cpp_reader parse_in;
+cpp_options parse_options;
+static enum cpp_token cpp_token;
+#endif
+
/* The elements of `ridpointers' are identifier nodes
for the reserved type names and storage classes.
It is indexed by a RID_... value. */
@@ -52,6 +59,32 @@ tree ridpointers[(int) RID_MAX];
/* Cause the `yydebug' variable to be defined. */
#define YYDEBUG 1
+#if USE_CPPLIB
+static unsigned char *yy_cur, *yy_lim;
+
+int
+yy_get_token ()
+{
+ for (;;)
+ {
+ parse_in.limit = parse_in.token_buffer;
+ cpp_token = cpp_get_token (&parse_in);
+ if (cpp_token == CPP_EOF)
+ return -1;
+ yy_lim = CPP_PWRITTEN (&parse_in);
+ yy_cur = parse_in.token_buffer;
+ if (yy_cur < yy_lim)
+ return *yy_cur++;
+ }
+}
+
+#define GETC() (yy_cur < yy_lim ? *yy_cur++ : yy_get_token ())
+#define UNGETC(c) ((c), yy_cur--)
+#else
+#define GETC() getc (finput)
+#define UNGETC(c) ungetc (c, finput)
+#endif
+
/* the declaration found for the last IDENTIFIER token read in.
yylex must look this up to detect typedefs, which get token type TYPENAME,
so it is left around in case the identifier is not a typedef but is
@@ -88,8 +121,10 @@ char *token_buffer; /* Pointer to token buffer.
/* Nonzero if end-of-file has been seen on input. */
static int end_of_file;
+#if !USE_CPPLIB
/* Buffered-back input character; faster than using ungetc. */
static int nextchar = -1;
+#endif
int check_newline ();
@@ -142,6 +177,31 @@ remember_protocol_qualifiers ()
wordlist[i].name = "oneway";
}
+#if USE_CPPLIB
+void
+init_parse (filename)
+ char *filename;
+{
+ init_lex ();
+ yy_cur = "\n";
+ yy_lim = yy_cur+1;
+
+ cpp_reader_init (&parse_in);
+ parse_in.data = &parse_options;
+ cpp_options_init (&parse_options);
+ cpp_handle_options (&parse_in, 0, NULL); /* FIXME */
+ parse_in.show_column = 1;
+ if (! cpp_start_read (&parse_in, filename))
+ abort ();
+}
+
+void
+finish_parse ()
+{
+ cpp_finish (&parse_in);
+}
+#endif
+
void
init_lex ()
{
@@ -289,7 +349,7 @@ skip_white_space (c)
case '\f':
case '\v':
case '\b':
- c = getc (finput);
+ c = GETC();
break;
case '\r':
@@ -301,16 +361,16 @@ skip_white_space (c)
warning ("(we only warn about the first carriage return)");
newline_warning = 1;
}
- c = getc (finput);
+ c = GETC();
break;
case '\\':
- c = getc (finput);
+ c = GETC();
if (c == '\n')
lineno++;
else
error ("stray '\\' in program");
- c = getc (finput);
+ c = GETC();
break;
default:
@@ -327,12 +387,14 @@ position_after_white_space ()
{
register int c;
+#if !USE_CPPLIB
if (nextchar != -1)
c = nextchar, nextchar = -1;
else
- c = getc (finput);
+#endif
+ c = GETC();
- ungetc (skip_white_space (c), finput);
+ UNGETC (skip_white_space (c));
}
/* Make the token buffer longer, preserving the data in it.
@@ -351,6 +413,89 @@ extend_token_buffer (p)
return token_buffer + offset;
}
+
+
+#if !USE_CPPLIB
+#define GET_DIRECTIVE_LINE() get_directive_line (finput)
+#else /* USE_CPPLIB */
+/* Read the rest of a #-directive from input stream FINPUT.
+ In normal use, the directive name and the white space after it
+ have already been read, so they won't be included in the result.
+ We allow for the fact that the directive line may contain
+ a newline embedded within a character or string literal which forms
+ a part of the directive.
+
+ The value is a string in a reusable buffer. It remains valid
+ only until the next time this function is called. */
+
+static char *
+GET_DIRECTIVE_LINE ()
+{
+ static char *directive_buffer = NULL;
+ static unsigned buffer_length = 0;
+ register char *p;
+ register char *buffer_limit;
+ register int looking_for = 0;
+ register int char_escaped = 0;
+
+ if (buffer_length == 0)
+ {
+ directive_buffer = (char *)xmalloc (128);
+ buffer_length = 128;
+ }
+
+ buffer_limit = &directive_buffer[buffer_length];
+
+ for (p = directive_buffer; ; )
+ {
+ int c;
+
+ /* Make buffer bigger if it is full. */
+ if (p >= buffer_limit)
+ {
+ register unsigned bytes_used = (p - directive_buffer);
+
+ buffer_length *= 2;
+ directive_buffer
+ = (char *)xrealloc (directive_buffer, buffer_length);
+ p = &directive_buffer[bytes_used];
+ buffer_limit = &directive_buffer[buffer_length];
+ }
+
+ c = GETC ();
+
+ /* Discard initial whitespace. */
+ if ((c == ' ' || c == '\t') && p == directive_buffer)
+ continue;
+
+ /* Detect the end of the directive. */
+ if (c == '\n' && looking_for == 0)
+ {
+ UNGETC (c);
+ c = '\0';
+ }
+
+ *p++ = c;
+
+ if (c == 0)
+ return directive_buffer;
+
+ /* Handle string and character constant syntax. */
+ if (looking_for)
+ {
+ if (looking_for == c && !char_escaped)
+ looking_for = 0; /* Found terminator... stop looking. */
+ }
+ else
+ if (c == '\'' || c == '"')
+ looking_for = c; /* Don't stop buffering until we see another
+ another one of these (or an EOF). */
+
+ /* Handle backslash. */
+ char_escaped = (c == '\\' && ! char_escaped);
+ }
+}
+#endif /* USE_CPPLIB */
/* At the beginning of a line, increment the line number
and process any #-directive on this line.
@@ -367,9 +512,9 @@ check_newline ()
/* Read first nonwhite char on the line. */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
if (c != '#')
{
@@ -379,9 +524,9 @@ check_newline ()
/* Read first nonwhite char after the `#'. */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
/* If a letter follows, then if the word here is `line', skip
it and ignore it; otherwise, ignore the line, with an error
@@ -391,34 +536,38 @@ check_newline ()
{
if (c == 'p')
{
- if (getc (finput) == 'r'
- && getc (finput) == 'a'
- && getc (finput) == 'g'
- && getc (finput) == 'm'
- && getc (finput) == 'a'
- && ((c = getc (finput)) == ' ' || c == '\t' || c == '\n'))
+ if (GETC() == 'r'
+ && GETC() == 'a'
+ && GETC() == 'g'
+ && GETC() == 'm'
+ && GETC() == 'a'
+ && ((c = GETC()) == ' ' || c == '\t' || c == '\n'))
{
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC ();
if (c == '\n')
return c;
#ifdef HANDLE_SYSV_PRAGMA
- ungetc (c, finput);
+ UNGETC (c);
token = yylex ();
if (token != IDENTIFIER)
goto skipline;
- return handle_sysv_pragma (finput, token);
+ return handle_sysv_pragma (token);
#else /* !HANDLE_SYSV_PRAGMA */
#ifdef HANDLE_PRAGMA
- ungetc (c, finput);
+#if !USE_CPPLIB
+ UNGETC (c);
token = yylex ();
if (token != IDENTIFIER)
goto skipline;
- if (HANDLE_PRAGMA (finput, yylval.ttype))
+ if (HANDLE_PRAGMA (yylval.ttype))
{
- c = getc (finput);
+ c = GETC ();
return c;
}
+#else
+ ??? do not know what to do ???;
+#endif /* !USE_CPPLIB */
#endif /* HANDLE_PRAGMA */
#endif /* !HANDLE_SYSV_PRAGMA */
goto skipline;
@@ -427,46 +576,46 @@ check_newline ()
else if (c == 'd')
{
- if (getc (finput) == 'e'
- && getc (finput) == 'f'
- && getc (finput) == 'i'
- && getc (finput) == 'n'
- && getc (finput) == 'e'
- && ((c = getc (finput)) == ' ' || c == '\t' || c == '\n'))
+ if (GETC() == 'e'
+ && GETC() == 'f'
+ && GETC() == 'i'
+ && GETC() == 'n'
+ && GETC() == 'e'
+ && ((c = GETC()) == ' ' || c == '\t' || c == '\n'))
{
if (c != '\n')
- debug_define (lineno, get_directive_line (finput));
+ debug_define (lineno, GET_DIRECTIVE_LINE ());
goto skipline;
}
}
else if (c == 'u')
{
- if (getc (finput) == 'n'
- && getc (finput) == 'd'
- && getc (finput) == 'e'
- && getc (finput) == 'f'
- && ((c = getc (finput)) == ' ' || c == '\t' || c == '\n'))
+ if (GETC() == 'n'
+ && GETC() == 'd'
+ && GETC() == 'e'
+ && GETC() == 'f'
+ && ((c = GETC()) == ' ' || c == '\t' || c == '\n'))
{
if (c != '\n')
- debug_undef (lineno, get_directive_line (finput));
+ debug_undef (lineno, GET_DIRECTIVE_LINE ());
goto skipline;
}
}
else if (c == 'l')
{
- if (getc (finput) == 'i'
- && getc (finput) == 'n'
- && getc (finput) == 'e'
- && ((c = getc (finput)) == ' ' || c == '\t'))
+ if (GETC() == 'i'
+ && GETC() == 'n'
+ && GETC() == 'e'
+ && ((c = GETC()) == ' ' || c == '\t'))
goto linenum;
}
else if (c == 'i')
{
- if (getc (finput) == 'd'
- && getc (finput) == 'e'
- && getc (finput) == 'n'
- && getc (finput) == 't'
- && ((c = getc (finput)) == ' ' || c == '\t'))
+ if (GETC() == 'd'
+ && GETC() == 'e'
+ && GETC() == 'n'
+ && GETC() == 't'
+ && ((c = GETC()) == ' ' || c == '\t'))
{
/* #ident. The pedantic warning is now in cccp.c. */
@@ -474,13 +623,13 @@ check_newline ()
A string constant should follow. */
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
/* If no argument, ignore the line. */
if (c == '\n')
return c;
- ungetc (c, finput);
+ UNGETC (c);
token = yylex ();
if (token != STRING
|| TREE_CODE (yylval.ttype) != STRING_CST)
@@ -510,7 +659,7 @@ linenum:
In either case, it should be a line number; a digit should follow. */
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
/* If the # is the only nonwhite char on the line,
just ignore it. Check the new newline. */
@@ -519,7 +668,7 @@ linenum:
/* Something follows the #; read a token. */
- ungetc (c, finput);
+ UNGETC (c);
token = yylex ();
if (token == CONSTANT
@@ -533,16 +682,16 @@ linenum:
int l = TREE_INT_CST_LOW (yylval.ttype) - 1;
/* Is this the last nonwhite stuff on the line? */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
if (c == '\n')
{
/* No more: store the line number and check following line. */
lineno = l;
return c;
}
- ungetc (c, finput);
+ UNGETC (c);
/* More follows: it must be a string constant (filename). */
@@ -568,9 +717,9 @@ linenum:
main_input_filename = input_filename;
/* Is this the last nonwhite stuff on the line? */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
if (c == '\n')
{
/* Update the name in the top element of input_file_stack. */
@@ -579,7 +728,7 @@ linenum:
return c;
}
- ungetc (c, finput);
+ UNGETC (c);
token = yylex ();
used_up = 0;
@@ -631,12 +780,12 @@ linenum:
if (used_up)
{
/* Is this the last nonwhite stuff on the line? */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
if (c == '\n')
return c;
- ungetc (c, finput);
+ UNGETC (c);
token = yylex ();
used_up = 0;
@@ -652,12 +801,12 @@ linenum:
if (used_up)
{
/* Is this the last nonwhite stuff on the line? */
- c = getc (finput);
+ c = GETC();
while (c == ' ' || c == '\t')
- c = getc (finput);
+ c = GETC();
if (c == '\n')
return c;
- ungetc (c, finput);
+ UNGETC (c);
}
warning ("unrecognized text at end of #line");
@@ -668,22 +817,32 @@ linenum:
/* skip the rest of this line. */
skipline:
while (c != '\n' && c != EOF)
- c = getc (finput);
+ c = GETC();
return c;
}
+
+void
+lang_init ()
+{
+#if !USE_CPPLIB
+ /* the beginning of the file is a new line; check for # */
+ /* With luck, we discover the real source file's name from that
+ and put it in input_filename. */
+ UNGETC (check_newline ());
+#endif
+}
#ifdef HANDLE_SYSV_PRAGMA
-/* Handle a #pragma directive. INPUT is the current input stream,
- and TOKEN is the token we read after `#pragma'. Processes the entire input
+/* Handle a #pragma directive.
+ TOKEN is the token we read after `#pragma'. Processes the entire input
line and returns a character for the caller to reread: either \n or EOF. */
/* This function has to be in this file, in order to get at
the token types. */
int
-handle_sysv_pragma (input, token)
- FILE *input;
+handle_sysv_pragma (token)
register int token;
{
register int c;
@@ -701,20 +860,21 @@ handle_sysv_pragma (input, token)
default:
handle_pragma_token (token_buffer, 0);
}
-
+#if !USE_CPPLIB
if (nextchar >= 0)
c = nextchar, nextchar = -1;
else
- c = getc (input);
+#endif
+ c = GETC ();
while (c == ' ' || c == '\t')
- c = getc (input);
+ c = GETC ();
if (c == '\n' || c == EOF)
{
handle_pragma_token (0, 0);
return c;
}
- ungetc (c, input);
+ UNGETC (c);
token = yylex ();
}
}
@@ -730,7 +890,7 @@ static int
readescape (ignore_ptr)
int *ignore_ptr;
{
- register int c = getc (finput);
+ register int c = GETC();
register int code;
register unsigned count;
unsigned firstdig = 0;
@@ -750,12 +910,12 @@ readescape (ignore_ptr)
nonnull = 0;
while (1)
{
- c = getc (finput);
+ c = GETC();
if (!(c >= 'a' && c <= 'f')
&& !(c >= 'A' && c <= 'F')
&& !(c >= '0' && c <= '9'))
{
- ungetc (c, finput);
+ UNGETC (c);
break;
}
code *= 16;
@@ -792,9 +952,9 @@ readescape (ignore_ptr)
while ((c <= '7') && (c >= '0') && (count++ < 3))
{
code = (code * 8) + (c - '0');
- c = getc (finput);
+ c = GETC();
}
- ungetc (c, finput);
+ UNGETC (c);
return code;
case '\\': case '\'': case '"':
@@ -918,10 +1078,12 @@ yylex ()
int wide_flag = 0;
int objc_flag = 0;
+#if !USE_CPPLIB
if (nextchar >= 0)
c = nextchar, nextchar = -1;
else
- c = getc (finput);
+#endif
+ c = GETC();
/* Effectively do c = skip_white_space (c)
but do it faster in the usual cases. */
@@ -933,7 +1095,7 @@ yylex ()
case '\f':
case '\v':
case '\b':
- c = getc (finput);
+ c = GETC();
break;
case '\r':
@@ -964,7 +1126,7 @@ yylex ()
case 'L':
/* Capital L may start a wide-string or wide-character constant. */
{
- register int c = getc (finput);
+ register int c = GETC();
if (c == '\'')
{
wide_flag = 1;
@@ -975,7 +1137,7 @@ yylex ()
wide_flag = 1;
goto string_constant;
}
- ungetc (c, finput);
+ UNGETC (c);
}
goto letter;
@@ -988,13 +1150,13 @@ yylex ()
else
{
/* '@' may start a constant string object. */
- register int c = getc(finput);
+ register int c = GETC ();
if (c == '"')
{
objc_flag = 1;
goto string_constant;
}
- ungetc(c, finput);
+ UNGETC (c);
/* Fall through to treat '@' as the start of an identifier. */
}
@@ -1031,11 +1193,15 @@ yylex ()
p = extend_token_buffer (p);
*p++ = c;
- c = getc (finput);
+ c = GETC();
}
*p = 0;
+#if USE_CPPLIB
+ UNGETC (c);
+#else
nextchar = c;
+#endif
value = IDENTIFIER;
yylval.itype = 0;
@@ -1120,8 +1286,8 @@ yylex ()
int next_c;
/* Check first for common special case: single-digit 0 or 1. */
- next_c = getc (finput);
- ungetc (next_c, finput); /* Always undo this lookahead. */
+ next_c = GETC ();
+ UNGETC (next_c); /* Always undo this lookahead. */
if (!isalnum (next_c) && next_c != '.')
{
token_buffer[0] = (char)c, token_buffer[1] = '\0';
@@ -1160,11 +1326,11 @@ yylex ()
if (c == '0')
{
- *p++ = (c = getc (finput));
+ *p++ = (c = GETC());
if ((c == 'x') || (c == 'X'))
{
base = 16;
- *p++ = (c = getc (finput));
+ *p++ = (c = GETC());
}
/* Leading 0 forces octal unless the 0 is the only digit. */
else if (c >= '0' && c <= '9')
@@ -1203,7 +1369,7 @@ yylex ()
floatflag = AFTER_POINT;
base = 10;
- *p++ = c = getc (finput);
+ *p++ = c = GETC();
/* Accept '.' as the start of a floating-point number
only when it is followed by a digit.
Otherwise, unread the following non-digit
@@ -1212,7 +1378,7 @@ yylex ()
{
if (c == '.')
{
- c = getc (finput);
+ c = GETC();
if (c == '.')
{
*p++ = c;
@@ -1221,7 +1387,7 @@ yylex ()
}
error ("parse error at `..'");
}
- ungetc (c, finput);
+ UNGETC (c);
token_buffer[1] = 0;
value = '.';
goto done;
@@ -1280,7 +1446,7 @@ yylex ()
if (p >= token_buffer + maxtoken - 3)
p = extend_token_buffer (p);
- *p++ = (c = getc (finput));
+ *p++ = (c = GETC());
}
}
@@ -1308,11 +1474,11 @@ yylex ()
if (p >= token_buffer + maxtoken - 3)
p = extend_token_buffer (p);
*p++ = c;
- c = getc (finput);
+ c = GETC();
if ((c == '+') || (c == '-'))
{
*p++ = c;
- c = getc (finput);
+ c = GETC();
}
if (! isdigit (c))
error ("floating constant exponent has no digits");
@@ -1321,7 +1487,7 @@ yylex ()
if (p >= token_buffer + maxtoken - 3)
p = extend_token_buffer (p);
*p++ = c;
- c = getc (finput);
+ c = GETC();
}
}
@@ -1383,7 +1549,7 @@ yylex ()
p = extend_token_buffer (p);
*p++ = c;
*p = 0;
- c = getc (finput);
+ c = GETC();
}
/* The second argument, machine_mode, of REAL_VALUE_ATOF
@@ -1490,7 +1656,7 @@ yylex ()
if (p >= token_buffer + maxtoken - 3)
p = extend_token_buffer (p);
*p++ = c;
- c = getc (finput);
+ c = GETC();
}
/* If the constant is not long long and it won't fit in an
@@ -1631,7 +1797,7 @@ yylex ()
TREE_TYPE (yylval.ttype) = type;
}
- ungetc (c, finput);
+ UNGETC (c);
*p = 0;
if (isalnum (c) || c == '.' || c == '_' || c == '$'
@@ -1666,7 +1832,7 @@ yylex ()
{
tryagain:
- c = getc (finput);
+ c = GETC();
if (c == '\'' || c == EOF)
break;
@@ -1776,7 +1942,7 @@ yylex ()
case '"':
string_constant:
{
- c = getc (finput);
+ c = GETC();
p = token_buffer + 1;
while (c != '"' && c >= 0)
@@ -1804,7 +1970,7 @@ yylex ()
*p++ = c;
skipnewline:
- c = getc (finput);
+ c = GETC();
}
*p = 0;
@@ -1918,7 +2084,7 @@ yylex ()
yylval.code = GT_EXPR; break;
}
- token_buffer[1] = c1 = getc (finput);
+ token_buffer[1] = c1 = GETC();
token_buffer[2] = 0;
if (c1 == '=')
@@ -1976,7 +2142,7 @@ yylex ()
{ value = '}'; goto done; }
break;
}
- ungetc (c1, finput);
+ UNGETC (c1);
token_buffer[1] = 0;
if ((c == '<') || (c == '>'))
diff --git a/gcc/toplev.c b/gcc/toplev.c
index 5f640c7..cb11ab4 100644
--- a/gcc/toplev.c
+++ b/gcc/toplev.c
@@ -209,9 +209,10 @@ char *input_filename;
char *main_input_filename;
+#if !USE_CPPLIB
/* Stream for reading from the input file. */
-
FILE *finput;
+#endif
/* Current line number in real source file. */
@@ -2123,6 +2124,7 @@ compile_file (name)
symout_time = 0;
dump_time = 0;
+#if !USE_CPPLIB
/* Open input file. */
if (name == 0 || !strcmp (name, "-"))
@@ -2138,12 +2140,17 @@ compile_file (name)
#ifdef IO_BUFFER_SIZE
setvbuf (finput, (char *) xmalloc (IO_BUFFER_SIZE), _IOFBF, IO_BUFFER_SIZE);
#endif
+#endif /* !USE_CPPLIB */
/* Initialize data in various passes. */
init_obstacks ();
init_tree_codes ();
+#if USE_CPPLIB
+ init_parse (name);
+#else
init_lex ();
+#endif
/* Some of these really don't need to be called when generating bytecode,
but the options would have to be parsed first to know that. -bson */
init_rtl ();
@@ -2722,7 +2729,11 @@ compile_file (name)
whether fclose returns an error, since the pages might still be on the
buffer chain while the file is open. */
+#if USE_CPPLIB
+ finish_parse ();
+#else
fclose (finput);
+#endif
if (ferror (asm_out_file) != 0 || fclose (asm_out_file) != 0)
fatal_io_error (asm_file_name);