Init
This commit is contained in:
130
lang/cpp/Makefile
Normal file
130
lang/cpp/Makefile
Normal file
@@ -0,0 +1,130 @@
|
||||
#
|
||||
# @(#)Makefile 1.1 94/10/31 SMI; from S5R2 1.9
|
||||
#
|
||||
|
||||
INS = install
|
||||
INSDIR = $(DESTDIR)/usr/lib
|
||||
#
|
||||
# Note: if the installed cpp doesn't know about -undef, do
|
||||
# rm cpp.o; make UNDEF="" ; make install
|
||||
# (/lib/cpp now knows about -undef, but may have bogus predefinitions)
|
||||
# rm cpp.o; make install
|
||||
# (/lib/cpp now knows about -undef, but predefines only the names below)
|
||||
#
|
||||
|
||||
cpu-sun2 = m68k
|
||||
cpu-sun3 = m68k
|
||||
cpu-sun3x = m68k
|
||||
cpu-sun4 = sparc
|
||||
cpu-sun4d = sparc
|
||||
cpu-sun386 = i386
|
||||
CPU = $(cpu$(TARGET_ARCH))
|
||||
|
||||
# To turn off the code browser, remove the following line.
|
||||
BROWSER = -DBROWSER
|
||||
BROWSER_DIR = ../browser/cblib
|
||||
BROWSER_BIN_DIR = $(BROWSER_DIR)/$(CPU)
|
||||
BROWSER_SRC_DIR = $(BROWSER_DIR)/src
|
||||
|
||||
BROWSER_LIB-DBROWSER = $(BROWSER_BIN_DIR)/libcb.a
|
||||
BROWSER_LIBRARY = $(BROWSER_LIB$(BROWSER))
|
||||
BROWSER_INCL-DBROWSER = -I$(BROWSER_SRC_DIR)
|
||||
BROWSER_FLAGS = $(BROWSER) $(BROWSER_INCL$(BROWSER))
|
||||
|
||||
|
||||
YACC = /usr/bin/yacc
|
||||
VROOT = ../vroot
|
||||
VROOTLIB = $(VROOT)/vroot.a
|
||||
CPPFLAGS = -DSUNPRO -DFLEXNAMES -I$(VROOT) $(BROWSER_FLAGS)
|
||||
COPTS = -O
|
||||
DBX = # Use 'make DBX=-g' for debuggable version
|
||||
CFLAGS = $(COPTS) $(CPPFLAGS) $(DBX)
|
||||
UNDEF = -Qoption cpp -undef
|
||||
SUNDEFS = -Dunix -Dsun
|
||||
SRCS = cpy.c cpp.c
|
||||
HDRS = $(VROOT)/vroot.h $(VROOT)/report.h
|
||||
# TARGET is the same as the host, by default, but may be overridden in the
|
||||
# "make" command line for a cross-preprocessor.
|
||||
TARGET:sh = arch
|
||||
|
||||
.DEFAULT:
|
||||
sccs get -G$@ $@
|
||||
|
||||
cpp : cpp.o cpy.o rodata.o yylex.o $(VROOTLIB)
|
||||
$(CC) $(LDFLAGS) $(DBX) -o cpp cpp.o rodata.o cpy.o yylex.o $(VROOTLIB)
|
||||
|
||||
cpp.o cpy.o: $(HDRS)
|
||||
|
||||
y.tab.h cpy.c : cpy.y yyfix.sh
|
||||
$(YACC) -d cpy.y
|
||||
/bin/sh ./yyfix.sh yyexca yyact yypact yypgo yyr1 yyr2 yychk yydef
|
||||
mv y.tab.c cpy.c
|
||||
|
||||
cpp.o : cpp.c $(BROWSER_LIBRARY)
|
||||
@set -x; case ${TARGET} in \
|
||||
sun2) \
|
||||
$(CC) $(CFLAGS) $(UNDEF) $(SUNDEFS) \
|
||||
-Dmc68000 -Dmc68010 -Umc68020 -Usparc -Ui386 -c cpp.c;;\
|
||||
sun3 | sun3? ) \
|
||||
$(CC) $(CFLAGS) $(UNDEF) $(SUNDEFS) \
|
||||
-Dmc68000 -Umc68010 -Dmc68020 -Usparc -Ui386 -c cpp.c;;\
|
||||
sun4*) \
|
||||
$(CC) $(CFLAGS) $(UNDEF) $(SUNDEFS) \
|
||||
-Umc68000 -Umc68010 -Umc68020 -Dsparc -Ui386 -c cpp.c;;\
|
||||
sun386) \
|
||||
$(CC) $(CFLAGS) $(UNDEF) $(SUNDEFS) \
|
||||
-Umc68000 -Umc68010 -Umc68020 -Usparc -Di386 -c cpp.c;;\
|
||||
* ) \
|
||||
echo 'Unknown machine???'; exit 2;;\
|
||||
esac
|
||||
|
||||
rodata.o : cpy.c
|
||||
$(CC) $(CFLAGS) -R -c rodata.c
|
||||
|
||||
$(HDRS) $(VROOTLIB): FRC
|
||||
cd $(@D); $(MAKE) $(@F)
|
||||
|
||||
$(BROWSER_BIN_DIR)/libcb.a: FRC
|
||||
cd $(@D); $(MAKE) $(@F)
|
||||
|
||||
FRC:
|
||||
|
||||
clean :
|
||||
rm -f *.s *.o
|
||||
rm -f cpy.c rodata.c cpp
|
||||
|
||||
install : cpp
|
||||
$(INS) -s cpp $(INSDIR)
|
||||
|
||||
depend: $(SRCS) $(HDRS) yylex.c
|
||||
rm -f makedep
|
||||
for i in $(SRCS) yylex.c; do \
|
||||
( $(CC) -M $(CPPFLAGS) $$i >> makedep ); \
|
||||
done
|
||||
echo '/^# DO NOT DELETE THIS LINE/+2,$$d' >eddep
|
||||
echo '$$r makedep' >>eddep
|
||||
echo 'w' >>eddep
|
||||
cp Makefile Makefile.bak
|
||||
ed - Makefile < eddep
|
||||
echo '# DEPENDENCIES MUST END AT END OF FILE' >> Makefile
|
||||
echo '# IF YOU PUT STUFF HERE IT WILL GO AWAY' >> Makefile
|
||||
echo '# see make depend above' >> Makefile
|
||||
rm -f eddep makedep
|
||||
|
||||
# DO NOT DELETE THIS LINE -- make depend uses it
|
||||
|
||||
cpy.o: cpy.c
|
||||
cpp.o: cpp.c
|
||||
cpp.o: /usr/include/stdio.h
|
||||
cpp.o: /usr/include/ctype.h
|
||||
cpp.o: /usr/include/sys/file.h
|
||||
cpp.o: /usr/include/sys/fcntlcom.h
|
||||
cpp.o: ../vroot/vroot.h
|
||||
cpp.o: /usr/include/stdio.h
|
||||
cpp.o: ../vroot/report.h
|
||||
cpp.o: /usr/include/stdio.h
|
||||
yylex.o: yylex.c
|
||||
yylex.o: ./y.tab.h
|
||||
# DEPENDENCIES MUST END AT END OF FILE
|
||||
# IF YOU PUT STUFF HERE IT WILL GO AWAY
|
||||
# see make depend above
|
||||
206
lang/cpp/README
Normal file
206
lang/cpp/README
Normal file
@@ -0,0 +1,206 @@
|
||||
#
|
||||
# @(#)README 1.1 94/10/31 SMI; from S5R2 1.2
|
||||
#
|
||||
|
||||
December 20, 1985
|
||||
Fixed by Vida Ghodssi, Guy Harris, Sun Microsystems
|
||||
System V version installed; faster, fixes many bugs (including Gilmore's
|
||||
"can't feed 'cpp's output to itself" bug, mentioned below).
|
||||
4.3BSD "-M" option added.
|
||||
|
||||
August 1, 1985
|
||||
Fixed by Vida Ghodssi, Sun Microsystems
|
||||
Remove the limit on the number of symbols handeled by the symbol table.
|
||||
This was done by making the symbol table bucket based rather than an array
|
||||
of fixed size.
|
||||
|
||||
December 16, 1983
|
||||
Fixed by John Gilmore, Sun Microsystems
|
||||
Remove the limit on the number of -D and -U options, by scanning them
|
||||
directly out of argc/argv when needed. Minor change in effect: previously
|
||||
a -U would override a -D even if the -D followed the -U on the command line.
|
||||
e.g. cpp -Ufoo -Dfoo=3 would leave foo undefined. This has been changed
|
||||
to process them in the specified order, leaving foo defined as 3. However,
|
||||
cpp -Dfoo=3 -Ufoo still leaves foo undefined, as it did before.
|
||||
BUG REPORT: cpp should accept lines of the form "# n name" as equivalent to
|
||||
"#line n name" since otherwise you can't run its output back thru itself.
|
||||
Silly for a filter.
|
||||
|
||||
August 30, 1982
|
||||
Fixed by Kurt Shoens, UCB
|
||||
If the "#line n name" occurs, then all future references
|
||||
to the current file are generated in terms of "name", instead
|
||||
of the name of file given to cpp in its command argument
|
||||
|
||||
August 25, 1978 updated to November 29, 1982
|
||||
|
||||
Files in this directory form the C preprocessor, which handles '#include'
|
||||
files and macro definition and expansion for the C compiler.
|
||||
This new version is from 5 to 12 times faster (on UNIX systems) than the old.
|
||||
|
||||
To create the executable file 'cpp' in the current directory:
|
||||
make
|
||||
|
||||
To install the preprocessor 'cpp' so it will be used by the C compiler:
|
||||
# safety first: backup the existing version
|
||||
cp /lib/cpp /lib/ocpp
|
||||
# install the new version
|
||||
cp cpp /lib/cpp
|
||||
|
||||
Invocation
|
||||
cpp [-CEPRM] [-Dname] ... [-Dname=def] ... [-Idirectory] ...
|
||||
[-Uname] ... [<infile> [<outfile>]]
|
||||
|
||||
If there are two non-flag arguments then the first is the name of the
|
||||
input file and the second is the name of the output file. If there is
|
||||
one non-flag argument then it is the name of the input file and the
|
||||
output is written on the standard output. If there are no non-flag
|
||||
arguments then the input is taken from the standard input and the output
|
||||
is written on the standard output. Flag arguments are:
|
||||
|
||||
-C retain comments in output
|
||||
-Dname define name as "1"
|
||||
-Dname=def define name as def
|
||||
-E ignored
|
||||
-Idirectory add directory to search list for #include files
|
||||
-M generate Makefile dependencies (-C and -M ignored)
|
||||
-P don't insert lines "# 12 \"foo.c\"" into output
|
||||
-R allow recursive macros
|
||||
-Uname undefine name
|
||||
|
||||
Documentation clarifications:
|
||||
Symbols defined on the command line by "-Dfoo" are defined as "1",
|
||||
i.e., as if they had been defined by "#define foo 1" or
|
||||
"-Dfoo=1".
|
||||
The directory search order for #include files is
|
||||
1) the directory of the file which contains the #include request
|
||||
(e.g. #include is relative to the file being scanned when
|
||||
the request is made)
|
||||
2) the directories specified by -I, in left-to-right order
|
||||
3) the standard directory(s) (which for UNIX is /usr/include)
|
||||
An unescaped linefeed (the single character "\n") terminates a
|
||||
character constant or quoted string.
|
||||
An escaped linefeed (the two-character sequence "\\\n") may be
|
||||
used in the body of a '#define' statement to continue
|
||||
the definition onto the next line. The escaped linefeed is
|
||||
converted into a single blank in the macro body.
|
||||
Comments are uniformly removed (except if the argument -C is specified).
|
||||
They are also ignored, except that a comment terminates a token.
|
||||
Thus "foo/* la di da */bar" may expand 'foo' and 'bar' but
|
||||
will never expand 'foobar'. If neither 'foo' nor 'bar' is a
|
||||
macro then the output is "foobar", even if 'foobar'
|
||||
is defined as something else. The file
|
||||
#define foo(a,b)b/**/a
|
||||
foo(1,2)
|
||||
produces "21" because the comment causes a break which enables
|
||||
the recognition of 'b' and 'a' as formals in the string
|
||||
"b/**/a".
|
||||
Macro formal parameters are recognized in '#define' bodies even inside
|
||||
character constants and quoted strings. The output from
|
||||
#define foo(a) '\a'
|
||||
foo(bar)
|
||||
is the six characters "'\\bar'". Macro names are not recognized
|
||||
inside character constants or quoted strings during the
|
||||
regular scan.
|
||||
Thus
|
||||
#define foo bar
|
||||
printf("foo");
|
||||
does not expand 'foo' in the second line, because it is inside
|
||||
a quoted string which is not part of a '#define' macro
|
||||
definition.
|
||||
Macros are not expanded while processing a '#define' or '#undef'.
|
||||
Thus
|
||||
#define foo bletch
|
||||
#define bar foo
|
||||
#undef foo
|
||||
bar
|
||||
produces "foo". The token appearing immediately after a
|
||||
'#ifdef' or '#ifndef' is not expanded (of course!).
|
||||
Macros are not expanded during the scan which determines the actual
|
||||
parameters to another macro call. Thus
|
||||
| #define foo(a,b)b a
|
||||
| #define bar hi
|
||||
| foo(bar,
|
||||
| #define bar bye
|
||||
| )
|
||||
|produces " bye" (and warns about the redefinition of 'bar').
|
||||
|--->not any longer. Newlines have been stripped by now, so
|
||||
the # is no longer at the beginning of a line.
|
||||
The note is still true, though. When a macro is expanded,
|
||||
the first step is to put the actual arguments in the
|
||||
corresponding locations in the token-string the macro
|
||||
is defined to be. The next step is to start to re-
|
||||
process the token-string as input text.
|
||||
|
||||
There are some differences between the new and the old preprocessor.
|
||||
Bugs fixed:
|
||||
"1.e4" is recognized as a floating-point number, rather than as an
|
||||
opportunity to expand the possible macro name "e4".
|
||||
Any kind and amount of white space (space, tab, linefeed, vertical tab,
|
||||
formfeed, carriage return) is allowed between a macro name and
|
||||
the left parenthesis which introduces its actual parameters.
|
||||
The comma operator is legal in preprocessor '#if' statements.
|
||||
Macros with parameters are legal in preprocessor '#if' statements.
|
||||
Single-character character constants are legal in preprocessor '#if'
|
||||
statements.
|
||||
Linefeeds are put out in the proper place when a multiline comment
|
||||
is not passed through to the output.
|
||||
The following example expands to "# # #" :
|
||||
#define foo #
|
||||
foo foo foo
|
||||
If the -R flag is not specified then the invocation of some recursive
|
||||
macros is trapped and the recursion forcibly terminated with an
|
||||
error message. The recursions that are trapped are the ones
|
||||
in which the nesting level is non-decreasing from some point on.
|
||||
In particular,
|
||||
#define a a
|
||||
a
|
||||
will be detected. (Use "#undef a" if that is what you want.)
|
||||
The recursion
|
||||
#define a c b
|
||||
#define b c a
|
||||
#define c foo
|
||||
a
|
||||
will not be detected because the nesting level decreases after
|
||||
each expansion of "c".
|
||||
The -R flag specifically allows recursive macros and recursion will
|
||||
be strictly obeyed (to the extent that space is available).
|
||||
Assuming that -R is specified:
|
||||
#define a a
|
||||
a
|
||||
causes an infinite loop with very little output. The tail
|
||||
recursion
|
||||
#define a <b
|
||||
#define b >a
|
||||
a
|
||||
causes the string "<>" to be output infinitely many times. The
|
||||
non-tail recursion
|
||||
#define a b>
|
||||
#define b a<
|
||||
a
|
||||
complains "too much pushback", dumps the pushback, and continues
|
||||
(again, infinitely).
|
||||
|
||||
Stylistic choice:
|
||||
Nothing (not even linefeeds) is output while a false '#if', '#ifdef',
|
||||
or '#ifndef' is in effect. Thus when all conditions become true
|
||||
a line of the form "# 12345 \"foo.c\"" is output (unless -P).
|
||||
Error and warning messages always appear on standard error (file
|
||||
descriptor 2).
|
||||
Mismatch between the number of formals and actuals in a macro call
|
||||
produces only a warning, and not an error. Excess actuals
|
||||
are ignored; missing actuals are turned into null strings.
|
||||
Comments which worked their way into #if lines no longer cause a
|
||||
syntax error.
|
||||
Newlines found during the scan for actual arguments are changed to
|
||||
blanks so that confusing (for cpp) situations did not occur.
|
||||
Formfeeds (^L) act like newlines w.r.t. recognizing # as the flag
|
||||
for cpp.
|
||||
|
||||
Incompatibility:
|
||||
The virgule '/' in "a=/*b" is interpreted as the first character of
|
||||
the pair "/*" which introduces a comment, rather than as the
|
||||
second character of the divide-and-replace operator "=/".
|
||||
This incompatibility reflects the recent change in the C
|
||||
language which made "a/=*b" the legal way to write such a
|
||||
statement if the meaning "a=a/ *b" is intended.
|
||||
3397
lang/cpp/cpp.c
Normal file
3397
lang/cpp/cpp.c
Normal file
File diff suppressed because it is too large
Load Diff
106
lang/cpp/cpy.y
Normal file
106
lang/cpp/cpy.y
Normal file
@@ -0,0 +1,106 @@
|
||||
/* Copyright (c) 1984 AT&T */
|
||||
/* All Rights Reserved */
|
||||
|
||||
/* THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF AT&T */
|
||||
/* The copyright notice above does not evidence any */
|
||||
/* actual or intended publication of such source code. */
|
||||
|
||||
%{
|
||||
#ifndef lint
|
||||
static char sccsid[] = "@(#)cpy.y 1.1 94/10/31 SMI"; /* from S5R3 1.5 */
|
||||
#endif
|
||||
%}
|
||||
|
||||
%term number stop DEFINED
|
||||
%term EQ NE LE GE LS RS
|
||||
%term ANDAND OROR
|
||||
%left ','
|
||||
%right '='
|
||||
%right '?' ':'
|
||||
%left OROR
|
||||
%left ANDAND
|
||||
%left '|' '^'
|
||||
%left '&'
|
||||
%binary EQ NE
|
||||
%binary '<' '>' LE GE
|
||||
%left LS RS
|
||||
%left '+' '-'
|
||||
%left '*' '/' '%'
|
||||
%right '!' '~' UMINUS
|
||||
%left '(' '.'
|
||||
%%
|
||||
S: e stop ={return($1);}
|
||||
|
||||
|
||||
e: e '*' e
|
||||
={$$ = $1 * $3;}
|
||||
| e '/' e
|
||||
={
|
||||
if ($3 == 0) {
|
||||
ppwarn("division by zero");
|
||||
$$ = 0;
|
||||
}
|
||||
else
|
||||
$$ = $1 / $3;
|
||||
}
|
||||
| e '%' e
|
||||
={
|
||||
if ($3 == 0) {
|
||||
ppwarn("remainder by zero");
|
||||
$$ = 0;
|
||||
}
|
||||
else
|
||||
$$ = $1 % $3;
|
||||
}
|
||||
| e '+' e
|
||||
={$$ = $1 + $3;}
|
||||
| e '-' e
|
||||
={$$ = $1 - $3;}
|
||||
| e LS e
|
||||
={$$ = $1 << $3;}
|
||||
| e RS e
|
||||
={$$ = $1 >> $3;}
|
||||
| e '<' e
|
||||
={$$ = $1 < $3;}
|
||||
| e '>' e
|
||||
={$$ = $1 > $3;}
|
||||
| e LE e
|
||||
={$$ = $1 <= $3;}
|
||||
| e GE e
|
||||
={$$ = $1 >= $3;}
|
||||
| e EQ e
|
||||
={$$ = $1 == $3;}
|
||||
| e NE e
|
||||
={$$ = $1 != $3;}
|
||||
| e '&' e
|
||||
={$$ = $1 & $3;}
|
||||
| e '^' e
|
||||
={$$ = $1 ^ $3;}
|
||||
| e '|' e
|
||||
={$$ = $1 | $3;}
|
||||
| e ANDAND e
|
||||
={$$ = $1 && $3;}
|
||||
| e OROR e
|
||||
={$$ = $1 || $3;}
|
||||
| e '?' e ':' e
|
||||
={$$ = $1 ? $3 : $5;}
|
||||
| e ',' e
|
||||
={$$ = $3;}
|
||||
| term
|
||||
={$$ = $1;}
|
||||
term:
|
||||
'-' term %prec UMINUS
|
||||
={$$ = -$2;}
|
||||
| '!' term
|
||||
={$$ = !$2;}
|
||||
| '~' term
|
||||
={$$ = ~$2;}
|
||||
| '(' e ')'
|
||||
={$$ = $2;}
|
||||
| DEFINED '(' number ')'
|
||||
={$$= $3;}
|
||||
| DEFINED number
|
||||
={$$ = $2;}
|
||||
| number
|
||||
={$$= $1;}
|
||||
%%
|
||||
24
lang/cpp/yyfix.sh
Normal file
24
lang/cpp/yyfix.sh
Normal file
@@ -0,0 +1,24 @@
|
||||
#! /bin/sh
|
||||
|
||||
#
|
||||
# @(#)yyfix.sh 1.1 10/31/94
|
||||
#
|
||||
|
||||
rm -f rodata.c
|
||||
>rodata.c
|
||||
for i in $*
|
||||
do
|
||||
rm -f rodata-temp.c
|
||||
>rodata-temp.c
|
||||
/bin/ed - y.tab.c <<!
|
||||
/^\(.*\)$i[ ]*\[][ ]*=[ ]*{/ka
|
||||
/}/kb
|
||||
'a,'bw rodata-temp.c
|
||||
'a s/^\(.*\)$i[ ]*\[][ ]*=[ ]*{/extern \1 $i[];/
|
||||
'a+1,'bd
|
||||
w y.tab.c
|
||||
q
|
||||
!
|
||||
cat rodata-temp.c >> rodata.c
|
||||
rm -f rodata-temp.c
|
||||
done
|
||||
270
lang/cpp/yylex.c
Normal file
270
lang/cpp/yylex.c
Normal file
@@ -0,0 +1,270 @@
|
||||
/* Copyright (c) 1984 AT&T */
|
||||
/* All Rights Reserved */
|
||||
|
||||
/* THIS IS UNPUBLISHED PROPRIETARY SOURCE CODE OF AT&T */
|
||||
/* The copyright notice above does not evidence any */
|
||||
/* actual or intended publication of such source code. */
|
||||
|
||||
#ifndef lint
|
||||
static char sccsid[] = "@(#)yylex.c 1.1 94/10/31 SMI"; /* from S5R3.1 1.11 */
|
||||
#endif
|
||||
|
||||
#include "y.tab.h"
|
||||
#ifdef FLEXNAMES
|
||||
# define NCPS 128
|
||||
#else
|
||||
# define NCPS 8
|
||||
#endif
|
||||
|
||||
#ifdef BROWSER
|
||||
# include <stdio.h>
|
||||
# include "cb_cpp_protocol.h"
|
||||
# define NOINCL ""
|
||||
extern int cbflag;
|
||||
extern int cbifsay;
|
||||
extern char *cbmacend;
|
||||
extern FILE *fout;
|
||||
extern int lineno[];
|
||||
extern int ifno;
|
||||
#endif
|
||||
|
||||
extern int ncps; /* actual number of chars. */
|
||||
extern int xline;
|
||||
extern int yylval;
|
||||
extern int cxref;
|
||||
|
||||
#define isid(a) ((fastab+COFF)[a]&IB)
|
||||
#define IB 1
|
||||
/* #if '\377' < 0 it would be nice if this worked properly!!!!! */
|
||||
#if pdp11 | vax | mc68000 | sparc | i386
|
||||
#define COFF 128
|
||||
#else
|
||||
#define COFF 0
|
||||
#endif
|
||||
|
||||
yylex()
|
||||
{
|
||||
static int ifdef = 0;
|
||||
static char *op2[] = {"||", "&&" , ">>", "<<", ">=", "<=", "!=", "=="};
|
||||
static int val2[] = {OROR, ANDAND, RS, LS, GE, LE, NE, EQ};
|
||||
static char *opc = "b\bt\tn\nf\fr\r\\\\";
|
||||
extern char fastab[];
|
||||
extern char *outp, *inp, *newp;
|
||||
extern int flslvl;
|
||||
register char savc, *s;
|
||||
char *skipbl();
|
||||
int val;
|
||||
register char **p2;
|
||||
struct symtab
|
||||
{
|
||||
char *name;
|
||||
char *value;
|
||||
struct symtab *next; /* pointer to next chain entry */
|
||||
} *sp, *lookup();
|
||||
|
||||
for ( ;; )
|
||||
{
|
||||
#ifdef BROWSER
|
||||
if ( ( cbmacend != NULL ) && ( outp >= cbmacend ) )
|
||||
{
|
||||
putc( CB_CHR_PREFIX, fout );
|
||||
putc( CB_CHR_MACRO_REF_END, fout );
|
||||
cbmacend = NULL;
|
||||
}
|
||||
#endif
|
||||
newp = skipbl( newp );
|
||||
if ( *inp == '\n' ) /* end of #if */
|
||||
return( stop );
|
||||
savc = *newp;
|
||||
*newp = '\0';
|
||||
if ( *inp == '/' && inp[1] == '*' )
|
||||
{
|
||||
/* found a comment with -C option, still toss here */
|
||||
*newp = savc;
|
||||
outp = inp = newp;
|
||||
continue;
|
||||
}
|
||||
for ( p2 = op2 + 8; --p2 >= op2; ) /* check 2-char ops */
|
||||
if ( strcmp( *p2, inp ) == 0 )
|
||||
{
|
||||
val = val2[ p2 - op2 ];
|
||||
goto ret;
|
||||
}
|
||||
s = "+-*/%<>&^|?:!~(),"; /* check 1-char ops */
|
||||
while ( *s )
|
||||
if ( *s++ == *inp )
|
||||
{
|
||||
val= *--s;
|
||||
goto ret;
|
||||
}
|
||||
if ( *inp<='9' && *inp>='0' ) /* a number */
|
||||
{
|
||||
if ( *inp == '0' )
|
||||
yylval= ( inp[1] == 'x' || inp[1] == 'X' ) ?
|
||||
tobinary( inp + 2, 16 ) :
|
||||
tobinary( inp + 1, 8 );
|
||||
else
|
||||
yylval = tobinary( inp, 10 );
|
||||
val = number;
|
||||
}
|
||||
else if ( isid( *inp ) )
|
||||
{
|
||||
if ( strcmp( inp, "defined" ) == 0 )
|
||||
{
|
||||
ifdef = 1;
|
||||
++flslvl;
|
||||
val = DEFINED;
|
||||
}
|
||||
else
|
||||
{
|
||||
if ( ifdef != 0 )
|
||||
{
|
||||
register char *p;
|
||||
register int savech;
|
||||
|
||||
/* make sure names <= ncps chars */
|
||||
if ( ( newp - inp ) > ncps )
|
||||
p = inp + ncps;
|
||||
else
|
||||
p = newp;
|
||||
savech = *p;
|
||||
*p = '\0';
|
||||
sp = lookup( inp, -1 );
|
||||
*p = savech;
|
||||
ifdef = 0;
|
||||
--flslvl;
|
||||
}
|
||||
else
|
||||
sp = lookup( inp, -1 );
|
||||
if ( cxref )
|
||||
ref(inp, xline);
|
||||
#ifdef BROWSER
|
||||
if ( cbflag )
|
||||
{
|
||||
register char *p;
|
||||
register int savech;
|
||||
|
||||
if ( ( newp - inp ) > ncps )
|
||||
p = inp + ncps;
|
||||
else
|
||||
p = newp;
|
||||
savech = *p;
|
||||
*p = '\0';
|
||||
if ( lineno[ifno] != cbifsay )
|
||||
{
|
||||
sayline( NOINCL );
|
||||
cbifsay = lineno[ifno];
|
||||
}
|
||||
if ( inp > cbmacend )
|
||||
{
|
||||
cbputid( fout,
|
||||
( sp == 0 ) ?
|
||||
CB_CHR_MACRO_REF_WO_FORMALS_UNDEFD :
|
||||
CB_CHR_MACRO_REF_WO_FORMALS_DEFD,
|
||||
inp );
|
||||
putc( CB_CHR_PREFIX, fout );
|
||||
putc( CB_CHR_MACRO_REF_END,
|
||||
fout );
|
||||
}
|
||||
*p = savech;
|
||||
}
|
||||
#endif
|
||||
yylval = ( sp == 0 ) ? 0 : 1;
|
||||
val = number;
|
||||
}
|
||||
}
|
||||
else if ( *inp == '\'' ) /* character constant */
|
||||
{
|
||||
val = number;
|
||||
if ( inp[1] == '\\' ) /* escaped */
|
||||
{
|
||||
char c;
|
||||
|
||||
if ( newp[-1] == '\'' )
|
||||
newp[-1] = '\0';
|
||||
s = opc;
|
||||
while ( *s )
|
||||
if ( *s++ != inp[2] )
|
||||
++s;
|
||||
else
|
||||
{
|
||||
yylval = *s;
|
||||
goto ret;
|
||||
}
|
||||
if ( inp[2] <= '9' && inp[2] >= '0' )
|
||||
yylval = c = tobinary( inp + 2, 8 );
|
||||
else
|
||||
yylval = inp[2];
|
||||
}
|
||||
else
|
||||
yylval = inp[1];
|
||||
}
|
||||
else if ( strcmp( "\\\n", inp ) == 0 )
|
||||
{
|
||||
*newp = savc;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
*newp = savc;
|
||||
pperror( "Illegal character %c in preprocessor if",
|
||||
*inp );
|
||||
continue;
|
||||
}
|
||||
ret:
|
||||
/* check for non-ident after defined (note need the paren!) */
|
||||
if ( ifdef && val != '(' && val != DEFINED )
|
||||
{
|
||||
pperror( "\"defined\" modifying non-identifier \"%s\" in preprocessor if", inp );
|
||||
ifdef = 0;
|
||||
flslvl--;
|
||||
}
|
||||
*newp = savc;
|
||||
outp = inp = newp;
|
||||
return( val );
|
||||
}
|
||||
}
|
||||
|
||||
tobinary( st, b )
|
||||
char *st;
|
||||
{
|
||||
int n, c, t;
|
||||
char *s;
|
||||
int warned = 0;
|
||||
|
||||
n = 0;
|
||||
s = st;
|
||||
while ( c = *s++ )
|
||||
{
|
||||
switch( c )
|
||||
{
|
||||
case '8': case '9':
|
||||
if (b <= 8 && !warned) {
|
||||
ppwarn("Illegal octal number %s", st);
|
||||
warned = 1;
|
||||
}
|
||||
case '0': case '1': case '2': case '3': case '4':
|
||||
case '5': case '6': case '7':
|
||||
t = c - '0';
|
||||
break;
|
||||
case 'a': case 'b': case 'c': case 'd': case 'e': case 'f':
|
||||
t = (c - 'a') + 10;
|
||||
if ( b > 10 )
|
||||
break;
|
||||
case 'A': case 'B': case 'C': case 'D': case 'E': case 'F':
|
||||
t = (c - 'A') + 10;
|
||||
if ( b > 10 )
|
||||
break;
|
||||
default:
|
||||
t = -1;
|
||||
if ( c == 'l' || c == 'L' )
|
||||
if ( *s == '\0' )
|
||||
break;
|
||||
pperror( "Illegal number %s", st );
|
||||
}
|
||||
if ( t < 0 )
|
||||
break;
|
||||
n = n * b + t;
|
||||
}
|
||||
return( n );
|
||||
}
|
||||
Reference in New Issue
Block a user