Flex-2.5.4.

This commit is contained in:
Philip Homburg 2005-07-11 12:54:10 +00:00
parent d21c2c2229
commit 054e68baf6
89 changed files with 44981 additions and 1 deletions

View file

@ -1,6 +1,7 @@
# Makefile for commands.
MAKE = exec make -$(MAKEFLAGS)
FLEX=flex-2.5.4
GZIP=gzip-1.2.4
PYTHON=python-1.5.2
@ -11,10 +12,12 @@ usage:
@false
all install::
cd $(FLEX) && ./configure --prefix=/usr && make $@
cd $(GZIP) && ./configure --prefix=/usr && make $@
cd $(PYTHON) && ./configure --prefix=/usr/local && make $@
clean::
if [ -f $(FLEX)/Makefile ] ; then cd $(FLEX) && make $@; fi
if [ -f $(GZIP)/Makefile ] ; then cd $(GZIP) && make $@; fi
if [ -f $(PYTHON)/Makefile ] ; then cd $(PYTHON) && make $@; fi
@ -34,7 +37,6 @@ all install clean::
cd dis88 && $(MAKE) $@
cd elle && $(MAKE) $@
cd elvis && $(MAKE) $@
cd flex-2.3.7 && $(MAKE) $@
cd ftp && $(MAKE) $@
cd ftpd && $(MAKE) $@
cd ftpd200 && $(MAKE) $@

View file

@ -0,0 +1,38 @@
Flex carries the copyright used for BSD software, slightly modified
because it originated at the Lawrence Berkeley (not Livermore!) Laboratory,
which operates under a contract with the Department of Energy:
Copyright (c) 1990 The Regents of the University of California.
All rights reserved.
This code is derived from software contributed to Berkeley by
Vern Paxson.
The United States Government has rights in this work pursuant
to contract no. DE-AC03-76SF00098 between the United States
Department of Energy and the University of California.
Redistribution and use in source and binary forms with or without
modification are permitted provided that: (1) source distributions
retain this entire copyright notice and comment, and (2)
distributions including binaries display the following
acknowledgement: ``This product includes software developed by the
University of California, Berkeley and its contributors'' in the
documentation or other materials provided with the distribution and
in all advertising materials mentioning features or use of this
software. Neither the name of the University nor the names of its
contributors may be used to endorse or promote products derived
from this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE.
This basically says "do whatever you please with this software except
remove this notice or take advantage of the University's (or the flex
authors') name".
Note that the "flex.skl" scanner skeleton carries no copyright notice.
You are free to do whatever you please with scanners generated using flex;
for them, you are not even bound by the above copyright.

View file

@ -0,0 +1,186 @@
// $Header$
// FlexLexer.h -- define interfaces for lexical analyzer classes generated
// by flex
// Copyright (c) 1993 The Regents of the University of California.
// All rights reserved.
//
// This code is derived from software contributed to Berkeley by
// Kent Williams and Tom Epperly.
//
// Redistribution and use in source and binary forms with or without
// modification are permitted provided that: (1) source distributions retain
// this entire copyright notice and comment, and (2) distributions including
// binaries display the following acknowledgement: ``This product includes
// software developed by the University of California, Berkeley and its
// contributors'' in the documentation or other materials provided with the
// distribution and in all advertising materials mentioning features or use
// of this software. Neither the name of the University nor the names of
// its contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
// THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
// WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
// MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
// This file defines FlexLexer, an abstract class which specifies the
// external interface provided to flex C++ lexer objects, and yyFlexLexer,
// which defines a particular lexer class.
//
// If you want to create multiple lexer classes, you use the -P flag
// to rename each yyFlexLexer to some other xxFlexLexer. You then
// include <FlexLexer.h> in your other sources once per lexer class:
//
// #undef yyFlexLexer
// #define yyFlexLexer xxFlexLexer
// #include <FlexLexer.h>
//
// #undef yyFlexLexer
// #define yyFlexLexer zzFlexLexer
// #include <FlexLexer.h>
// ...
#ifndef __FLEX_LEXER_H
// Never included before - need to define base class.
#define __FLEX_LEXER_H
#include <iostream.h>
extern "C++" {
struct yy_buffer_state;
typedef int yy_state_type;
class FlexLexer {
public:
virtual ~FlexLexer() { }
const char* YYText() { return yytext; }
int YYLeng() { return yyleng; }
virtual void
yy_switch_to_buffer( struct yy_buffer_state* new_buffer ) = 0;
virtual struct yy_buffer_state*
yy_create_buffer( istream* s, int size ) = 0;
virtual void yy_delete_buffer( struct yy_buffer_state* b ) = 0;
virtual void yyrestart( istream* s ) = 0;
virtual int yylex() = 0;
// Call yylex with new input/output sources.
int yylex( istream* new_in, ostream* new_out = 0 )
{
switch_streams( new_in, new_out );
return yylex();
}
// Switch to new input/output streams. A nil stream pointer
// indicates "keep the current one".
virtual void switch_streams( istream* new_in = 0,
ostream* new_out = 0 ) = 0;
int lineno() const { return yylineno; }
int debug() const { return yy_flex_debug; }
void set_debug( int flag ) { yy_flex_debug = flag; }
protected:
char* yytext;
int yyleng;
int yylineno; // only maintained if you use %option yylineno
int yy_flex_debug; // only has effect with -d or "%option debug"
};
}
#endif
#if defined(yyFlexLexer) || ! defined(yyFlexLexerOnce)
// Either this is the first time through (yyFlexLexerOnce not defined),
// or this is a repeated include to define a different flavor of
// yyFlexLexer, as discussed in the flex man page.
#define yyFlexLexerOnce
class yyFlexLexer : public FlexLexer {
public:
// arg_yyin and arg_yyout default to the cin and cout, but we
// only make that assignment when initializing in yylex().
yyFlexLexer( istream* arg_yyin = 0, ostream* arg_yyout = 0 );
virtual ~yyFlexLexer();
void yy_switch_to_buffer( struct yy_buffer_state* new_buffer );
struct yy_buffer_state* yy_create_buffer( istream* s, int size );
void yy_delete_buffer( struct yy_buffer_state* b );
void yyrestart( istream* s );
virtual int yylex();
virtual void switch_streams( istream* new_in, ostream* new_out );
protected:
virtual int LexerInput( char* buf, int max_size );
virtual void LexerOutput( const char* buf, int size );
virtual void LexerError( const char* msg );
void yyunput( int c, char* buf_ptr );
int yyinput();
void yy_load_buffer_state();
void yy_init_buffer( struct yy_buffer_state* b, istream* s );
void yy_flush_buffer( struct yy_buffer_state* b );
int yy_start_stack_ptr;
int yy_start_stack_depth;
int* yy_start_stack;
void yy_push_state( int new_state );
void yy_pop_state();
int yy_top_state();
yy_state_type yy_get_previous_state();
yy_state_type yy_try_NUL_trans( yy_state_type current_state );
int yy_get_next_buffer();
istream* yyin; // input source for default LexerInput
ostream* yyout; // output sink for default LexerOutput
struct yy_buffer_state* yy_current_buffer;
// yy_hold_char holds the character lost when yytext is formed.
char yy_hold_char;
// Number of characters read into yy_ch_buf.
int yy_n_chars;
// Points to current character in buffer.
char* yy_c_buf_p;
int yy_init; // whether we need to initialize
int yy_start; // start state number
// Flag which is used to allow yywrap()'s to do buffer switches
// instead of setting up a fresh yyin. A bit of a hack ...
int yy_did_buffer_switch_on_eof;
// The following are not always needed, but may be depending
// on use of certain flex features (like REJECT or yymore()).
yy_state_type yy_last_accepting_state;
char* yy_last_accepting_cpos;
yy_state_type* yy_state_buf;
yy_state_type* yy_state_ptr;
char* yy_full_match;
int* yy_full_state;
int yy_full_lp;
int yy_lp;
int yy_looking_for_trail_begin;
int yy_more_flag;
int yy_more_len;
int yy_more_offset;
int yy_prev_more_offset;
};
#endif

117
commands/flex-2.5.4/INSTALL Normal file
View file

@ -0,0 +1,117 @@
This is a generic INSTALL file for utilities distributions.
If this package does not come with, e.g., installable documentation or
data files, please ignore the references to them below.
To compile this package:
1. Configure the package for your system. In the directory that this
file is in, type `./configure'. If you're using `csh' on an old
version of System V, you might need to type `sh configure' instead to
prevent `csh' from trying to execute `configure' itself.
The `configure' shell script attempts to guess correct values for
various system-dependent variables used during compilation, and
creates the Makefile(s) (one in each subdirectory of the source
directory). In some packages it creates a C header file containing
system-dependent definitions. It also creates a file `config.status'
that you can run in the future to recreate the current configuration.
Running `configure' takes a minute or two. While it is running, it
prints some messages that tell what it is doing. If you don't want to
see the messages, run `configure' with its standard output redirected
to `/dev/null'; for example, `./configure >/dev/null'.
To compile the package in a different directory from the one
containing the source code, you must use a version of `make' that
supports the VPATH variable, such as GNU `make'. `cd' to the directory
where you want the object files and executables to go and run
`configure'. `configure' automatically checks for the source code in
the directory that `configure' is in and in `..'. If for some reason
`configure' is not in the source code directory that you are
configuring, then it will report that it can't find the source code.
In that case, run `configure' with the option `--srcdir=DIR', where
DIR is the directory that contains the source code.
By default, `make install' will install the package's files in
/usr/local/bin, /usr/local/lib, /usr/local/man, etc. You can specify
an installation prefix other than /usr/local by giving `configure' the
option `--prefix=PATH'. Alternately, you can do so by giving a value
for the `prefix' variable when you run `make', e.g.,
make prefix=/usr/gnu
You can specify separate installation prefixes for
architecture-specific files and architecture-independent files. If
you give `configure' the option `--exec-prefix=PATH' or set the
`make' variable `exec_prefix' to PATH, the package will use PATH as
the prefix for installing programs and libraries. Data files and
documentation will still use the regular prefix. Normally, all files
are installed using the regular prefix.
Another `configure' option is useful mainly in `Makefile' rules for
updating `config.status' and `Makefile'. The `--no-create' option
figures out the configuration for your system and records it in
`config.status', without actually configuring the package (creating
`Makefile's and perhaps a configuration header file). Later, you can
run `./config.status' to actually configure the package. You can also
give `config.status' the `--recheck' option, which makes it re-run
`configure' with the same arguments you used before. This option is
useful if you change `configure'.
Some packages pay attention to `--with-PACKAGE' options to `configure',
where PACKAGE is something like `gnu-libc' or `x' (for X windows).
The README should mention any --with- options that the package recognizes.
`configure' ignores any other arguments that you give it.
If your system requires unusual options for compilation or linking
that `configure' doesn't know about, you can give `configure' initial
values for some variables by setting them in the environment. In
Bourne-compatible shells, you can do that on the command line like
this:
CC='gcc -traditional' DEFS=-D_POSIX_SOURCE ./configure
The `make' variables that you might want to override with environment
variables when running `configure' are:
(For these variables, any value given in the environment overrides the
value that `configure' would choose:)
CC C compiler program.
Default is `cc', or `gcc' if `gcc' is in your PATH.
INSTALL Program to use to install files.
Default is `install' if you have it, `cp' otherwise.
(For these variables, any value given in the environment is added to
the value that `configure' chooses:)
DEFS Configuration options, in the form `-Dfoo -Dbar ...'
Do not use this variable in packages that create a
configuration header file.
LIBS Libraries to link with, in the form `-lfoo -lbar ...'
If you need to do unusual things to compile the package, we encourage
you to figure out how `configure' could check whether to do them, and
mail diffs or instructions to the address given in the README so we
can include them in the next release.
2. Type `make' to compile the package. If you want, you can override
the `make' variables CFLAGS and LDFLAGS like this:
make CFLAGS=-O2 LDFLAGS=-s
3. If the package comes with self-tests and you want to run them,
type `make check'. If you're not sure whether there are any, try it;
if `make' responds with something like
make: *** No way to make target `check'. Stop.
then the package does not come with self-tests.
4. Type `make install' to install programs, data files, and
documentation.
5. You can remove the program binaries and object files from the
source directory by typing `make clean'. To also remove the
Makefile(s), the header file containing system-dependent definitions
(if the package uses one), and `config.status' (all the files that
`configure' created), type `make distclean'.
The file `configure.in' is used as a template to create `configure' by
a program called `autoconf'. You will only need it if you want to
regenerate `configure' using a newer version of `autoconf'.

View file

@ -0,0 +1,72 @@
This file, ./MISC/Amiga/README.amiga, describes the necessary steps to get
the FLEX 2.5.1 program up and running on the Commodore AMIGA with the
help of SAS/C++ 6.51 and SMake 6.50. Also it describes the contents of the
subdirectory ./MISC/Amiga, where `.' denotes the root directory of the
standard installation of FLEX 2.5.1.
FILES ADDED FOR INSTALLING FLEX 2.5.1 ON THE AMIGA
The standard distribution of FLEX 2.5.1 is assumed to be installed on
your AMIGA computer. `Installed' means that all source files from the
original archive are present in a root directory (denoted by `.' in what
follows) and, if appropriate, one or more subdirectories, on your machine.
The original source files are totally left untouched, the necessary changes
are applied in the form of `change files'. For installing FLEX 2.5.1 on
the AMIGA, several additional files come with this patch.
-----rw-d 2 738 Apr 3 11:49 config.h
-----rw-d 1 169 Apr 3 11:33 libmain.ch
-----rw-d 1 159 Apr 3 11:33 libyywrap.ch
-----rw-d 1 167 Apr 3 11:33 parse.ych
-----rw-d 6 2840 Apr 3 11:34 README.amiga
-----rw-d 11 5503 Apr 3 11:45 smakefile
Dirs:0 Files:6 Blocks:22 Bytes:9576
HOW TO INSTALL FLEX 2.5.1 ON THE AMIGA
Copy all files from ./MISC/Amiga to the root directory of the FLEX 2.5.1
distribution and edit `SMakefile' as it instructs you. There shouldn't be
too many changes necessary. Then say "make bootflex". This creates a
preliminary version of FLEX 2.5.1 without using itself.
WARNING: Don't say "make flex" yet. Any pre-2.5 version of FLEX will fail
on the file `scan.l' due to some new features only present in FLEX 2.5.
Then say "make flex". At least once the FLEX program created in the first
step will be used. To make sure that everything is alright, finally say
"make check". If you change the code, you should also say "make bigcheck"
for some more thorough testing.
When you are satisfied with the results, say "make install". This will
copy the `flex' binary, the `libfl.lib' file, and the `FlexLexer.h' header
to the paths specified in the `SMakefile'.
Finally, you should say "make clean" to remove all intermediate files from
the root directory. "make veryclean" also removes `flex' and `scan.c'.
TROUBLE SHOOTING
FLEX 2.5.1 was ported to the AMIGA and tested with the following setup:
AMIGA 2000
GVP G-Force 030/50/50/8
SAS/C++ 6.51
SED 2.05
BISON 1.22
WMERGE from the CWEB distribution
Should you encounter problems with this AMIGA patch for FLEX 2.5.1 or
should you have ideas for further improvements, like using GnuMake instead
of SMake, contact the author of this contribution
Andreas Scherer
Roland-Stra{\ss}e 16
52070 Aachen
Germany
<scherer@genesis.informatik.rwth-aachen.de> (Internet)

View file

@ -0,0 +1,195 @@
# @(#) $Header$ (LBL)
# If your version of "make" does not define $(MAKE), comment in the
# definition of "MAKE" below. (You only need to do this if you intend
# to do "make bigcheck" or "make dist".)
MAKE = smake
# Possible values for DEFS:
#
# For flex to always generate 8-bit scanners, add "-DDEFAULT_CSIZE=256"
# to DEFS.
#
# For Vax/VMS, add "-DVMS" to DEFS.
#
# For MS-DOS, add "-DMS_DOS" to DEFS. See the directory MISC/MSDOS for
# additional info.
CFLAGS = data=far ignore=85 noicons stackextend optimize
DEFS = define=YYBISON=1 define=YY_NEVER_INTERACTIVE=1
LDFLAGS = noicons
LIBS =
# Installation targeting. Files will be installed under the tree
# rooted at prefix. flex will be installed in bindir, libfl.lib in
# libdir, FlexLexer.h will be installed in includedir, and the manual
# pages will be installed in mandir with extension manext.
#
# Raw, unformatted troff source will be installed if INSTALLMAN=man,
# nroff preformatted versions will be installed if INSTALLMAN=cat.
prefix = Programmer:other # Change this for your AMIGA system.
exec_prefix = $(prefix)
bindir = $(exec_prefix)/bin
libdir = $(exec_prefix)/lib
includedir = $(prefix)/include
manext = 1
mandir = $(prefix)/man/man$(manext)
# You can define this to be "lex" if you want to replace lex at your site.
FLEX = flex
INSTALLMAN = man
SHELL =
srcdir = .
VPATH =
LN_S =
YACC = bison -y
SED = sed
CC = sc
WMERGE = wmerge # from the CWEB distribution
AR = oml
RANLIB =
INSTALL = copy clone
INSTALL_DATA = $(INSTALL)
INSTALL_PROGRAM = $(INSTALL)
# You normally do not need to modify anything below this point.
# ------------------------------------------------------------
CPPFLAGS = idir=. idir=$(srcdir) $(DEFS)
.c.o:
$(CC) $(CPPFLAGS) $(CFLAGS) $<
HEADERS = flexdef.h version.h
SOURCES = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.y \
scan.l skel.c sym.c tblcmp.c yylex.c
OBJECTS = ccl.o dfa.o ecs.o gen.o main.o misc.o nfa.o parse.o \
skel.o sym.o tblcmp.o yylex.o \
$(libdir)/alloca.o $(libdir)/xmalloc.o
LIBSRCS = libmain.c libyywrap.c
LIBOBJS = ansilibmain.o ansilibyywrap.o
LINTSRCS = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.c \
scan.c skel.c sym.c tblcmp.c yylex.c
DISTFILES = README NEWS COPYING INSTALL FlexLexer.h \
configure.in conf.in Makefile.in mkskel.sh skel.c flex.skl \
$(HEADERS) $(SOURCES) $(LIBSRCS) MISC \
flex.1 scan.c install.sh mkinstalldirs configure
DIST_NAME = flex
# which "flex" to use to generate scan.c from scan.l
FLEX_EXEC = ./$(FLEX)
FLEX_FLAGS = -t $(PERF_REPORT)
COMPRESSION =
PERF_REPORT = -p
FLEXLIB = libfl.lib
all: $(FLEX)
$(FLEX): $(OBJECTS) $(FLEXLIB) scan.o
$(CC) $(CFLAGS) link to $(FLEX) $(LDFLAGS) $(OBJECTS) scan.o $(FLEXLIB) $(LIBS)
bootflex: $(OBJECTS) $(FLEXLIB) initscan.o
$(CC) $(CFLAGS) link to $(FLEX) $(LDFLAGS) $(OBJECTS) initscan.o $(FLEXLIB) $(LIBS)
parse.c: ansiparse.y
$(YACC) -d ansiparse.y
$(SED) "/extern char.*malloc/d" <y.tab.c >parse.tmp
copy parse.tmp parse.c
copy y.tab.h parse.h
@delete y.tab.c y.tab.h parse.tmp
ansiparse.y: $(srcdir)/parse.y parse.ych
$(WMERGE) $(srcdir)/parse.y parse.ych ansiparse.y
parse.h: parse.c
scan.c: scan.l
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) $(srcdir)/scan.l >scan.tmp
$(SED) s,\"$(srcdir)/scan.l\",\"scan.l\", <scan.tmp >scan.c
@delete scan.tmp
scan.o: scan.c parse.h flexdef.h config.h
initscan.o: initscan.c parse.h flexdef.h config.h
yylex.o: yylex.c parse.h flexdef.h config.h
skel.c: flex.skl mkskel.sh
$(SHELL) $(srcdir)/mkskel.sh $(srcdir)/flex.skl >skel.c
main.o: main.c flexdef.h config.h version.h
ccl.o: ccl.c flexdef.h config.h
dfa.o: dfa.c flexdef.h config.h
ecs.o: ecs.c flexdef.h config.h
gen.o: gen.c flexdef.h config.h
misc.o: misc.c flexdef.h config.h
nfa.o: nfa.c flexdef.h config.h
parse.o: parse.c flexdef.h config.h
skel.o: skel.c flexdef.h config.h
sym.o: sym.c flexdef.h config.h
tblcmp.o: tblcmp.c flexdef.h config.h
alloca.o: alloca.c
$(CC) $(CPPFLAGS) $(CFLAGS) define=xmalloc=yy_flex_xmalloc alloca.c
alloca.c: $(srcdir)/MISC/alloca.c
@delete alloca.c
copy $(srcdir)/MISC/alloca.c .
test: check
check: flex
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) $(srcdir)/scan.l > temp_a
$(SED) s,"$(srcdir)/scan.l","scan.l", < temp_a > temp_b
-diff scan.c temp_b -l10000 -w
@delete temp_?
@echo "Check successful, using COMPRESSION='$(COMPRESSION)'"
bigcheck:
delete scan.c
$(MAKE) COMPRESSION=-C check
delete scan.c
$(MAKE) COMPRESSION=-Ce check
delete scan.c
$(MAKE) COMPRESSION=-Cm check
delete scan.c
$(MAKE) COMPRESSION=-Cfea check
delete scan.c
$(MAKE) COMPRESSION=-CFer check
delete scan.c
$(MAKE) COMPRESSION=-l PERF_REPORT= check
delete scan.c
$(MAKE)
@echo "All checks successful"
$(FLEXLIB): $(LIBOBJS)
$(AR) $(FLEXLIB) R $(LIBOBJS)
$(FLEX).man: flex.1 # SMAKE can't `cd', sorry. And, I don't have nroff.
# cd $(srcdir), nroff -man flex.1 >$(FLEX).man
install: $(FLEX) $(FLEXLIB)
$(INSTALL_PROGRAM) $(FLEX) $(bindir)/$(FLEX)
# @delete $(bindir)/$(FLEX)++
$(INSTALL_DATA) $(FLEXLIB) $(libdir)/libfl.lib
$(INSTALL_DATA) $(srcdir)/FlexLexer.h $(includedir)/FlexLexer.h
ansilibmain.o: ansilibmain.c
ansilibmain.c: libmain.c libmain.ch
$(WMERGE) libmain.c libmain.ch ansilibmain.c
ansilibyywrap.o: ansilibyywrap.c
ansilibyywrap.c: libyywrap.c libyywrap.ch
$(WMERGE) libyywrap.c libyywrap.ch ansilibyywrap.c
clean:
-delete parse.(c|h) ansi\#? \#?.(bak|o|lnk) \
alloca.c lex.yy.(c|cc) $(FLEXLIB)
veryclean: clean
-delete $(FLEX) scan.c

View file

@ -0,0 +1,25 @@
/* $Header$ */
/* Define to empty if the keyword does not work. */
#undef const
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* Define if you have the ANSI C header files. */
#define STDC_HEADERS 1
/* Define if you have the <malloc.h> header file. */
#undef HAVE_MALLOC_H
/* Define if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#undef HAVE_ALLOCA_H
/* Define if platform-specific command line handling is necessary. */
#undef NEED_ARGV_FIXUP

View file

@ -0,0 +1,8 @@
Changes for LIBMAIN.C 2.4.7 by Andreas Scherer, January 19, 1995.
Modified for LIBMAIN.C 2.5.1, April 3, 1995.
@x l.5
extern int yylex();
@y
extern int yylex(void);
@z

View file

@ -0,0 +1,8 @@
Changes for LIBYYWRAP.C 2.4.7 by Andreas Scherer, January 19, 1995.
Modified for LIBYYWRAP.C 2.5.1, April 3, 1995.
@x l.5
int yywrap()
@y
int yywrap(void)
@z

View file

@ -0,0 +1,8 @@
Changes for PARSE.Y 2.4.7 by Andreas Scherer, January 20, 1995.
Modified for PARSE.Y 2.5.1, April 3, 1995.
@x l.60
char *alloca ();
@y
char *alloca(unsigned int);
@z

View file

@ -0,0 +1,911 @@
(Message inbox:32)
Date: Mon, 03 Jul 89 21:15:32 CET
From: V61%DHDURZ1.BITNET@lbl.gov
Subject: Flex, bug fix, improvments, patches for Minix & TOS
To: vern@lbl-csam.arpa
At first I have to thank you for your wonderful program. I had ported the
old version to OS9,TOS (Atari ST) and Minix and the new version 2.1 Beta
to Minix and TOS.
While porting and using flex I detected a bug and made some improvements.
I have included a shared, compressed and uuencoded file contaning all cdiffs
and additional files (Sorry, but I'm on EBCDIC-Bitnet) and a short discussion
of the changes. Even some of the TOS specific changes might be of general
interest !
I posted these cdiffs to the minix discussion group, but I think it's up
to you to post them to the unix-sources group. If you plan to post even
the TOS compiler specific patches please contact me because there might be
further compiler (P.D.) additions. If you have an interest I could also
port the new version to OS9 -- this is a little bit more difficult, because
OS9 uses CR as end of line character (the EOL char. is coded into the
initscan.c tables,...). It is necessary to change all occurences of '\n' to
macros and variables and it's useful to add a new -n options (see commented
line in main.c)
The changes: (1.7.89 RAL)
- Bug fix: The original flex didn't like trailing spaces in exclusive start
condition lists ! If you add an trailing space to line 68 in scan.l
"%x SECT2 SECT2PROLOG SECT3 CODEBLOCK PICKUPDEF SC CARETISBOL NUM QUOTE "
you get a misleading error message:
"Syntax error at line 69: bad start condition list"
This bug can either be fixed in parse.y or in scan.l . I have chosen the
last because there the fix is minimal: Just change the rule (line 128)
"\n" to "{OPTWS}\n"
- Enhancements:
- new option "-?" that provides some help information about the other
flags (main.c)
- new option "-aTMPPATH" that allows a redefinition of the standard
path for the temporary file (this might be rather large >200k if
F,f options are selected). (main.c, flexdef.h (l.376))
- hexdump of illegal characters -- this proved to be a useful debugging
tool especialy if invisible control characters occur which weren't
covered by the rules. (scan.l fprintf statement line 129,...)
- Patches due to TOS
- General: TOS uses CR,LF as end of line char., Flex wants only a single
LF as EOL char. Therefore all I/O must be translated using f* calls.
This is done everywhere besides the YY_INPUT macro (flex.skel (scan.c),
line 31) that uses a low level 'read'. This should be definitly changed
to fread, so that all I/O calls occur on the same level.
- the short action_file_name has been "flexXXXXXX.tmp", but that's too
much for TOS,MSDOS ! I changed it to "flexXXXX.tmp" in main.c (patch
covered by the -a option additions)
- some compilers don't like external names that are ambiguous within
the first 8 characters. I defined macros that change all these long
external names to names that are unique within the first 8 characters.
Just define SHORT_EXTERNAL_NAMES to use this feature (flexdef.h)
- some statement changes that some compiler don't like:
typedef *xxx[] -> typedef **xxx (flexdef.h.,l.308)
"/*" -> '/','*' within a comment in (scan.l, l.209)
- changed short "lexyy.c" to "lex_yy.c" what's more similar to the unix
"lex.yy.c" (main.c).
- a few further really compiler dependent changes provided with
#ifdef ATARI && LATTICE res. TURBO braces.
- Additional TOS only files
- Makefile.tos: Common makefile for all TOS compilers. If you add further
ones please email me the new makefile.
- flex.lnk: Lattice - GST linker argument extension file
- flex.tlk: Turbo linker argument extension file
Additional remarks:
I didn't add a new initscan.c (= flex -ist scan.l). The current one is good
enough for a first compilation. With this first version of flex you can
rebuild your own scan.c and the final flex version !
Minix ST :
- I had to "chmem =70000 cv" (>50000) to get flex linked
- 'memset' (PC 1.3, EFTH40,...) is necessary
- chmem =90000 flex may be sufficient
Minix PC :
It should be possible to port Flex to Minix PC. The current sizes of flex
are:
Minix ST (ACK) Lattice (TOS) Turbo (TOS)
size 75300 83305 57957
compilation time 22' 15' 3'40"
flex -is scan.l 1'49" 43" 30"
The Minix ST size includes the bad generated code using only a subset of
the 68000 commands, long addresses only and a huge relocation table.
Therefore the PC size will be <64 k ! More serious is the fact that I had
to chmem =90000 flex to get scan.l converted to scan.c . But I never saw
a more complex lex source than scan.l -- so it should be possible to
reduce some array sizes without limitation for all day usage.
No one volunteered yet for a Minix PC port -- but if someone will try it
I would provide him with a new scan.c and some hints.
TOS:
Don't forget to adapt the flexskel path within flexdef.h !
Bitnet: V61@DHDURZ1 Ronald Lamprecht
UUCP: ...!unido!DHDURZ1.bitnet!V61 Theoretische Physik
ARPAnet: V61%DHDURZ1.BITNET@CUNYVM.CUNY.EDU (Heidelberg, West Germany)
(Message inbox:36)
Date: Wed, 05 Jul 89 21:16:07 CET
From: V61%DHDURZ1.BITNET@csa2.lbl.gov
Subject: Re: What is TOS
To: vern@lbl-csam.arpa
TOS is the name of the Atari ST operating system that is very similar
to MSDOS (Both use CR,LF as end of line character). Therefore I have
been astonished that no EOL convertion porblems occur within MSDOS.
I have been aware of the double buffering when changing read to fread and I
accept your argument of a possible slow down. But if you integrate the other
Atari - TOS changes, please insert a
#ifdef ATARI
fread ....
#else
read ....
#endif
in flex.skel .
Bitnet: V61@DHDURZ1 Ronald Lamprecht
UUCP: ...!unido!DHDURZ1.bitnet!V61 Theoretische Physik
ARPAnet: V61%DHDURZ1.BITNET@CUNYVM.CUNY.EDU (Heidelberg, West Germany)
echo x - Makefile_cdiff
sed '/^X/s///' > Makefile_cdiff << '/'
X*** Src_2.1/Makefile Thu Jun 28 00:06:42 1989
X--- Makefile Thu Jul 3 02:12:48 1989
X***************
X*** 5,10 ****
X--- 5,11 ----
X # Porting considerations:
X #
X # For System V Unix machines, add -DSYS_V to CFLAGS.
X+ # For Minix (ST), add -DSYS_V to CFLAGS
X # For Vax/VMS, add -DSYS_V to CFLAGS.
X # For MS-DOS, add "-DMS_DOS -DSYS_V" to CFLAGS. Create \tmp if not present.
X # You will also want to rename flex.skel to something with a three
X***************
X*** 21,28 ****
X SKELETON_DIR = /usr/local/lib
X SKELETON_FILE = flex.skel
X SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_DIR)/$(SKELETON_FILE)\"
X! CFLAGS = -O
X! LDFLAGS = -s
X
X FLEX_FLAGS =
X FLEX = ./flex
X--- 22,29 ----
X SKELETON_DIR = /usr/local/lib
X SKELETON_FILE = flex.skel
X SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_DIR)/$(SKELETON_FILE)\"
X! CFLAGS = -O -DSYS_V
X! LDFLAGS =
X
X FLEX_FLAGS =
X FLEX = ./flex
X***************
X*** 57,63 ****
X yylex.c
X
X flex : $(FLEXOBJS)
X! $(CC) $(CFLAGS) -o flex $(LDFLAGS) $(FLEXOBJS)
X
X first_flex:
X cp initscan.c scan.c
X--- 58,65 ----
X yylex.c
X
X flex : $(FLEXOBJS)
X! $(CC) $(CFLAGS) -o flex $(FLEXOBJS) $(LDFLAGS)
X! chmem =150000 flex
X
X first_flex:
X cp initscan.c scan.c
/
echo x - flex.skel_cdif
sed '/^X/s///' > flex.skel_cdif << '/'
X*** Src_2.1/flex.skel Thu Jun 28 00:19:20 1989
X--- flex.skel Thu Jul 2 22:18:31 1989
X***************
X*** 28,34 ****
X * is returned in "result".
X */
X #define YY_INPUT(buf,result,max_size) \
X! if ( (result = read( fileno(yyin), buf, max_size )) < 0 ) \
X YY_FATAL_ERROR( "read() in flex scanner failed" );
X #define YY_NULL 0
X #define yyterminate() return ( YY_NULL )
X--- 28,34 ----
X * is returned in "result".
X */
X #define YY_INPUT(buf,result,max_size) \
X! if ( (result = fread( buf,1, max_size, yyin )) < 0 ) \
X YY_FATAL_ERROR( "read() in flex scanner failed" );
X #define YY_NULL 0
X #define yyterminate() return ( YY_NULL )
/
echo x - flexdef.h_cdif
sed '/^X/s///' > flexdef.h_cdif << '/'
X*** Src_2.1/flexdef.h Thu Jun 28 00:43:27 1989
X--- flexdef.h Thu Jul 3 02:45:50 1989
X***************
X*** 26,31 ****
X--- 26,40 ----
X
X /* @(#) $Header$ (LBL) */
X
X+ #ifdef ATARI
X+ #define SYS_V
X+ #define abs(x) ((x) < 0 ? -(x) : (x))
X+ #define SHORT_FILE_NAMES
X+ #ifdef TURBO
X+ #define SHORT_EXTERNAL_NAMES
X+ #endif
X+ #endif
X+
X #ifndef FILE
X #include <stdio.h>
X #endif
X***************
X*** 41,47 ****
X #endif
X
X #ifndef VMS
X! char *memset();
X #else
X /* memset is needed for old versions of the VMS C runtime library */
X #define memset(s, c, n) \
X--- 50,58 ----
X #endif
X
X #ifndef VMS
X! #ifndef ATARI && TURBO
X! char *memset();
X! #endif
X #else
X /* memset is needed for old versions of the VMS C runtime library */
X #define memset(s, c, n) \
X***************
X*** 81,91 ****
X--- 92,129 ----
X #define true 1
X #define false 0
X
X+ #ifdef ATARI
X+ #define DEFAULT_SKELETON_FILE "D:\\include\\flexskel"
X+ #endif
X+
X
X #ifndef DEFAULT_SKELETON_FILE
X #define DEFAULT_SKELETON_FILE "flex.skel"
X #endif
X
X+ #ifdef SHORT_EXTERNAL_NAMES
X+ /* avoid long external names that are ambiguous within the first 8 characters */
X+ #define current_mns c__mns
X+ #define current_max_rules c__max_rules
X+ #define current_max_state_type c__max_state_type
X+ #define current_max_scs c__max_scs
X+ #define current_max_dfa_size c__max__size
X+ #define current_max_xpairs c__max_xpairs
X+ #define current_max_template_xpairs c__max_template_xpairs
X+ #define current_max_dfas c__max_dfas
X+ #define current_maxccls c__maxccles
X+ #define current_max_ccl_tbl_size c__max_ccl_tbl_size
X+ #define indent_puts ind_puts
X+ #define indent_put2s ind_put2s
X+ #define gen_next_compressed_state gen_n_comressed_state
X+ #define gen_next_match gen_n_match
X+ #define gen_next_state gen_n_state
X+ #define variable_trailing_context_rules var_tr_context_rules
X+ #define variable_trailing_rule var_tr_rule
X+ #define backtrack_report backtr_report
X+ #define backtrack_file backtr_file
X+ #endif
X+
X /* special chk[] values marking the slots taking by end-of-buffer and action
X * numbers
X */
X***************
X*** 305,311 ****
X int int_val;
X } ;
X
X! typedef struct hash_entry *hash_table[];
X
X #define NAME_TABLE_HASH_SIZE 101
X #define START_COND_HASH_SIZE 101
X--- 343,349 ----
X int int_val;
X } ;
X
X! typedef struct hash_entry **hash_table;
X
X #define NAME_TABLE_HASH_SIZE 101
X #define START_COND_HASH_SIZE 101
X***************
X*** 372,378 ****
X extern int datapos, dataline, linenum;
X extern FILE *skelfile, *yyin, *temp_action_file, *backtrack_file;
X extern char *infilename;
X! extern char action_file_name[];
X
X
X /* variables for stack of states having only one out-transition:
X--- 410,416 ----
X extern int datapos, dataline, linenum;
X extern FILE *skelfile, *yyin, *temp_action_file, *backtrack_file;
X extern char *infilename;
X! extern char *action_file_name;
X
X
X /* variables for stack of states having only one out-transition:
/
echo x - main.c_cdiff
sed '/^X/s///' > main.c_cdiff << '/'
X*** Src_2.1/main.c Thu Jun 28 00:30:39 1989
X--- main.c Thu Jul 3 02:27:47 1989
X***************
X*** 81,96 ****
X FILE *temp_action_file;
X FILE *backtrack_file;
X int end_of_buffer_state;
X! #ifndef SHORT_FILE_NAMES
X! char action_file_name[] = "/tmp/flexXXXXXX";
X! #else
X! char action_file_name[] = "flexXXXXXX.tmp";
X! #endif
X!
X #ifndef SHORT_FILE_NAMES
X static char outfile[] = "lex.yy.c";
X #else
X! static char outfile[] = "lexyy.c";
X #endif
X static int outfile_created = 0;
X
X--- 81,91 ----
X FILE *temp_action_file;
X FILE *backtrack_file;
X int end_of_buffer_state;
X! char *action_file_name;
X #ifndef SHORT_FILE_NAMES
X static char outfile[] = "lex.yy.c";
X #else
X! static char outfile[] = "lex_yy.c";
X #endif
X static int outfile_created = 0;
X
X***************
X*** 328,333 ****
X--- 323,329 ----
X {
X int i, sawcmpflag, use_stdout;
X char *arg, *skelname = NULL, *flex_gettime(), clower(), *mktemp();
X+ char *tmp_action =(char *)0, *malloc();
X
X printstats = syntaxerror = trace = spprdflt = interactive = caseins = false;
X backtrack_report = performance_report = ddebug = fulltbl = fullspd = false;
X***************
X*** 349,354 ****
X--- 345,355 ----
X for ( i = 1; arg[i] != '\0'; ++i )
X switch ( arg[i] )
X {
X+ case 'a':
X+ if ( i != 1 )
X+ flexerror( "-a flag must be given separately" );
X+ tmp_action = &arg[i+1];
X+ goto get_next_arg;
X case 'b':
X backtrack_report = true;
X break;
X***************
X*** 445,452 ****
X printstats = true;
X break;
X
X! default:
X! lerrif( "unknown flag %c", (int) arg[i] );
X break;
X }
X
X--- 446,458 ----
X printstats = true;
X break;
X
X! case '?':
X! flexinfo(0);
X! break;
X!
X! default:
X! fprintf(stderr,"flex : unknown flag %c\n", (int) arg[i] );
X! flexinfo(1);
X break;
X }
X
X***************
X*** 454,459 ****
X--- 460,493 ----
X ;
X }
X
X+
X+ /* if you change the default tmp file names don't forget to change the
X+ initialization for i, too !
X+
X+ */
X+ #ifndef SHORT_FILE_NAMES
X+ i = 10;
X+ if (!tmp_action) i += 5;
X+ #else
X+ i = 12;
X+ #endif
X+ if (tmp_action)
X+ i += strlen(tmp_action) + 1;
X+ if((action_file_name = malloc(i+1)) == (char *)0)
X+ flexerror("No memory for action_file_name");
X+ *action_file_name = (char) NULL;
X+ if (tmp_action)
X+ strcat(action_file_name,tmp_action);
X+ #ifndef SHORT_FILE_NAMES
X+ else
X+ strcat(action_file_name,"/tmp");
X+ strcat(action_file_name,"/flexXXXXXX");
X+ #else
X+ if (tmp_action)
X+ strcat(action_file_name,"/");
X+ strcat(action_file_name,"flexXXXX.tmp");
X+ #endif
X+
X if ( (fulltbl || fullspd) && usemecs )
X flexerror( "full table and -cm don't make sense together" );
X
X***************
X*** 520,526 ****
X if ( (skelfile = fopen( skelname, "r" )) == NULL )
X lerrsf( "can't open skeleton file %s", skelname );
X
X! (void) mktemp( action_file_name );
X
X if ( (temp_action_file = fopen( action_file_name, "w" )) == NULL )
X lerrsf( "can't open temporary action file %s", action_file_name );
X--- 554,562 ----
X if ( (skelfile = fopen( skelname, "r" )) == NULL )
X lerrsf( "can't open skeleton file %s", skelname );
X
X! #ifndef ATARI && LATTICE
X! (void) mktemp( action_file_name );
X! #endif
X
X if ( (temp_action_file = fopen( action_file_name, "w" )) == NULL )
X lerrsf( "can't open temporary action file %s", action_file_name );
X***************
X*** 566,571 ****
X--- 602,640 ----
X }
X
X
X+ flexinfo(status)
X+ int status;
X+ {
X+ fprintf(stderr,"Syntax : FLEX inp_file\n");
X+ fprintf(stderr,"Function: fast lexical analyzer generator V%s\n",flex_version);
X+ fprintf(stderr,"Options : a dir_path : directory path for temporary files\n");
X+ fprintf(stderr," - b : generate backtracking information to lex.backtrack\n");
X+ fprintf(stderr," - c : compressed table, no equiv., no meta equiv.classes\n");
X+ fprintf(stderr," e : equivalence classes\n");
X+ fprintf(stderr," F : fast table\n");
X+ fprintf(stderr," |f : full table\n");
X+ fprintf(stderr," |m : meta equivalence classes\n");
X+ fprintf(stderr," - d : generate debugging scanner\n");
X+ fprintf(stderr," - F : fast table\n");
X+ fprintf(stderr," - f : full (not compressed) table\n");
X+ fprintf(stderr," - I : generate interactive scanner\n");
X+ fprintf(stderr," - i : generate case-insensitive scanner\n");
X+ fprintf(stderr," - L : supress #line directives\n");
X+ /* fprintf(stderr," - n hexnum : generate scanner using <hexnum> as newline char.\n");*/
X+ fprintf(stderr," - p : generate performance report to stderr\n");
X+ fprintf(stderr," - S skeleton_path : file path for skeleton file\n");
X+ fprintf(stderr," - s : suppress echo of unmatched scanner input to stdout\n");
X+ fprintf(stderr," - T : run flex in trace mode\n");
X+ #ifdef ATARI
X+ fprintf(stderr," - t : place result on stdout instead of lex_yy.c\n");
X+ #else
X+ fprintf(stderr," - t : place result on stdout instead of lex.yy.c\n");
X+ #endif
X+ fprintf(stderr," - v : print statistics of generated scanner\n");
X+ fprintf(stderr," default = -cem\n");
X+ exit(status);
X+ }
X+
X /* readin - read in the rules section of the input file(s)
X *
X * synopsis
/
echo x - scan.l_cdiff
sed '/^X/s///' > scan.l_cdiff << '/'
X*** Src_2.1/scan.l Thu Jun 30 19:42:00 1989
X--- scan.l Thu Jul 2 22:19:26 1989
X***************
X*** 125,132 ****
X
X {SCNAME} RETURNNAME;
X ^{OPTWS}\n ++linenum; /* allows blank lines in section 1 */
X! \n ++linenum; return ( '\n' );
X! . synerr( "illegal character" ); BEGIN(RECOVER);
X
X
X <C_COMMENT>"*/" ECHO; BEGIN(0);
X--- 125,136 ----
X
X {SCNAME} RETURNNAME;
X ^{OPTWS}\n ++linenum; /* allows blank lines in section 1 */
X! {OPTWS}\n ++linenum; return ( '\n' );
X! . {
X! synerr( "illegal character" );
X! fprintf(stderr,"Char : $%x\n",yytext[yyleng-1]);
X! BEGIN(RECOVER);
X! }
X
X
X <C_COMMENT>"*/" ECHO; BEGIN(0);
X***************
X*** 206,212 ****
X <SECT2>^{OPTWS}\n ++linenum; /* allow blank lines in section 2 */
X
X /* this horrible mess of a rule matches indented lines which
X! * do not contain "/*". We need to make the distinction because
X * otherwise this rule will be taken instead of the rule which
X * matches the beginning of comments like this one
X */
X--- 210,216 ----
X <SECT2>^{OPTWS}\n ++linenum; /* allow blank lines in section 2 */
X
X /* this horrible mess of a rule matches indented lines which
X! * do not contain '/','*'. We need to make the distinction because
X * otherwise this rule will be taken instead of the rule which
X * matches the beginning of comments like this one
X */
/
echo x - Makefile.tos
sed '/^X/s///' > Makefile.tos << '/'
X# make file for "flex" tool
X
X# @(#) $Header$ (LBL)
X
X# Porting considerations:
X#
X# For System V Unix machines, add -DSYS_V to CFLAGS.
X# For Vax/VMS, add -DSYS_V to CFLAGS.
X# For MS-DOS, add "-DMS_DOS -DSYS_V" to CFLAGS. Create \tmp if not present.
X# You will also want to rename flex.skel to something with a three
X# character extension, change SKELETON_FILE below appropriately,
X# For Amiga, add "-DAMIGA -DSYS_V" to CFLAGS.
X#
X# A long time ago, flex was successfully built using Microsoft C and
X# the following options: /AL, /stack:10000, -LARGE, -Ml, -Mt128, -DSYS_V
X
X
X# the first time around use "make first_flex"
X
X# The following definitions must be set according to your compiler -
X# examples for a Lattice Compiler with GST assembler and TURBO C with
X# assembler are provided below and must just be updated (don't forget to
X# update the linker argument extension files (*.lnk,*.tlk), too) :
X#
X#CCPATH = path to compiler directory without trailing \
X#CHPATH = path to header files without trailing \
X#CC = filename of the compiler
X#CFLAGS = compiler option flags
X#CIEXT = extension of C sources that should be used for input filenames
X#ASMPATH = path to assembler directory without trailing \
X#ASM = filename of the assembler
X#AFLAGS = assembler option flags
X#AIEXT = extension of assembler sources that should be used for assembler
X# input filenames
X#AEXT = general assembler filename extension
X#LNKPATH = path to linker directory without trailing \
X#LINK = filename of the linker
X#LFLAG0 = first option (full pathname of C startupcode)
X#LFLAG1 = further options + option flag for argument extension filename
X#LFLAG2 = further options + option flag for output-filename
X#LNKEXT = extension of linker argument extension file
X#OIEXT = extension of objects that should be used for linker input files
X#OEXT = general object file extension
X
X# Lattice definitions
XCCPATH = d:\latt
XCHPATH = d:\latt\include
XCC = lc.ttp
XCFLAGS = -h -n -cw -cc -i$(CHPATH)\ -g$(CCPATH)\ -dLATTICE -dATARI
XCIEXT =
XASMPATH = d:\gst
XASM = assem.ttp
XAFLAGS = -nolist -errors errors.out
XAIEXT =
XAEXT = .asm
XLNKPATH = d:\gst
XLINK = ld.ttp
XLFLAG0 =
XLFLAG1 = -with
XLFLAG2 = -nolist -sec -mem 200 -prog
XLNKEXT = .lnk
XOIEXT =
XOEXT = .bin
X
X# Turbo definitions
X#CCPATH = d:\turbo
X#CHPATH = d:\turbo\include
X#CC = tcc.prg
X#CFLAGS = -GJMPRZ -H=$(CHPATH)\ -w- -DTURBO -DATARI
X#CIEXT = .c
X#ASMPATH = d:\turbo
X#ASM = mas.prg
X#AFLAGS =
X#AIEXT = .s
X#AEXT = .s
X#LNKPATH = d:\turbo
X#LINK = tlink.ttp
X#LFLAG0 = $(LNKPATH)\lib\tcstart.o
X#LFLAG1 = -I=
X#LFLAG2 = -O=
X#LNKEXT = .tlk
X#OIEXT = .o
X#OEXT = .o
X
X# Other definitions
X# (not used for Atari because of short argument string - defined in flexdef.h
X
XSKELETON_DIR = /usr/lib
XSKELETON_FILE = flex.skel
XSKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_DIR)/$(SKELETON_FILE)\"
X
X
XFLEX = d:\etc\flex.ttp
XFLEX_FLAGS = -is
XYACC = d:\etc\yacc.ttp
XRENAME = d:\bin\rename
XDEL = d:\bin\del
X
X# Internal definitions
XLNK = $(LNKPATH)\$(LINK)
X
XFLEXOBJS = \
X ccl$(OEXT) \
X dfa$(OEXT) \
X ecs$(OEXT) \
X gen$(OEXT) \
X main$(OEXT) \
X misc$(OEXT) \
X nfa$(OEXT) \
X parse$(OEXT) \
X scan$(OEXT) \
X sym$(OEXT) \
X tblcmp$(OEXT) \
X yylex$(OEXT)
X
XFLEX_C_SOURCES = \
X ccl.c \
X dfa.c \
X ecs.c \
X gen.c \
X main.c \
X misc.c \
X nfa.c \
X parse.c \
X scan.c \
X sym.c \
X tblcmp.c \
X yylex.c
X
Xflex : $(FLEXOBJS)
X $(LNK) $(LFLAG0) $(LFLAG1)flex$(LNKEXT) $(LFLAG2)flex.ttp
X
Xfirst_flex:
X cp initscan.c scan.c
X make $(MFLAGS) flex
X
Xparse.h parse.c : parse.y
X $(YACC) -d parse.y
X $(DEL) parse.c
X $(RENAME) y_tab.c parse.c
X $(DEL) parse.h
X $(RENAME) y_tab.h parse.h
X
Xscan.c : scan.l
X $(FLEX) $(FLEX_FLAGS) scan.l
X $(RENAME) lex_yy.c scan.c
X
Xscan$(OEXT) : scan.c parse.h flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) scan$(CIEXT)
X
Xmain$(OEXT) : main.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) main$(CIEXT)
X
Xccl$(OEXT) : ccl.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) ccl$(CIEXT)
X
Xdfa$(OEXT) : dfa.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) dfa$(CIEXT)
X
Xecs$(OEXT) : ecs.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) ecs$(CIEXT)
X
Xgen$(OEXT) : gen.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) gen$(CIEXT)
X
Xmisc$(OEXT) : misc.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) misc$(CIEXT)
X
Xnfa$(OEXT) : nfa.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) nfa$(CIEXT)
X
Xparse$(OEXT) : parse.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) parse$(CIEXT)
X
Xsym$(OEXT) : sym.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) sym$(CIEXT)
X
Xtblcmp$(OEXT) : tblcmp.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) tblcmp$(CIEXT)
X
Xyylex$(OEXT) : yylex.c flexdef.h
X $(CCPATH)\$(CC) $(CFLAGS) yylex$(CIEXT)
X
Xflex.man : flex.1
X nroff -man flex.1 >flex.man
X
Xlint : $(FLEX_C_SOURCES)
X lint $(FLEX_C_SOURCES) > flex.lint
X
Xdistrib :
X mv scan.c initscan.c
X chmod 444 initscan.c
X $(MAKE) $(MFLAGS) clean
X
Xclean :
X rm -f core errs flex *$(OEXT) parse.c *.lint parse.h flex.man tags
X
Xtags :
X ctags $(FLEX_C_SOURCES)
X
Xvms : flex.man
X $(MAKE) $(MFLAGS) distrib
X
Xtest :
X $(FLEX) $(FLEX_FLAGS) scan.l
X $(RENAME) lex_yy.c scan.ctest
X cmp scan.c scan.ctest
X
/
echo x - Readme2
sed '/^X/s///' > Readme2 << '/'
XThe changes: (1.7.89 RAL)
X
X - Bug fix: The original flex didn't like trailing spaces in exclusive start
X condition lists ! If you add an trailing space to line 68 in scan.l
X
X "%x SECT2 SECT2PROLOG SECT3 CODEBLOCK PICKUPDEF SC CARETISBOL NUM QUOTE "
X
X you get a misleading error message:
X
X "Syntax error at line 69: bad start condition list"
X
X This bug can either be fixed in parse.y or in scan.l . I have chosen the
X last because there the fix is minimal: Just change the rule (line 128)
X
X "\n" to "{OPTWS}\n"
X
X - Enhancements:
X - new option "-?" that provides some help information about the other
X flags (main.c)
X - new option "-aTMPPATH" that allows a redefinition of the standard
X path for the temporary file (this might be rather large >200k if
X F,f options are selected). (main.c, flexdef.h (l.376))
X - hexdump of illegal characters -- this proved to be a useful debugging
X tool especialy if invisible control characters occur which weren't
X covered by the rules. (scan.l fprintf statement line 129,...)
X
X - Patches due to TOS
X - General: TOS uses CR,LF as end of line char., Flex wants only a single
X LF as EOL char. Therefore all I/O must be translated using f* calls.
X This is done everywhere besides the YY_INPUT macro (flex.skel (scan.c),
X line 31) that uses a low level 'read'. This should be definitly changed
X to fread, so that all I/O calls occur on the same level.
X - the short action_file_name has been "flexXXXXXX.tmp", but that's too
X much for TOS,MSDOS ! I changed it to "flexXXXX.tmp" in main.c (patch
X covered by the -a option additions)
X - some compilers don't like external names that are ambiguous within
X the first 8 characters. I defined macros that change all these long
X external names to names that are unique within the first 8 characters.
X Just define SHORT_EXTERNAL_NAMES to use this feature (flexdef.h)
X - some statement changes that some compiler don't like:
X typedef *xxx[] -> typedef **xxx (flexdef.h.,l.308)
X "/*" -> '/','*' within a comment in (scan.l, l.209)
X - changed short "lexyy.c" to "lex_yy.c" what's more similar to the unix
X "lex.yy.c" (main.c).
X - a few further really compiler dependent changes provided with
X #ifdef ATARI && LATTICE res. TURBO braces.
X
X - Additional TOS only files
X - Makefile.tos: Common makefile for all TOS compilers. If you add further
X ones please email me the new makefile.
X - flex.lnk: Lattice - GST linker argument extension file
X - flex.tlk: Turbo linker argument extension file
X
X
XAdditional remarks:
X
XI didn't add a new initscan.c (= flex -ist scan.l). The current one is good
Xenough for a first compilation. With this first version of flex you can
Xrebuild your own scan.c and the final flex version !
X
XMinix ST :
X - I had to "chmem =70000 cv" (>50000) to get flex linked
X - 'memset' (PC 1.3, EFTH40,...) is necessary
X - chmem =90000 flex may be sufficient
X
XMinix PC :
X It should be possible to port Flex to Minix PC. The current sizes of flex
X are:
X Minix ST (ACK) Lattice (TOS) Turbo (TOS)
X
X size 75300 83305 57957
X compilation time 22' 15' 3'40"
X flex -is scan.l 1'49" 43" 30"
X
X The Minix ST size includes the bad generated code using only a subset of
X the 68000 commands, long addresses only and a huge relocation table.
X Therefore the PC size will be <64 k ! More serious is the fact that I had
X to chmem =90000 flex to get scan.l converted to scan.c . But I never saw
X a more complex lex source than scan.l -- so it should be possible to
X reduce some array sizes without limitation for all day usage.
X
X No one volunteered yet for a Minix PC port -- but if someone will try it
X I would provide him with a new scan.c and some hints.
X
XTOS:
X Don't forget to adapt the flexskel path within flexdef.h !
X
X
/
echo x - flex.lnk
sed '/^X/s///' > flex.lnk << '/'
X*
X*
X* linker control file for flex.ttp
X*
X*
X*
XINPUT d:\latt\lib\startup.bin
X*
XINPUT ccl.bin
XINPUT dfa.bin
XINPUT ecs.bin
XINPUT gen.bin
XINPUT misc.bin
XINPUT nfa.bin
XINPUT parse.bin
XINPUT sym.bin
XINPUT tblcmp.bin
XINPUT main.bin
XINPUT yylex.bin
XINPUT scan.bin
X*
XLIBRARY d:\latt\lib\clib.bin
X
/
echo x - flex.tlk
sed '/^X/s///' > flex.tlk << '/'
Xccl.o
Xdfa.o
Xecs.o
Xgen.o
Xmisc.o
Xnfa.o
Xparse.o
Xsym.o
Xtblcmp.o
Xyylex.o
Xmain.o
Xscan.o
Xd:\turbo\lib\tcstdlib.lib ; standard lib
Xd:\turbo\lib\tcextlib.lib ; extended lib
Xd:\turbo\lib\tctoslib.lib ; TOS lib
Xd:\turbo\lib\tcgemlib.lib ; AES and VDI lib
X-S=200000
/

View file

@ -0,0 +1,419 @@
Received: from 128.140.1.1 by ee.lbl.gov for <vern@ee.lbl.gov> (8.6.9/1.43r)
id HAA01193; Thu, 29 Sep 1994 07:26:54 -0700
Received: from larry-le0.cc.emory.edu by
emoryu1.cc.emory.edu (5.65/Emory_cc.4.0.1) via SMTP
id AA07292 ; Thu, 29 Sep 94 10:26:41 -0400
From: tkane01@unix.cc.emory.edu (Terrence O Kane)
Received: by larry.cc.emory.edu (5.0) id AA11757; Thu, 29 Sep 1994 10:26:43 +0500
Message-Id: <9409291426.AA11757@larry.cc.emory.edu>
Subject: patches and makefile for Borland C 4.02, flex 2.4.7
To: vern@ee.lbl.gov
Date: Thu, 29 Sep 1994 10:26:42 -0400 (EDT)
X-Mailer: ELM [version 2.4 PL23]
Mime-Version: 1.0
Content-Type: text/plain; charset=US-ASCII
Content-Transfer-Encoding: 7bit
Content-Length: 9900
Enclosed are unified diffs and a makefile for Borland 4.02
The changes in the enclosed are 1) make the size parameters for memory
allocation "size_t", 2) change an include file when the lexer is
compiled within 'extern "C" {...}' in a C++ file, and 3) include pragmas
in the header suitable for BCC 4.02 to hush on warnings.
The latter is done because of the limit on command line size. A tradeoff
exists between putting pragmas in the header, or #defines in the header -
I put in the pragmas since they're suppoed to be ignored unless
understood - *and* they're enclosed in BCC specific ifdefs, anyway.
All changes are enclosed in "#ifdef __BORLANDC__".
--- misc.c Tue Jan 04 14:33:10 1994
+++ ../misc.c Wed Sep 28 18:44:32 1994
@@ -55,15 +55,19 @@
action_index += len;
}
/* allocate_array - allocate memory for an integer array of the given size */
void *allocate_array( size, element_size )
+#ifndef __BORLANDC__
int size, element_size;
+#else /* __BORLANDC__ */
+size_t size, element_size;
+#endif /* __BORLANDC__ */
{
register void *mem;
/* On 16-bit int machines (e.g., 80286) we might be trying to
* allocate more than a signed int can hold, and that won't
* work. Cheap test:
*/
@@ -634,15 +638,19 @@
}
/* reallocate_array - increase the size of a dynamic array */
void *reallocate_array( array, size, element_size )
void *array;
+#ifndef __BORLANDC__
int size, element_size;
+#else /* __BORLANDC__ */
+size_t size, element_size;
+#endif /* __BORLANDC__ */
{
register void *new_array;
/* Same worry as in allocate_array(): */
if ( size * element_size <= 0 )
flexfatal(
"attempt to increase array size by less than 1 byte" );
@@ -739,15 +747,19 @@
}
/* The following is only needed when building flex's parser using certain
* broken versions of bison.
*/
void *yy_flex_xmalloc( size )
+#ifndef __BORLANDC__
int size;
+#else /* __BORLANDC__ */
+size_t size;
+#endif /* __BORLANDC__ */
{
void *result = flex_alloc( size );
if ( ! result )
flexfatal( "memory allocation failed in yy_flex_xmalloc()" );
return result;
--- skel.c Wed Aug 03 11:38:32 1994
+++ ../skel.c Wed Sep 28 18:50:58 1994
@@ -26,15 +26,19 @@
"",
"#ifdef __cplusplus",
"",
"#include <stdlib.h>",
"%+",
"class istream;",
"%*",
+ "#ifndef __BORLANDC__",
"#include <unistd.h>",
+ "#else /* __BORLANDC__ */",
+ "#include <io.h>",
+ "#endif /* __BORLANDC__ */",
"",
"/* Use prototypes in function declarations. */",
"#define YY_USE_PROTOS",
"",
"/* The \"const\" storage-class-modifier is valid. */",
"#define YY_USE_CONST",
"",
@@ -240,16 +244,21 @@
"static int yy_start_stack_depth = 0;",
"static int *yy_start_stack = 0;",
"static void yy_push_state YY_PROTO(( int new_state ));",
"static void yy_pop_state YY_PROTO(( void ));",
"static int yy_top_state YY_PROTO(( void ));",
"%*",
"",
+ "#ifndef __BORLANDC__",
"static void *yy_flex_alloc YY_PROTO(( unsigned int ));",
"static void *yy_flex_realloc YY_PROTO(( void *, unsigned int ));",
+ "#else /* __BORLANDC__ */",
+ "static void *yy_flex_alloc YY_PROTO(( size_t ));",
+ "static void *yy_flex_realloc YY_PROTO(( void *, size_t ));",
+ "#endif /* __BORLANDC__ */",
"static void yy_flex_free YY_PROTO(( void * ));",
"",
"#define yy_new_buffer yy_create_buffer",
"",
"%% yytext/yyin/yyout/yy_state_type/yylineno etc. def's & init go here",
"",
"#ifndef yytext_ptr",
--- initscan.c Wed Aug 03 11:42:46 1994
+++ ../initscan.c Wed Sep 28 18:51:34 1994
@@ -16,15 +16,19 @@
#endif
#endif
#ifdef __cplusplus
#include <stdlib.h>
+#ifndef __BORLANDC__
#include <unistd.h>
+#else /* __BORLANDC__ */
+#include <io.h>
+#endif /* __BORLANDC__ */
/* Use prototypes in function declarations. */
#define YY_USE_PROTOS
/* The "const" storage-class-modifier is valid. */
#define YY_USE_CONST
@@ -220,16 +224,21 @@
static int yy_start_stack_ptr = 0;
static int yy_start_stack_depth = 0;
static int *yy_start_stack = 0;
static void yy_push_state YY_PROTO(( int new_state ));
static void yy_pop_state YY_PROTO(( void ));
static int yy_top_state YY_PROTO(( void ));
+#ifndef __BORLANDC__
static void *yy_flex_alloc YY_PROTO(( unsigned int ));
static void *yy_flex_realloc YY_PROTO(( void *, unsigned int ));
+#else /* __BORLANDC__ */
+static void *yy_flex_alloc YY_PROTO(( size_t ));
+static void *yy_flex_realloc YY_PROTO(( void *, size_t ));
+#endif /* __BORLANDC__ */
static void yy_flex_free YY_PROTO(( void * ));
#define yy_new_buffer yy_create_buffer
#define INITIAL 0
#define SECT2 1
#define SECT2PROLOG 2
--- flexdef.h Tue Jan 04 14:33:14 1994
+++ ../flexdef.h Wed Sep 28 18:53:44 1994
@@ -27,14 +27,25 @@
*/
/* @(#) $Header$ (LBL) */
#include <stdio.h>
#include <ctype.h>
+#ifdef __BORLANDC__
+#include <malloc.h>
+
+#pragma warn -pro
+#pragma warn -rch
+#pragma warn -use
+#pragma warn -aus
+#pragma warn -par
+#pragma warn -pia
+
+#endif /* __BORLANDC__ */
#if HAVE_STRING_H
#include <string.h>
#else
#include <strings.h>
#endif
#if __STDC__
@@ -607,19 +618,29 @@
*/
extern char nmstr[MAXLINE];
extern int sectnum, nummt, hshcol, dfaeql, numeps, eps2, num_reallocs;
extern int tmpuses, totnst, peakpairs, numuniq, numdup, hshsave;
extern int num_backing_up, bol_needed;
+#ifndef __BORLANDC__
void *allocate_array PROTO((int, int));
void *reallocate_array PROTO((void*, int, int));
+#else /* __BORLANDC__ */
+void *allocate_array PROTO((size_t, size_t));
+void *reallocate_array PROTO((void*, size_t, size_t));
+#endif /* __BORLANDC__ */
+#ifndef __BORLANDC__
void *flex_alloc PROTO((unsigned int));
void *flex_realloc PROTO((void*, unsigned int));
+#else /* __BORLANDC__ */
+void *flex_alloc PROTO((size_t));
+void *flex_realloc PROTO((void*, size_t));
+#endif /* __BORLANDC__ */
void flex_free PROTO((void*));
#define allocate_integer_array(size) \
(int *) allocate_array( size, sizeof( int ) )
#define reallocate_integer_array(array,size) \
(int *) reallocate_array( (void *) array, size, sizeof( int ) )
@@ -772,15 +793,19 @@
/* Write out one section of the skeleton file. */
extern void skelout PROTO((void));
/* Output a yy_trans_info structure. */
extern void transition_struct_out PROTO((int, int));
/* Only needed when using certain broken versions of bison to build parse.c. */
+#ifndef __BORLANDC__
extern void *yy_flex_xmalloc PROTO(( int ));
+#else /* __BORLANDC__ */
+extern void *yy_flex_xmalloc PROTO(( size_t ));
+#endif /* __BORLANDC__ */
/* Set a region of memory to 0. */
extern void zero_out PROTO((char *, int));
/* from file nfa.c */
###############################################################################
# Makefile for flex 2.4.7 with Borland C/C++ version 4.02
#
# This will probably need to be adjusted for your existing lexer/parser
# generators. See definitions for FLEX and YACC near the bottom of the
# makefile.
#
# Copy initscan.c to scan.c to make your first executable. After that,
# you may choose to try alternate compression options for your everyday
# flex executable.
#
# This will build flex with the large model. Don't use huge, but if you
# feel like experimenting with other models, post your success stories to
# comp.compilers, OK?
#
# This makefile does *not* implement the big testing found in "makefile.in".
#
# I also assume the availability of sed and the gnu file utilities on the
# system - they're readily available, so if you don't have them, why not?
# <grin>
#
# The resulting generated lexer (the real goal, right?) will compile
# (and run nicely, too) as a .c file, as well as being included such as
# extern "C" { #include "lexyyc" } in a .cplusplus file.
#
###############################################################################
DEBUG = 1
.autodepend
all: flex.exe
###############################################################################
#
# standard utilitities? ha.
#
CC = bcc
CPP = bcc
###############################################################################
#
MODEL = l
!if $(DEBUG) == 1
!message Building with debug.
debugCompile = -v
debugLink = /v
!else
!message Building without debug.
debugCompile =
debugLink =
!endif
LOADER = c0$(MODEL).obj
LIBS = c$(MODEL).lib
LINKFLAGS = $(debugLink)
DATASEG = -dc -Ff
SizeOPT = -Os -G-
Defines = -DSHORT_FILE_NAMES=1 -DHAVE_STRING_H=1
COMMON = -A -c -m$(MODEL) $(SizeOPT) $(DATASEG) $(Defines) $(debugCompile)
CFLAGS = -o$@ $(COMMON)
CCFLAGS = -o$@ $(COMMON) -Pcc
###############################################################################
.SUFFIXES: .cc
.cc.obj:
$(CPP) $(CCFLAGS) $<
.c.obj:
$(CPP) $(CFLAGS) $<
###############################################################################
#
# source & object files
#
SRC = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.c \
scan.c sym.c tblcmp.c yylex.c skel.c
OBJS = $(SRC:.c=.obj)
objects: $(OBJS)
@echo $(OBJS)
###############################################################################
#
# Executable
#
flex.exe: $(OBJS)
tlink $(LINKFLAGS) @&&!
$(LOADER) $**
$&.exe
$&.map
$(LIBS)
!
#
###############################################################################
#
# Lex files
#
FLEX = .\flex
FLEX_FLAGS = -ist
scan.c: scan.l
$(FLEX) $(FLEX_FLAGS) scan.l >scan.tmp
sed s,\"$(srcdir)/scan.l\",\"scan.l\", <scan.tmp >scan.c
@rm scan.tmp
###############################################################################
#
# YACC files
#
YACC = .\bison
YFLAGS = -vdyl
parse.c: parse.y
$(YACC) -ydl parse.y
@sed "/extern char.*malloc/d" <y_tab.c >parse.c
@rm -f y_tab.c
@mv y_tab.h parse.h
#
# end Makefile
#
###############################################################################

View file

@ -0,0 +1,179 @@
Received: from 128.84.254.220 by ee.lbl.gov for <vern@ee.lbl.gov> (8.6.8.1/1.43r)
id PAA27266; Mon, 18 Apr 1994 15:08:26 -0700
Received: from CLOYD.CS.CORNELL.EDU by thialfi.cs.cornell.edu (5.67/I-1.99E)
id AA28742; Mon, 18 Apr 94 18:08:14 -0400
Received: from iraun1.ira.uka.de by cloyd.cs.cornell.edu (5.67/I-1.99D)
id AA19613; Mon, 18 Apr 94 18:08:19 -0400
Received: from t500i2.telematik.informatik. (actually t500i2.telematik.informatik.uni-karlsruhe.de)
by iraun1.ira.uka.de with SMTP (PP); Tue, 19 Apr 1994 00:07:55 +0200
Received: by t500i2.telematik.informatik.uni-karlsruhe.de (5.57/Ultrix3.0-C)
id AA10269; Tue, 19 Apr 94 00:09:14 +0200
From: beigl@t500i2.telematik.informatik.uni-karlsruhe.de (Michael Beigl)
Message-Id: <9404182209.AA10269@t500i2.telematik.informatik.uni-karlsruhe.de>
Subject: Makefile-TurboC
To: vern@cs.cornell.edu
Date: Tue, 19 Apr 1994 00:09:13 +0200 (MET DST)
X-Mailer: ELM [version 2.4 PL22]
Mime-Version: 1.0
Content-Type: text/plain; charset=US-ASCII
Content-Transfer-Encoding: 7bit
Content-Length: 2739
Hello
Here are some additional adjustments to my Makefile. I was using "pure" DOS
and an old Turbo C++ 1.0 version, so I had some problems with systemtools
like mv etc. and problems with variables in my Makefile.
Now follows my Makefile
############################################################################
# make file for "flex" tool
# @(#) $Header$ (LBL)
# Porting considerations:
#
# For BSD machines:
# CFLAGS =
# LDFLAGS = -s
# LINK = $(CC) $(CFLAGS) -o flex $(LDFLAGS) $(FLEXOBJS)
# SKELETON_DIR = .
# SKELETON_FILE = flex.skel
# SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_DIR)/$(SKELETON_FILE)\"
# O = o
# YTAB = y.tab
# FLEX = ./flex
#
# For System V Unix or Vax/VMS machines, merely add:
# CFLAGS = -DSYS_V
#
# For MS-DOS, Turbo C:
CC = tcc
# -2+ 286 Options
CFLAGS = -DSYS_V -DMS_DOS -O -G -Z -ml -v -2
# /3 enable 32 bit processing
# /ye expanded memory swapping
# /yx extended memory swapping
LINK = tlink @flex.lnk/c/x/v/3/ye
SKELETON_DIR = .
SKELETON_FILE = flex.skl
SKELFLAGS = -DDEFAULT_SKELETON_FILE="$(SKELETON_DIR)/$(SKELETON_FILE)"
O = obj
EXE = .exe
YTAB = y_tab
FLEX = flex
YACC = /yacc/byacc
#
# the first time around use "make first_flex"
#
FLEX_FLAGS =
FLEXOBJS = \
ccl.$O \
dfa.$O \
ecs.$O \
gen.$O \
main.$O \
misc.$O \
nfa.$O \
parse.$O \
scan.$O \
sym.$O \
tblcmp.$O \
yylex.$O
FLEX_C_SOURCES = \
ccl.c \
dfa.c \
ecs.c \
gen.c \
main.c \
misc.c \
nfa.c \
parse.c \
scan.c \
sym.c \
tblcmp.c \
yylex.c
FLEX_C_SOURCES_1 = \
ccl.c \
dfa.c \
ecs.c \
gen.c \
main.c \
misc.c
FLEX_C_SOURCES_2 = \
nfa.c \
parse.c \
scan.c \
sym.c \
tblcmp.c \
yylex.c
flex.exe: $(FLEXOBJS)
$(LINK)
flex: $(FLEX_C_SOURCES)
$(CC) $(CFLAGS) -c $(SKELFLAGS) $(FLEX_C_SOURCES_1)
$(CC) $(CFLAGS) -c $(SKELFLAGS) $(FLEX_C_SOURCES_2)
$(LINK)
first_flex:
copy initscan.c scan.c
$(MAKE) flex
parse.h parse.c: parse.y
$(YACC) -d parse.y
@rename $(YTAB).c parse.c
@rename $(YTAB).h parse.h
scan.c: scan.l
$(FLEX) -ist $(FLEX_FLAGS) scan.l >scan.c
scan.$O: scan.c parse.h
main.$O: main.c
$(CC) $(CFLAGS) -c $(SKELFLAGS) main.c
flex.man: flex.1
nroff -man flex.1 >flex.man
lint: $(FLEX_C_SOURCES)
lint $(FLEX_C_SOURCES) > flex.lint
distrib:
rename scan.c initscan.c
attrib +R -A -H -S initscan.c
$(MAKE) clean
clean:
del *.obj
del *.lint
del core
del errs
del flex.exe
del parse.c
del parse.h
del flex.man
del tags
tags:
ctags $(FLEX_C_SOURCES)
vms: flex.man
$(MAKE) distrib
test:
$(FLEX) -ist $(FLEX_FLAGS) scan.l | diff scan.c -
############################################################################
I think this Makefile will help some other simple DOS user
M. Beigl

View file

@ -0,0 +1,163 @@
###############################################################################
# Makefile for flex 2.5.0.6 (beta) with Borland C/C++ version 4.02
#
# This will probably need to be adjusted for your existing lexer/parser
# generators. See definitions for FLEX and YACC near the bottom of the
# makefile.
#
# This makefile builds initflex.exe and flex.exe by default. It
# removes initflex.exe after making flex.exe. After that, you may
# choose to try alternate compression options for your everyday flex
# executable.
#
# This will build flex with the large model. Don't use huge, but if you
# feel like experimenting with other models, post your success stories to
# comp.compilers, OK?
#
# This makefile does *not* implement the big testing found in "makefile.in".
#
# I also assume the availability of sed and the gnu file utilities on the
# system - they're readily available, so if you don't have them, why not?
# <grin>
#
# The resulting generated lexer (the real goal, right?) will compile
# (and run nicely, too) as a .c file, as well as being included such as
# extern "C" { #include "lexyyc" } in a .cplusplus file.
#
###############################################################################
DEBUG = 1
.autodepend
all: initflex.exe flex.exe
rm initflex.exe initflex.map
###############################################################################
#
# standard utilitities? ha.
#
CC = bcc
CPP = bcc
###############################################################################
#
MODEL = l
!if $(DEBUG) == 1
!message Building with debug.
debugCompile = -v
debugLink = /v
!else
!message Building without debug.
debugCompile =
debugLink =
!endif
LOADER = c0$(MODEL).obj
LIBS = c$(MODEL).lib
LINKFLAGS = $(debugLink)
DATASEG = -dc -Ff
SizeOPT = -Os -G-
Defines =
COMMON = -A -c -m$(MODEL) $(SizeOPT) $(DATASEG) $(Defines) $(debugCompile)
CFLAGS = -o$@ $(COMMON)
CCFLAGS = -o$@ $(COMMON) -Pcc
###############################################################################
.SUFFIXES: .cc
.cc.obj:
$(CPP) $(CCFLAGS) $<
.c.obj:
$(CPP) $(CFLAGS) $<
###############################################################################
#
# source & object files
#
BASESRC = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.c \
sym.c tblcmp.c yylex.c skel.c
INITSRC = $(BASESRC) initscan.c
INITOBJS = $(INITSRC:.c=.obj)
SRC = $(BASESRC) scan.c
OBJS = $(SRC:.c=.obj)
objects: $(OBJS)
@echo $(OBJS)
###############################################################################
#
# Executable
#
initflex.exe: $(INITOBJS)
tlink $(LINKFLAGS) @&&!
$(LOADER) $**
$&.exe
$(LIBS)
!
flex.exe: $(OBJS)
tlink $(LINKFLAGS) @&&!
$(LOADER) $**
$&.exe
$(LIBS)
!
#
###############################################################################
#
# Lex files
#
FLEX = .\initflex
FLEX_FLAGS = -ist
scan.c: scan.l
$(FLEX) $(FLEX_FLAGS) scan.l >scan.tmp
sed s,\"$(srcdir)/scan.l\",\"scan.l\", <scan.tmp >scan.c
@rm scan.tmp
###############################################################################
#
# YACC files
#
YACC = .\bison
YFLAGS = -vdyl
parse.c: parse.y
$(YACC) -ydl parse.y
@sed "/extern char.*malloc/d" <y_tab.c >parse.c
@rm -f y_tab.c
@mv y_tab.h parse.h
###############################################################################
#
# cleanup
#
clean:
-rm *.obj *.map initflex.exe
realclean: clean
-rm flex.exe
#
# end Makefile
#
###############################################################################

View file

@ -0,0 +1,66 @@
Received: from 128.140.1.1 by ee.lbl.gov for <vern@ee.lbl.gov> (8.6.9/1.43r)
id PAA03966; Tue, 24 Jan 1995 15:03:57 -0800
Received: from larry-le0.cc.emory.edu by
emoryu1.cc.emory.edu (5.65/Emory_cc.4.0.1) via SMTP
id AA24158 ; Tue, 24 Jan 95 17:18:18 -0500
From: tkane01@unix.cc.emory.edu (Terrence O Kane)
Received: by larry.cc.emory.edu (5.0) id AA21979; Tue, 24 Jan 1995 17:17:40 -0500
Message-Id: <9501242217.AA21979@larry.cc.emory.edu>
Subject: Re: Beta test for DOS
To: vern@ee.lbl.gov (Vern Paxson)
Date: Tue, 24 Jan 1995 17:17:38 -0500 (EST)
In-Reply-To: <199501232138.NAA11430@daffy.ee.lbl.gov> from "Vern Paxson" at Jan 23, 95 01:38:02 pm
X-Mailer: ELM [version 2.4 PL23]
Mime-Version: 1.0
Content-Type: text/plain; charset=US-ASCII
Content-Transfer-Encoding: 7bit
Content-Length: 5792
Vern,
I've made flex 2.5.0.6 successfully with no changes to the source
code at all. I'm including the Borland 4.02 makefile and config.h
at the end of this message.
When you're ready for release, I'll be happy to take care of getting
the appropriate archive files up to Simtel if you wish.
I have not used this version for any of my "work-related" scanners
yet, but have run the fastwc benchmark. The compiles were for large
memory model and optimization for fastest possible code. The test
machine was a Pentium-90 (hey! timing output was integer!) with
enhanced IDE on a PCI bus and no file system caching. I ran the
test on two different input files.
(Times are in seconds.)
The first input was a typical postscript file concatenated 10 times;
by typical, I mean that there were relatively few spaces, lots of lines
with no space, using lots of parentheses.
lines words characters
91200 356260 5889240
mywc 8.89
wc1s 15.22 default
wc1 10.82 -Cf
wc2 10.16 -Cf
wc3 9.17 -Cf
wc4 9.22 -Cf
wc5 10.98 -Cf
The second test run was on a file that consisted of 20 concatenations
of 'misc/flex.man'.
lines words characters
69960 305140 2399960
mywc 4.01
wc1s 6.87
wc1 5.32
wc2 4.95
wc3 4.12
wc4 4.12
wc5 5.05
[[Makefile and config.h moved to separate files -VP]]

View file

@ -0,0 +1,29 @@
/* $Header$ */
/* ------------------------------------------------ */
/* version of config.h for Borland C/C++ v4.02 */
/* flex version 2.5.0.6 (beta) */
/* ------------------------------------------------ */
/* Define to empty if the keyword does not work. */
#undef const
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* Define if you have the ANSI C header files. */
#define STDC_HEADERS 1
/* Define if you have the <malloc.h> header file. */
#define HAVE_MALLOC_H 1
/* Define if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#undef HAVE_ALLOCA_H
/* Define if platform-specific command line handling is necessary. */
#undef NEED_ARGV_FIXUP

View file

@ -0,0 +1,48 @@
Return-Path: Mark_Ganter@liz.com
Received: from 192.216.61.11 by horse.ee.lbl.gov for vern (5.65/1.43r)
id AA02152; Tue, 11 Jan 94 06:19:36 -0800
Received: from melonville.radiomail.net (mayberry.radiomail.net) by radiomail.net with SMTP id AA20220
(5.65c+/IDA-1.4.4 for <vern@horse.ee.lbl.gov>); Tue, 11 Jan 1994 06:19:35 -0800
Message-Id: <199401111419.AA20220@radiomail.net>
Received: from liz.com by melonville.radiomail.net with CCGW-1.7(930217);
Tue, 11 Jan 94 06:19:17
From: Mark_Ganter@liz.com
Date: 11 Jan 94 09:05
To: vern@horse.ee.lbl.gov
Subject: Re[2]: Flex on an AS400
I have no problem at all with being a contact for advice
on porting Flex to EBCDIC. The code was put on an AS400, so
filing the message under /MISC/AS400 is more appropriate.
The port was an interesting, very educational experience.
Thanks again.
Mark
------------------------------------------------------------------------
Date: Tue, 18 Apr 1995 12:33:48 -0400
To: "Michael W. Duffy" <mduffy@netcom.com>, Mark_Ganter@liz.com,
vern@ee.lbl.gov (Vern Paxson), slayten@cas.org
From: slayten@cas.org (Steve Layten)
Subject: RE: Porting LEX scanner on EBCDIC machine
X-Mailer: <Windows Eudora Version 2.0.2>
Content-Length: 918
I came in late on this discussion - I don't follow comp.compilers very
closely these days because my job has shifted somewhat.
I ported (quite some time ago) flex 2.3.6 to an IBM 3090 under MVS, using
the SAS C compiler. The approach I used was, as Vern suggested, was to
translate the tables to reflect EBCDIC-based indices. I haven't even
downloaded flex 2.4 yet, so I don't know what's in the current distribution.
My patches were in the flex 2.3 distribution for a while in the MISC
directory. If you want any more info feel free to drop me a line - I still
have (somewhere) the patches that I created from version 2.3.6.
Steve Layten
--
Steven W. Layten, Senior Research Scientist
Chemical Abstracts Service PO BOX 3012, Columbus, OH 43210 +1 614 447 3600
INET: slayten@cas.org FAX: +1 614 447 3813
# # Speaking only for myself, and NOT for Chemical Abstracts Service! # # #

View file

@ -0,0 +1,115 @@
#
# make file for "flex" tool
# @(#) $Header: /usr/fsys/odin/a/vern/flex/RCS/Makefile,v 2.9 90/05/26 17:28:44
vern Exp $ (LBL)
#
# the first time around use "make f_flex"
#
# This makefile is specific for Microsoft's C/C++ compiler (v7), nmake and
# lib
# - Paul Stuart, Jan 93 (pjs@scammell.ecos.tne.oz.au)
#
SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"c:/src/flex/flex.skl\"
CFLAGS = -nologo -AL -W2 -F 8000 -Ox -Gt16000 -DMS_DOS -DUSG
LDFLAGS = /nologo /NOI /BATCH /ONERROR:NOEXE /STACK:8000
FLEX_FLAGS = -ist8 -Sflex.skl
FLEX = .\flex.exe
CC = cl
YACC = c:\lib\byacc
MAKE = nmake /nologo
#
# break obj-list into two because of 128 character command-line limit of
# Microsoft's link and lib utilities.
#
FLEXOBJS1 = \
ccl.obj \
dfa.obj \
ecs.obj \
gen.obj \
main.obj \
misc.obj \
nfa.obj \
parse.obj
FLEXOBJS2 = \
scan.obj \
sym.obj \
tblcmp.obj \
yylex.obj
FLEX_C_SOURCES = \
ccl.c \
dfa.c \
ecs.c \
gen.c \
main.c \
misc.c \
nfa.c \
parse.c \
scan.c \
sym.c \
tblcmp.c \
yylex.c
FLEX_LIB_OBJS = \
libmain.obj
all : flex.exe
#
# lib is used to get around the 128 character command-line limit of 'link'.
#
flex.exe : $(FLEXOBJS1) $(FLEXOBJS2)
lib /nologo tmplib $(FLEXOBJS1);
link $(LDFLAGS) $(FLEXOBJS2),$*.exe,,tmplib;
del tmplib.lib
f_flex:
copy initscan.c scan.c
touch scan.c
@echo compiling first flex
$(MAKE) flex.exe
del scan.c
@echo using first flex to generate final version...
$(MAKE) flex.exe
#
# general inference rule
#
.c.obj:
$(CC) -c $(CFLAGS) $*.c
parse.h parse.c : parse.y
$(YACC) -d parse.y
@mv y_tab.c parse.c
@mv y_tab.h parse.h
scan.c : scan.l
$(FLEX) $(FLEX_FLAGS) $(COMPRESSION) scan.l >scan.c
scan.obj : scan.c parse.h flexdef.h
main.obj : main.c flexdef.h
$(CC) $(CFLAGS) -c $(SKELFLAGS) main.c
ccl.obj : ccl.c flexdef.h
dfa.obj : dfa.c flexdef.h
ecs.obj : ecs.c flexdef.h
gen.obj : gen.c flexdef.h
misc.obj : misc.c flexdef.h
nfa.obj : nfa.c flexdef.h
parse.obj : parse.c flexdef.h
sym.obj : sym.c flexdef.h
tblcmp.obj : tblcmp.c flexdef.h
yylex.obj : yylex.c flexdef.h
clean :
del *.obj
del *.map

View file

@ -0,0 +1,6 @@
@echo off
sed -e "s/y\.tab\./parse_tab\./" -e "/sed/ s/'/\"/g" < Makefile.in > Makefile
sed -f MISC/MSDOS/djgpp.sed Makefile.in > Makefile
update initscan.c scan.c

View file

@ -0,0 +1,12 @@
s/y\.tab\./parse_tab\./
s/@DEFS@/-DMS_DOS/
s/@LIBS@//
s/@srcdir@/./
s/@YACC@/bison/
s/@CC@/gcc/
s/@RANLIB@/ranlib/
s/@ALLOCA@//
/^flex/ s/\.bootstrap//
/sed.*extern.*malloc/ c\
@mv parse_tab.c parse.c
/rm.*parse_tab.c/ d

View file

@ -0,0 +1,56 @@
(Message inbox:40)
Date: Tue, 17 Jul 1990 11:56 EDT
From: swl26%CAS.BITNET@CORNELLC.cit.cornell.edu
Subject: Re(2): port of flex-2.3 to IBM/MVS
To: vern@cs.cornell.edu
>Message received. I'm sending this response to
>swl26%CAS.BITNET@CORNELLC.cit.cornell.edu.
Great -- we can talk.
>How extensive are the diffs? If they're fairly short then yes, please
>send them. If they're pretty involved then probably not, as I'm not aware
>of many MVS flex users ...
I've built a context diff file which is ~850 lines.
Summary of major changes necessary:
o a new initscan.c -- because MVS is ebcdic, the initial scanner had
to be changed. I built a scanner from scan.l using -Ce, then
hand-manipulated the yy_ec table to fit EBCDIC instead of ASCII
chars. (This is not included in the diff file above.)
o changes in main and flexdef.h to change how files are handled. (No
dynamic file names, etc.)
o Some lines had to be shortened to 80 bytes. This mostly impacted
your RCSID lines, which with the full path name were too long.
o SASC and the linker don't allow externals to be longer than 8 chars.
I thus wrote a Q&D program to shorten all externals. (This would be
a separate file 'fixit.l', which is not included in the diffs.)
o There are several places where there are tests for 'isascii' (which I
deleted conditionally, using #ifdefs), and tests for 'A' <= x <= 'Z'
which I changed to 'isupper'.
Many of the changes I've incorporated without impacting other systems.
Others are with 'ifdefs'. Still others (the short external names and new
initscan) are 'isolable' as separate files which would have to be
included with a distribution.
Obviously, you are not going to want to (even if you can :-) ) worry about
testing new versions in the MVS environment. Likewise, I don't have the
time or resources to provide much support. (I'm not sure my management
would allow any :-( )
With all of the above feel free to say "Thanks, but no thanks." If you
want to see the diffs anyway, I will certainly mail them.
Thanks for your time and efforts.
Steve Layten
Chemical Abstracts Service, PO Box 3012, Columbus, OH 43210, +1 614 421-3600
INET: swl26%cas.BITNET@CUNYVM.CUNY.Edu

View file

@ -0,0 +1,23 @@
(Message inbox:47)
Date: Wed, 18 Jul 1990 14:16 EDT
From: swl26%CAS.BITNET@CORNELLC.cit.cornell.edu
Subject: Re(2): Re(2): diffs for mvs port of flex-2.3
To: vern@cs.cornell.edu
>Thanks, I've successfully unpacked the archive. I may simply distribute
>the diffs as a set of files in the MISC/ directory rather than incorporating
>them into the 2.4 release. Let me know if you don't want me to do so.
>
> Vern
Thank you! What you propose is okay. I might suggest, however, that you
look in the diffs for dfa.c, misc.c, and yylex.c, and consider removing
some of the ASCIIisms which are probably unnecessary. The manner in
which I made the changes was pure brute force, and there might be a
better way, but the changes I made there shouldn't hurt anything.
regards,
Steve

View file

@ -0,0 +1,341 @@
Received: from CU-ARPA.CS.CORNELL.EDU by loki.cs.cornell.edu (5.61/I-1.91f)
id AA25874; Wed, 18 Jul 90 12:02:22 -0400
Message-Id: <9007181320.AA24810@cu-arpa.cs.cornell.edu>
Received: from CORNELLC.CIT.CORNELL.EDU by cu-arpa.cs.cornell.edu (5.61+2/1.91d)
id AA24810; Wed, 18 Jul 90 09:20:21 -0400
Received: from CORNELLC by CORNELLC.cit.cornell.edu (IBM VM SMTP R1.2.1MX) with BSMTP id 6769; Wed, 18 Jul 90 09:18:46 EDT
Received: from CAS.BITNET (MAILER) by CORNELLC (Mailer R2.05X) with BSMTP id
5378; Wed, 18 Jul 90 09:18:38 EDT
From: swl26%CAS.BITNET@CORNELLC.cit.cornell.edu
Date: Wed, 18 Jul 1990 09:16 EDT
Subject: Re(2): diffs for mvs port of flex-2.3
In-Reply-To: Your message of Tue, 17 Jul 90 17:42:3
To: vern@cs.cornell.edu
Sorry about the trailing blank problem. It's farily common with data sent
through bitnet paths, but ever the optimist ...
>I think there should be an 'M' at the beginning of the second line.
This isn't a problem. I believe that the first byte of the line indicates
it's length (in some manner).
Rather than re-send the data, how about a uudecode that compensates for
the trailing blank problem? I manually mangled the uuencoded file and ran
the following decode, and it seemed to work.
#! /bin/sh
# This is a shell archive. Remove anything before this line, then feed it
# into a shell via "sh file" or similar. To overwrite existing files,
# type "sh file -c".
# The tool that generated this appeared in the comp.sources.unix newsgroup;
# send mail to comp-sources-unix@uunet.uu.net if you want that tool.
# If this archive is complete, you will see the following message at the end:
# "End of shell archive."
# Contents: uudecode.c
# Wrapped by swl26@swl26aws on Wed Jul 18 08:59:24 1990
PATH=/bin:/usr/bin:/usr/ucb ; export PATH
if test -f 'uudecode.c' -a "${1}" != "-c" ; then
echo shar: Will not clobber existing file \"'uudecode.c'\"
else
echo shar: Extracting \"'uudecode.c'\" \(6418 characters\)
sed "s/^X//" >'uudecode.c' <<'END_OF_FILE'
X/* #ifndef lint
Xstatic char sccsid[] = "@(#)uudecode.c 5.3-1 (Berkeley) 9/1/87";
X#endif */
X
X/* Written by Mark Horton */
X/* Modified by ajr (Alan J Rosenthatl,flaps@utcsri.UUCP) to use checksums */
X/* Modified by fnf (Fred Fish,well!fnf) to use Keith Pyle's suggestion for
X compatibility */
X/* Modified by bcn (Bryce Nesbitt,ucbvax!cogsci!bryce) to fix a misleading
X error message on the Amiga port, to fix a bug that prevented decoding
X certain files, to work even if trailing spaces have been removed from a
X file, to check the filesize (if present), to add some error checking, to
X loop for multiple decodes from a single file, and to handle common
X BITNET mangling. Also kludged around a missing string function in Aztec
X C */
X
X/*
X * uudecode [input]
X *
X * Decode a file encoded with uuencode. WIll extract multiple encoded
X * modules from a single file. Can deal with most mangled files, including
X * BITNET.
X */
X
X#include <stdio.h>
X#include <ctype.h>
X
X#ifdef AMIGA
X#define AMIGA_LATTICE /* Set for Amiga Lattice C */
X#define MCH_AMIGA
X#define MPU68000
X#endif
X
X#ifdef unix
X#include <pwd.h>
X#include <sys/types.h>
X#include <sys/stat.h>
X#endif
X
X#define SUMSIZE 64
X#define DEC(c) (((c) - ' ') & 077) /* single character decode */
X
Xmain(argc, argv)
Xchar **argv;
X{
XFILE *in, *out;
Xint through_loop=0; /* Dejavu indicator */
Xint mode; /* file's mode (from header) */
Xlong filesize; /* theoretical file size (from header) */
Xchar dest[128];
Xchar buf[80];
X
X#ifdef AMIGA_LATTICE
Xextern int Enable_Abort;
X Enable_Abort=1;
X#endif
X
X /* A filename can be specified to be uudecoded, or nothing can
X be specified, and the input will come from STDIN */
X
X switch (argc)
X {
X case 1:
X in=stdin;
X break;
X
X case 2:
X if ((in = fopen(argv[1], "r")) == NULL)
X {
X fprintf(stderr, "ERROR: can't find %s\n", argv[1]);
X fprintf(stderr, "USAGE: uudecode [infile]\n");
X exit(10);
X }
X break;
X
X default:
X fprintf(stderr, "USAGE: uudecode [infile]\n");
X exit(11);
X break;
X }
X
X /* Loop through file, searching for headers. Decode anything with a
X header, complain if there where no headers. */
X
Xfor (;;)
X{
X /* search file for header line */
X for (;;)
X {
X if (fgets(buf, sizeof buf, in) == NULL)
X {
X if (!through_loop)
X {
X fprintf(stderr, "ERROR: no `begin' line!\n");
X exit(12);
X }
X else
X {
X exit(0);
X }
X }
X if (strncmp(buf, "begin ", 6) == 0)
X break;
X }
X sscanf(buf, "begin %o %s", &mode, dest);
X
X#ifdef unix
X /* handle ~user/file format */
X if (dest[0] == '~')
X {
X char *sl;
X struct passwd *getpwnam();
X char *index();
X struct passwd *user;
X char dnbuf[100];
X
X sl = index(dest, '/');
X if (sl == NULL)
X {
X fprintf(stderr, "Illegal ~user\n");
X exit(13);
X }
X *sl++ = 0;
X user = getpwnam(dest+1);
X if (user == NULL)
X {
X fprintf(stderr, "No such user as %s\n", dest);
X exit(14);
X }
X strcpy(dnbuf, user->pw_dir);
X strcat(dnbuf, "/");
X strcat(dnbuf, sl);
X strcpy(dest, dnbuf);
X }
X#endif
X
X /* create output file */
X if ((out = fopen(dest, "w")) == NULL)
X {
X fprintf(stderr, "ERROR: can't open output file %s\n", dest);
X exit(15);
X }
X#ifdef unix
X chmod(dest, mode);
X#endif
X
X decode(in, out, dest);
X
X if (fgets(buf, sizeof buf, in) == NULL || strncmp(buf,"end",3))
X { /* don't be overly picky about newline ^ */
X fprintf(stderr, "ERROR: no `end' line\n");
X exit(16);
X }
X
X if (!(fgets(buf,sizeof buf,in) == NULL || strncmp(buf,"size ",3)))
X {
X sscanf(buf, "size %ld", &filesize);
X if (ftell(out) != filesize)
X {
X fprintf(stderr, "ERROR: file should have been %ld bytes long but was
X exit(17);
X }
X }
X through_loop = 1;
X} /* forever */
X} /* main */
X
X/*
X * Copy from in to out, decoding as you go.
X * If a return or newline is encountered too early in a line, it is
X * assumed that means that some editor has truncated trailing spaces.
X */
Xdecode(in, out, dest)
XFILE *in;
XFILE *out;
Xchar *dest;
X{
Xchar buf[81];
Xchar *bp;
Xint nosum=0;
X#ifndef unix
Xextern errno;
X#endif
Xregister int j;
Xregister int n;
Xint checksum, line;
X
X for (line = 1; ; line++) /* for each input line */
X {
X if (fgets(buf, sizeof buf, in) == NULL)
X {
X fprintf(stderr, "ERROR: input ended unexpectedly!\n");
X exit(18);
X }
X
X /* Pad end of lines in case some editor truncated trailing
X spaces */
X
X for (n=0;n<79;n++) /* search for first \r, \n or \000 */
X {
X if (buf[n]=='\176') /* If BITNET made a twiddle, */
X buf[n]='\136'; /* we make a caret */
X if (buf[n]=='\r'||buf[n]=='\n'||buf[n]=='\000')
X break;
X }
X for (;n<79;n++) /* when found, fill rest of line with space */
X {
X buf[n]=' ';
X }
X buf[79]=0; /* terminate new string */
X
X checksum = 0;
X n = DEC(buf[0]);
X if (n <= 0)
X break; /* 0 bytes on a line?? Must be the last line */
X
X bp = &buf[1];
X
X /* FOUR input characters go into each THREE output charcters */
X
X while (n >= 4)
X {
X j = DEC(bp[0]) << 2 | DEC(bp[1]) >> 4; putc(j, out); checksum += j;
X j = DEC(bp[1]) << 4 | DEC(bp[2]) >> 2; putc(j, out); checksum += j;
X j = DEC(bp[2]) << 6 | DEC(bp[3]); putc(j, out); checksum += j;
X checksum = checksum % SUMSIZE;
X bp += 4;
X n -= 3;
X }
X
X j = DEC(bp[0]) << 2 | DEC(bp[1]) >> 4;
X checksum += j;
X if (n >= 1)
X putc(j, out);
X j = DEC(bp[1]) << 4 | DEC(bp[2]) >> 2;
X checksum += j;
X if (n >= 2)
X putc(j, out);
X j = DEC(bp[2]) << 6 | DEC(bp[3]);
X checksum += j;
X if (n >= 3)
X putc(j, out);
X checksum = checksum % SUMSIZE;
X bp += 4;
X n -= 3;
X
X#ifndef unix
X /* Error checking under UNIX??? You must be kidding... */
X /* Check if an error occured while writing to that last line */
X if (errno)
X {
X fprintf(stderr, "ERROR: error writing to %s\n",dest);
X exit(19);
X }
X#endif
X
X /* The line has been decoded; now check that sum */
X
X nosum |= !isspace(*bp);
X if (nosum) /* Is there a checksum at all?? */
X {
X if (checksum != DEC(*bp)) /* Does that checksum match? */
X {
X fprintf(stderr, "ERROR: checksum mismatch decoding %s, line %d.\
X }
X } /* sum */
X } /* line */
X} /* function */
X
X#ifdef unix
X/*
X * Return the ptr in sp at which the character c appears;
X * 0 if not found
X */
Xchar *
Xindex(sp, c)
Xregister char *sp, c;
X{
X do
X {
X if (*sp == c)
X return(sp);
X }
X while (*sp++);
X
X return(0);
X}
X#endif unix
X
END_OF_FILE
echo shar: NEWLINE appended to \"'uudecode.c'\"
if test 6419 -ne `wc -c <'uudecode.c'`; then
echo shar: \"'uudecode.c'\" unpacked with wrong size!
fi
# end of 'uudecode.c'
fi
echo shar: End of shell archive.
exit 0

View file

@ -0,0 +1,44 @@
These patches and supplemental programs should allow porting to MVS or MVS/XA
in an EBCDIC envrionment, using SAS C V4.00C.
Included are:
-rw-r--r-- 1 swl26 1573 Jul 17 14:32 README
-rw-rw-r-- 1 swl26 20861 Jul 17 13:41 diffs
-rw-rw-r-- 1 swl26 5022 Jul 17 14:00 fixit.l
-rw-rw-r-- 1 swl26 97644 Jul 17 13:42 initscan.mvs.c
-rw-rw-r-- 1 swl26 4898 Jul 17 14:08 unfixit.l
The file "diffs" contains context diffs for changes to flex 2.3.
The file "fixit.l" contains flex sources for a program to shorten external
variable and function names to 8 characters or less. This is required for the
"dumb" compiler linker used.
The file "unfixit.l" reverses the changes in "fixit.l", to restore long names.
This is useful when trying to build diff files as created here.
The file "initscan.mvs.c" is an already "flexed" version of scan.l, in an
EBCDIC environment.
To install in an MVS environment, use patch to apply the diffs to flex 2.3,
then run "fixit" on all .c, .h, .l, .y, and .skel files. Move the files
to the MVS machine, and compile each of the .c files. (You will need a
"yacc" functional equivalent under MVS to expand parse.y in that
environment.) Link together, and the resulting flex should be ready to
go. To test, run the MVSflex -is8 -Ce on the scan.l, and you should get
back a file which is identical to initscan.mvs.c.
Enjoy.
Steven W. Layten
Senior Engineer
Chemical Abstracts Service
PO Box 3012
2540 Olentangy River Road
Columbus, Ohio 43210
+1 614 421 3600 extension 3451
INET: swl26%cas.BITNET@CUNYVM.CUNY.Edu
UUCP: osu-cis!chemabs!swl26
BITNET: swl26@cas.bitnet

View file

@ -0,0 +1,854 @@
diff -c ../Makefile ./Makefile
*** ../Makefile Thu Jun 28 00:44:07 1990
--- ./Makefile Mon Jul 16 13:57:26 1990
***************
*** 39,49 ****
# AUXDIR, manual pages will be installed in MANDIR with extension MANEXT.
# Raw, unformatted troff source will be installed if INSTALLMAN=man, nroff
# preformatted versions will be installed if INSTALLMAN=cat.
! DESTDIR =
BINDIR = /usr/local
LIBDIR = /usr/local/lib
AUXDIR = /usr/local/lib
MANDIR = /usr/man/manl
MANEXT = l
INSTALLMAN = man
--- 39,50 ----
# AUXDIR, manual pages will be installed in MANDIR with extension MANEXT.
# Raw, unformatted troff source will be installed if INSTALLMAN=man, nroff
# preformatted versions will be installed if INSTALLMAN=cat.
! DESTDIR = /projects/m751stereo/code/c/swl26
BINDIR = /usr/local
LIBDIR = /usr/local/lib
AUXDIR = /usr/local/lib
MANDIR = /usr/man/manl
+ INCLUDEDIR = .
MANEXT = l
INSTALLMAN = man
***************
*** 52,58 ****
SKELETON_FILE = $(DESTDIR)$(AUXDIR)/flex.skel
SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_FILE)\"
! CFLAGS = -O
LDFLAGS = -s
COMPRESSION =
--- 53,59 ----
SKELETON_FILE = $(DESTDIR)$(AUXDIR)/flex.skel
SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"$(SKELETON_FILE)\"
! CFLAGS = -O -DUSG -I$(INCLUDEDIR)
LDFLAGS = -s
COMPRESSION =
diff -c ../ccl.c ./ccl.c
*** ../ccl.c Thu Jun 28 00:44:07 1990
--- ./ccl.c Mon Jul 16 13:57:27 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* ccladd - add a single character to a ccl
*
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* ccladd - add a single character to a ccl
*
diff -c ../dfa.c ./dfa.c
*** ../dfa.c Thu Jun 28 00:44:08 1990
--- ./dfa.c Mon Jul 16 13:57:28 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* declare functions that have forward references */
--- 28,38 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
! #include <ctype.h>
/* declare functions that have forward references */
***************
*** 682,688 ****
register int j;
for ( i = 'A', j = 'a'; i <= 'Z'; ++i, ++j )
! state[i] = state[j];
}
if ( ds > num_start_states )
--- 683,692 ----
register int j;
for ( i = 'A', j = 'a'; i <= 'Z'; ++i, ++j )
! {
! if (isupper(i) )
! state[i] = state[j];
! }
}
if ( ds > num_start_states )
***************
*** 958,964 ****
}
}
! else if ( sym >= 'A' && sym <= 'Z' && caseins )
flexfatal( "consistency check failed in symfollowset" );
else if ( sym == SYM_EPSILON )
--- 962,968 ----
}
}
! else if ( isupper ( sym ) && caseins )
flexfatal( "consistency check failed in symfollowset" );
else if ( sym == SYM_EPSILON )
Only in .: diffs
Only in .: diffs.new
diff -c ../ecs.c ./ecs.c
*** ../ecs.c Thu Jun 28 00:44:08 1990
--- ./ecs.c Mon Jul 16 13:57:28 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* ccl2ecl - convert character classes to set of equivalence classes
*
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* ccl2ecl - convert character classes to set of equivalence classes
*
diff -c ../flex.skel ./flex.skel
*** ../flex.skel Thu Jun 28 00:44:27 1990
--- ./flex.skel Mon Jul 16 13:57:29 1990
***************
*** 1,7 ****
/* A lexical scanner generated by flex */
/* scanner skeleton version:
! * $Header$
*/
#define FLEX_SCANNER
--- 1,7 ----
/* A lexical scanner generated by flex */
/* scanner skeleton version:
! * $Header$
*/
#define FLEX_SCANNER
diff -c ../flexdef.h ./flexdef.h
*** ../flexdef.h Thu Jun 28 00:44:27 1990
--- ./flexdef.h Mon Jul 16 13:57:30 1990
***************
*** 26,32 ****
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
! /* @(#) $Header$ (LBL) */
#ifndef FILE
#include <stdio.h>
--- 26,32 ----
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
! /* @(#) $Header$ (LBL) */
#ifndef FILE
#include <stdio.h>
***************
*** 45,51 ****
/* size of input alphabet - should be size of ASCII set */
#ifndef DEFAULT_CSIZE
! #define DEFAULT_CSIZE 128
#endif
#ifndef PROTO
--- 45,51 ----
/* size of input alphabet - should be size of ASCII set */
#ifndef DEFAULT_CSIZE
! #define DEFAULT_CSIZE 256
#endif
#ifndef PROTO
***************
*** 90,96 ****
--- 90,98 ----
#define SHORT_FILE_NAMES
#endif
+ #ifndef OSVS
char *malloc(), *realloc();
+ #endif
/* maximum line length we'll have to deal with */
***************
*** 116,125 ****
#define true 1
#define false 0
-
#ifndef DEFAULT_SKELETON_FILE
#define DEFAULT_SKELETON_FILE "flex.skel"
! #endif
/* special chk[] values marking the slots taking by end-of-buffer and action
* numbers
--- 118,132 ----
#define true 1
#define false 0
#ifndef DEFAULT_SKELETON_FILE
+ #ifdef OSVS
+ #define DEFAULT_SKELETON_FILE "ctri01"
+ #define SYSUT1 "sysut1"
+ #define SYSUT2 "sysut2"
+ #else
#define DEFAULT_SKELETON_FILE "flex.skel"
! #endif /* OSVS */
! #endif /* DEFAULT_SKELETON_FILE */
/* special chk[] values marking the slots taking by end-of-buffer and action
* numbers
***************
*** 226,233 ****
#define INITIAL_MAX_SCS 40 /* maximum number of start conditions */
#define MAX_SCS_INCREMENT 40 /* amount to bump by if it's not enough */
! #define ONE_STACK_SIZE 500 /* stack of states with only one out-transition */
! #define SAME_TRANS -1 /* transition is the same as "default" entry for state */
/* the following percentages are used to tune table compression:
--- 233,240 ----
#define INITIAL_MAX_SCS 40 /* maximum number of start conditions */
#define MAX_SCS_INCREMENT 40 /* amount to bump by if it's not enough */
! #define ONE_STACK_SIZE 500 /*stack of states with only one out-transition*/
! #define SAME_TRANS -1 /*transition is the same as "default" entry for state */
/* the following percentages are used to tune table compression:
diff -c ../gen.c ./gen.c
*** ../gen.c Thu Jun 28 00:44:28 1990
--- ./gen.c Mon Jul 16 13:57:32 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* declare functions that have forward references */
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* declare functions that have forward references */
***************
*** 292,298 ****
indent_puts( "{" );
! indent_puts( "if ( yy_lp && yy_lp < yy_accept[yy_current_state + 1] )" );
indent_up();
indent_puts( "{" );
indent_puts( "yy_act = yy_acclist[yy_lp];" );
--- 292,298 ----
indent_puts( "{" );
! indent_puts("if( yy_lp && yy_lp < yy_accept[yy_current_state + 1] )");
indent_up();
indent_puts( "{" );
indent_puts( "yy_act = yy_acclist[yy_lp];" );
diff -c ../initscan.c ./initscan.c
*** ../initscan.c Thu Jun 28 00:44:51 1990
--- ./initscan.c Mon Jul 16 13:57:33 1990
***************
*** 1,7 ****
/* A lexical scanner generated by flex */
/* scanner skeleton version:
! * $Header$
*/
#define FLEX_SCANNER
--- 1,7 ----
/* A lexical scanner generated by flex */
/* scanner skeleton version:
! * $Header$
*/
#define FLEX_SCANNER
***************
*** 193,199 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#undef yywrap
--- 193,199 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#undef yywrap
diff -c ../libmain.c ./libmain.c
*** ../libmain.c Thu Jun 28 00:44:28 1990
--- ./libmain.c Mon Jul 16 13:57:34 1990
***************
*** 1,6 ****
/* libmain - flex run-time support library "main" function */
! /* $Header$ */
extern int yylex();
--- 1,6 ----
/* libmain - flex run-time support library "main" function */
! /* $Header$ */
extern int yylex();
diff -c ../main.c ./main.c
*** ../main.c Thu Jun 28 00:44:29 1990
--- ./main.c Mon Jul 16 13:57:34 1990
***************
*** 34,44 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
static char flex_version[] = "2.3";
--- 34,44 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
static char flex_version[] = "2.3";
***************
*** 97,106 ****
char *program_name;
#ifndef SHORT_FILE_NAMES
static char *outfile = "lex.yy.c";
! #else
static char *outfile = "lexyy.c";
! #endif
static int outfile_created = 0;
static int use_stdout;
static char *skelname = NULL;
--- 97,110 ----
char *program_name;
#ifndef SHORT_FILE_NAMES
+ #ifdef OSVS
+ static char *outfile = "ctro01";
+ #else /* not OSVS */
static char *outfile = "lex.yy.c";
! #endif /* not OSVS */
! #else /* SHORT_FILE_NAMES */
static char *outfile = "lexyy.c";
! #endif /* SHORT_FILE_NAMES */
static int outfile_created = 0;
static int use_stdout;
static char *skelname = NULL;
***************
*** 209,216 ****
--- 213,222 ----
else if ( fclose( temp_action_file ) )
flexfatal( "error occurred when closing temporary action file" );
+ #ifndef OSVS
else if ( unlink( action_file_name ) )
flexfatal( "error occurred when deleting temporary action file" );
+ #endif
}
if ( status != 0 && outfile_created )
***************
*** 221,228 ****
--- 227,236 ----
else if ( fclose( stdout ) )
flexfatal( "error occurred when closing output file" );
+ #ifndef OSVS
else if ( unlink( outfile ) )
flexfatal( "error occurred when deleting output file" );
+ #endif
}
if ( backtrack_report && backtrack_file )
***************
*** 574,583 ****
if ( backtrack_report )
{
#ifndef SHORT_FILE_NAMES
backtrack_file = fopen( "lex.backtrack", "w" );
! #else
backtrack_file = fopen( "lex.bck", "w" );
! #endif
if ( backtrack_file == NULL )
flexerror( "could not create lex.backtrack" );
--- 582,595 ----
if ( backtrack_report )
{
#ifndef SHORT_FILE_NAMES
+ #ifdef OSVS
+ backtrack_file = fopen( SYSUT2, "w");
+ #else /* not OSVS */
backtrack_file = fopen( "lex.backtrack", "w" );
! #endif /* OSVS */
! #else /* SHORT_FILE_NAMES */
backtrack_file = fopen( "lex.bck", "w" );
! #endif /* SHORT_FILE_NAMES */
if ( backtrack_file == NULL )
flexerror( "could not create lex.backtrack" );
***************
*** 597,604 ****
lerrsf( "can't open skeleton file %s", skelname );
#ifdef SYS_V
action_file_name = tmpnam( NULL );
! #endif
if ( action_file_name == NULL )
{
--- 609,620 ----
lerrsf( "can't open skeleton file %s", skelname );
#ifdef SYS_V
+ #ifndef OSVS
action_file_name = tmpnam( NULL );
! #else /* OSVS */
! action_file_name = SYSUT1;
! #endif /* OSVS */
! #endif /* SYS_V */
if ( action_file_name == NULL )
{
***************
*** 609,615 ****
--- 625,636 ----
#else
(void) strcpy( temp_action_file_name, "flexXXXXXX.tmp" );
#endif
+ #ifndef OSVS
(void) mktemp( temp_action_file_name );
+ #else /* OSVS */
+ /* should never be executed in OSVS as IF should always be false */
+ (void) strcpy( temp_action_file_name, SYSUT1 ) ;
+ #endif /* OSVS */
action_file_name = temp_action_file_name;
}
diff -c ../misc.c ./misc.c
*** ../misc.c Thu Jun 28 00:44:40 1990
--- ./misc.c Mon Jul 16 13:57:35 1990
***************
*** 28,38 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#include <ctype.h>
! #include "flexdef.h"
/* ANSI C does not guarantee that isascii() is defined */
--- 28,38 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#include <ctype.h>
! #include <flexdef.h>
/* ANSI C does not guarantee that isascii() is defined */
***************
*** 107,113 ****
--- 107,117 ----
{
while ( *str )
{
+ #ifdef OSVS
+ if ( ! islower( *str ) )
+ #else
if ( ! isascii( *str ) || ! islower( *str ) )
+ #endif
return ( 0 );
++str;
}
***************
*** 130,136 ****
--- 134,144 ----
{
while ( *str )
{
+ #ifdef OSVS
+ if ( ! isupper( (char) *str ) )
+ #else
if ( ! isascii( *str ) || ! isupper( (char) *str ) )
+ #endif
return ( 0 );
++str;
}
***************
*** 182,188 ****
--- 190,200 ----
register int c;
{
+ #ifdef OSVS
+ return ( isupper( c ) ? (Char) tolower( c ) : (Char) c );
+ #else
return ( (isascii( c ) && isupper( c )) ? tolower( c ) : c );
+ #endif
}
***************
*** 204,210 ****
for ( c = str; *c; ++c )
;
! copy = malloc( (unsigned) ((c - str + 1) * sizeof( char )) );
if ( copy == NULL )
flexfatal( "dynamic memory failure in copy_string()" );
--- 216,222 ----
for ( c = str; *c; ++c )
;
! copy = (char *) malloc( (unsigned) ((c - str + 1) * sizeof( char )) );
if ( copy == NULL )
flexfatal( "dynamic memory failure in copy_string()" );
***************
*** 392,403 ****
--- 404,421 ----
#ifndef MS_DOS
#ifndef VMS
+ #ifndef OSVS
#include <sys/types.h>
+ #endif /* OSVS */
#else
#include <types.h>
#endif
#endif
+ #ifdef OSVS
+ #include <time.h>
+ #endif /* OSVS */
+
#ifdef MS_DOS
#include <time.h>
typedef long time_t;
***************
*** 615,621 ****
--- 633,643 ----
if ( array[1] == 'x' )
++sptr;
+ #ifdef OSVS
+ while ( isdigit( array[sptr] ) )
+ #else
while ( isascii( array[sptr] ) && isdigit( array[sptr] ) )
+ #endif
/* don't increment inside loop control because if
* isdigit() is a macro it will expand it to two
* increments ...
Only in ..: new
diff -c ../nfa.c ./nfa.c
*** ../nfa.c Thu Jun 28 00:44:40 1990
--- ./nfa.c Mon Jul 16 13:57:36 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* declare functions that have forward references */
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* declare functions that have forward references */
***************
*** 110,116 ****
{
int sym, tsp1, tsp2, anum, ns;
! fprintf( stderr, "\n\n********** beginning dump of nfa with start state %d\n",
state1 );
/* we probably should loop starting at firstst[state1] and going to
--- 110,116 ----
{
int sym, tsp1, tsp2, anum, ns;
! fprintf(stderr,"\n\n********* beginning dump of nfa with start state %d\n",
state1 );
/* we probably should loop starting at firstst[state1] and going to
diff -c ../parse.y ./parse.y
*** ../parse.y Thu Jun 28 00:44:40 1990
--- ./parse.y Mon Jul 16 13:57:36 1990
***************
*** 32,45 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
int pat, scnum, eps, headcnt, trailcnt, anyccl, lastchar, i, actvp, rulelen;
int trlcontxt, xcluflg, cclsorted, varlength, variable_trail_rule;
Char clower();
static int madeany = false; /* whether we've made the '.' character class */
int previous_continued_action; /* whether the previous rule's action was '|' */
--- 32,47 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
int pat, scnum, eps, headcnt, trailcnt, anyccl, lastchar, i, actvp, rulelen;
int trlcontxt, xcluflg, cclsorted, varlength, variable_trail_rule;
Char clower();
+ void build_eof_action();
+ void yyerror();
static int madeany = false; /* whether we've made the '.' character class */
int previous_continued_action; /* whether the previous rule's action was '|' */
diff -c ../scan.l ./scan.l
*** ../scan.l Thu Jun 28 00:44:41 1990
--- ./scan.l Mon Jul 16 13:57:37 1990
***************
*** 30,42 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#undef yywrap
! #include "flexdef.h"
! #include "parse.h"
#define ACTION_ECHO fprintf( temp_action_file, "%s", yytext )
#define MARK_END_OF_PROLOG fprintf( temp_action_file, "%%%% end of prolog\n" );
--- 30,42 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#undef yywrap
! #include <flexdef.h>
! #include <parse.h>
#define ACTION_ECHO fprintf( temp_action_file, "%s", yytext )
#define MARK_END_OF_PROLOG fprintf( temp_action_file, "%%%% end of prolog\n" );
diff -c ../sym.c ./sym.c
*** ../sym.c Thu Jun 28 00:44:41 1990
--- ./sym.c Mon Jul 16 13:57:37 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* declare functions that have forward references */
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* declare functions that have forward references */
diff -c ../tblcmp.c ./tblcmp.c
*** ../tblcmp.c Thu Jun 28 00:44:41 1990
--- ./tblcmp.c Mon Jul 16 13:57:38 1990
***************
*** 28,37 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include "flexdef.h"
/* declarations for functions that have forward references */
--- 28,37 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
! #include <flexdef.h>
/* declarations for functions that have forward references */
diff -c ../yylex.c ./yylex.c
*** ../yylex.c Thu Jun 28 00:44:41 1990
--- ./yylex.c Mon Jul 16 13:57:38 1990
***************
*** 28,39 ****
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#include <ctype.h>
! #include "flexdef.h"
! #include "parse.h"
/* ANSI C does not guarantee that isascii() is defined */
--- 28,39 ----
#ifndef lint
static char rcsid[] =
! "@(#) $Header$ (LBL)";
#endif
#include <ctype.h>
! #include <flexdef.h>
! #include <parse.h>
/* ANSI C does not guarantee that isascii() is defined */
***************
*** 180,186 ****
--- 180,190 ----
break;
default:
+ #ifdef OSVS
+ if ( ! isprint( yylval ) )
+ #else
if ( ! isascii( yylval ) || ! isprint( yylval ) )
+ #endif
fprintf( stderr, "\\%.3o", yylval );
else
(void) putc( yylval, stderr );

View file

@ -0,0 +1,138 @@
%{
/* fixit.l - convert long external names to names of 8-bytes or less */
/*
* This program is included to satisfy "dumb" compilers/linkers which
* do not know about externals of names longer than 8 bytes.
*
* Steven W. Layten
* Chemical Abstracts Service
* PO BOX 3012
* Columbus, OH 43210
*/
%}
%%
"action_file_name" printf("actfilnm");
"action_out" printf("actnout");
"add_accept" printf("addacpt");
"all_lower" printf("alllower");
"all_upper" printf("allupper");
"allocate_array" printf("allocarr");
"assoc_rule" printf("asscrule");
"backtrack_file" printf("bktrkfil");
"backtrack_report" printf("bktrkrep");
"bol_needed" printf("bol_nded");
"build_eof_action" printf("bldeofac");
"cclinstal" printf("cclnstal");
"ccllookup" printf("ccllookp");
"cclnegate" printf("cclnegat");
"cclsorted" printf("cclsrted");
"check_for_backtracking" printf("ck4bktrk");
"check_trailing_context" printf("cktrlcnt");
"continued_action" printf("cntdactn");
"copy_string" printf("copystrn");
"copy_unsigned_string" printf("cpunsstr");
"copyright" printf("cpyrght");
"copysingl" printf("copysngl");
"current_max_ccl_tbl_size" printf("c_mx_ccl");
"current_max_dfa_size" printf("c_mx_dfa");
"current_max_dfas" printf("c_mxdfas");
"current_max_rules" printf("curmxrls");
"current_max_scs" printf("c_mx_scs");
"current_max_template_xpairs" printf("c_mx_tmp");
"current_max_xpairs" printf("c_mx_xpr");
"current_maxccls" printf("c_mxccls");
"current_mns" printf("curr_mns");
"current_state_type" printf("cursttyp");
"dataflush" printf("datflush");
"dfaacc_union" printf("dfacunin");
"do_indent" printf("do_indnt");
"dump_associated_rules" printf("dmpasrl");
"dump_transitions" printf("dmptrns");
"dupmachine" printf("dupmach");
"ecs_from_xlation" printf("ecsfrmxt");
"end_of_buffer_state" printf("eobstate");
"epsclosure" printf("epsclos");
"expand_nxt_chk" printf("expnxtck");
"find_table_space" printf("fndtblsp");
"finish_rule" printf("fnshrule");
"firstfree" printf("firstfre");
"firstprot" printf("firstprt");
"flex_gettime" printf("flxgettm");
"flexerror" printf("flxerror");
"flexfatal" printf("flxfatal");
"format_pinpoint_message" printf("fmtptmsg");
"gen_NUL_trans" printf("gnNULtrn");
"gen_backtracking" printf("gnbktrkg");
"gen_bt_action" printf("gnbtactn");
"gen_find_action" printf("gnfndact");
"gen_line_dirs" printf("gnlindir");
"gen_next_compressed_state" printf("gnnxcste");
"gen_next_match" printf("gnnxmtch");
"gen_next_state" printf("gnnxtst");
"gen_start_state" printf("gnstrtst");
"hash_entry" printf("hshentry");
"hashfunct" printf("hshfct");
"increase_max_dfas" printf("incmxdfa");
"indent_put2s" printf("indput2s");
"indent_puts" printf("indputs");
"infilename" printf("infilnam");
"input_files" printf("inp_fles");
"interactive" printf("intractv");
"line_directive_out" printf("lndirout");
"link_machines" printf("lnkmchns");
"list_character_set" printf("lst_cset");
"make_tables" printf("maketbls");
"mark_beginning_as_normal" printf("mkbgnorm");
"mktemplate" printf("mktmplat");
"num_backtracking" printf("nbktrckg");
"num_input_files" printf("ninfiles");
"num_reallocs" printf("numraloc");
"num_rules" printf("numrules");
"num_xlations" printf("nuxlatns");
"numsnpairs" printf("numnpair");
"output_file_name" printf("outfilnm");
"peakpairs" printf("peakpair");
"performance_report" printf("perf_rep");
"pinpoint_message" printf("pptmsg");
"place_state" printf("plcstate");
"previous_continued_action" printf("prvctdan");
"printstats" printf("prtstats");
"program_name" printf("pgm_name");
"protcomst" printf("prtcomst");
"readable_form" printf("rdblefrm");
"real_reject" printf("realrjct");
"reallocate_array" printf("rallocar");
"reject_really_used" printf("rjctused");
"rule_linenum" printf("rulelnno");
"rule_type" printf("ruletype");
"set_input_file" printf("stinpfle");
"set_up_initial_allocations" printf("setupia");
"starttime" printf("startime");
"state_type" printf("ste_type");
"symfollowset" printf("symfollo");
"sympartition" printf("sympartn");
"syntaxerror" printf("syntxerr");
"temp_action_file" printf("tmpactfl");
"todo_head" printf("todohead");
"todo_next" printf("todonext");
"transchar" printf("trnschar");
"transition_struct_out" printf("trnstout");
"trlcontxt" printf("trlcntxt");
"variable_trail_rule" printf("vtrailrl");
"variable_trailing_context_rules" printf("vtrlctrl");
"varlength" printf("varlngth");
"yy_create_buffer" printf("yycrbffr");
"yy_delete_buffer" printf("yydlbffr");
"yy_init_buffer" printf("yyinbffr");
"yy_load_buffer_state" printf("yyldbfst");
"yy_switch_to_buffer" printf("yyswtobf");
"yyerrflag" printf("yyerrflg");
"yymore_really_used" printf("yymrreus");
"yymore_used" printf("yymrused");
"yyrestart" printf("yyrestrt");
. ECHO;
%%
main()
{
yylex();
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,141 @@
%{
/* unfixit.l - convert shortened external names to names back to their
* original names. (See fixit.l)
*/
/*
* This program is included to satisfy "dumb" compilers/linkers which
* do not know about externals of names longer than 8 bytes.
*
* Steven W. Layten
* Chemical Abstracts Service
* PO BOX 3012
* Columbus, OH 43210
*/
%}
%%
"actfilnm" printf("action_file_name");
"actnout" printf("action_out");
"addacpt" printf("add_accept");
"alllower" printf("all_lower");
"allupper" printf("all_upper");
"allocarr" printf("allocate_array");
"asscrule" printf("assoc_rule");
"bktrkfil" printf("backtrack_file");
"bktrkrep" printf("backtrack_report");
"bol_nded" printf("bol_needed");
"bldeofac" printf("build_eof_action");
"cclnstal" printf("cclinstal");
"ccllookp" printf("ccllookup");
"cclnegat" printf("cclnegate");
"cclsrted" printf("cclsorted");
"ck4bktrk" printf("check_for_backtracking");
"cktrlcnt" printf("check_trailing_context");
"cntdactn" printf("continued_action");
"copystrn" printf("copy_string");
"cpunsstr" printf("copy_unsigned_string");
"cpyrght" printf("copyright");
"copysngl" printf("copysingl");
"c_mx_ccl" printf("current_max_ccl_tbl_size");
"c_mx_dfa" printf("current_max_dfa_size");
"c_mxdfas" printf("current_max_dfas");
"curmxrls" printf("current_max_rules");
"c_mx_scs" printf("current_max_scs");
"c_mx_tmp" printf("current_max_template_xpairs");
"c_mx_xpr" printf("current_max_xpairs");
"c_mxccls" printf("current_maxccls");
"curr_mns" printf("current_mns");
"cursttyp" printf("current_state_type");
"datflush" printf("dataflush");
"dfacunin" printf("dfaacc_union");
"do_indnt" printf("do_indent");
"dmpasrl" printf("dump_associated_rules");
"dmptrns" printf("dump_transitions");
"dupmach" printf("dupmachine");
"ecsfrmxt" printf("ecs_from_xlation");
"eobstate" printf("end_of_buffer_state");
"epsclos" printf("epsclosure");
"expnxtck" printf("expand_nxt_chk");
"fndtblsp" printf("find_table_space");
"fnshrule" printf("finish_rule");
"firstfre" printf("firstfree");
"firstprt" printf("firstprot");
"flxgettm" printf("flex_gettime");
"flxerror" printf("flexerror");
"flxfatal" printf("flexfatal");
"fmtptmsg" printf("format_pinpoint_message");
"gnNULtrn" printf("gen_NUL_trans");
"gnbktrkg" printf("gen_backtracking");
"gnbtactn" printf("gen_bt_action");
"gnfndact" printf("gen_find_action");
"gnlindir" printf("gen_line_dirs");
"gnnxcste" printf("gen_next_compressed_state");
"gnnxmtch" printf("gen_next_match");
"gnnxtst" printf("gen_next_state");
"gnstrtst" printf("gen_start_state");
"hshentry" printf("hash_entry");
"hshfct" printf("hashfunct");
"incmxdfa" printf("increase_max_dfas");
"indput2s" printf("indent_put2s");
"indputs" printf("indent_puts");
"infilnam" printf("infilename");
"inp_fles" printf("input_files");
"intractv" printf("interactive");
"lndirout" printf("line_directive_out");
"lnkmchns" printf("link_machines");
"lst_cset" printf("list_character_set");
"maketbls" printf("make_tables");
"mkbgnorm" printf("mark_beginning_as_normal");
"mktmplat" printf("mktemplate");
"nbktrckg" printf("num_backtracking");
"ninfiles" printf("num_input_files");
"numraloc" printf("num_reallocs");
"numrules" printf("num_rules");
"nuxlatns" printf("num_xlations");
"numnpair" printf("numsnpairs");
"outfilnm" printf("output_file_name");
"peakpair" printf("peakpairs");
"perf_rep" printf("performance_report");
"pptmsg" printf("pinpoint_message");
"plcstate" printf("place_state");
"prvctdan" printf("previous_continued_action");
"prtstats" printf("printstats");
"pgm_name" printf("program_name");
"prtcomst" printf("protcomst");
"rdblefrm" printf("readable_form");
"realrjct" printf("real_reject");
"rallocar" printf("reallocate_array");
"rjctused" printf("reject_really_used");
"rulelnno" printf("rule_linenum");
"ruletype" printf("rule_type");
"stinpfle" printf("set_input_file");
"setupia" printf("set_up_initial_allocations");
"startime" printf("starttime");
"ste_type" printf("state_type");
"symfollo" printf("symfollowset");
"sympartn" printf("sympartition");
"syntxerr" printf("syntaxerror");
"tmpactfl" printf("temp_action_file");
"todohead" printf("todo_head");
"todonext" printf("todo_next");
"trnschar" printf("transchar");
"trnstout" printf("transition_struct_out");
"trlcntxt" printf("trlcontxt");
"vtrailrl" printf("variable_trail_rule");
"vtrlctrl" printf("variable_trailing_context_rules");
"varlngth" printf("varlength");
"yycrbffr" printf("yy_create_buffer");
"yydlbffr" printf("yy_delete_buffer");
"yyinbffr" printf("yy_init_buffer");
"yyldbfst" printf("yy_load_buffer_state");
"yyswtobf" printf("yy_switch_to_buffer");
"yyerrflg" printf("yyerrflag");
"yymrreus" printf("yymore_really_used");
"yymrused" printf("yymore_used");
"yyrestrt" printf("yyrestart");
. ECHO;
%%
main()
{
yylex();
}

View file

@ -0,0 +1,100 @@
Notes on the THINK C version of Flex 2.4.6
Scott Hofmann 23-JUL-94
Internet: scotth@visix.com
The only changes needed to compile Flex 2.4.6 under Symantec C++ 6.0 was
to #include <console.h> in main.c and call ccommand() just before flexinit()
in main(). The notes below are mostly of historical significance only; most
of the workarounds below were to get around restrictions/problems in earlier
versions of THINK C. The only section which still applies is Russell Finn's
description of how to make Flex generate output of type 'KAHL'. Also, 4-byte
ints must be used by any project which uses Flex output.
If you want to recreate the project, you'll need to add the files
alloca.c and xmalloc.c in this directory. Both files are copylefted; see
the GNU General Public License for details. You will also need to recompile
both the ANSI and unix libraries to use 4 byte ints, and if you want the
files that flex creates to have 'KAHL' as the creator you'll need to apply
Russell Finn's patch.
Notes on the THINK C version of Flex 2.3.7
Jonas Barklund, 25-JAN-92
Internet: jonas@csd.uu.se
I have merged the sources for Flex version 2.3.7 with the older version
which was hacked for THINK C version 4. I have conditionalized the code
so that I think it should work with both THINK C version 4 and 5 (for
those of you who don't know: the THINK_C symbol is defined as 1 in version
4 and as 5 in version 5). I have put in some missing prototypes, so it
compiles also with "require prototypes" on.
Most of the notes below still apply, in particular that about the MakeRes
program.
Notes on the THINK C version of Flex
Russell S. Finn, 19-FEB-90
Internet: rsfinn@athena.mit.edu, rsfinn@neutron.lcs.mit.edu
CompuServe: 76377,1107
GEnie: RSFINN
Flex appears to be covered by a copyright notice from the University of
California, similar to the one covering Berkeley Unix; the Free Software
Foundation is not part of the picture here. So here is a version
created with THINK C 4.0, along with the source code; as with the
Bison distribution, I am including *all* of the source code I received
with the package.
The current version (modification date January 25, 1990) has only the
bare-bones interface provided by the THINK C library routine "ccommand",
which allows the user to type a command line and to redirect the output.
Perhaps someday I may try to implement a "real" user interface; perhaps
not.
The only modifications made to the source file are surrounded by "#ifdef
THINK_C"..."#endif"; in theory, then, these sources could be recompiled
on another system if necessary. These are the actual files modified:
alloca.c, dfa.c, flexdef.h, main.c, misc.c, scan.c, sym.c. Most of these
changes were minor, and many of them would have been unnecessary if the
original Flex source code had been written for an ANSI-compliant C compiler.
In addition, the file "macutils.c" is completely new; see the discussion
of "MakeRes" below.
THINK C users may find it convenient to have the output text files written
by Flex be THINK C documents. To do this, create a copy of the "ANSI"
project called "ANSI-KAHL", and a copy of the file "fopen.c" called
"fopen-KAHL.c". In the copy, find the routine "setfiletype", and replace
the lines:
if (!(oflag & F_BINARY))
pb.ioFlFndrInfo.fdType = 'TEXT';
with the lines:
if (!(oflag & F_BINARY)) {
pb.ioFlFndrInfo.fdType = 'TEXT';
pb.ioFlFndrInfo.fdCreator = 'KAHL';
}
Replace "fopen.c" with the new "fopen-KAHL.c", rebuild the new project
"ANSI-KAHL", and use this project in the project file "Flex.¹"
instead of the "ANSI" project.
** The "MakeRes" program
The output files created by Flex contain large amounts of preinitialized
static data; the file "scan.c" contained in the Flex.¹ project is one
such file. However, the Macintosh architecture limits normal applications
to 32K of global data. In many cases (including Flex), this limit can
be surpassed by the static data generated by Flex.
The solution I have implemented for the THINK C version of Flex is to
extract the data tables from the Flex output file, and paste them into
the file "MakeRes.c". Then, by recompiling and running the program in
the "MakeRes.¹" project (it is not necessary to create an application),
a resource file called "Flex.¹.rsrc" is created in the current directory.
The Flex output file "scan.c" has been modified to load the static data
from the resource fork of the Flex application. This is done by calling
the "load_table" function, which is defined in the file "macutils.c".
In the application for which I needed Flex, the data tables were small
enough that I didn't need to do this. However, if your application
requires you to do this, simply follow the model of "scan.c"; the MakeRes
project and source code has been included for your use.

View file

@ -0,0 +1,195 @@
/*
alloca -- (mostly) portable public-domain implementation -- D A Gwyn
last edit: 86/05/30 rms
include config.h, since on VMS it renames some symbols.
Use xmalloc instead of malloc.
This implementation of the PWB library alloca() function,
which is used to allocate space off the run-time stack so
that it is automatically reclaimed upon procedure exit,
was inspired by discussions with J. Q. Johnson of Cornell.
It should work under any C implementation that uses an
actual procedure stack (as opposed to a linked list of
frames). There are some preprocessor constants that can
be defined when compiling for your specific system, for
improved efficiency; however, the defaults should be okay.
The general concept of this implementation is to keep
track of all alloca()-allocated blocks, and reclaim any
that are found to be deeper in the stack than the current
invocation. This heuristic does not reclaim storage as
soon as it becomes invalid, but it will do so eventually.
As a special case, alloca(0) reclaims storage without
allocating any. It is a good idea to use alloca(0) in
your main control loop, etc. to force garbage collection.
*/
#ifndef lint
static char SCCSid[] = "@(#)alloca.c 1.1"; /* for the "what" utility */
#endif
#ifdef emacs
#include "config.h"
#ifdef static
/* actually, only want this if static is defined as ""
-- this is for usg, in which emacs must undefine static
in order to make unexec workable
*/
#ifndef STACK_DIRECTION
you
lose
-- must know STACK_DIRECTION at compile-time
#endif /* STACK_DIRECTION undefined */
#endif /* static */
#endif /* emacs */
#ifndef alloca /* If compiling with GCC, this file's not needed. */
#ifdef __STDC__
typedef void *pointer; /* generic pointer type */
#else
typedef char *pointer; /* generic pointer type */
#endif
#define NULL 0 /* null pointer constant */
extern void free();
extern pointer xmalloc();
/*
Define STACK_DIRECTION if you know the direction of stack
growth for your system; otherwise it will be automatically
deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown
*/
#ifndef STACK_DIRECTION
#define STACK_DIRECTION 0 /* direction unknown */
#endif
#if STACK_DIRECTION != 0
#define STACK_DIR STACK_DIRECTION /* known at compile-time */
#else /* STACK_DIRECTION == 0; need run-time code */
static int stack_dir; /* 1 or -1 once known */
#define STACK_DIR stack_dir
static void
find_stack_direction (/* void */)
{
static char *addr = NULL; /* address of first
`dummy', once known */
auto char dummy; /* to get stack address */
if (addr == NULL)
{ /* initial entry */
addr = &dummy;
find_stack_direction (); /* recurse once */
}
else /* second entry */
if (&dummy > addr)
stack_dir = 1; /* stack grew upward */
else
stack_dir = -1; /* stack grew downward */
}
#endif /* STACK_DIRECTION == 0 */
/*
An "alloca header" is used to:
(a) chain together all alloca()ed blocks;
(b) keep track of stack depth.
It is very important that sizeof(header) agree with malloc()
alignment chunk size. The following default should work okay.
*/
#ifndef ALIGN_SIZE
#define ALIGN_SIZE sizeof(double)
#endif
typedef union hdr
{
char align[ALIGN_SIZE]; /* to force sizeof(header) */
struct
{
union hdr *next; /* for chaining headers */
char *deep; /* for stack depth measure */
} h;
} header;
/*
alloca( size ) returns a pointer to at least `size' bytes of
storage which will be automatically reclaimed upon exit from
the procedure that called alloca(). Originally, this space
was supposed to be taken from the current stack frame of the
caller, but that method cannot be made to work for some
implementations of C, for example under Gould's UTX/32.
*/
static header *last_alloca_header = NULL; /* -> last alloca header */
pointer
alloca (size) /* returns pointer to storage */
unsigned size; /* # bytes to allocate */
{
auto char probe; /* probes stack depth: */
register char *depth = &probe;
#if STACK_DIRECTION == 0
if (STACK_DIR == 0) /* unknown growth direction */
find_stack_direction ();
#endif
/* Reclaim garbage, defined as all alloca()ed storage that
was allocated from deeper in the stack than currently. */
{
register header *hp; /* traverses linked list */
for (hp = last_alloca_header; hp != NULL;)
if ((STACK_DIR > 0 && hp->h.deep > depth)
|| (STACK_DIR < 0 && hp->h.deep < depth))
{
register header *np = hp->h.next;
free ((pointer) hp); /* collect garbage */
hp = np; /* -> next header */
}
else
break; /* rest are not deeper */
last_alloca_header = hp; /* -> last valid storage */
}
if (size == 0)
return NULL; /* no allocation required */
/* Allocate combined header + user data storage. */
{
register pointer new = xmalloc (sizeof (header) + size);
/* address of header */
((header *)new)->h.next = last_alloca_header;
((header *)new)->h.deep = depth;
last_alloca_header = (header *)new;
/* User storage begins just after header. */
return (pointer)((char *)new + sizeof(header));
}
}
#endif /* no alloca */

View file

@ -0,0 +1,10 @@
/****************
** alloca.h
**
** header for alloca()
*****************/
typedef void *pointer;
pointer alloca(unsigned size);

View file

@ -0,0 +1,69 @@
/* xmalloc.c -- malloc with out of memory checking
Copyright (C) 1990, 1991 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#if STDC_HEADERS || THINK_C
#include <stdlib.h>
#else
char *malloc ();
char *realloc ();
void free ();
#endif
#ifdef THINK_C
#define error(x, y, z) perror(z) /* Throw out meaningless arguments */
#else
void error ();
#endif
/* Allocate N bytes of memory dynamically, with error checking. */
char *
xmalloc (n)
unsigned n;
{
char *p;
p = malloc (n);
if (p == 0)
/* Must exit with 2 for `cmp'. */
error (2, 0, "virtual memory exhausted");
return p;
}
/* Change the size of an allocated block of memory P to N bytes,
with error checking.
If P is NULL, run xmalloc.
If N is 0, run free and return NULL. */
char *
xrealloc (p, n)
char *p;
unsigned n;
{
if (p == 0)
return xmalloc (n);
if (n == 0)
{
free (p);
return 0;
}
p = realloc (p, n);
if (p == 0)
/* Must exit with 2 for `cmp'. */
error (2, 0, "virtual memory exhausted");
return p;
}

View file

@ -0,0 +1,103 @@
#
# make file for "flex" tool
# @(#) $Header: /usr/fsys/odin/a/vern/flex/RCS/Makefile,v 2.9
# 90/05/26 17:28:44 vern Exp $ (LBL)
#
# the first time around use "nmake f_flex"
#
# This makefile is specific for Microsoft's Visual C 2.0, & nmake
#
# - Stan Adermann <stana@leonardo.lmt.com>
#
SKELFLAGS = -DDEFAULT_SKELETON_FILE=\"c:/src/flex/flex.skl\"
CFLAGS = -nologo -W2 -F 8000 -Ox -DUSG
LDFLAGS = /nologo /BATCH /STACK:8000
FLEX_FLAGS = -ist8 -Sflex.skl
FLEX = .\flex.exe
CC = cl
YACC = c:\lib\byacc
MAKE = nmake /nologo
FLEXOBJS = \
ccl.obj \
dfa.obj \
ecs.obj \
gen.obj \
main.obj \
misc.obj \
nfa.obj \
parse.obj \
scan.obj \
skel.obj \
sym.obj \
tblcmp.obj \
yylex.obj
FLEX_C_SOURCES = \
ccl.c \
dfa.c \
ecs.c \
gen.c \
main.c \
misc.c \
nfa.c \
parse.c \
scan.c \
skel.c \
sym.c \
tblcmp.c \
yylex.c
all : flex.exe
flex.exe : $(FLEXOBJS)
link $(LDFLAGS) $(FLEXOBJS) -out:$*.exe
f_flex:
copy initscan.c scan.c
touch scan.c
@echo compiling first flex
$(MAKE) flex.exe
del scan.c
@echo using first flex to generate final version...
$(MAKE) flex.exe
#
# general inference rule
#
.c.obj:
$(CC) -c $(CFLAGS) $*.c
parse.h parse.c : parse.y
$(YACC) -d parse.y
@move y_tab.c parse.c
@move y_tab.h parse.h
scan.c : scan.l
$(FLEX) $(FLEX_FLAGS) $(COMPRESSION) scan.l >scan.c
scan.obj : scan.c parse.h flexdef.h
main.obj : main.c flexdef.h
$(CC) $(CFLAGS) -c $(SKELFLAGS) main.c
ccl.obj : ccl.c flexdef.h
dfa.obj : dfa.c flexdef.h
ecs.obj : ecs.c flexdef.h
gen.obj : gen.c flexdef.h
misc.obj : misc.c flexdef.h
nfa.obj : nfa.c flexdef.h
parse.obj : parse.c flexdef.h
sym.obj : sym.c flexdef.h
tblcmp.obj : tblcmp.c flexdef.h
yylex.obj : yylex.c flexdef.h
skel.obj : skel.c flexdef.h
clean :
del *.obj
del *.map

View file

@ -0,0 +1,32 @@
/* config.h. Generated automatically by configure. */
/* $Header: /home/daffy/u0/vern/flex/RCS/conf.in,v 1.2 95/01/09
12:11:51 vern Exp $ */
/* Define to empty if the keyword does not work. */
/* #undef const */
/* Define to `unsigned' if <sys/types.h> doesn't define. */
/* #undef size_t */
/* Define if you have the ANSI C header files. */
#define STDC_HEADERS 1
/* Define if you have the <malloc.h> header file. */
#define HAVE_MALLOC_H 1
/* Define if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define if you have <alloca.h> and it should be used (not on
Ultrix). */
#define HAVE_ALLOCA_H 0
/* Define if platform-specific command line handling is necessary. */
/* #undef NEED_ARGV_FIXUP */
/* Define if you use FAT file system, leave undefined for NTFS */
#undef SHORT_FILE_NAMES
/* #define SHORT_FILE_NAMES 1 */

View file

@ -0,0 +1,34 @@
this API is not documented/supported by NeXT and may go away at any time,
so test again when you upgrade (works fine for me on NEXTSTEP_Dev_3.2)
-------------------------------------------------------------------------
See KBNS.32.2.029 from the successor of:
ftp://ftp.cs.orst.edu/software/NeXT/documents/KBNS.32.1.rtf
Otherwise (that successor not yet having been published), ask me for a copy
of the item on RfSchtkt@maze.ruca.ua.ac.be. Bison's messages are not as
disciplined as flex' ones, so it should get more discipline first.
Specifically (in addition to what's described in the KBNS item):
makeUser.o and make_support.o should be added to OBJECTS in Makefile.in
In parse.y, line_pinpoint() (assumption all messages ultimately go there), add:
make_support(
// don't worry about declaring: cc's source doesn't either,
// it seems
syntaxerror?0:1,
NULL,
infilename,
line,
str,
0,0,0
);
FMyIO: in cc, these files contain the word make_support:
ChangeLog-NeXT
Makefile.in
config/next.h: defines REPORT_EVENT in terms of make_support
make_support.c
FMyIO: in cc, these files contain the word REPORT_EVENT:
cccp.c
config/next.h
gcc.c
toplev.c

View file

@ -0,0 +1,72 @@
# make file for "flex" tool, emx+gcc
release:
$(MAKE) -f Makefile.os2 flex.exe \
CC="gcc -Zomf -O" O=".obj" A=".lib" AR="emxomfar" \
LDFLAGS="-s -Zcrtdll -Zstack 512"
debug:
$(MAKE) -f Makefile.os2 flex.exe \
CC="gcc -g" O=".o" A=".a" AR="ar"
CFLAGS = -DOS2 -DSHORT_FILE_NAMES
YACC = bison
FLEX = flex
FLEX_FLAGS = -ist
.SUFFIXES: .c $O
.c$O:
$(CC) $(CFLAGS) -c $<
FLEXLIB = fl$A
FLEXOBJS = ccl$O dfa$O ecs$O gen$O main$O misc$O nfa$O parse$O \
scan$O skel$O sym$O tblcmp$O yylex$O
LIBOBJS = libmain$O libyywrap$O
flex.exe : $(FLEXOBJS) $(FLEXLIB)
$(CC) $(LDFLAGS) -o $@ $(FLEXOBJS) $(FLEXLIB)
first_flex:
cp initscan.c scan.c
$(MAKE) $(MFLAGS) flex
$(FLEXLIB): $(LIBOBJS)
$(AR) cru $(FLEXLIB) $(LIBOBJS)
$(AR) s $(FLEXLIB)
parse.h parse.c: parse.y
$(YACC) -d -o parse.c parse.y
scan.c : scan.l
$(FLEX) $(FLEX_FLAGS) $(COMPRESSION) scan.l >scan.c
scan$O : scan.c parse.h flexdef.h
main$O : main.c flexdef.h
ccl$O : ccl.c flexdef.h
dfa$O : dfa.c flexdef.h
ecs$O : ecs.c flexdef.h
gen$O : gen.c flexdef.h
misc$O : misc.c flexdef.h
nfa$O : nfa.c flexdef.h
parse$O : parse.c flexdef.h
sym$O : sym.c flexdef.h
tblcmp$O : tblcmp.c flexdef.h
yylex$O : yylex.c flexdef.h
skel.c: flex.skl mkskel.sh
$(SHELL) mkskel.sh flex.skl >skel.c
test : flex
flex $(FLEX_FLAGS) $(COMPRESSION) scan.l | diff scan.c -
bigtest :
rm -f scan.c ; $(MAKE) COMPRESSION="-C" test
rm -f scan.c ; $(MAKE) COMPRESSION="-Ce" test
rm -f scan.c ; $(MAKE) COMPRESSION="-Cm" test
rm -f scan.c ; $(MAKE) COMPRESSION="-Cfe" test
rm -f scan.c ; $(MAKE) COMPRESSION="-CFe" test
rm -f scan.c ; $(MAKE) COMPRESSION="-Cf" test
rm -f scan.c ; $(MAKE) COMPRESSION="-CF" test
rm -f scan.c ; $(MAKE)

View file

@ -0,0 +1,28 @@
/* ------------------------------------------------ */
/* version of config.h for OS/2 */
/* ------------------------------------------------ */
/* Define to empty if the keyword does not work. */
#undef const
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* Define if you have the ANSI C header files. */
#define STDC_HEADERS 1
/* Define if you have the <malloc.h> header file. */
#define HAVE_MALLOC_H 1
/* Define if you have the <string.h> header file. */
#define HAVE_STRING_H 1
/* Define if you have the <sys/types.h> header file. */
#define HAVE_SYS_TYPES_H 1
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#define HAVE_ALLOCA_H
/* Define if platform-specific command line handling is necessary. */
#define NEED_ARGV_FIXUP
#define argv_fixup(ac,av) { _response(ac,av); _wildcard(ac,av);}

View file

@ -0,0 +1,76 @@
Miscellaneous flex stuff. The items which have been tested with flex 2.5 are:
- texinfo/, a subdirectory containing a "texinfo" version of flex(1)
and the corresponding "info" files (contributed by Francois Pinard).
- VMS/, a subdirectory containing makefiles, configuration files,
run-time support, and installation notes for building flex 2.5
on VMS (contributed by Pat Rankin).
- Borland/ - makefile and config.h for Borland 4.02 compiler
(contributed by Terrence O Kane, who notes that no source
code changes were necessary).
- NT/ - Makefile and config.h for NT, contributed by Stan Adermann.
- OS2/ - Makefile and config.h for building flex under OS/2,
contributed by Kai Uwe Rommel.
- Amiga/: notes on building flex for the Amiga, contributed
by Andreas Scherer.
- parse.c, parse.h - output of running yacc (byacc, actually)
on parse.y. If your system doesn't have a flavor of yacc available,
copy these into the main flex source directory instead.
- flex.man - preformatted version of flex man page
The following have been tested using flex 2.4:
- debflex.awk, an awk script for anotating flex debug output.
It presently only works with gawk and mawk, not with "old"
or "new" awk.
- NeXT: ProjectBuilder.app support for use in the NeXT world.
- Notes on building flex for the Macintosh using Think-C,
in the Macintosh/ subdirectory.
- testxxLexer.l, a sample C++ program that uses flex's scanner
class option ("-+").
- fastwc/, a subdirectory containing examples of how to use flex
to write progressively higher-performance versions of the Unix
"wc" utility. This certainly should work with 2.5, but hasn't
been tested.
- Borland.old/: notes on building flex 2.4 for Borland C++ 3.1
on MS-DOS. These shouldn't be needed for flex 2.5. Included
only in case you encounter unanticipated difficulties.
- EBCDIC: contact information for building flex for EBCDIC.
The following are all out-of-date with respect to flex release 2.4 (and
in general up-to-date for flex 2.3):
- Atari/Atari.patches, patches for porting flex to the Atari and
to Minix.
- A number of notes and Makefiles for compiling flex under MS-DOS,
in the MSDOS/ subdirectory.
- Notes on building flex for MVS, in the MVS/ subdirectory.
If any of this is out-of-date and can be deleted, please let me know.
And the following is included for compatibility with some broken versions
of bison:
- alloca.c, a public-domain, mostly-portable version of the
alloca() routine (used by bison's parsers) written by D. A. Gwyn.
Many thanks to those who contributed these files. Updated versions will
be appreciated!

View file

@ -0,0 +1,83 @@
Brief instructions for building flex 2.5.x for VMS:
0) if you have either MMS (from Digital) or MMK (freeware) for use
as a `make' utility, follow the directions in steps #1 through #5 below.
If not, execute
@BUILD.COM xxxC
where "xxxC" is either "VAXC" or "DECC" or "GNUC", and then skip to
step #5.
1) set default to the source directory (not the [.MISC.VMS] subdirectory
where this file is located).
2) COPY [.MISC.VMS]DESCRIP.MMS []*.*
(Recursive invocations of `make' for the `bigcheck' test assume that the
makefile will be found as descrip.mms in the current directory.)
To build with VAX C for VAX/VMS:
3) MMS /MACRO=("VAXC=1") FLEX.EXE
(The /macro qualifier is optional in this case.)
To build with GNU C for VAX/VMS:
2.5) possibly edit descrip.mms to uncomment `SET COMMAND' for GCCINIT,
depending on local site configuration
3) MMS /MACRO=("GNUC=1") FLEX.EXE
To build with DEC C for either VAX/VMS or Alpha/VMS:
3) MMS /MACRO=("DECC=1") FLEX.EXE
(Expect one or two informational messages from the compiler about
implicitly declared functions.)
Minimal testing of the resulting program:
4) MMS CHECK
(If `diff' reports no warnings, the test has succeeded.)
More thorough testing:
4.5) MMS /MACRO=("xxxC=1") BIGCHECK ! "xxxC=1" as in step #3 above
(If using an older version of MMK rather than MMS, this might fail when
`make' is invoked recursively due to excessive BYTLM usage by MMK.)
Installation (the VMS makefile does not support an `install' target;
you'll need to do this part manually):
5) copy flex.exe, flex.doc, flex.skl, flexlib.olb, and FlexLexer.h to
location(s) appropriate for your site. To use flex, define a "foreign"
command by making a DCL symbol whose value begins with a dollar sign
immediately followed by the filename for flex.exe, as in
$ flex :== $local_tools:flex.exe
where `local_tools:' is the logical name pointing to flex.exe's location.
This symbol will ordinarily be a candidate for your login.com. When
invoking flex, upper- or mixed-case command line options must be enclosed
in quotes. For example,
$ flex "-Pxyz" "-L" -t mylexer.l > mylexer.c
(use prefix "xyz" instead of "yy", suppress `#line' compiler directives
in the output, write the output to `stdout', process file mylexer.l,
and capture `stdout' in file mylexer.c). As illustrated here, this VMS
version of flex supports emulation of command line I/O redirection used
by Unix shells.
flex.exe -- the executable image for the flex program;
flex.doc -- documentation, the "man page" describing flex (flex.1
processed with `nroff -man' followed by `col -b');
flex.skl -- a text file containing flex's default skeleton;
with this version of flex, it is for reference only;
flex.exe does not need to know where to find it;
flexlib.olb -- an object library containing some support routines;
you might need to link your generated lexer against
it, depending on how your program is designed;
flex.exe does not access it; it corresponds to
`libfl.a' under Unix;
FlexLexer.h -- header file used for C++ class-based lexers; not
needed for ordinary C lexers.
Notes:
This VMS port of flex supports only the original Unix command line
interface, not the native DCL interface which was available for flex 2.3.
build.com -- DCL command procedure as alternative to descrip.mms;
descrip.mms -- 2.5.x makefile for use with MMS or MMK (see step #1);
mkskel.tpu -- TPU program used to make skel.c from flex.skl for full
build from scratch; performs same function as mkskel.sh;
vms-conf.h -- pre-configured `conf.in', copied to [-.-]config.h;
vms-code.c -- VMS-specific support code, copied to [-.-]vms-code.c;
README.VMS -- this file

View file

@ -0,0 +1,155 @@
$! VMS build procedure for flex 2.5.x;
$ v = 'f$verify(0)'
$!
$! usage:
$! $ @[.MISC.VMS]BUILD.COM compiler parser [test]
$! where `compiler' is either "GNUC" or "DECC" or "VAXC" or empty
$! and `parser' is either "BISON" or "BYACC" or "YACC" or empty
$! and `[test]' is either "CHECK-ONLY" or "NO-CHECK" or empty
$! empty compiler defaults to VAX C (even under Alpha/VMS);
$! special "LINK" compiler value does link without compilation;
$! empty parser defaults to using supplied parse code in [.MISC];
$! optional test is performed by default.
$!
$
$! we start from [.MISC.VMS], then move to the main source directory
$ where = f$parse("_._;",f$environ("PROCEDURE")) - "_._;"
$ set default 'where'
$ brkt = f$extract(f$length(where)-1,1,where)
$ if f$locate(".MISC.VMS"+brkt,where).lt.f$length(where) then -
set default 'f$string(f$extract(0,1,f$dir()) + "-.-" + brkt)'
$
$ p1 := 'p1'
$ p2 := 'p2'
$ p3 := 'p3'
$ if p1.eqs."LINK" then goto link
$ if p3.eqs."CHECK-ONLY" then goto check
$ p2 = p2 - "_PARSER"
$!
$ CDEFS = "/Define=(""VMS"")" ! =(""VMS"",""DEFAULT_CSIZE=256"")
$!
$ if p1.eqs."GNUC"
$ then CC = "gcc"
$ CFLAGS = "/noList/Opt=2/Debug/noVerbose"
$ LIBS = "gnu_cc:[000000]gcclib.olb/Library, sys$library:vaxcrtl.olb/Library"
$ else CC = "cc"
$ if p1.eqs."DECC"
$ then CFLAGS = "/noList/Prefix=All"
$ LIBS = ""
$ if f$trnlnm("DECC$CC_DEFAULT").nes."" then CC = CC + "/DECC"
$ else CFLAGS = "/noList/Optimize=noInline"
$ LIBS = "sys$share:vaxcrtl.exe/Shareable"
$ if f$trnlnm("DECC$CC_DEFAULT").nes."" then CC = CC + "/VAXC"
$ if p1.nes."" .and. p1.nes."VAXC" then exit %x002C
$ endif
$ endif
$!
$ no_parser = 0
$ if p2.eqs."BISON"
$ then YACC = "bison"
$ YACCFLAGS = "/Defines/Fixed_Outfiles"
$ ALLOCA = ",[]alloca.obj"
$ else
$ YACCFLAGS = "-d"
$ ALLOCA = ""
$ if p2.eqs."BYACC" .or. p2.eqs."YACC"
$ then YACC = f$edit(p2,"LOWERCASE")
$ else YACC = "! yacc"
$ if p2.nes."" .and. p2.nes."NO" .and. p2.nes."NONE" then exit %x002C
$ no_parser = 1
$ endif
$ endif
$!
$ ECHO = "write sys$output"
$ COPY = "copy_"
$ MOVE = "rename_/New_Vers"
$ MUNG = "search_/Exact/Match=NOR"
$ PURGE = "purge_/noConfirm/noLog"
$ REMOVE = "delete_/noConfirm/noLog"
$ TPU = "edit_/TPU/noJournal/noDisplay/noSection"
$!
$ if v then set verify
$!
$ 'COPY' [.misc.vms]vms-conf.h config.h
$ 'COPY' [.misc.vms]vms-code.c vms-code.c
$ 'COPY' [.misc]flex.man flex.doc
$ if ALLOCA.nes."" then 'COPY' [.MISC]alloca.c alloca.c
$ 'COPY' initscan.c scan.c !make.bootstrap
$!
$ if f$search("skel.c").nes."" then -
if f$cvtime(f$file_attr("skel.c","RDT")).gts. -
f$cvtime(f$file_attr("flex.skl","RDT")) then goto skip_mkskel
$ 'TPU' /Command=[.misc.vms]mkskel.tpu flex.skl /Output=skel.c
$skip_mkskel:
$!
$ if f$search("parse.c").nes."" .and. f$search("parse.h").nes."" then -
if f$cvtime(f$file_attr("parse.c","RDT")).gts. -
f$cvtime(f$file_attr("parse.y","RDT")) then goto skip_yacc
$ if f$search("y_tab.%").nes."" then 'REMOVE' y_tab.%;*
$ if no_parser
$ then 'COPY' [.misc]parse.% sys$disk:[]y_tab.*
$ else 'YACC' 'YACCFLAGS' parse.y
$ endif
$ 'MUNG' y_tab.c "#module","#line" /Output=parse.c
$ 'REMOVE' y_tab.c;*
$ 'MOVE' y_tab.h parse.h
$skip_yacc:
$!
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] ccl.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] dfa.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] ecs.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] gen.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] main.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] misc.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] nfa.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] parse.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] scan.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] skel.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] sym.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] tblcmp.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] yylex.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] vms-code.c
$ if ALLOCA.nes."" then - !bison
'CC' 'CFLAGS' /Define=("STACK_DIRECTION=-1","xmalloc=yy_flex_xmalloc") alloca.c
$!
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] libmain.c
$ 'CC' 'CFLAGS' 'CDEFS' /Include=[] libyywrap.c
$ library/Obj flexlib.olb/Create libmain.obj,libyywrap.obj/Insert
$ if f$search("flexlib.olb;-1").nes."" then 'PURGE' flexlib.olb
$!
$ open/Write optfile sys$disk:[]crtl.opt
$ write optfile LIBS
$ close optfile
$ if f$search("crtl.opt;-1").nes."" then 'PURGE' crtl.opt
$!
$ version = "# flex ""2.5""" !default, overridden by version.h
$ open/Read/Error=v_h_2 hfile version.h
$ read/End=v_h_1 hfile version
$v_h_1: close/noLog hfile
$v_h_2: version = f$element(1,"""",version)
$ open/Write optfile sys$disk:[]ident.opt
$ write optfile "identification=""flex ''version'"""
$ close optfile
$ if f$search("ident.opt;-1").nes."" then 'PURGE' ident.opt
$!
$link:
$ link/noMap/Exe=flex.exe ccl.obj,dfa.obj,ecs.obj,gen.obj,main.obj,misc.obj,-
nfa.obj,parse.obj,scan.obj,skel.obj,sym.obj,tblcmp.obj,yylex.obj,-
vms-code.obj 'ALLOCA' ,flexlib.olb/Lib,-
sys$disk:[]crtl.opt/Opt,sys$disk:[]ident.opt/Opt
$!
$ if p3.eqs."NO-CHECK" .or. p3.eqs."NOCHECK" then goto done
$
$check:
$ 'ECHO' ""
$ 'ECHO' " Checking with COMPRESSION="""""
$ mcr sys$disk:[]flex.exe -t -p scan.l > scan.chk
$ diff_/Output=_NL:/Maximum_Diff=1 scan.c scan.chk
$ if $status
$ then 'ECHO' " Test passed."
$ 'REMOVE' scan.chk;*
$ else 'ECHO' "? Test failed!"
$ endif
$
$done:
$ exit

View file

@ -0,0 +1,311 @@
# descrip.mms -- makefile for building `flex' using MMS or MMK on VMS;
# created manually from Makefile.in
# flex 2.5.0 Jan'95
MAKEFILE = descrip.mms # from [.MISC.VMS]
MAKE = $(MMS) /Descr=$(MAKEFILE)
MAKEFLAGS = $(MMSQUALIFIERS)
# Possible values for DEFS:
# "VMS" -- used just to make sure parentheses aren't empty;
# For flex to always generate 8-bit scanners, append
# ,"DEFAULT_CSIZE=256" inside /Define=() of DEFS.
DEFS = /Define=("VMS")
LDFLAGS = /noMap
# compiler handling
.ifdef GNUC
CC = gcc
GCCINIT = ! SET COMMAND GNU_CC:[000000]GCC
CFLAGS = /noList/Opt=2/Debug/noVerbose
LIBS = gnu_cc:[000000]gcclib.olb/Library, sys$library:vaxcrtl.olb/Library
C_CHOICE = "GNUC=1"
.else ! not GNU C
CC = cc
GCCINIT =
.ifdef DECC
CFLAGS = /noList/Prefix=All
LIBS =
C_CHOICE = "DECC=1"
.else ! not DEC C; assume VAX C
CFLAGS = /noList/Optimize=noInline
LIBS = sys$share:vaxcrtl.exe/Shareable
C_CHOICE = "VAXC=1"
.endif
.endif
# parser handling
# mms/macro=("xxxC=1","zzz_parser=1"), where "zzz_parser" is
# either "bison_parser" or "byacc_parser" or "yacc_parser",
# otherwise assumed to be "no_parser"; and where "xxxC=1" is
# either "VAXC=1", "GNUC=1", or "DECC=1" as above
.ifdef bison_parser
YACC = bison
YACCFLAGS = /Defines/Fixed_Outfiles
YACCINIT = set command gnu_bison:[000000]bison
ALLOCA = ,[]alloca.obj # note leading comma
.else
YACCFLAGS = -d
YACCINIT =
ALLOCA =
.ifdef byacc_parser
YACC = byacc
.else
.ifdef yacc_parser
YACC = yacc
.else
# none of bison, byacc, or yacc specified
.ifdef no_parser
.else
no_parser=1
.endif #<none>
.endif #yacc
.endif #byacc
.endif #bison
# VMS-specific hackery
ECHO = write sys$output # requires single quoted arg
COPY = copy_ #
MOVE = rename_/New_Vers # within same device only
MUNG = search_/Exact/Match=NOR # to strip unwanted `#module' directive
NOOP = continue # non-empty command that does nothing
PURGE = purge_/noConfirm/noLog # relatively quiet file removal
REMOVE = delete_/noConfirm/noLog # ditto
TOUCH = append_/New _NL: # requires single file arg
TPU = edit_/TPU/noJournal/noDisplay/noSection
# You can define this to be "lex.exe" if you want to replace lex at your site.
FLEX =flex.exe
# note: there should be no whitespace between `=' and the name,
# or else $(FLEX_EXEC) below will not function properly.
FLEXLIB = flexlib.olb
# You normally do not need to modify anything below this point.
# ------------------------------------------------------------
VMSDIR = [.MISC.VMS]
MISCDIR = [.MISC]
CURDIR = sys$disk:[]
CPPFLAGS = $(DEFS)/Include=[]
LIBOPT = $(CURDIR)crtl.opt # run-time library(s)
ID_OPT = $(CURDIR)ident.opt # version identification
.SUFFIXES : # avoid overhead of umpteen built-in rules
.SUFFIXES : .obj .c
.c.obj :
$(CC)$(CFLAGS)$(CPPFLAGS) $<
VMSHDRS = $(VMSDIR)vms-conf.h # copied to []config.h
VMSSRCS = $(VMSDIR)vms-code.c # copied to []vms-code.c
VMSOBJS = ,vms-code.obj # note leading comma
HEADERS = flexdef.h version.h
SOURCES = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.y \
scan.l skel.c sym.c tblcmp.c yylex.c
OBJECTS = ccl.obj,dfa.obj,ecs.obj,gen.obj,main.obj,misc.obj,nfa.obj,parse.obj,\
scan.obj,skel.obj,sym.obj,tblcmp.obj,yylex.obj $(VMSOBJS) $(ALLOCA)
LIBSRCS = libmain.c libyywrap.c
LIBOBJS = libmain.obj,libyywrap.obj
LINTSRCS = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.c \
scan.c skel.c sym.c tblcmp.c yylex.c
DISTFILES = README NEWS COPYING INSTALL FlexLexer.h \
configure.in conf.in Makefile.in mkskel.sh flex.skl \
$(HEADERS) $(SOURCES) $(LIBSRCS) MISC \
flex.1 scan.c install.sh mkinstalldirs configure
DIST_NAME = flex
# flex options to use when generating scan.c from scan.l
COMPRESSION =
PERF_REPORT = -p
# which "flex" to use to generate scan.c from scan.l
FLEX_EXEC = mcr $(CURDIR)$(FLEX)
FLEX_FLAGS = -t $(PERF_REPORT) #$(COMPRESSION)
MARKER = make.bootstrap
##### targets start here #####
all : $(FLEX) flex.doc
@ $(NOOP)
install : $(FLEX) flex.doc flex.skl $(FLEXLIB) FlexLexer.h
@ $(ECHO) "-- Installation must be done manually."
@ $(ECHO) " $+"
.ifdef GCCINIT
.FIRST
$(GCCINIT)
.endif #GCCINIT
flex : $(FLEX)
@ $(NOOP)
$(FLEX) : $(MARKER) $(OBJECTS) $(FLEXLIB) $(LIBOPT) $(ID_OPT)
$(LINK)/Exe=$(FLEX) $(LDFLAGS)\
$(OBJECTS),$(FLEXLIB)/Lib,$(LIBOPT)/Opt,$(ID_OPT)/Opt
$(MARKER) : initscan.c
@- if f$search("scan.c").nes."" then $(REMOVE) scan.c;*
$(COPY) initscan.c scan.c
@ $(TOUCH) $(MARKER)
parse.c : parse.y
@- if f$search("y_tab.%").nes."" then $(REMOVE) y_tab.%;*
.ifdef no_parser
$(COPY) $(MISCDIR)parse.% $(CURDIR)y_tab.*
.else
$(YACCINIT)
$(YACC) $(YACCFLAGS) parse.y
.endif
$(MUNG) y_tab.c "#module","#line" /Output=parse.c
@- $(REMOVE) y_tab.c;*
$(MOVE) y_tab.h parse.h
parse.h : parse.c
@ $(TOUCH) parse.h
scan.c : scan.l
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) scan.l > scan.c
scan.obj : scan.c parse.h flexdef.h config.h
yylex.obj : yylex.c parse.h flexdef.h config.h
skel.c : flex.skl $(VMSDIR)mkskel.tpu
$(TPU) /Command=$(VMSDIR)mkskel.tpu flex.skl /Output=skel.c
main.obj : main.c flexdef.h config.h version.h
ccl.obj : ccl.c flexdef.h config.h
dfa.obj : dfa.c flexdef.h config.h
ecs.obj : ecs.c flexdef.h config.h
gen.obj : gen.c flexdef.h config.h
misc.obj : misc.c flexdef.h config.h
nfa.obj : nfa.c flexdef.h config.h
parse.obj : parse.c flexdef.h config.h
skel.obj : skel.c flexdef.h config.h
sym.obj : sym.c flexdef.h config.h
tblcmp.obj : tblcmp.c flexdef.h config.h
vms-code.obj : vms-code.c flexdef.h config.h
[]alloca.obj : alloca.c
$(CC)$(CFLAGS)/Define=("STACK_DIRECTION=-1","xmalloc=yy_flex_xmalloc") alloca.c
alloca.c : $(MISCDIR)alloca.c
$(COPY) $(MISCDIR)alloca.c alloca.c
config.h : $(VMSDIR)vms-conf.h
$(COPY) $(VMSDIR)vms-conf.h config.h
vms-code.c : $(VMSDIR)vms-code.c
$(COPY) $(VMSDIR)vms-code.c vms-code.c
test : check
@ $(NOOP)
check : $(FLEX)
@ $(ECHO) ""
@ $(ECHO) " Checking with COMPRESSION="$(COMPRESSION)""
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) scan.l > scan.chk
diff_/Output=_NL:/Maximum_Diff=1 scan.c scan.chk
bigcheck :
@- if f$search("scan.c").nes."" then $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-C""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-Ce""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-Cm""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-f""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-Cfea""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-CFer""") check
@- $(REMOVE) scan.c;*
$(MAKE)$(MAKEFLAGS) /Macro=($(C_CHOICE),"COMPRESSION=""-l""","PERF_REPORT=") check
@- $(REMOVE) scan.c;*,scan.chk;*
$(MAKE)$(MAKEFLAGS) $(FLEX)
@- $(PURGE) scan.obj
@ $(ECHO) "All checks successful"
$(FLEXLIB) : $(LIBOBJS)
library/Obj $(FLEXLIB)/Create $(LIBOBJS)/Insert
@ if f$search("$(FLEXLIB);-1").nes."" then $(PURGE) $(FLEXLIB)
# We call it .doc instead of .man, to lessen culture shock. :-}
# If MISC/flex.man is out of date relative to flex.1, there's
# not much we can do about it with the tools readily available.
flex.doc : flex.1
@ if f$search("$(MISCDIR)flex.man").eqs."" then \
$(COPY) flex.1 $(MISCDIR)flex.man
$(COPY) $(MISCDIR)flex.man flex.doc
#
# This is completely VMS-specific...
#
# Linker options file specifying run-time library(s) to link against;
# choice depends on which C compiler is used, and might be empty.
$(LIBOPT) : $(MAKEFILE)
@ open/Write optfile $(LIBOPT)
@ write optfile "$(LIBS)"
@ close optfile
# Linker options file putting the version number where the ANALYZE/IMAGE
# command will be able to find and report it; assumes that the first line
# of version.h has the version number enclosed within the first and second
# double quotes on it [as in ``#define FLEX_VERSION "2.5.0"''].
$(ID_OPT) : version.h
@ version = "# flex ""2.5""" !default, overridden by version.h
@- open/Read hfile version.h
@- read hfile version
@- close/noLog hfile
@ version = f$element(1,"""",version)
@ open/Write optfile $(ID_OPT)
@ write optfile "identification=""flex ''version'"""
@ close optfile
#
# This is the only stuff moderately useful from the remainder
# of Makefile.in...
#
mostlyclean :
@- if f$search("scan.chk").nes."" then $(REMOVE) scan.chk;*
@- if f$search("*.obj;-1").nes."" then $(PURGE) *.obj
@- if f$search("*.exe;-1").nes."" then $(PURGE) *.exe
@- if f$search("*.opt;-1").nes."" then $(PURGE) *.opt
clean : mostlyclean
@- if f$search("*.obj").nes."" then $(REMOVE) *.obj;*
@- if f$search("parse.h").nes."" then $(REMOVE) parse.h;*
@- if f$search("parse.c").nes."" then $(REMOVE) parse.c;*
@- if f$search("alloca.c").nes."" .and.-
f$search("$(MISCDIR)alloca.c").nes."" then $(REMOVE) alloca.c;*
@- if f$search("$(LIBOPT)").nes."" then $(REMOVE) $(LIBOPT);*
@- if f$search("$(ID_OPT)").nes."" then $(REMOVE) $(ID_OPT);*
distclean : clean
@- if f$search("$(MARKER)").nes."" then $(REMOVE) $(MARKER);*
@- if f$search("$(FLEX)").nes."" then $(REMOVE) $(FLEX);*
@- if f$search("$(FLEXLIB)").nes."" then $(REMOVE) $(FLEXLIB);*
@- if f$search("flex.doc").nes."" then $(REMOVE) flex.doc;*
@- if f$search("scan.c").nes."" then $(REMOVE) scan.c;*
@- if f$search("vms-code.c").nes."" .and.-
f$search("$(VMSDIR)vms-code.c").nes."" then $(REMOVE) vms-code.c;*
@- if f$search("config.h").nes."" .and.-
f$search("$(VMSDIR)vms-conf.h").nes."" then $(REMOVE) config.h;*
# @- if f$search("descrip.mms").nes."" .and.-
# f$search("$(VMSDIR)descrip.mms").nes."" then $(REMOVE) descrip.mms;*
realclean : distclean
@- if f$search("skel.c").nes."" then $(REMOVE) skel.c;*

View file

@ -0,0 +1,45 @@
! mkskel.tpu
! usage:
! edit/TPU/noDisplay/noSection/Command=mkskel.tpu flex.skl /Output=skel.c
!
! Create a C source file from the flex skeleton data. Copy the file,
! changing backslash (\) to doubled backslash (\\) and quote (")
! to backslash quote (\"). For each line, insert space+space+quote
! at the beginning and quote+comma at the end. Bracket the updated
! text with several lines of prologue and epilogue.
!
skelfile := CREATE_BUFFER("file", GET_INFO(COMMAND_LINE, "file_name"));
SET(NO_WRITE, skelfile);
target := '"' | '\'; !do this once, outside loops
POSITION(BEGINNING_OF(skelfile)); !start here
rest_of_line := CREATE_RANGE(MARK(NONE), MARK(NONE)); !also outside loops
LOOP
EXITIF MARK(NONE) = END_OF(skelfile); !are we done yet?
COPY_TEXT(' "'); start_pos := MARK(NONE);
POSITION(LINE_END); end_pos := MARK(NONE);
MODIFY_RANGE(rest_of_line, start_pos, end_pos);
LOOP
next_match := SEARCH_QUIETLY(target, FORWARD, EXACT, rest_of_line);
EXITIF next_match = 0;
POSITION(BEGINNING_OF(next_match));
COPY_TEXT('\'); MOVE_HORIZONTAL(1); !past the matched character
MODIFY_RANGE(rest_of_line, MARK(NONE), end_pos);
ENDLOOP;
POSITION(LINE_END); COPY_TEXT('",');
MOVE_VERTICAL(1); POSITION(LINE_BEGIN); !go to next line
ENDLOOP;
POSITION(BEGINNING_OF(skelfile)); !insert five line prologue
COPY_TEXT('/* File created from flex.skl via mkskel.tpu */'); SPLIT_LINE;
SPLIT_LINE;
COPY_TEXT('#include "flexdef.h"'); SPLIT_LINE;
SPLIT_LINE;
COPY_TEXT('const char *skel[] = {'); SPLIT_LINE;
POSITION(END_OF(skelfile)); !append two line epilogue
COPY_TEXT(' 0'); SPLIT_LINE;
COPY_TEXT('};'); !! SPLIT_LINE;
WRITE_FILE(skelfile, GET_INFO(COMMAND_LINE, "output_file"));
QUIT
!--<eof>--

View file

@ -0,0 +1,152 @@
/* vms-code.c -- additional VMS-specific support code for flex
*/
#include "flexdef.h"
static const char *original_arg0;
static const char default_arg0[] = "flex.exe";
#define IN_FD 0
#define OUT_FD 1
#define ERR_FD 2
static char *fix_arg0 PROTO((const char *));
/* Command line arguments fixup -- simplify argv[0], and handle `>'
output redirection request; called first thing from main(). */
void argv_fixup( iargc, iargv )
int *iargc;
char ***iargv;
{
const char *mode[3], *rfm[3], *name[3];
char *p;
int i, oargc, punct, which, append, alt_rfm;
/*
* Get original argv[0] supplied by run-time library startup code,
* then replace it with a stripped down one.
*/
original_arg0 = (*iargv)[0];
(*iargv)[0] = fix_arg0(original_arg0);
/*
* Check command line arguments for redirection request(s).
* For simplicity, if multiple attempts are made, the last one wins.
*/
name[0] = name[1] = name[2] = 0;
oargc = 1; /* number of args caller will see; count includes argv[0] */
for (i = 1; i < *iargc; i++) {
p = (*iargv)[i];
switch (*p) {
case '<':
/* might be "<dir>file"; then again, perhaps "<<dir>file" */
punct = (strchr(p, '>') != 0);
if (p[1] == '<') {
if (!punct || p[2] == '<')
flexerror("<<'sentinel' input not supported.");
punct = 0;
}
if (punct) /* the '<' seems to be directory punctuation */
goto arg; /*GOTO*/
mode[IN_FD] = "r";
rfm[IN_FD] = 0;
name[IN_FD] = ++p;
if (!*p && (i + 1) < *iargc)
name[IN_FD] = (*iargv)[++i];
break;
case '>':
append = (p[1] == '>');
if (append) ++p;
alt_rfm = (p[1] == '$');
if (alt_rfm) ++p;
which = (p[1] == '&' ? ERR_FD : OUT_FD);
if (which == ERR_FD) ++p;
mode[which] = append ? "a" : "w";
rfm[which] = alt_rfm ? "rfm=var" : "rfm=stmlf";
name[which] = ++p;
if (!*p && (i + 1) < *iargc)
name[which] = (*iargv)[++i];
break;
case '|':
flexerror("pipe output not supported.");
/*NOTREACHED*/
break;
default:
arg: /* ordinary option or argument */
(*iargv)[oargc++] = p;
break;
}
}
/* perform any requested redirection; don't bother with SYS$xxx logicals */
if (name[IN_FD])
if (!freopen(name[IN_FD], mode[IN_FD], stdin))
lerrsf("failed to redirect `stdin' from \"%s\"", name[IN_FD]);
if (name[OUT_FD])
if (!freopen(name[OUT_FD], mode[OUT_FD], stdout,
rfm[OUT_FD], "rat=cr", "mbc=32", "shr=nil"))
lerrsf("failed to redirect `stdout' to \"%s\"", name[OUT_FD]);
if (name[ERR_FD]) /* likely won't see message if this fails; oh well... */
if (!freopen(name[ERR_FD], mode[ERR_FD], stderr,
rfm[ERR_FD], "rat=cr"))
lerrsf("failed to redirect `stderr' to \"%s\"", name[ERR_FD]);
/* remove any excess arguments (used up from redirection) */
while (*iargc > oargc)
(*iargv)[--*iargc] = 0;
/* all done */
return;
}
/* Pick out the basename of a full filename, and return a pointer
to a modifiable copy of it. */
static char *fix_arg0( arg0 )
const char *arg0;
{
char *p, *new_arg0;
if (arg0) {
/* strip off the path */
if ((p = strrchr(arg0, ':')) != 0) /* device punctuation */
arg0 = p + 1;
if ((p = strrchr(arg0, ']')) != 0) /* directory punctuation */
arg0 = p + 1;
if ((p = strrchr(arg0, '>')) != 0) /* alternate dir punct */
arg0 = p + 1;
}
if (!arg0 || !*arg0)
arg0 = default_arg0;
/* should now have "something.exe;#"; make a modifiable copy */
new_arg0 = copy_string(arg0);
/* strip off ".exe" and/or ";#" (version number),
unless it ended up as the whole name */
if ((p = strchr(new_arg0, '.')) != 0 && (p > new_arg0)
&& (p[1] == 'e' || p[1] == 'E')
&& (p[2] == 'x' || p[2] == 'X')
&& (p[3] == 'e' || p[3] == 'E')
&& (p[4] == ';' || p[4] == '.' || p[4] == '\0'))
*p = '\0';
else if ((p = strchr(new_arg0, ';')) != 0 && (p > new_arg0))
*p = '\0';
return new_arg0;
}
#include <ssdef.h>
#include <stsdef.h>
#ifdef exit
#undef exit
extern void exit PROTO((int)); /* <stdlib.h> ended up prototyping vms_exit */
#endif
/* Convert zero to VMS success and non-zero to VMS failure. The latter
does not bother trying to distinguish between various failure reasons. */
void vms_exit( status )
int status;
{
exit( status == 0 ? SS$_NORMAL : (SS$_ABORT | STS$M_INHIB_MSG) );
}

View file

@ -0,0 +1,32 @@
/* config.h manually constructed for VMS */
/* Define to empty if the keyword does not work. */
#undef const
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* Define if you have the ANSI C header files. */
#define STDC_HEADERS
/* Define if you have the <malloc.h> header file. */
#undef HAVE_MALLOC_H
/* Define if you have the <string.h> header file. */
#define HAVE_STRING_H
/* Define if you have the <sys/types.h> header file. */
#ifndef __GNUC__
#undef HAVE_SYS_TYPES_H
#else
#define HAVE_SYS_TYPES_H
#endif
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#undef HAVE_ALLOCA_H
/* Extra platform-specific command line handling. */
#define NEED_ARGV_FIXUP
/* Override default exit behavior. */
#define exit vms_exit

View file

@ -0,0 +1,484 @@
/* alloca.c -- allocate automatically reclaimed memory
(Mostly) portable public-domain implementation -- D A Gwyn
This implementation of the PWB library alloca function,
which is used to allocate space off the run-time stack so
that it is automatically reclaimed upon procedure exit,
was inspired by discussions with J. Q. Johnson of Cornell.
J.Otto Tennant <jot@cray.com> contributed the Cray support.
There are some preprocessor constants that can
be defined when compiling for your specific system, for
improved efficiency; however, the defaults should be okay.
The general concept of this implementation is to keep
track of all alloca-allocated blocks, and reclaim any
that are found to be deeper in the stack than the current
invocation. This heuristic does not reclaim storage as
soon as it becomes invalid, but it will do so eventually.
As a special case, alloca(0) reclaims storage without
allocating any. It is a good idea to use alloca(0) in
your main control loop, etc. to force garbage collection. */
#ifdef HAVE_CONFIG_H
#if defined (emacs) || defined (CONFIG_BROKETS)
#include <config.h>
#else
#include "config.h"
#endif
#endif
/* If compiling with GCC 2, this file's not needed. */
#if !defined (__GNUC__) || __GNUC__ < 2
/* If someone has defined alloca as a macro,
there must be some other way alloca is supposed to work. */
#ifndef alloca
#ifdef emacs
#ifdef static
/* actually, only want this if static is defined as ""
-- this is for usg, in which emacs must undefine static
in order to make unexec workable
*/
#ifndef STACK_DIRECTION
you
lose
-- must know STACK_DIRECTION at compile-time
#endif /* STACK_DIRECTION undefined */
#endif /* static */
#endif /* emacs */
/* If your stack is a linked list of frames, you have to
provide an "address metric" ADDRESS_FUNCTION macro. */
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
long i00afunc ();
#define ADDRESS_FUNCTION(arg) (char *) i00afunc (&(arg))
#else
#define ADDRESS_FUNCTION(arg) &(arg)
#endif
#if __STDC__
typedef void *pointer;
#else
typedef char *pointer;
#endif
#define NULL 0
/* Different portions of Emacs need to call different versions of
malloc. The Emacs executable needs alloca to call xmalloc, because
ordinary malloc isn't protected from input signals. On the other
hand, the utilities in lib-src need alloca to call malloc; some of
them are very simple, and don't have an xmalloc routine.
Non-Emacs programs expect this to call use xmalloc.
Callers below should use malloc. */
#ifndef emacs
#define malloc xmalloc
#endif
extern pointer malloc ();
/* Define STACK_DIRECTION if you know the direction of stack
growth for your system; otherwise it will be automatically
deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown */
#ifndef STACK_DIRECTION
#define STACK_DIRECTION 0 /* Direction unknown. */
#endif
#if STACK_DIRECTION != 0
#define STACK_DIR STACK_DIRECTION /* Known at compile-time. */
#else /* STACK_DIRECTION == 0; need run-time code. */
static int stack_dir; /* 1 or -1 once known. */
#define STACK_DIR stack_dir
static void
find_stack_direction ()
{
static char *addr = NULL; /* Address of first `dummy', once known. */
auto char dummy; /* To get stack address. */
if (addr == NULL)
{ /* Initial entry. */
addr = ADDRESS_FUNCTION (dummy);
find_stack_direction (); /* Recurse once. */
}
else
{
/* Second entry. */
if (ADDRESS_FUNCTION (dummy) > addr)
stack_dir = 1; /* Stack grew upward. */
else
stack_dir = -1; /* Stack grew downward. */
}
}
#endif /* STACK_DIRECTION == 0 */
/* An "alloca header" is used to:
(a) chain together all alloca'ed blocks;
(b) keep track of stack depth.
It is very important that sizeof(header) agree with malloc
alignment chunk size. The following default should work okay. */
#ifndef ALIGN_SIZE
#define ALIGN_SIZE sizeof(double)
#endif
typedef union hdr
{
char align[ALIGN_SIZE]; /* To force sizeof(header). */
struct
{
union hdr *next; /* For chaining headers. */
char *deep; /* For stack depth measure. */
} h;
} header;
static header *last_alloca_header = NULL; /* -> last alloca header. */
/* Return a pointer to at least SIZE bytes of storage,
which will be automatically reclaimed upon exit from
the procedure that called alloca. Originally, this space
was supposed to be taken from the current stack frame of the
caller, but that method cannot be made to work for some
implementations of C, for example under Gould's UTX/32. */
pointer
alloca (size)
unsigned size;
{
auto char probe; /* Probes stack depth: */
register char *depth = ADDRESS_FUNCTION (probe);
#if STACK_DIRECTION == 0
if (STACK_DIR == 0) /* Unknown growth direction. */
find_stack_direction ();
#endif
/* Reclaim garbage, defined as all alloca'd storage that
was allocated from deeper in the stack than currently. */
{
register header *hp; /* Traverses linked list. */
for (hp = last_alloca_header; hp != NULL;)
if ((STACK_DIR > 0 && hp->h.deep > depth)
|| (STACK_DIR < 0 && hp->h.deep < depth))
{
register header *np = hp->h.next;
free ((pointer) hp); /* Collect garbage. */
hp = np; /* -> next header. */
}
else
break; /* Rest are not deeper. */
last_alloca_header = hp; /* -> last valid storage. */
}
if (size == 0)
return NULL; /* No allocation required. */
/* Allocate combined header + user data storage. */
{
register pointer new = malloc (sizeof (header) + size);
/* Address of header. */
((header *) new)->h.next = last_alloca_header;
((header *) new)->h.deep = depth;
last_alloca_header = (header *) new;
/* User storage begins just after header. */
return (pointer) ((char *) new + sizeof (header));
}
}
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
#ifdef DEBUG_I00AFUNC
#include <stdio.h>
#endif
#ifndef CRAY_STACK
#define CRAY_STACK
#ifndef CRAY2
/* Stack structures for CRAY-1, CRAY X-MP, and CRAY Y-MP */
struct stack_control_header
{
long shgrow:32; /* Number of times stack has grown. */
long shaseg:32; /* Size of increments to stack. */
long shhwm:32; /* High water mark of stack. */
long shsize:32; /* Current size of stack (all segments). */
};
/* The stack segment linkage control information occurs at
the high-address end of a stack segment. (The stack
grows from low addresses to high addresses.) The initial
part of the stack segment linkage control information is
0200 (octal) words. This provides for register storage
for the routine which overflows the stack. */
struct stack_segment_linkage
{
long ss[0200]; /* 0200 overflow words. */
long sssize:32; /* Number of words in this segment. */
long ssbase:32; /* Offset to stack base. */
long:32;
long sspseg:32; /* Offset to linkage control of previous
segment of stack. */
long:32;
long sstcpt:32; /* Pointer to task common address block. */
long sscsnm; /* Private control structure number for
microtasking. */
long ssusr1; /* Reserved for user. */
long ssusr2; /* Reserved for user. */
long sstpid; /* Process ID for pid based multi-tasking. */
long ssgvup; /* Pointer to multitasking thread giveup. */
long sscray[7]; /* Reserved for Cray Research. */
long ssa0;
long ssa1;
long ssa2;
long ssa3;
long ssa4;
long ssa5;
long ssa6;
long ssa7;
long sss0;
long sss1;
long sss2;
long sss3;
long sss4;
long sss5;
long sss6;
long sss7;
};
#else /* CRAY2 */
/* The following structure defines the vector of words
returned by the STKSTAT library routine. */
struct stk_stat
{
long now; /* Current total stack size. */
long maxc; /* Amount of contiguous space which would
be required to satisfy the maximum
stack demand to date. */
long high_water; /* Stack high-water mark. */
long overflows; /* Number of stack overflow ($STKOFEN) calls. */
long hits; /* Number of internal buffer hits. */
long extends; /* Number of block extensions. */
long stko_mallocs; /* Block allocations by $STKOFEN. */
long underflows; /* Number of stack underflow calls ($STKRETN). */
long stko_free; /* Number of deallocations by $STKRETN. */
long stkm_free; /* Number of deallocations by $STKMRET. */
long segments; /* Current number of stack segments. */
long maxs; /* Maximum number of stack segments so far. */
long pad_size; /* Stack pad size. */
long current_address; /* Current stack segment address. */
long current_size; /* Current stack segment size. This
number is actually corrupted by STKSTAT to
include the fifteen word trailer area. */
long initial_address; /* Address of initial segment. */
long initial_size; /* Size of initial segment. */
};
/* The following structure describes the data structure which trails
any stack segment. I think that the description in 'asdef' is
out of date. I only describe the parts that I am sure about. */
struct stk_trailer
{
long this_address; /* Address of this block. */
long this_size; /* Size of this block (does not include
this trailer). */
long unknown2;
long unknown3;
long link; /* Address of trailer block of previous
segment. */
long unknown5;
long unknown6;
long unknown7;
long unknown8;
long unknown9;
long unknown10;
long unknown11;
long unknown12;
long unknown13;
long unknown14;
};
#endif /* CRAY2 */
#endif /* not CRAY_STACK */
#ifdef CRAY2
/* Determine a "stack measure" for an arbitrary ADDRESS.
I doubt that "lint" will like this much. */
static long
i00afunc (long *address)
{
struct stk_stat status;
struct stk_trailer *trailer;
long *block, size;
long result = 0;
/* We want to iterate through all of the segments. The first
step is to get the stack status structure. We could do this
more quickly and more directly, perhaps, by referencing the
$LM00 common block, but I know that this works. */
STKSTAT (&status);
/* Set up the iteration. */
trailer = (struct stk_trailer *) (status.current_address
+ status.current_size
- 15);
/* There must be at least one stack segment. Therefore it is
a fatal error if "trailer" is null. */
if (trailer == 0)
abort ();
/* Discard segments that do not contain our argument address. */
while (trailer != 0)
{
block = (long *) trailer->this_address;
size = trailer->this_size;
if (block == 0 || size == 0)
abort ();
trailer = (struct stk_trailer *) trailer->link;
if ((block <= address) && (address < (block + size)))
break;
}
/* Set the result to the offset in this segment and add the sizes
of all predecessor segments. */
result = address - block;
if (trailer == 0)
{
return result;
}
do
{
if (trailer->this_size <= 0)
abort ();
result += trailer->this_size;
trailer = (struct stk_trailer *) trailer->link;
}
while (trailer != 0);
/* We are done. Note that if you present a bogus address (one
not in any segment), you will get a different number back, formed
from subtracting the address of the first block. This is probably
not what you want. */
return (result);
}
#else /* not CRAY2 */
/* Stack address function for a CRAY-1, CRAY X-MP, or CRAY Y-MP.
Determine the number of the cell within the stack,
given the address of the cell. The purpose of this
routine is to linearize, in some sense, stack addresses
for alloca. */
static long
i00afunc (long address)
{
long stkl = 0;
long size, pseg, this_segment, stack;
long result = 0;
struct stack_segment_linkage *ssptr;
/* Register B67 contains the address of the end of the
current stack segment. If you (as a subprogram) store
your registers on the stack and find that you are past
the contents of B67, you have overflowed the segment.
B67 also points to the stack segment linkage control
area, which is what we are really interested in. */
stkl = CRAY_STACKSEG_END ();
ssptr = (struct stack_segment_linkage *) stkl;
/* If one subtracts 'size' from the end of the segment,
one has the address of the first word of the segment.
If this is not the first segment, 'pseg' will be
nonzero. */
pseg = ssptr->sspseg;
size = ssptr->sssize;
this_segment = stkl - size;
/* It is possible that calling this routine itself caused
a stack overflow. Discard stack segments which do not
contain the target address. */
while (!(this_segment <= address && address <= stkl))
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o %011o\n", this_segment, address, stkl);
#endif
if (pseg == 0)
break;
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
this_segment = stkl - size;
}
result = address - this_segment;
/* If you subtract pseg from the current end of the stack,
you get the address of the previous stack segment's end.
This seems a little convoluted to me, but I'll bet you save
a cycle somewhere. */
while (pseg != 0)
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o\n", pseg, size);
#endif
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
result += size;
}
return (result);
}
#endif /* not CRAY2 */
#endif /* CRAY */
#endif /* no alloca */
#endif /* not GCC version 2 */

View file

@ -0,0 +1,119 @@
# Clarify the flex debug trace by substituting first line of each rule.
# Francois Pinard <pinard@iro.umontreal.ca>, July 1990.
#
# Rewritten to process correctly \n's in scanner input.
# BEGIN section modified to correct a collection of rules.
# Michal Jaegermann <michal@phys.ualberta.ca>, December 1993
#
# Sample usage:
# flex -d PROGRAM.l
# gcc -o PROGRAM PROGRAM.c -lfl
# PROGRAM 2>&1 | gawk -f debflex.awk PROGRAM.l
#
# (VP's note: this script presently does not work with either "old" or
# "new" awk; fixes so it does will be welcome)
BEGIN {
# Insure proper usage.
if (ARGC != 2) {
print "usage: gawk -f debflex.awk FLEX_SOURCE <DEBUG_OUTPUT";
exit (1);
}
# Remove and save the name of flex source.
source = ARGV[1];
ARGC--;
# Swallow the flex source file.
line = 0;
section = 1;
while (getline <source) {
# Count the lines.
line++;
# Count the sections. When encountering section 3,
# break out of the awk BEGIN block.
if (match ($0, /^%%/)) {
section++;
if (section == 3) {
break;
}
}
else {
# Only the lines in section 2 which do not begin in a
# tab or space might be referred to by the flex debug
# trace. Save only those lines.
if (section == 2 && match ($0, /^[^ \t]/)) {
rules[line] = $0;
}
}
}
dashes = "-----------------------------------------------------------";
collect = "";
line = 0;
}
# collect complete rule output from a scanner
$0 !~ /^--/ {
collect = collect "\n" $0;
next;
}
# otherwise we have a new rule - process what we got so far
{
process();
}
# and the same thing if we hit EOF
END {
process();
}
function process() {
# splitting this way we loose some double dashes and
# left parentheses from echoed input - a small price to pay
n = split(collect, field, "\n--|[(]");
# this loop kicks in only when we already collected something
for (i = 1; i <= n; i++) {
if (0 != line) {
# we do not care for traces of newlines.
if (0 == match(field[i], /\"\n+\"[)]/)) {
if (rules[line]) {
text = field[i];
while ( ++i <= n) {
text = text field[i];
}
printf("%s:%d: %-8s -- %s\n",
source, line, text, rules[line]);
}
else {
print;
printf "%s:%d: *** No such rule.\n", source, line;
}
}
line = 0;
break;
}
if ("" != field[i]) {
if ("end of buffer or a NUL)" == field[i]) {
print dashes; # Simplify trace of buffer reloads
continue;
}
if (match(field[i], /accepting rule at line /)) {
# force interpretation of line as a number
line = 0 + substr(field[i], RLENGTH);
continue;
}
# echo everything else
printf("--%s\n", field[i]);
}
}
collect = "\n" $0; # ... and start next trace
}

View file

@ -0,0 +1,56 @@
This directory contains some examples illustrating techniques for extracting
high-performance from flex scanners. Each program implements a simplified
version of the Unix "wc" tool: read text from stdin and print the number of
characters, words, and lines present in the text. All programs were compiled
using gcc (version unavailable, sorry) with the -O flag, and run on a
SPARCstation 1+. The input used was a PostScript file, mainly containing
figures, with the following "wc" counts:
lines words characters
214217 635954 2592172
The basic principles illustrated by these programs are:
- match as much text with each rule as possible
- adding rules does not slow you down!
- avoid backing up
and the big caveat that comes with them is:
- you buy performance with decreased maintainability; make
sure you really need it before applying the above techniques.
See the "Performance Considerations" section of flexdoc for more
details regarding these principles.
The different versions of "wc":
mywc.c
a simple but fairly efficient C version
wc1.l a naive flex "wc" implementation
wc2.l somewhat faster; adds rules to match multiple tokens at once
wc3.l faster still; adds more rules to match longer runs of tokens
wc4.l fastest; still more rules added; hard to do much better
using flex (or, I suspect, hand-coding)
wc5.l identical to wc3.l except one rule has been slightly
shortened, introducing backing-up
Timing results (all times in user CPU seconds):
program time notes
------- ---- -----
wc1 16.4 default flex table compression (= -Cem)
wc1 6.7 -Cf compression option
/bin/wc 5.8 Sun's standard "wc" tool
mywc 4.6 simple but better C implementation!
wc2 4.6 as good as C implementation; built using -Cf
wc3 3.8 -Cf
wc4 3.3 -Cf
wc5 5.7 -Cf; ouch, backing up is expensive

View file

@ -0,0 +1,26 @@
/* A simple but fairly efficient C version of the Unix "wc" tool */
#include <stdio.h>
#include <ctype.h>
main()
{
register int c, cc = 0, wc = 0, lc = 0;
FILE *f = stdin;
while ((c = getc(f)) != EOF) {
++cc;
if (isgraph(c)) {
++wc;
do {
c = getc(f);
if (c == EOF)
goto done;
++cc;
} while (isgraph(c));
}
if (c == '\n')
++lc;
}
done: printf( "%8d%8d%8d\n", lc, wc, cc );
}

View file

@ -0,0 +1,18 @@
/* First cut at a flex-based "wc" tool. */
ws [ \t]
nonws [^ \t\n]
%%
int cc = 0, wc = 0, lc = 0;
{nonws}+ cc += yyleng; ++wc;
{ws}+ cc += yyleng;
\n ++lc; ++cc;
<<EOF>> {
printf( "%8d %8d %8d\n", lc, wc, cc );
yyterminate();
}

View file

@ -0,0 +1,20 @@
/* Somewhat faster "wc" tool: match more text with each rule */
ws [ \t]
nonws [^ \t\n]
word {ws}*{nonws}+
%%
int cc = 0, wc = 0, lc = 0;
{word}{ws}* cc += yyleng; ++wc;
{word}{ws}*\n cc += yyleng; ++wc; ++lc;
{ws}+ cc += yyleng;
\n+ cc += yyleng; lc += yyleng;
<<EOF>> {
printf( "%8d %8d %8d\n", lc, wc, cc );
yyterminate();
}

View file

@ -0,0 +1,24 @@
/* Somewhat faster still: potentially match a lot of text with each rule */
ws [ \t]
nonws [^ \t\n]
word {ws}*{nonws}+
words {word}{ws}+
%%
int cc = 0, wc = 0, lc = 0;
{word}{ws}* cc += yyleng; ++wc;
{word}{ws}*\n cc += yyleng; ++wc; ++lc;
{words}{word}{ws}* cc += yyleng; wc += 2;
{words}{2}{word}{ws}* cc += yyleng; wc += 3;
{words}{3}{word}{ws}* cc += yyleng; wc += 4;
{ws}+ cc += yyleng;
\n+ cc += yyleng; lc += yyleng;
<<EOF>> {
printf( "%8d %8d %8d\n", lc, wc, cc );
yyterminate();
}

View file

@ -0,0 +1,27 @@
/* Fastest version of wc: add rules to pick up newlines, too */
ws [ \t]
nonws [^ \t\n]
word {ws}*{nonws}+
words {word}{ws}+
%%
int cc = 0, wc = 0, lc = 0;
{word}{ws}* ++wc; cc += yyleng;
{word}{ws}*\n ++wc; cc += yyleng; ++lc;
{words}{word}{ws}* wc += 2; cc += yyleng;
{words}{word}{ws}*\n wc += 2; cc += yyleng; ++lc;
{words}{2}{word}{ws}* wc += 3; cc += yyleng;
{words}{2}{word}{ws}*\n wc += 3; cc += yyleng; ++lc;
{words}{3}{word}{ws}* wc += 4; cc += yyleng;
{words}{3}{word}{ws}*\n wc += 4; cc += yyleng; ++lc;
{ws}+ cc += yyleng;
\n+ cc += yyleng; lc += yyleng;
<<EOF>> {
printf( "%8d %8d %8d\n", lc, wc, cc );
yyterminate();
}

View file

@ -0,0 +1,24 @@
/* Oops; slight change from wc3.l introduces backtracking */
ws [ \t]
nonws [^ \t\n]
word {ws}*{nonws}+
words {word}{ws}+
%%
int cc = 0, wc = 0, lc = 0;
{word}{ws}* cc += yyleng; ++wc;
{word}{ws}*\n cc += yyleng; ++wc; ++lc;
{words}{word} cc += yyleng; wc += 2; /* oops */
{words}{2}{word}{ws}* cc += yyleng; wc += 3;
{words}{3}{word}{ws}* cc += yyleng; wc += 4;
{ws}+ cc += yyleng;
\n+ cc += yyleng; lc += yyleng;
<<EOF>> {
printf( "%8d %8d %8d\n", lc, wc, cc );
yyterminate();
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,24 @@
#define CHAR 257
#define NUMBER 258
#define SECTEND 259
#define SCDECL 260
#define XSCDECL 261
#define NAME 262
#define PREVCCL 263
#define EOF_OP 264
#define OPTION_OP 265
#define OPT_OUTFILE 266
#define OPT_PREFIX 267
#define OPT_YYCLASS 268
#define CCE_ALNUM 269
#define CCE_ALPHA 270
#define CCE_BLANK 271
#define CCE_CNTRL 272
#define CCE_DIGIT 273
#define CCE_GRAPH 274
#define CCE_LOWER 275
#define CCE_PRINT 276
#define CCE_PUNCT 277
#define CCE_SPACE 278
#define CCE_UPPER 279
#define CCE_XDIGIT 280

View file

@ -0,0 +1,58 @@
// An example of using the flex C++ scanner class.
%option C++ noyywrap
%{
int mylineno = 0;
%}
string \"[^\n"]+\"
ws [ \t]+
alpha [A-Za-z]
dig [0-9]
name ({alpha}|{dig}|\$)({alpha}|{dig}|\_|\.|\-|\/|\$)*
num1 [-+]?{dig}+\.?([eE][-+]?{dig}+)?
num2 [-+]?{dig}*\.{dig}+([eE][-+]?{dig}+)?
number {num1}|{num2}
%%
{ws} /* skip blanks and tabs */
"/*" {
int c;
while((c = yyinput()) != 0)
{
if(c == '\n')
++mylineno;
else if(c == '*')
{
if((c = yyinput()) == '/')
break;
else
unput(c);
}
}
}
{number} cout << "number " << YYText() << '\n';
\n mylineno++;
{name} cout << "name " << YYText() << '\n';
{string} cout << "string " << YYText() << '\n';
%%
int main( int /* argc */, char** /* argv */ )
{
FlexLexer* lexer = new yyFlexLexer;
while(lexer->yylex() != 0)
;
return 0;
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,262 @@
# @(#) $Header$ (LBL)
@SET_MAKE@
# Possible values for DEFS:
#
# By default, flex generates 8-bit scanners when using table compression,
# and 7-bit scanners when using uncompressed tables (-f or -F options).
# For flex to always generate 8-bit scanners, add "-DDEFAULT_CSIZE=256"
# to DEFS.
#
# For Vax/VMS, add "-DVMS" to DEFS.
#
# For MS-DOS, add "-DMS_DOS" to DEFS. See the directory MISC/MSDOS for
# additional info.
CFLAGS = @CFLAGS@
CPPFLAGS = @CPPFLAGS@
DEFS = @DEFS@
LDFLAGS = -stack 256k
LIBS = @LIBS@
# Installation targeting. Files will be installed under the tree
# rooted at prefix. flex will be installed in bindir, libfl.a in
# libdir, FlexLexer.h will be installed in includedir, and the manual
# pages will be installed in mandir with extension manext.
#
# Raw, unformatted troff source will be installed if INSTALLMAN=man,
# nroff preformatted versions will be installed if INSTALLMAN=cat.
prefix = @prefix@
exec_prefix = @exec_prefix@
bindir = $(exec_prefix)/bin
libdir = $(exec_prefix)/lib
includedir = $(prefix)/include
manext = 1
mandir = $(prefix)/man/man$(manext)
# You can define these to be "lex" and "libl.a" if you want to replace
# lex at your site.
FLEX = flex
FLEXLIB = libfl.a
INSTALLMAN = man
SHELL = /bin/sh
srcdir = @srcdir@
VPATH = @srcdir@
LN_S = @LN_S@
YACC = @YACC@
CC = @CC@
AR = ar
RANLIB = @RANLIB@
INSTALL = @INSTALL@
INSTALL_DATA = @INSTALL_DATA@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
# You normally do not need to modify anything below this point.
# ------------------------------------------------------------
CPPFLAGS = -I. -I$(srcdir)
.c.o:
$(CC) -c $(CPPFLAGS) $(CFLAGS) $<
HEADERS = flexdef.h version.h
SOURCES = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.y \
scan.l skel.c sym.c tblcmp.c yylex.c
OBJECTS = ccl.o dfa.o ecs.o gen.o main.o misc.o nfa.o parse.o \
scan.o skel.o sym.o tblcmp.o yylex.o @ALLOCA@
LIBSRCS = libmain.c libyywrap.c
LIBOBJS = libmain.o libyywrap.o
LINTSRCS = ccl.c dfa.c ecs.c gen.c main.c misc.c nfa.c parse.c \
scan.c skel.c sym.c tblcmp.c yylex.c
DISTFILES = README NEWS COPYING INSTALL FlexLexer.h \
configure.in conf.in Makefile.in mkskel.sh flex.skl \
$(HEADERS) $(SOURCES) $(LIBSRCS) MISC \
flex.1 scan.c install.sh mkinstalldirs configure
DIST_NAME = flex
# which "flex" to use to generate scan.c from scan.l
FLEX_EXEC = ./$(FLEX)
FLEX_FLAGS = -t $(PERF_REPORT)
COMPRESSION =
PERF_REPORT = -p
all: $(FLEX)
$(FLEX): .bootstrap $(OBJECTS) $(FLEXLIB)
$(CC) $(CFLAGS) -o $(FLEX) $(LDFLAGS) $(OBJECTS) $(FLEXLIB) $(LIBS)
.bootstrap: initscan.c
@rm -f scan.c
cp $(srcdir)/initscan.c scan.c
touch .bootstrap
parse.c: parse.y
$(YACC) -d $(srcdir)/parse.y
@sed '/extern char.*malloc/d' <y.tab.c >parse.tmp
@mv parse.tmp parse.c
@mv y.tab.h parse.h
@rm -f y.tab.c
parse.h: parse.c
scan.c: scan.l
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) $(srcdir)/scan.l >scan.c
@sed s,\"$(srcdir)/scan.l\",\"scan.l\", <scan.c >scan.tmp
@mv scan.tmp scan.c
scan.o: scan.c parse.h flexdef.h config.h
yylex.o: yylex.c parse.h flexdef.h config.h
skel.c: flex.skl mkskel.sh
$(SHELL) $(srcdir)/mkskel.sh $(srcdir)/flex.skl >skel.c
main.o: main.c flexdef.h config.h version.h
ccl.o: ccl.c flexdef.h config.h
dfa.o: dfa.c flexdef.h config.h
ecs.o: ecs.c flexdef.h config.h
gen.o: gen.c flexdef.h config.h
misc.o: misc.c flexdef.h config.h
nfa.o: nfa.c flexdef.h config.h
parse.o: parse.c flexdef.h config.h
skel.o: skel.c flexdef.h config.h
sym.o: sym.c flexdef.h config.h
tblcmp.o: tblcmp.c flexdef.h config.h
alloca.o: alloca.c
$(CC) $(CPPFLAGS) $(CFLAGS) -c -Dxmalloc=yy_flex_xmalloc alloca.c
alloca.c: $(srcdir)/MISC/alloca.c
@rm -f alloca.c
cp $(srcdir)/MISC/alloca.c .
test: check
check: $(FLEX)
$(FLEX_EXEC) $(FLEX_FLAGS) $(COMPRESSION) $(srcdir)/scan.l \
| sed s,\"$(srcdir)/scan.l\",\"scan.l\", \
| diff scan.c -
@echo "Check successful, using COMPRESSION=\"$(COMPRESSION)\""
bigcheck:
rm -f scan.c ; $(MAKE) COMPRESSION="-C" check
rm -f scan.c ; $(MAKE) COMPRESSION="-Ce" check
rm -f scan.c ; $(MAKE) COMPRESSION="-Cm" check
rm -f scan.c ; $(MAKE) COMPRESSION="-f" check
rm -f scan.c ; $(MAKE) COMPRESSION="-Cfea" check
rm -f scan.c ; $(MAKE) COMPRESSION="-CFer" check
rm -f scan.c ; $(MAKE) COMPRESSION="-l" PERF_REPORT="" check
rm -f scan.c ; $(MAKE)
@echo "All checks successful"
$(FLEXLIB): $(LIBOBJS)
$(AR) cru $(FLEXLIB) $(LIBOBJS)
-$(RANLIB) $(FLEXLIB)
$(FLEX).man: flex.1
cd $(srcdir) && nroff -man flex.1 >$(FLEX).man
install: $(FLEX) $(FLEXLIB) installdirs install.$(INSTALLMAN)
$(INSTALL_PROGRAM) $(FLEX) $(bindir)/$(FLEX)
@rm -f $(bindir)/$(FLEX)++
cd $(bindir) && $(LN_S) $(FLEX) $(FLEX)++
$(INSTALL_DATA) $(FLEXLIB) $(libdir)/$(FLEXLIB)
-cd $(libdir) && $(RANLIB) $(FLEXLIB)
$(INSTALL_DATA) $(srcdir)/FlexLexer.h $(includedir)/FlexLexer.h
# Note, the following rules delete any vestigial flexdoc installed
# for a prior flex release.
install.man: flex.1
rm -f $(mandir)/$(FLEX)doc.$(manext)
$(INSTALL_DATA) $(srcdir)/flex.1 $(mandir)/$(FLEX).$(manext)
install.cat: $(FLEX).man
rm -f $(mandir)/$(FLEX)doc.$(manext)
$(INSTALL_DATA) $(srcdir)/$(FLEX).man $(mandir)/$(FLEX).$(manext)
installdirs:
$(SHELL) $(srcdir)/mkinstalldirs \
$(bindir) $(libdir) $(includedir) $(mandir)
uninstall:
rm -f $(bindir)/$(FLEX) $(bindir)/$(FLEX)++
rm -f $(libdir)/$(FLEXLIB)
rm -f $(includedir)/FlexLexer.h
rm -f $(mandir)/$(FLEX).$(manext) $(mandir)/$(FLEX)doc.$(manext)
tags: $(SOURCES)
ctags $(SOURCES)
TAGS: $(SOURCES)
etags $(SOURCES)
lint: $(LINTSRCS)
lint -Dconst= $(LINTSRCS) > flex.lint
gcc-lint: $(LINTSRCS)
gcc -Dlint -Wall $(LINTSRCS) >flex.gcc-lint 2>&1
mostlyclean:
rm -f a.out *.bak core errs scan.tmp
clean: mostlyclean
rm -f flex parse.c parse.h *.o alloca.c *.lint lex.yy.c lex.yy.cc \
$(FLEXLIB) config.log config.cache
distclean: clean
rm -f .bootstrap $(FLEX) scan.c tags TAGS Makefile config.status \
config.h stamp-h config.log config.cache
maintainer-clean: distclean
@echo "This command is intended for maintainers to use;"
@echo "it deletes files that may require special tools to rebuild."
rm -f $(FLEX).man skel.c flex*.tar.gz flex*.tar.Z
dist: $(FLEX) $(DISTFILES) parse.c parse.h $(srcdir)/$(FLEX).man
$(MAKE) DIST_NAME=flex-`sed <version.h 's/[^"]*"//' | sed 's/"//'` dist2
dist2:
@rm -rf $(DIST_NAME)
@rm -f $(DIST_NAME).tar $(DIST_NAME).tar.Z $(DIST_NAME).tar.gz
@mkdir $(DIST_NAME)
tar cf - $(DISTFILES) | (cd $(DIST_NAME) && tar xfB -)
@mv $(DIST_NAME)/scan.c $(DIST_NAME)/initscan.c
@chmod 444 $(DIST_NAME)/initscan.c
@chmod +w $(DIST_NAME)/Makefile.in
@cp parse.c parse.h $(DIST_NAME)/MISC
@col -b <$(srcdir)/$(FLEX).man >$(DIST_NAME)/MISC/flex.man
tar chf $(DIST_NAME).tar $(DIST_NAME)
compress <$(DIST_NAME).tar >$(DIST_NAME).tar.Z
gzip <$(DIST_NAME).tar >$(DIST_NAME).tar.gz
@rm $(DIST_NAME).tar
# For an explanation of the following Makefile rules, see node
# `Automatic Remaking' in GNU Autoconf documentation.
Makefile: $(srcdir)/Makefile.in config.status
CONFIG_FILES=$@ CONFIG_HEADERS= ./config.status
config.status: configure
./config.status --recheck
configure: configure.in
cd $(srcdir) && autoconf
#config.h: stamp-h
stamp-h: conf.in config.status
CONFIG_FILES= CONFIG_HEADERS=config.h:conf.in ./config.status
echo timestamp >stamp-h
# conf.in: stamp-h.in
# stamp-h.in: configure.in acconfig.h
# cd $(srcdir) && autoheader
# config.h.in conf.in
# cho timestamp > $(srcdir)/stamp-h.in
# Tell versions [3.59,3.63) of GNU make not to export all variables.
# Otherwise a system limit (for SysV at least) may be exceeded.
.NOEXPORT:

1233
commands/flex-2.5.4/NEWS Normal file

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,60 @@
This is release 2.5 of flex. See "version.h" for the exact patch-level.
See the file "NEWS" to find out what is new in this Flex release.
Read the file "INSTALL" for general installation directives. Peek near
the beginning of the file "Makefile.in" for special DEFS values. On most
systems, you can just run the "configure" script and type "make" to build
flex; then "make check" to test whether it built correctly; and if it did,
then "make install" to install it.
If you're feeling adventurous, you can also issue "make bigcheck" (be
prepared to wait a while).
Note that flex is distributed under a copyright very similar to that of
BSD Unix, and not under the GNU General Public License (GPL), except for
the "configure" script, which is covered by the GPL.
Many thanks to the 2.5 beta-testers for finding bugs and helping test and
increase portability: Stan Adermann, Scott David Daniels, Charles Elliott,
Joe Gayda, Chris Meier, James Nordby, Terrence O'Kane, Karsten Pahnke,
Francois Pinard, Pat Rankin, Andreas Scherer, Marc Wiese, Nathan Zelle.
Please send bug reports and feedback to: Vern Paxson (vern@ee.lbl.gov).
The flex distribution consists of the following files:
README This message
NEWS Differences between the various releases
INSTALL General installation information
COPYING flex's copyright
conf.in, configure.in, configure, Makefile.in, install.sh,
mkinstalldirs
elements of the "autoconf" auto-configuration process
flexdef.h, parse.y, scan.l, ccl.c, dfa.c, ecs.c, gen.c, main.c,
misc.c, nfa.c, sym.c, tblcmp.c, yylex.c
source files
version.h version of this flex release
flex.skl flex scanner skeleton
mkskel.sh script for converting flex.skl to C source file skel.c
skel.c pre-converted C version of flex.skl
libmain.c flex library (-lfl) sources
libyywrap.c
initscan.c pre-flex'd version of scan.l
FlexLexer.h header file for C++ lexer class
flex.1 user documentation
MISC/ a directory containing miscellaneous contributions.
See MISC/README for details.

149
commands/flex-2.5.4/ccl.c Normal file
View file

@ -0,0 +1,149 @@
/* ccl - routines for character classes */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
/* ccladd - add a single character to a ccl */
void ccladd( cclp, ch )
int cclp;
int ch;
{
int ind, len, newpos, i;
check_char( ch );
len = ccllen[cclp];
ind = cclmap[cclp];
/* check to see if the character is already in the ccl */
for ( i = 0; i < len; ++i )
if ( ccltbl[ind + i] == ch )
return;
newpos = ind + len;
if ( newpos >= current_max_ccl_tbl_size )
{
current_max_ccl_tbl_size += MAX_CCL_TBL_SIZE_INCREMENT;
++num_reallocs;
ccltbl = reallocate_Character_array( ccltbl,
current_max_ccl_tbl_size );
}
ccllen[cclp] = len + 1;
ccltbl[newpos] = ch;
}
/* cclinit - return an empty ccl */
int cclinit()
{
if ( ++lastccl >= current_maxccls )
{
current_maxccls += MAX_CCLS_INCREMENT;
++num_reallocs;
cclmap = reallocate_integer_array( cclmap, current_maxccls );
ccllen = reallocate_integer_array( ccllen, current_maxccls );
cclng = reallocate_integer_array( cclng, current_maxccls );
}
if ( lastccl == 1 )
/* we're making the first ccl */
cclmap[lastccl] = 0;
else
/* The new pointer is just past the end of the last ccl.
* Since the cclmap points to the \first/ character of a
* ccl, adding the length of the ccl to the cclmap pointer
* will produce a cursor to the first free space.
*/
cclmap[lastccl] = cclmap[lastccl - 1] + ccllen[lastccl - 1];
ccllen[lastccl] = 0;
cclng[lastccl] = 0; /* ccl's start out life un-negated */
return lastccl;
}
/* cclnegate - negate the given ccl */
void cclnegate( cclp )
int cclp;
{
cclng[cclp] = 1;
}
/* list_character_set - list the members of a set of characters in CCL form
*
* Writes to the given file a character-class representation of those
* characters present in the given CCL. A character is present if it
* has a non-zero value in the cset array.
*/
void list_character_set( file, cset )
FILE *file;
int cset[];
{
register int i;
putc( '[', file );
for ( i = 0; i < csize; ++i )
{
if ( cset[i] )
{
register int start_char = i;
putc( ' ', file );
fputs( readable_form( i ), file );
while ( ++i < csize && cset[i] )
;
if ( i - 1 > start_char )
/* this was a run */
fprintf( file, "-%s", readable_form( i - 1 ) );
putc( ' ', file );
}
}
putc( ']', file );
}

View file

@ -0,0 +1,25 @@
/* $Header$ */
/* Define to empty if the keyword does not work. */
#undef const
/* Define to `unsigned' if <sys/types.h> doesn't define. */
#undef size_t
/* Define if you have the ANSI C header files. */
#undef STDC_HEADERS
/* Define if you have the <malloc.h> header file. */
#undef HAVE_MALLOC_H
/* Define if you have the <string.h> header file. */
#undef HAVE_STRING_H
/* Define if you have the <sys/types.h> header file. */
#undef HAVE_SYS_TYPES_H
/* Define if you have <alloca.h> and it should be used (not on Ultrix). */
#undef HAVE_ALLOCA_H
/* Define if platform-specific command line handling is necessary. */
#undef NEED_ARGV_FIXUP

1632
commands/flex-2.5.4/configure vendored Executable file

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,24 @@
dnl Process this file with autoconf to produce a configure script.
dnl
AC_INIT(initscan.c)
AC_CONFIG_HEADER(config.h:conf.in)
AC_LN_S
AC_PROG_YACC
AC_PROG_CC
AC_PROG_RANLIB
AC_PROG_INSTALL
AC_PROG_MAKE_SET
AC_CONST
AC_TYPE_SIZE_T
AC_HEADER_STDC
AC_HAVE_HEADERS(string.h malloc.h sys/types.h)
case "$YACC" in
*bison*)
AC_ALLOCA
;;
esac
AC_OUTPUT(Makefile,
[test -z "$CONFIG_HEADERS" || echo timestamp > stamp-h])

View file

@ -0,0 +1,2 @@
#!/bin/sh
./configure --prefix=/usr

1095
commands/flex-2.5.4/dfa.c Normal file

File diff suppressed because it is too large Load diff

225
commands/flex-2.5.4/ecs.c Normal file
View file

@ -0,0 +1,225 @@
/* ecs - equivalence class routines */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
/* ccl2ecl - convert character classes to set of equivalence classes */
void ccl2ecl()
{
int i, ich, newlen, cclp, ccls, cclmec;
for ( i = 1; i <= lastccl; ++i )
{
/* We loop through each character class, and for each character
* in the class, add the character's equivalence class to the
* new "character" class we are creating. Thus when we are all
* done, character classes will really consist of collections
* of equivalence classes
*/
newlen = 0;
cclp = cclmap[i];
for ( ccls = 0; ccls < ccllen[i]; ++ccls )
{
ich = ccltbl[cclp + ccls];
cclmec = ecgroup[ich];
if ( cclmec > 0 )
{
ccltbl[cclp + newlen] = cclmec;
++newlen;
}
}
ccllen[i] = newlen;
}
}
/* cre8ecs - associate equivalence class numbers with class members
*
* fwd is the forward linked-list of equivalence class members. bck
* is the backward linked-list, and num is the number of class members.
*
* Returned is the number of classes.
*/
int cre8ecs( fwd, bck, num )
int fwd[], bck[], num;
{
int i, j, numcl;
numcl = 0;
/* Create equivalence class numbers. From now on, ABS( bck(x) )
* is the equivalence class number for object x. If bck(x)
* is positive, then x is the representative of its equivalence
* class.
*/
for ( i = 1; i <= num; ++i )
if ( bck[i] == NIL )
{
bck[i] = ++numcl;
for ( j = fwd[i]; j != NIL; j = fwd[j] )
bck[j] = -numcl;
}
return numcl;
}
/* mkeccl - update equivalence classes based on character class xtions
*
* synopsis
* Char ccls[];
* int lenccl, fwd[llsiz], bck[llsiz], llsiz, NUL_mapping;
* void mkeccl( Char ccls[], int lenccl, int fwd[llsiz], int bck[llsiz],
* int llsiz, int NUL_mapping );
*
* ccls contains the elements of the character class, lenccl is the
* number of elements in the ccl, fwd is the forward link-list of equivalent
* characters, bck is the backward link-list, and llsiz size of the link-list.
*
* NUL_mapping is the value which NUL (0) should be mapped to.
*/
void mkeccl( ccls, lenccl, fwd, bck, llsiz, NUL_mapping )
Char ccls[];
int lenccl, fwd[], bck[], llsiz, NUL_mapping;
{
int cclp, oldec, newec;
int cclm, i, j;
static unsigned char cclflags[CSIZE]; /* initialized to all '\0' */
/* Note that it doesn't matter whether or not the character class is
* negated. The same results will be obtained in either case.
*/
cclp = 0;
while ( cclp < lenccl )
{
cclm = ccls[cclp];
if ( NUL_mapping && cclm == 0 )
cclm = NUL_mapping;
oldec = bck[cclm];
newec = cclm;
j = cclp + 1;
for ( i = fwd[cclm]; i != NIL && i <= llsiz; i = fwd[i] )
{ /* look for the symbol in the character class */
for ( ; j < lenccl; ++j )
{
register int ccl_char;
if ( NUL_mapping && ccls[j] == 0 )
ccl_char = NUL_mapping;
else
ccl_char = ccls[j];
if ( ccl_char > i )
break;
if ( ccl_char == i && ! cclflags[j] )
{
/* We found an old companion of cclm
* in the ccl. Link it into the new
* equivalence class and flag it as
* having been processed.
*/
bck[i] = newec;
fwd[newec] = i;
newec = i;
/* Set flag so we don't reprocess. */
cclflags[j] = 1;
/* Get next equivalence class member. */
/* continue 2 */
goto next_pt;
}
}
/* Symbol isn't in character class. Put it in the old
* equivalence class.
*/
bck[i] = oldec;
if ( oldec != NIL )
fwd[oldec] = i;
oldec = i;
next_pt: ;
}
if ( bck[cclm] != NIL || oldec != bck[cclm] )
{
bck[cclm] = NIL;
fwd[oldec] = NIL;
}
fwd[newec] = NIL;
/* Find next ccl member to process. */
for ( ++cclp; cclflags[cclp] && cclp < lenccl; ++cclp )
{
/* Reset "doesn't need processing" flag. */
cclflags[cclp] = 0;
}
}
}
/* mkechar - create equivalence class for single character */
void mkechar( tch, fwd, bck )
int tch, fwd[], bck[];
{
/* If until now the character has been a proper subset of
* an equivalence class, break it away to create a new ec
*/
if ( fwd[tch] != NIL )
bck[fwd[tch]] = bck[tch];
if ( bck[tch] != NIL )
fwd[bck[tch]] = fwd[tch];
fwd[tch] = NIL;
bck[tch] = NIL;
}

4060
commands/flex-2.5.4/flex.1 Normal file

File diff suppressed because it is too large Load diff

1541
commands/flex-2.5.4/flex.skl Normal file

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

1625
commands/flex-2.5.4/gen.c Normal file

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

119
commands/flex-2.5.4/install.sh Executable file
View file

@ -0,0 +1,119 @@
#!/bin/sh
#
# install - install a program, script, or datafile
# This comes from X11R5; it is not part of GNU.
#
# $XConsortium: install.sh,v 1.2 89/12/18 14:47:22 jim Exp $
#
# This script is compatible with the BSD install script, but was written
# from scratch.
#
# set DOITPROG to echo to test this script
# Don't use :- since 4.3BSD and earlier shells don't like it.
doit="${DOITPROG-}"
# put in absolute paths if you don't have them in your path; or use env. vars.
mvprog="${MVPROG-mv}"
cpprog="${CPPROG-cp}"
chmodprog="${CHMODPROG-chmod}"
chownprog="${CHOWNPROG-chown}"
chgrpprog="${CHGRPPROG-chgrp}"
stripprog="${STRIPPROG-strip}"
rmprog="${RMPROG-rm}"
instcmd="$mvprog"
chmodcmd=""
chowncmd=""
chgrpcmd=""
stripcmd=""
rmcmd="$rmprog -f"
mvcmd="$mvprog"
src=""
dst=""
while [ x"$1" != x ]; do
case $1 in
-c) instcmd="$cpprog"
shift
continue;;
-m) chmodcmd="$chmodprog $2"
shift
shift
continue;;
-o) chowncmd="$chownprog $2"
shift
shift
continue;;
-g) chgrpcmd="$chgrpprog $2"
shift
shift
continue;;
-s) stripcmd="$stripprog"
shift
continue;;
*) if [ x"$src" = x ]
then
src=$1
else
dst=$1
fi
shift
continue;;
esac
done
if [ x"$src" = x ]
then
echo "install: no input file specified"
exit 1
fi
if [ x"$dst" = x ]
then
echo "install: no destination specified"
exit 1
fi
# If destination is a directory, append the input filename; if your system
# does not like double slashes in filenames, you may need to add some logic
if [ -d $dst ]
then
dst="$dst"/`basename $src`
fi
# Make a temp file name in the proper directory.
dstdir=`dirname $dst`
dsttmp=$dstdir/#inst.$$#
# Move or copy the file name to the temp name
$doit $instcmd $src $dsttmp
# and set any options; do chmod last to preserve setuid bits
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; fi
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; fi
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; fi
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; fi
# Now rename the file to the real destination.
$doit $rmcmd $dst
$doit $mvcmd $dsttmp $dst
exit 0

View file

@ -0,0 +1,15 @@
/* libmain - flex run-time support library "main" function */
/* $Header$ */
extern int yylex();
int main( argc, argv )
int argc;
char *argv[];
{
while ( yylex() != 0 )
;
return 0;
}

View file

@ -0,0 +1,8 @@
/* libyywrap - flex run-time support library "yywrap" function */
/* $Header$ */
int yywrap()
{
return 1;
}

1177
commands/flex-2.5.4/main.c Normal file

File diff suppressed because it is too large Load diff

886
commands/flex-2.5.4/misc.c Normal file
View file

@ -0,0 +1,886 @@
/* misc - miscellaneous flex routines */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
void action_define( defname, value )
char *defname;
int value;
{
char buf[MAXLINE];
if ( (int) strlen( defname ) > MAXLINE / 2 )
{
format_pinpoint_message( _( "name \"%s\" ridiculously long" ),
defname );
return;
}
sprintf( buf, "#define %s %d\n", defname, value );
add_action( buf );
}
void add_action( new_text )
char *new_text;
{
int len = strlen( new_text );
while ( len + action_index >= action_size - 10 /* slop */ )
{
int new_size = action_size * 2;
if ( new_size <= 0 )
/* Increase just a little, to try to avoid overflow
* on 16-bit machines.
*/
action_size += action_size / 8;
else
action_size = new_size;
action_array =
reallocate_character_array( action_array, action_size );
}
strcpy( &action_array[action_index], new_text );
action_index += len;
}
/* allocate_array - allocate memory for an integer array of the given size */
void *allocate_array( size, element_size )
int size;
size_t element_size;
{
register void *mem;
size_t num_bytes = element_size * size;
mem = flex_alloc( num_bytes );
if ( ! mem )
flexfatal(
_( "memory allocation failed in allocate_array()" ) );
return mem;
}
/* all_lower - true if a string is all lower-case */
int all_lower( str )
register char *str;
{
while ( *str )
{
if ( ! isascii( (Char) *str ) || ! islower( *str ) )
return 0;
++str;
}
return 1;
}
/* all_upper - true if a string is all upper-case */
int all_upper( str )
register char *str;
{
while ( *str )
{
if ( ! isascii( (Char) *str ) || ! isupper( *str ) )
return 0;
++str;
}
return 1;
}
/* bubble - bubble sort an integer array in increasing order
*
* synopsis
* int v[n], n;
* void bubble( v, n );
*
* description
* sorts the first n elements of array v and replaces them in
* increasing order.
*
* passed
* v - the array to be sorted
* n - the number of elements of 'v' to be sorted
*/
void bubble( v, n )
int v[], n;
{
register int i, j, k;
for ( i = n; i > 1; --i )
for ( j = 1; j < i; ++j )
if ( v[j] > v[j + 1] ) /* compare */
{
k = v[j]; /* exchange */
v[j] = v[j + 1];
v[j + 1] = k;
}
}
/* check_char - checks a character to make sure it's within the range
* we're expecting. If not, generates fatal error message
* and exits.
*/
void check_char( c )
int c;
{
if ( c >= CSIZE )
lerrsf( _( "bad character '%s' detected in check_char()" ),
readable_form( c ) );
if ( c >= csize )
lerrsf(
_( "scanner requires -8 flag to use the character %s" ),
readable_form( c ) );
}
/* clower - replace upper-case letter to lower-case */
Char clower( c )
register int c;
{
return (Char) ((isascii( c ) && isupper( c )) ? tolower( c ) : c);
}
/* copy_string - returns a dynamically allocated copy of a string */
char *copy_string( str )
register const char *str;
{
register const char *c1;
register char *c2;
char *copy;
unsigned int size;
/* find length */
for ( c1 = str; *c1; ++c1 )
;
size = (c1 - str + 1) * sizeof( char );
copy = (char *) flex_alloc( size );
if ( copy == NULL )
flexfatal( _( "dynamic memory failure in copy_string()" ) );
for ( c2 = copy; (*c2++ = *str++) != 0; )
;
return copy;
}
/* copy_unsigned_string -
* returns a dynamically allocated copy of a (potentially) unsigned string
*/
Char *copy_unsigned_string( str )
register Char *str;
{
register Char *c;
Char *copy;
/* find length */
for ( c = str; *c; ++c )
;
copy = allocate_Character_array( c - str + 1 );
for ( c = copy; (*c++ = *str++) != 0; )
;
return copy;
}
/* cshell - shell sort a character array in increasing order
*
* synopsis
*
* Char v[n];
* int n, special_case_0;
* cshell( v, n, special_case_0 );
*
* description
* Does a shell sort of the first n elements of array v.
* If special_case_0 is true, then any element equal to 0
* is instead assumed to have infinite weight.
*
* passed
* v - array to be sorted
* n - number of elements of v to be sorted
*/
void cshell( v, n, special_case_0 )
Char v[];
int n, special_case_0;
{
int gap, i, j, jg;
Char k;
for ( gap = n / 2; gap > 0; gap = gap / 2 )
for ( i = gap; i < n; ++i )
for ( j = i - gap; j >= 0; j = j - gap )
{
jg = j + gap;
if ( special_case_0 )
{
if ( v[jg] == 0 )
break;
else if ( v[j] != 0 && v[j] <= v[jg] )
break;
}
else if ( v[j] <= v[jg] )
break;
k = v[j];
v[j] = v[jg];
v[jg] = k;
}
}
/* dataend - finish up a block of data declarations */
void dataend()
{
if ( datapos > 0 )
dataflush();
/* add terminator for initialization; { for vi */
outn( " } ;\n" );
dataline = 0;
datapos = 0;
}
/* dataflush - flush generated data statements */
void dataflush()
{
outc( '\n' );
if ( ++dataline >= NUMDATALINES )
{
/* Put out a blank line so that the table is grouped into
* large blocks that enable the user to find elements easily.
*/
outc( '\n' );
dataline = 0;
}
/* Reset the number of characters written on the current line. */
datapos = 0;
}
/* flexerror - report an error message and terminate */
void flexerror( msg )
const char msg[];
{
fprintf( stderr, "%s: %s\n", program_name, msg );
flexend( 1 );
}
/* flexfatal - report a fatal error message and terminate */
void flexfatal( msg )
const char msg[];
{
fprintf( stderr, _( "%s: fatal internal error, %s\n" ),
program_name, msg );
exit( 1 );
}
/* htoi - convert a hexadecimal digit string to an integer value */
int htoi( str )
Char str[];
{
unsigned int result;
(void) sscanf( (char *) str, "%x", &result );
return result;
}
/* lerrif - report an error message formatted with one integer argument */
void lerrif( msg, arg )
const char msg[];
int arg;
{
char errmsg[MAXLINE];
(void) sprintf( errmsg, msg, arg );
flexerror( errmsg );
}
/* lerrsf - report an error message formatted with one string argument */
void lerrsf( msg, arg )
const char msg[], arg[];
{
char errmsg[MAXLINE];
(void) sprintf( errmsg, msg, arg );
flexerror( errmsg );
}
/* line_directive_out - spit out a "#line" statement */
void line_directive_out( output_file, do_infile )
FILE *output_file;
int do_infile;
{
char directive[MAXLINE], filename[MAXLINE];
char *s1, *s2, *s3;
static char line_fmt[] = "#line %d \"%s\"\n";
if ( ! gen_line_dirs )
return;
if ( (do_infile && ! infilename) || (! do_infile && ! outfilename) )
/* don't know the filename to use, skip */
return;
s1 = do_infile ? infilename : outfilename;
s2 = filename;
s3 = &filename[sizeof( filename ) - 2];
while ( s2 < s3 && *s1 )
{
if ( *s1 == '\\' )
/* Escape the '\' */
*s2++ = '\\';
*s2++ = *s1++;
}
*s2 = '\0';
if ( do_infile )
sprintf( directive, line_fmt, linenum, filename );
else
{
if ( output_file == stdout )
/* Account for the line directive itself. */
++out_linenum;
sprintf( directive, line_fmt, out_linenum, filename );
}
/* If output_file is nil then we should put the directive in
* the accumulated actions.
*/
if ( output_file )
{
fputs( directive, output_file );
}
else
add_action( directive );
}
/* mark_defs1 - mark the current position in the action array as
* representing where the user's section 1 definitions end
* and the prolog begins
*/
void mark_defs1()
{
defs1_offset = 0;
action_array[action_index++] = '\0';
action_offset = prolog_offset = action_index;
action_array[action_index] = '\0';
}
/* mark_prolog - mark the current position in the action array as
* representing the end of the action prolog
*/
void mark_prolog()
{
action_array[action_index++] = '\0';
action_offset = action_index;
action_array[action_index] = '\0';
}
/* mk2data - generate a data statement for a two-dimensional array
*
* Generates a data statement initializing the current 2-D array to "value".
*/
void mk2data( value )
int value;
{
if ( datapos >= NUMDATAITEMS )
{
outc( ',' );
dataflush();
}
if ( datapos == 0 )
/* Indent. */
out( " " );
else
outc( ',' );
++datapos;
out_dec( "%5d", value );
}
/* mkdata - generate a data statement
*
* Generates a data statement initializing the current array element to
* "value".
*/
void mkdata( value )
int value;
{
if ( datapos >= NUMDATAITEMS )
{
outc( ',' );
dataflush();
}
if ( datapos == 0 )
/* Indent. */
out( " " );
else
outc( ',' );
++datapos;
out_dec( "%5d", value );
}
/* myctoi - return the integer represented by a string of digits */
int myctoi( array )
char array[];
{
int val = 0;
(void) sscanf( array, "%d", &val );
return val;
}
/* myesc - return character corresponding to escape sequence */
Char myesc( array )
Char array[];
{
Char c, esc_char;
switch ( array[1] )
{
case 'b': return '\b';
case 'f': return '\f';
case 'n': return '\n';
case 'r': return '\r';
case 't': return '\t';
#if __STDC__
case 'a': return '\a';
case 'v': return '\v';
#else
case 'a': return '\007';
case 'v': return '\013';
#endif
case '0':
case '1':
case '2':
case '3':
case '4':
case '5':
case '6':
case '7':
{ /* \<octal> */
int sptr = 1;
while ( isascii( array[sptr] ) &&
isdigit( array[sptr] ) )
/* Don't increment inside loop control
* because if isdigit() is a macro it might
* expand into multiple increments ...
*/
++sptr;
c = array[sptr];
array[sptr] = '\0';
esc_char = otoi( array + 1 );
array[sptr] = c;
return esc_char;
}
case 'x':
{ /* \x<hex> */
int sptr = 2;
while ( isascii( array[sptr] ) &&
isxdigit( (char) array[sptr] ) )
/* Don't increment inside loop control
* because if isdigit() is a macro it might
* expand into multiple increments ...
*/
++sptr;
c = array[sptr];
array[sptr] = '\0';
esc_char = htoi( array + 2 );
array[sptr] = c;
return esc_char;
}
default:
return array[1];
}
}
/* otoi - convert an octal digit string to an integer value */
int otoi( str )
Char str[];
{
unsigned int result;
(void) sscanf( (char *) str, "%o", &result );
return result;
}
/* out - various flavors of outputing a (possibly formatted) string for the
* generated scanner, keeping track of the line count.
*/
void out( str )
const char str[];
{
fputs( str, stdout );
out_line_count( str );
}
void out_dec( fmt, n )
const char fmt[];
int n;
{
printf( fmt, n );
out_line_count( fmt );
}
void out_dec2( fmt, n1, n2 )
const char fmt[];
int n1, n2;
{
printf( fmt, n1, n2 );
out_line_count( fmt );
}
void out_hex( fmt, x )
const char fmt[];
unsigned int x;
{
printf( fmt, x );
out_line_count( fmt );
}
void out_line_count( str )
const char str[];
{
register int i;
for ( i = 0; str[i]; ++i )
if ( str[i] == '\n' )
++out_linenum;
}
void out_str( fmt, str )
const char fmt[], str[];
{
printf( fmt, str );
out_line_count( fmt );
out_line_count( str );
}
void out_str3( fmt, s1, s2, s3 )
const char fmt[], s1[], s2[], s3[];
{
printf( fmt, s1, s2, s3 );
out_line_count( fmt );
out_line_count( s1 );
out_line_count( s2 );
out_line_count( s3 );
}
void out_str_dec( fmt, str, n )
const char fmt[], str[];
int n;
{
printf( fmt, str, n );
out_line_count( fmt );
out_line_count( str );
}
void outc( c )
int c;
{
putc( c, stdout );
if ( c == '\n' )
++out_linenum;
}
void outn( str )
const char str[];
{
puts( str );
out_line_count( str );
++out_linenum;
}
/* readable_form - return the the human-readable form of a character
*
* The returned string is in static storage.
*/
char *readable_form( c )
register int c;
{
static char rform[10];
if ( (c >= 0 && c < 32) || c >= 127 )
{
switch ( c )
{
case '\b': return "\\b";
case '\f': return "\\f";
case '\n': return "\\n";
case '\r': return "\\r";
case '\t': return "\\t";
#if __STDC__
case '\a': return "\\a";
case '\v': return "\\v";
#endif
default:
(void) sprintf( rform, "\\%.3o",
(unsigned int) c );
return rform;
}
}
else if ( c == ' ' )
return "' '";
else
{
rform[0] = c;
rform[1] = '\0';
return rform;
}
}
/* reallocate_array - increase the size of a dynamic array */
void *reallocate_array( array, size, element_size )
void *array;
int size;
size_t element_size;
{
register void *new_array;
size_t num_bytes = element_size * size;
new_array = flex_realloc( array, num_bytes );
if ( ! new_array )
flexfatal( _( "attempt to increase array size failed" ) );
return new_array;
}
/* skelout - write out one section of the skeleton file
*
* Description
* Copies skelfile or skel array to stdout until a line beginning with
* "%%" or EOF is found.
*/
void skelout()
{
char buf_storage[MAXLINE];
char *buf = buf_storage;
int do_copy = 1;
/* Loop pulling lines either from the skelfile, if we're using
* one, or from the skel[] array.
*/
while ( skelfile ?
(fgets( buf, MAXLINE, skelfile ) != NULL) :
((buf = (char *) skel[skel_ind++]) != 0) )
{ /* copy from skel array */
if ( buf[0] == '%' )
{ /* control line */
switch ( buf[1] )
{
case '%':
return;
case '+':
do_copy = C_plus_plus;
break;
case '-':
do_copy = ! C_plus_plus;
break;
case '*':
do_copy = 1;
break;
default:
flexfatal(
_( "bad line in skeleton file" ) );
}
}
else if ( do_copy )
{
if ( skelfile )
/* Skeleton file reads include final
* newline, skel[] array does not.
*/
out( buf );
else
outn( buf );
}
}
}
/* transition_struct_out - output a yy_trans_info structure
*
* outputs the yy_trans_info structure with the two elements, element_v and
* element_n. Formats the output with spaces and carriage returns.
*/
void transition_struct_out( element_v, element_n )
int element_v, element_n;
{
out_dec2( " {%4d,%4d },", element_v, element_n );
datapos += TRANS_STRUCT_PRINT_LENGTH;
if ( datapos >= 79 - TRANS_STRUCT_PRINT_LENGTH )
{
outc( '\n' );
if ( ++dataline % 10 == 0 )
outc( '\n' );
datapos = 0;
}
}
/* The following is only needed when building flex's parser using certain
* broken versions of bison.
*/
void *yy_flex_xmalloc( size )
int size;
{
void *result = flex_alloc( (size_t) size );
if ( ! result )
flexfatal(
_( "memory allocation failed in yy_flex_xmalloc()" ) );
return result;
}
/* zero_out - set a region of memory to 0
*
* Sets region_ptr[0] through region_ptr[size_in_bytes - 1] to zero.
*/
void zero_out( region_ptr, size_in_bytes )
char *region_ptr;
size_t size_in_bytes;
{
register char *rp, *rp_end;
rp = region_ptr;
rp_end = region_ptr + size_in_bytes;
while ( rp < rp_end )
*rp++ = 0;
}

View file

@ -0,0 +1,35 @@
#!/bin/sh
# Make directory hierarchy.
# Written by Noah Friedman <friedman@prep.ai.mit.edu>
# Public domain.
defaultIFS='
'
IFS="${IFS-${defaultIFS}}"
errstatus=0
for file in ${1+"$@"} ; do
oIFS="${IFS}"
# Some sh's can't handle IFS=/ for some reason.
IFS='%'
set - `echo ${file} | sed -e 's@/@%@g' -e 's@^%@/@'`
IFS="${oIFS}"
pathcomp=''
for d in ${1+"$@"} ; do
pathcomp="${pathcomp}${d}"
if test ! -d "${pathcomp}"; then
echo "mkdir $pathcomp" 1>&2
mkdir "${pathcomp}" || errstatus=$?
fi
pathcomp="${pathcomp}/"
done
done
exit $errstatus
# eof

16
commands/flex-2.5.4/mkskel.sh Executable file
View file

@ -0,0 +1,16 @@
#! /bin/sh
cat <<!
/* File created from flex.skl via mkskel.sh */
#include "flexdef.h"
const char *skel[] = {
!
sed 's/\\/&&/g' $* | sed 's/"/\\"/g' | sed 's/.*/ "&",/'
cat <<!
0
};
!

709
commands/flex-2.5.4/nfa.c Normal file
View file

@ -0,0 +1,709 @@
/* nfa - NFA construction routines */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
/* declare functions that have forward references */
int dupmachine PROTO((int));
void mkxtion PROTO((int, int));
/* add_accept - add an accepting state to a machine
*
* accepting_number becomes mach's accepting number.
*/
void add_accept( mach, accepting_number )
int mach, accepting_number;
{
/* Hang the accepting number off an epsilon state. if it is associated
* with a state that has a non-epsilon out-transition, then the state
* will accept BEFORE it makes that transition, i.e., one character
* too soon.
*/
if ( transchar[finalst[mach]] == SYM_EPSILON )
accptnum[finalst[mach]] = accepting_number;
else
{
int astate = mkstate( SYM_EPSILON );
accptnum[astate] = accepting_number;
(void) link_machines( mach, astate );
}
}
/* copysingl - make a given number of copies of a singleton machine
*
* synopsis
*
* newsng = copysingl( singl, num );
*
* newsng - a new singleton composed of num copies of singl
* singl - a singleton machine
* num - the number of copies of singl to be present in newsng
*/
int copysingl( singl, num )
int singl, num;
{
int copy, i;
copy = mkstate( SYM_EPSILON );
for ( i = 1; i <= num; ++i )
copy = link_machines( copy, dupmachine( singl ) );
return copy;
}
/* dumpnfa - debugging routine to write out an nfa */
void dumpnfa( state1 )
int state1;
{
int sym, tsp1, tsp2, anum, ns;
fprintf( stderr,
_( "\n\n********** beginning dump of nfa with start state %d\n" ),
state1 );
/* We probably should loop starting at firstst[state1] and going to
* lastst[state1], but they're not maintained properly when we "or"
* all of the rules together. So we use our knowledge that the machine
* starts at state 1 and ends at lastnfa.
*/
/* for ( ns = firstst[state1]; ns <= lastst[state1]; ++ns ) */
for ( ns = 1; ns <= lastnfa; ++ns )
{
fprintf( stderr, _( "state # %4d\t" ), ns );
sym = transchar[ns];
tsp1 = trans1[ns];
tsp2 = trans2[ns];
anum = accptnum[ns];
fprintf( stderr, "%3d: %4d, %4d", sym, tsp1, tsp2 );
if ( anum != NIL )
fprintf( stderr, " [%d]", anum );
fprintf( stderr, "\n" );
}
fprintf( stderr, _( "********** end of dump\n" ) );
}
/* dupmachine - make a duplicate of a given machine
*
* synopsis
*
* copy = dupmachine( mach );
*
* copy - holds duplicate of mach
* mach - machine to be duplicated
*
* note that the copy of mach is NOT an exact duplicate; rather, all the
* transition states values are adjusted so that the copy is self-contained,
* as the original should have been.
*
* also note that the original MUST be contiguous, with its low and high
* states accessible by the arrays firstst and lastst
*/
int dupmachine( mach )
int mach;
{
int i, init, state_offset;
int state = 0;
int last = lastst[mach];
for ( i = firstst[mach]; i <= last; ++i )
{
state = mkstate( transchar[i] );
if ( trans1[i] != NO_TRANSITION )
{
mkxtion( finalst[state], trans1[i] + state - i );
if ( transchar[i] == SYM_EPSILON &&
trans2[i] != NO_TRANSITION )
mkxtion( finalst[state],
trans2[i] + state - i );
}
accptnum[state] = accptnum[i];
}
if ( state == 0 )
flexfatal( _( "empty machine in dupmachine()" ) );
state_offset = state - i + 1;
init = mach + state_offset;
firstst[init] = firstst[mach] + state_offset;
finalst[init] = finalst[mach] + state_offset;
lastst[init] = lastst[mach] + state_offset;
return init;
}
/* finish_rule - finish up the processing for a rule
*
* An accepting number is added to the given machine. If variable_trail_rule
* is true then the rule has trailing context and both the head and trail
* are variable size. Otherwise if headcnt or trailcnt is non-zero then
* the machine recognizes a pattern with trailing context and headcnt is
* the number of characters in the matched part of the pattern, or zero
* if the matched part has variable length. trailcnt is the number of
* trailing context characters in the pattern, or zero if the trailing
* context has variable length.
*/
void finish_rule( mach, variable_trail_rule, headcnt, trailcnt )
int mach, variable_trail_rule, headcnt, trailcnt;
{
char action_text[MAXLINE];
add_accept( mach, num_rules );
/* We did this in new_rule(), but it often gets the wrong
* number because we do it before we start parsing the current rule.
*/
rule_linenum[num_rules] = linenum;
/* If this is a continued action, then the line-number has already
* been updated, giving us the wrong number.
*/
if ( continued_action )
--rule_linenum[num_rules];
sprintf( action_text, "case %d:\n", num_rules );
add_action( action_text );
if ( variable_trail_rule )
{
rule_type[num_rules] = RULE_VARIABLE;
if ( performance_report > 0 )
fprintf( stderr,
_( "Variable trailing context rule at line %d\n" ),
rule_linenum[num_rules] );
variable_trailing_context_rules = true;
}
else
{
rule_type[num_rules] = RULE_NORMAL;
if ( headcnt > 0 || trailcnt > 0 )
{
/* Do trailing context magic to not match the trailing
* characters.
*/
char *scanner_cp = "yy_c_buf_p = yy_cp";
char *scanner_bp = "yy_bp";
add_action(
"*yy_cp = yy_hold_char; /* undo effects of setting up yytext */\n" );
if ( headcnt > 0 )
{
sprintf( action_text, "%s = %s + %d;\n",
scanner_cp, scanner_bp, headcnt );
add_action( action_text );
}
else
{
sprintf( action_text, "%s -= %d;\n",
scanner_cp, trailcnt );
add_action( action_text );
}
add_action(
"YY_DO_BEFORE_ACTION; /* set up yytext again */\n" );
}
}
/* Okay, in the action code at this point yytext and yyleng have
* their proper final values for this rule, so here's the point
* to do any user action. But don't do it for continued actions,
* as that'll result in multiple YY_RULE_SETUP's.
*/
if ( ! continued_action )
add_action( "YY_RULE_SETUP\n" );
line_directive_out( (FILE *) 0, 1 );
}
/* link_machines - connect two machines together
*
* synopsis
*
* new = link_machines( first, last );
*
* new - a machine constructed by connecting first to last
* first - the machine whose successor is to be last
* last - the machine whose predecessor is to be first
*
* note: this routine concatenates the machine first with the machine
* last to produce a machine new which will pattern-match first first
* and then last, and will fail if either of the sub-patterns fails.
* FIRST is set to new by the operation. last is unmolested.
*/
int link_machines( first, last )
int first, last;
{
if ( first == NIL )
return last;
else if ( last == NIL )
return first;
else
{
mkxtion( finalst[first], last );
finalst[first] = finalst[last];
lastst[first] = MAX( lastst[first], lastst[last] );
firstst[first] = MIN( firstst[first], firstst[last] );
return first;
}
}
/* mark_beginning_as_normal - mark each "beginning" state in a machine
* as being a "normal" (i.e., not trailing context-
* associated) states
*
* The "beginning" states are the epsilon closure of the first state
*/
void mark_beginning_as_normal( mach )
register int mach;
{
switch ( state_type[mach] )
{
case STATE_NORMAL:
/* Oh, we've already visited here. */
return;
case STATE_TRAILING_CONTEXT:
state_type[mach] = STATE_NORMAL;
if ( transchar[mach] == SYM_EPSILON )
{
if ( trans1[mach] != NO_TRANSITION )
mark_beginning_as_normal(
trans1[mach] );
if ( trans2[mach] != NO_TRANSITION )
mark_beginning_as_normal(
trans2[mach] );
}
break;
default:
flexerror(
_( "bad state type in mark_beginning_as_normal()" ) );
break;
}
}
/* mkbranch - make a machine that branches to two machines
*
* synopsis
*
* branch = mkbranch( first, second );
*
* branch - a machine which matches either first's pattern or second's
* first, second - machines whose patterns are to be or'ed (the | operator)
*
* Note that first and second are NEITHER destroyed by the operation. Also,
* the resulting machine CANNOT be used with any other "mk" operation except
* more mkbranch's. Compare with mkor()
*/
int mkbranch( first, second )
int first, second;
{
int eps;
if ( first == NO_TRANSITION )
return second;
else if ( second == NO_TRANSITION )
return first;
eps = mkstate( SYM_EPSILON );
mkxtion( eps, first );
mkxtion( eps, second );
return eps;
}
/* mkclos - convert a machine into a closure
*
* synopsis
* new = mkclos( state );
*
* new - a new state which matches the closure of "state"
*/
int mkclos( state )
int state;
{
return mkopt( mkposcl( state ) );
}
/* mkopt - make a machine optional
*
* synopsis
*
* new = mkopt( mach );
*
* new - a machine which optionally matches whatever mach matched
* mach - the machine to make optional
*
* notes:
* 1. mach must be the last machine created
* 2. mach is destroyed by the call
*/
int mkopt( mach )
int mach;
{
int eps;
if ( ! SUPER_FREE_EPSILON(finalst[mach]) )
{
eps = mkstate( SYM_EPSILON );
mach = link_machines( mach, eps );
}
/* Can't skimp on the following if FREE_EPSILON(mach) is true because
* some state interior to "mach" might point back to the beginning
* for a closure.
*/
eps = mkstate( SYM_EPSILON );
mach = link_machines( eps, mach );
mkxtion( mach, finalst[mach] );
return mach;
}
/* mkor - make a machine that matches either one of two machines
*
* synopsis
*
* new = mkor( first, second );
*
* new - a machine which matches either first's pattern or second's
* first, second - machines whose patterns are to be or'ed (the | operator)
*
* note that first and second are both destroyed by the operation
* the code is rather convoluted because an attempt is made to minimize
* the number of epsilon states needed
*/
int mkor( first, second )
int first, second;
{
int eps, orend;
if ( first == NIL )
return second;
else if ( second == NIL )
return first;
else
{
/* See comment in mkopt() about why we can't use the first
* state of "first" or "second" if they satisfy "FREE_EPSILON".
*/
eps = mkstate( SYM_EPSILON );
first = link_machines( eps, first );
mkxtion( first, second );
if ( SUPER_FREE_EPSILON(finalst[first]) &&
accptnum[finalst[first]] == NIL )
{
orend = finalst[first];
mkxtion( finalst[second], orend );
}
else if ( SUPER_FREE_EPSILON(finalst[second]) &&
accptnum[finalst[second]] == NIL )
{
orend = finalst[second];
mkxtion( finalst[first], orend );
}
else
{
eps = mkstate( SYM_EPSILON );
first = link_machines( first, eps );
orend = finalst[first];
mkxtion( finalst[second], orend );
}
}
finalst[first] = orend;
return first;
}
/* mkposcl - convert a machine into a positive closure
*
* synopsis
* new = mkposcl( state );
*
* new - a machine matching the positive closure of "state"
*/
int mkposcl( state )
int state;
{
int eps;
if ( SUPER_FREE_EPSILON(finalst[state]) )
{
mkxtion( finalst[state], state );
return state;
}
else
{
eps = mkstate( SYM_EPSILON );
mkxtion( eps, state );
return link_machines( state, eps );
}
}
/* mkrep - make a replicated machine
*
* synopsis
* new = mkrep( mach, lb, ub );
*
* new - a machine that matches whatever "mach" matched from "lb"
* number of times to "ub" number of times
*
* note
* if "ub" is INFINITY then "new" matches "lb" or more occurrences of "mach"
*/
int mkrep( mach, lb, ub )
int mach, lb, ub;
{
int base_mach, tail, copy, i;
base_mach = copysingl( mach, lb - 1 );
if ( ub == INFINITY )
{
copy = dupmachine( mach );
mach = link_machines( mach,
link_machines( base_mach, mkclos( copy ) ) );
}
else
{
tail = mkstate( SYM_EPSILON );
for ( i = lb; i < ub; ++i )
{
copy = dupmachine( mach );
tail = mkopt( link_machines( copy, tail ) );
}
mach = link_machines( mach, link_machines( base_mach, tail ) );
}
return mach;
}
/* mkstate - create a state with a transition on a given symbol
*
* synopsis
*
* state = mkstate( sym );
*
* state - a new state matching sym
* sym - the symbol the new state is to have an out-transition on
*
* note that this routine makes new states in ascending order through the
* state array (and increments LASTNFA accordingly). The routine DUPMACHINE
* relies on machines being made in ascending order and that they are
* CONTIGUOUS. Change it and you will have to rewrite DUPMACHINE (kludge
* that it admittedly is)
*/
int mkstate( sym )
int sym;
{
if ( ++lastnfa >= current_mns )
{
if ( (current_mns += MNS_INCREMENT) >= MAXIMUM_MNS )
lerrif(
_( "input rules are too complicated (>= %d NFA states)" ),
current_mns );
++num_reallocs;
firstst = reallocate_integer_array( firstst, current_mns );
lastst = reallocate_integer_array( lastst, current_mns );
finalst = reallocate_integer_array( finalst, current_mns );
transchar = reallocate_integer_array( transchar, current_mns );
trans1 = reallocate_integer_array( trans1, current_mns );
trans2 = reallocate_integer_array( trans2, current_mns );
accptnum = reallocate_integer_array( accptnum, current_mns );
assoc_rule =
reallocate_integer_array( assoc_rule, current_mns );
state_type =
reallocate_integer_array( state_type, current_mns );
}
firstst[lastnfa] = lastnfa;
finalst[lastnfa] = lastnfa;
lastst[lastnfa] = lastnfa;
transchar[lastnfa] = sym;
trans1[lastnfa] = NO_TRANSITION;
trans2[lastnfa] = NO_TRANSITION;
accptnum[lastnfa] = NIL;
assoc_rule[lastnfa] = num_rules;
state_type[lastnfa] = current_state_type;
/* Fix up equivalence classes base on this transition. Note that any
* character which has its own transition gets its own equivalence
* class. Thus only characters which are only in character classes
* have a chance at being in the same equivalence class. E.g. "a|b"
* puts 'a' and 'b' into two different equivalence classes. "[ab]"
* puts them in the same equivalence class (barring other differences
* elsewhere in the input).
*/
if ( sym < 0 )
{
/* We don't have to update the equivalence classes since
* that was already done when the ccl was created for the
* first time.
*/
}
else if ( sym == SYM_EPSILON )
++numeps;
else
{
check_char( sym );
if ( useecs )
/* Map NUL's to csize. */
mkechar( sym ? sym : csize, nextecm, ecgroup );
}
return lastnfa;
}
/* mkxtion - make a transition from one state to another
*
* synopsis
*
* mkxtion( statefrom, stateto );
*
* statefrom - the state from which the transition is to be made
* stateto - the state to which the transition is to be made
*/
void mkxtion( statefrom, stateto )
int statefrom, stateto;
{
if ( trans1[statefrom] == NO_TRANSITION )
trans1[statefrom] = stateto;
else if ( (transchar[statefrom] != SYM_EPSILON) ||
(trans2[statefrom] != NO_TRANSITION) )
flexfatal( _( "found too many transitions in mkxtion()" ) );
else
{ /* second out-transition for an epsilon state */
++eps2;
trans2[statefrom] = stateto;
}
}
/* new_rule - initialize for a new rule */
void new_rule()
{
if ( ++num_rules >= current_max_rules )
{
++num_reallocs;
current_max_rules += MAX_RULES_INCREMENT;
rule_type = reallocate_integer_array( rule_type,
current_max_rules );
rule_linenum = reallocate_integer_array( rule_linenum,
current_max_rules );
rule_useful = reallocate_integer_array( rule_useful,
current_max_rules );
}
if ( num_rules > MAX_RULE )
lerrif( _( "too many rules (> %d)!" ), MAX_RULE );
rule_linenum[num_rules] = linenum;
rule_useful[num_rules] = false;
}

913
commands/flex-2.5.4/parse.y Normal file
View file

@ -0,0 +1,913 @@
/* parse.y - parser for flex input */
%token CHAR NUMBER SECTEND SCDECL XSCDECL NAME PREVCCL EOF_OP
%token OPTION_OP OPT_OUTFILE OPT_PREFIX OPT_YYCLASS
%token CCE_ALNUM CCE_ALPHA CCE_BLANK CCE_CNTRL CCE_DIGIT CCE_GRAPH
%token CCE_LOWER CCE_PRINT CCE_PUNCT CCE_SPACE CCE_UPPER CCE_XDIGIT
%{
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
/* Some versions of bison are broken in that they use alloca() but don't
* declare it properly. The following is the patented (just kidding!)
* #ifdef chud to fix the problem, courtesy of Francois Pinard.
*/
#ifdef YYBISON
/* AIX requires this to be the first thing in the file. What a piece. */
# ifdef _AIX
#pragma alloca
# endif
#endif
#include "flexdef.h"
/* The remainder of the alloca() cruft has to come after including flexdef.h,
* so HAVE_ALLOCA_H is (possibly) defined.
*/
#ifdef YYBISON
# ifdef __GNUC__
# ifndef alloca
# define alloca __builtin_alloca
# endif
# else
# if HAVE_ALLOCA_H
# include <alloca.h>
# else
# ifdef __hpux
void *alloca ();
# else
# ifdef __TURBOC__
# include <malloc.h>
# else
char *alloca ();
# endif
# endif
# endif
# endif
#endif
/* Bletch, ^^^^ that was ugly! */
int pat, scnum, eps, headcnt, trailcnt, anyccl, lastchar, i, rulelen;
int trlcontxt, xcluflg, currccl, cclsorted, varlength, variable_trail_rule;
int *scon_stk;
int scon_stk_ptr;
static int madeany = false; /* whether we've made the '.' character class */
int previous_continued_action; /* whether the previous rule's action was '|' */
/* Expand a POSIX character class expression. */
#define CCL_EXPR(func) \
{ \
int c; \
for ( c = 0; c < csize; ++c ) \
if ( isascii(c) && func(c) ) \
ccladd( currccl, c ); \
}
/* While POSIX defines isblank(), it's not ANSI C. */
#define IS_BLANK(c) ((c) == ' ' || (c) == '\t')
/* On some over-ambitious machines, such as DEC Alpha's, the default
* token type is "long" instead of "int"; this leads to problems with
* declaring yylval in flexdef.h. But so far, all the yacc's I've seen
* wrap their definitions of YYSTYPE with "#ifndef YYSTYPE"'s, so the
* following should ensure that the default token type is "int".
*/
#define YYSTYPE int
%}
%%
goal : initlex sect1 sect1end sect2 initforrule
{ /* add default rule */
int def_rule;
pat = cclinit();
cclnegate( pat );
def_rule = mkstate( -pat );
/* Remember the number of the default rule so we
* don't generate "can't match" warnings for it.
*/
default_rule = num_rules;
finish_rule( def_rule, false, 0, 0 );
for ( i = 1; i <= lastsc; ++i )
scset[i] = mkbranch( scset[i], def_rule );
if ( spprdflt )
add_action(
"YY_FATAL_ERROR( \"flex scanner jammed\" )" );
else
add_action( "ECHO" );
add_action( ";\n\tYY_BREAK\n" );
}
;
initlex :
{ /* initialize for processing rules */
/* Create default DFA start condition. */
scinstal( "INITIAL", false );
}
;
sect1 : sect1 startconddecl namelist1
| sect1 options
|
| error
{ synerr( "unknown error processing section 1" ); }
;
sect1end : SECTEND
{
check_options();
scon_stk = allocate_integer_array( lastsc + 1 );
scon_stk_ptr = 0;
}
;
startconddecl : SCDECL
{ xcluflg = false; }
| XSCDECL
{ xcluflg = true; }
;
namelist1 : namelist1 NAME
{ scinstal( nmstr, xcluflg ); }
| NAME
{ scinstal( nmstr, xcluflg ); }
| error
{ synerr( "bad start condition list" ); }
;
options : OPTION_OP optionlist
;
optionlist : optionlist option
|
;
option : OPT_OUTFILE '=' NAME
{
outfilename = copy_string( nmstr );
did_outfilename = 1;
}
| OPT_PREFIX '=' NAME
{ prefix = copy_string( nmstr ); }
| OPT_YYCLASS '=' NAME
{ yyclass = copy_string( nmstr ); }
;
sect2 : sect2 scon initforrule flexrule '\n'
{ scon_stk_ptr = $2; }
| sect2 scon '{' sect2 '}'
{ scon_stk_ptr = $2; }
|
;
initforrule :
{
/* Initialize for a parse of one rule. */
trlcontxt = variable_trail_rule = varlength = false;
trailcnt = headcnt = rulelen = 0;
current_state_type = STATE_NORMAL;
previous_continued_action = continued_action;
in_rule = true;
new_rule();
}
;
flexrule : '^' rule
{
pat = $2;
finish_rule( pat, variable_trail_rule,
headcnt, trailcnt );
if ( scon_stk_ptr > 0 )
{
for ( i = 1; i <= scon_stk_ptr; ++i )
scbol[scon_stk[i]] =
mkbranch( scbol[scon_stk[i]],
pat );
}
else
{
/* Add to all non-exclusive start conditions,
* including the default (0) start condition.
*/
for ( i = 1; i <= lastsc; ++i )
if ( ! scxclu[i] )
scbol[i] = mkbranch( scbol[i],
pat );
}
if ( ! bol_needed )
{
bol_needed = true;
if ( performance_report > 1 )
pinpoint_message(
"'^' operator results in sub-optimal performance" );
}
}
| rule
{
pat = $1;
finish_rule( pat, variable_trail_rule,
headcnt, trailcnt );
if ( scon_stk_ptr > 0 )
{
for ( i = 1; i <= scon_stk_ptr; ++i )
scset[scon_stk[i]] =
mkbranch( scset[scon_stk[i]],
pat );
}
else
{
for ( i = 1; i <= lastsc; ++i )
if ( ! scxclu[i] )
scset[i] =
mkbranch( scset[i],
pat );
}
}
| EOF_OP
{
if ( scon_stk_ptr > 0 )
build_eof_action();
else
{
/* This EOF applies to all start conditions
* which don't already have EOF actions.
*/
for ( i = 1; i <= lastsc; ++i )
if ( ! sceof[i] )
scon_stk[++scon_stk_ptr] = i;
if ( scon_stk_ptr == 0 )
warn(
"all start conditions already have <<EOF>> rules" );
else
build_eof_action();
}
}
| error
{ synerr( "unrecognized rule" ); }
;
scon_stk_ptr :
{ $$ = scon_stk_ptr; }
;
scon : '<' scon_stk_ptr namelist2 '>'
{ $$ = $2; }
| '<' '*' '>'
{
$$ = scon_stk_ptr;
for ( i = 1; i <= lastsc; ++i )
{
int j;
for ( j = 1; j <= scon_stk_ptr; ++j )
if ( scon_stk[j] == i )
break;
if ( j > scon_stk_ptr )
scon_stk[++scon_stk_ptr] = i;
}
}
|
{ $$ = scon_stk_ptr; }
;
namelist2 : namelist2 ',' sconname
| sconname
| error
{ synerr( "bad start condition list" ); }
;
sconname : NAME
{
if ( (scnum = sclookup( nmstr )) == 0 )
format_pinpoint_message(
"undeclared start condition %s",
nmstr );
else
{
for ( i = 1; i <= scon_stk_ptr; ++i )
if ( scon_stk[i] == scnum )
{
format_warn(
"<%s> specified twice",
scname[scnum] );
break;
}
if ( i > scon_stk_ptr )
scon_stk[++scon_stk_ptr] = scnum;
}
}
;
rule : re2 re
{
if ( transchar[lastst[$2]] != SYM_EPSILON )
/* Provide final transition \now/ so it
* will be marked as a trailing context
* state.
*/
$2 = link_machines( $2,
mkstate( SYM_EPSILON ) );
mark_beginning_as_normal( $2 );
current_state_type = STATE_NORMAL;
if ( previous_continued_action )
{
/* We need to treat this as variable trailing
* context so that the backup does not happen
* in the action but before the action switch
* statement. If the backup happens in the
* action, then the rules "falling into" this
* one's action will *also* do the backup,
* erroneously.
*/
if ( ! varlength || headcnt != 0 )
warn(
"trailing context made variable due to preceding '|' action" );
/* Mark as variable. */
varlength = true;
headcnt = 0;
}
if ( lex_compat || (varlength && headcnt == 0) )
{ /* variable trailing context rule */
/* Mark the first part of the rule as the
* accepting "head" part of a trailing
* context rule.
*
* By the way, we didn't do this at the
* beginning of this production because back
* then current_state_type was set up for a
* trail rule, and add_accept() can create
* a new state ...
*/
add_accept( $1,
num_rules | YY_TRAILING_HEAD_MASK );
variable_trail_rule = true;
}
else
trailcnt = rulelen;
$$ = link_machines( $1, $2 );
}
| re2 re '$'
{ synerr( "trailing context used twice" ); }
| re '$'
{
headcnt = 0;
trailcnt = 1;
rulelen = 1;
varlength = false;
current_state_type = STATE_TRAILING_CONTEXT;
if ( trlcontxt )
{
synerr( "trailing context used twice" );
$$ = mkstate( SYM_EPSILON );
}
else if ( previous_continued_action )
{
/* See the comment in the rule for "re2 re"
* above.
*/
warn(
"trailing context made variable due to preceding '|' action" );
varlength = true;
}
if ( lex_compat || varlength )
{
/* Again, see the comment in the rule for
* "re2 re" above.
*/
add_accept( $1,
num_rules | YY_TRAILING_HEAD_MASK );
variable_trail_rule = true;
}
trlcontxt = true;
eps = mkstate( SYM_EPSILON );
$$ = link_machines( $1,
link_machines( eps, mkstate( '\n' ) ) );
}
| re
{
$$ = $1;
if ( trlcontxt )
{
if ( lex_compat || (varlength && headcnt == 0) )
/* Both head and trail are
* variable-length.
*/
variable_trail_rule = true;
else
trailcnt = rulelen;
}
}
;
re : re '|' series
{
varlength = true;
$$ = mkor( $1, $3 );
}
| series
{ $$ = $1; }
;
re2 : re '/'
{
/* This rule is written separately so the
* reduction will occur before the trailing
* series is parsed.
*/
if ( trlcontxt )
synerr( "trailing context used twice" );
else
trlcontxt = true;
if ( varlength )
/* We hope the trailing context is
* fixed-length.
*/
varlength = false;
else
headcnt = rulelen;
rulelen = 0;
current_state_type = STATE_TRAILING_CONTEXT;
$$ = $1;
}
;
series : series singleton
{
/* This is where concatenation of adjacent patterns
* gets done.
*/
$$ = link_machines( $1, $2 );
}
| singleton
{ $$ = $1; }
;
singleton : singleton '*'
{
varlength = true;
$$ = mkclos( $1 );
}
| singleton '+'
{
varlength = true;
$$ = mkposcl( $1 );
}
| singleton '?'
{
varlength = true;
$$ = mkopt( $1 );
}
| singleton '{' NUMBER ',' NUMBER '}'
{
varlength = true;
if ( $3 > $5 || $3 < 0 )
{
synerr( "bad iteration values" );
$$ = $1;
}
else
{
if ( $3 == 0 )
{
if ( $5 <= 0 )
{
synerr(
"bad iteration values" );
$$ = $1;
}
else
$$ = mkopt(
mkrep( $1, 1, $5 ) );
}
else
$$ = mkrep( $1, $3, $5 );
}
}
| singleton '{' NUMBER ',' '}'
{
varlength = true;
if ( $3 <= 0 )
{
synerr( "iteration value must be positive" );
$$ = $1;
}
else
$$ = mkrep( $1, $3, INFINITY );
}
| singleton '{' NUMBER '}'
{
/* The singleton could be something like "(foo)",
* in which case we have no idea what its length
* is, so we punt here.
*/
varlength = true;
if ( $3 <= 0 )
{
synerr( "iteration value must be positive" );
$$ = $1;
}
else
$$ = link_machines( $1,
copysingl( $1, $3 - 1 ) );
}
| '.'
{
if ( ! madeany )
{
/* Create the '.' character class. */
anyccl = cclinit();
ccladd( anyccl, '\n' );
cclnegate( anyccl );
if ( useecs )
mkeccl( ccltbl + cclmap[anyccl],
ccllen[anyccl], nextecm,
ecgroup, csize, csize );
madeany = true;
}
++rulelen;
$$ = mkstate( -anyccl );
}
| fullccl
{
if ( ! cclsorted )
/* Sort characters for fast searching. We
* use a shell sort since this list could
* be large.
*/
cshell( ccltbl + cclmap[$1], ccllen[$1], true );
if ( useecs )
mkeccl( ccltbl + cclmap[$1], ccllen[$1],
nextecm, ecgroup, csize, csize );
++rulelen;
$$ = mkstate( -$1 );
}
| PREVCCL
{
++rulelen;
$$ = mkstate( -$1 );
}
| '"' string '"'
{ $$ = $2; }
| '(' re ')'
{ $$ = $2; }
| CHAR
{
++rulelen;
if ( caseins && $1 >= 'A' && $1 <= 'Z' )
$1 = clower( $1 );
$$ = mkstate( $1 );
}
;
fullccl : '[' ccl ']'
{ $$ = $2; }
| '[' '^' ccl ']'
{
cclnegate( $3 );
$$ = $3;
}
;
ccl : ccl CHAR '-' CHAR
{
if ( caseins )
{
if ( $2 >= 'A' && $2 <= 'Z' )
$2 = clower( $2 );
if ( $4 >= 'A' && $4 <= 'Z' )
$4 = clower( $4 );
}
if ( $2 > $4 )
synerr( "negative range in character class" );
else
{
for ( i = $2; i <= $4; ++i )
ccladd( $1, i );
/* Keep track if this ccl is staying in
* alphabetical order.
*/
cclsorted = cclsorted && ($2 > lastchar);
lastchar = $4;
}
$$ = $1;
}
| ccl CHAR
{
if ( caseins && $2 >= 'A' && $2 <= 'Z' )
$2 = clower( $2 );
ccladd( $1, $2 );
cclsorted = cclsorted && ($2 > lastchar);
lastchar = $2;
$$ = $1;
}
| ccl ccl_expr
{
/* Too hard to properly maintain cclsorted. */
cclsorted = false;
$$ = $1;
}
|
{
cclsorted = true;
lastchar = 0;
currccl = $$ = cclinit();
}
;
ccl_expr: CCE_ALNUM { CCL_EXPR(isalnum) }
| CCE_ALPHA { CCL_EXPR(isalpha) }
| CCE_BLANK { CCL_EXPR(IS_BLANK) }
| CCE_CNTRL { CCL_EXPR(iscntrl) }
| CCE_DIGIT { CCL_EXPR(isdigit) }
| CCE_GRAPH { CCL_EXPR(isgraph) }
| CCE_LOWER { CCL_EXPR(islower) }
| CCE_PRINT { CCL_EXPR(isprint) }
| CCE_PUNCT { CCL_EXPR(ispunct) }
| CCE_SPACE { CCL_EXPR(isspace) }
| CCE_UPPER {
if ( caseins )
CCL_EXPR(islower)
else
CCL_EXPR(isupper)
}
| CCE_XDIGIT { CCL_EXPR(isxdigit) }
;
string : string CHAR
{
if ( caseins && $2 >= 'A' && $2 <= 'Z' )
$2 = clower( $2 );
++rulelen;
$$ = link_machines( $1, mkstate( $2 ) );
}
|
{ $$ = mkstate( SYM_EPSILON ); }
;
%%
/* build_eof_action - build the "<<EOF>>" action for the active start
* conditions
*/
void build_eof_action()
{
register int i;
char action_text[MAXLINE];
for ( i = 1; i <= scon_stk_ptr; ++i )
{
if ( sceof[scon_stk[i]] )
format_pinpoint_message(
"multiple <<EOF>> rules for start condition %s",
scname[scon_stk[i]] );
else
{
sceof[scon_stk[i]] = true;
sprintf( action_text, "case YY_STATE_EOF(%s):\n",
scname[scon_stk[i]] );
add_action( action_text );
}
}
line_directive_out( (FILE *) 0, 1 );
/* This isn't a normal rule after all - don't count it as
* such, so we don't have any holes in the rule numbering
* (which make generating "rule can never match" warnings
* more difficult.
*/
--num_rules;
++num_eof_rules;
}
/* format_synerr - write out formatted syntax error */
void format_synerr( msg, arg )
char msg[], arg[];
{
char errmsg[MAXLINE];
(void) sprintf( errmsg, msg, arg );
synerr( errmsg );
}
/* synerr - report a syntax error */
void synerr( str )
char str[];
{
syntaxerror = true;
pinpoint_message( str );
}
/* format_warn - write out formatted warning */
void format_warn( msg, arg )
char msg[], arg[];
{
char warn_msg[MAXLINE];
(void) sprintf( warn_msg, msg, arg );
warn( warn_msg );
}
/* warn - report a warning, unless -w was given */
void warn( str )
char str[];
{
line_warning( str, linenum );
}
/* format_pinpoint_message - write out a message formatted with one string,
* pinpointing its location
*/
void format_pinpoint_message( msg, arg )
char msg[], arg[];
{
char errmsg[MAXLINE];
(void) sprintf( errmsg, msg, arg );
pinpoint_message( errmsg );
}
/* pinpoint_message - write out a message, pinpointing its location */
void pinpoint_message( str )
char str[];
{
line_pinpoint( str, linenum );
}
/* line_warning - report a warning at a given line, unless -w was given */
void line_warning( str, line )
char str[];
int line;
{
char warning[MAXLINE];
if ( ! nowarn )
{
sprintf( warning, "warning, %s", str );
line_pinpoint( warning, line );
}
}
/* line_pinpoint - write out a message, pinpointing it at the given line */
void line_pinpoint( str, line )
char str[];
int line;
{
fprintf( stderr, "\"%s\", line %d: %s\n", infilename, line, str );
}
/* yyerror - eat up an error message from the parser;
* currently, messages are ignore
*/
void yyerror( msg )
char msg[];
{
}

710
commands/flex-2.5.4/scan.l Normal file
View file

@ -0,0 +1,710 @@
/* scan.l - scanner for flex input */
%{
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
#include "parse.h"
#define ACTION_ECHO add_action( yytext )
#define ACTION_IFDEF(def, should_define) \
{ \
if ( should_define ) \
action_define( def, 1 ); \
}
#define MARK_END_OF_PROLOG mark_prolog();
#define YY_DECL \
int flexscan()
#define RETURNCHAR \
yylval = (unsigned char) yytext[0]; \
return CHAR;
#define RETURNNAME \
strcpy( nmstr, yytext ); \
return NAME;
#define PUT_BACK_STRING(str, start) \
for ( i = strlen( str ) - 1; i >= start; --i ) \
unput((str)[i])
#define CHECK_REJECT(str) \
if ( all_upper( str ) ) \
reject = true;
#define CHECK_YYMORE(str) \
if ( all_lower( str ) ) \
yymore_used = true;
%}
%option caseless nodefault outfile="scan.c" stack noyy_top_state
%option nostdinit
%x SECT2 SECT2PROLOG SECT3 CODEBLOCK PICKUPDEF SC CARETISBOL NUM QUOTE
%x FIRSTCCL CCL ACTION RECOVER COMMENT ACTION_STRING PERCENT_BRACE_ACTION
%x OPTION LINEDIR
WS [[:blank:]]+
OPTWS [[:blank:]]*
NOT_WS [^[:blank:]\n]
NL \r?\n
NAME ([[:alpha:]_][[:alnum:]_-]*)
NOT_NAME [^[:alpha:]_*\n]+
SCNAME {NAME}
ESCSEQ (\\([^\n]|[0-7]{1,3}|x[[:xdigit:]]{1,2}))
FIRST_CCL_CHAR ([^\\\n]|{ESCSEQ})
CCL_CHAR ([^\\\n\]]|{ESCSEQ})
CCL_EXPR ("[:"[[:alpha:]]+":]")
LEXOPT [aceknopr]
%%
static int bracelevel, didadef, indented_code;
static int doing_rule_action = false;
static int option_sense;
int doing_codeblock = false;
int i;
Char nmdef[MAXLINE], myesc();
<INITIAL>{
^{WS} indented_code = true; BEGIN(CODEBLOCK);
^"/*" ACTION_ECHO; yy_push_state( COMMENT );
^#{OPTWS}line{WS} yy_push_state( LINEDIR );
^"%s"{NAME}? return SCDECL;
^"%x"{NAME}? return XSCDECL;
^"%{".*{NL} {
++linenum;
line_directive_out( (FILE *) 0, 1 );
indented_code = false;
BEGIN(CODEBLOCK);
}
{WS} /* discard */
^"%%".* {
sectnum = 2;
bracelevel = 0;
mark_defs1();
line_directive_out( (FILE *) 0, 1 );
BEGIN(SECT2PROLOG);
return SECTEND;
}
^"%pointer".*{NL} yytext_is_array = false; ++linenum;
^"%array".*{NL} yytext_is_array = true; ++linenum;
^"%option" BEGIN(OPTION); return OPTION_OP;
^"%"{LEXOPT}{OPTWS}[[:digit:]]*{OPTWS}{NL} ++linenum; /* ignore */
^"%"{LEXOPT}{WS}.*{NL} ++linenum; /* ignore */
^"%"[^sxaceknopr{}].* synerr( _( "unrecognized '%' directive" ) );
^{NAME} {
strcpy( nmstr, yytext );
didadef = false;
BEGIN(PICKUPDEF);
}
{SCNAME} RETURNNAME;
^{OPTWS}{NL} ++linenum; /* allows blank lines in section 1 */
{OPTWS}{NL} ACTION_ECHO; ++linenum; /* maybe end of comment line */
}
<COMMENT>{
"*/" ACTION_ECHO; yy_pop_state();
"*" ACTION_ECHO;
[^*\n]+ ACTION_ECHO;
[^*\n]*{NL} ++linenum; ACTION_ECHO;
}
<LINEDIR>{
\n yy_pop_state();
[[:digit:]]+ linenum = myctoi( yytext );
\"[^"\n]*\" {
flex_free( (void *) infilename );
infilename = copy_string( yytext + 1 );
infilename[strlen( infilename ) - 1] = '\0';
}
. /* ignore spurious characters */
}
<CODEBLOCK>{
^"%}".*{NL} ++linenum; BEGIN(INITIAL);
{NAME}|{NOT_NAME}|. ACTION_ECHO;
{NL} {
++linenum;
ACTION_ECHO;
if ( indented_code )
BEGIN(INITIAL);
}
}
<PICKUPDEF>{
{WS} /* separates name and definition */
{NOT_WS}.* {
strcpy( (char *) nmdef, yytext );
/* Skip trailing whitespace. */
for ( i = strlen( (char *) nmdef ) - 1;
i >= 0 && (nmdef[i] == ' ' || nmdef[i] == '\t');
--i )
;
nmdef[i + 1] = '\0';
ndinstal( nmstr, nmdef );
didadef = true;
}
{NL} {
if ( ! didadef )
synerr( _( "incomplete name definition" ) );
BEGIN(INITIAL);
++linenum;
}
}
<OPTION>{
{NL} ++linenum; BEGIN(INITIAL);
{WS} option_sense = true;
"=" return '=';
no option_sense = ! option_sense;
7bit csize = option_sense ? 128 : 256;
8bit csize = option_sense ? 256 : 128;
align long_align = option_sense;
always-interactive {
action_define( "YY_ALWAYS_INTERACTIVE", option_sense );
}
array yytext_is_array = option_sense;
backup backing_up_report = option_sense;
batch interactive = ! option_sense;
"c++" C_plus_plus = option_sense;
caseful|case-sensitive caseins = ! option_sense;
caseless|case-insensitive caseins = option_sense;
debug ddebug = option_sense;
default spprdflt = ! option_sense;
ecs useecs = option_sense;
fast {
useecs = usemecs = false;
use_read = fullspd = true;
}
full {
useecs = usemecs = false;
use_read = fulltbl = true;
}
input ACTION_IFDEF("YY_NO_INPUT", ! option_sense);
interactive interactive = option_sense;
lex-compat lex_compat = option_sense;
main {
action_define( "YY_MAIN", option_sense );
do_yywrap = ! option_sense;
}
meta-ecs usemecs = option_sense;
never-interactive {
action_define( "YY_NEVER_INTERACTIVE", option_sense );
}
perf-report performance_report += option_sense ? 1 : -1;
pointer yytext_is_array = ! option_sense;
read use_read = option_sense;
reject reject_really_used = option_sense;
stack action_define( "YY_STACK_USED", option_sense );
stdinit do_stdinit = option_sense;
stdout use_stdout = option_sense;
unput ACTION_IFDEF("YY_NO_UNPUT", ! option_sense);
verbose printstats = option_sense;
warn nowarn = ! option_sense;
yylineno do_yylineno = option_sense;
yymore yymore_really_used = option_sense;
yywrap do_yywrap = option_sense;
yy_push_state ACTION_IFDEF("YY_NO_PUSH_STATE", ! option_sense);
yy_pop_state ACTION_IFDEF("YY_NO_POP_STATE", ! option_sense);
yy_top_state ACTION_IFDEF("YY_NO_TOP_STATE", ! option_sense);
yy_scan_buffer ACTION_IFDEF("YY_NO_SCAN_BUFFER", ! option_sense);
yy_scan_bytes ACTION_IFDEF("YY_NO_SCAN_BYTES", ! option_sense);
yy_scan_string ACTION_IFDEF("YY_NO_SCAN_STRING", ! option_sense);
outfile return OPT_OUTFILE;
prefix return OPT_PREFIX;
yyclass return OPT_YYCLASS;
\"[^"\n]*\" {
strcpy( nmstr, yytext + 1 );
nmstr[strlen( nmstr ) - 1] = '\0';
return NAME;
}
(([a-mo-z]|n[a-np-z])[[:alpha:]\-+]*)|. {
format_synerr( _( "unrecognized %%option: %s" ),
yytext );
BEGIN(RECOVER);
}
}
<RECOVER>.*{NL} ++linenum; BEGIN(INITIAL);
<SECT2PROLOG>{
^"%{".* ++bracelevel; yyless( 2 ); /* eat only %{ */
^"%}".* --bracelevel; yyless( 2 ); /* eat only %} */
^{WS}.* ACTION_ECHO; /* indented code in prolog */
^{NOT_WS}.* { /* non-indented code */
if ( bracelevel <= 0 )
{ /* not in %{ ... %} */
yyless( 0 ); /* put it all back */
yy_set_bol( 1 );
mark_prolog();
BEGIN(SECT2);
}
else
ACTION_ECHO;
}
.* ACTION_ECHO;
{NL} ++linenum; ACTION_ECHO;
<<EOF>> {
mark_prolog();
sectnum = 0;
yyterminate(); /* to stop the parser */
}
}
<SECT2>{
^{OPTWS}{NL} ++linenum; /* allow blank lines in section 2 */
^{OPTWS}"%{" {
indented_code = false;
doing_codeblock = true;
bracelevel = 1;
BEGIN(PERCENT_BRACE_ACTION);
}
^{OPTWS}"<" BEGIN(SC); return '<';
^{OPTWS}"^" return '^';
\" BEGIN(QUOTE); return '"';
"{"/[[:digit:]] BEGIN(NUM); return '{';
"$"/([[:blank:]]|{NL}) return '$';
{WS}"%{" {
bracelevel = 1;
BEGIN(PERCENT_BRACE_ACTION);
if ( in_rule )
{
doing_rule_action = true;
in_rule = false;
return '\n';
}
}
{WS}"|".*{NL} continued_action = true; ++linenum; return '\n';
^{WS}"/*" {
yyless( yyleng - 2 ); /* put back '/', '*' */
bracelevel = 0;
continued_action = false;
BEGIN(ACTION);
}
^{WS} /* allow indented rules */
{WS} {
/* This rule is separate from the one below because
* otherwise we get variable trailing context, so
* we can't build the scanner using -{f,F}.
*/
bracelevel = 0;
continued_action = false;
BEGIN(ACTION);
if ( in_rule )
{
doing_rule_action = true;
in_rule = false;
return '\n';
}
}
{OPTWS}{NL} {
bracelevel = 0;
continued_action = false;
BEGIN(ACTION);
unput( '\n' ); /* so <ACTION> sees it */
if ( in_rule )
{
doing_rule_action = true;
in_rule = false;
return '\n';
}
}
^{OPTWS}"<<EOF>>" |
"<<EOF>>" return EOF_OP;
^"%%".* {
sectnum = 3;
BEGIN(SECT3);
yyterminate(); /* to stop the parser */
}
"["({FIRST_CCL_CHAR}|{CCL_EXPR})({CCL_CHAR}|{CCL_EXPR})* {
int cclval;
strcpy( nmstr, yytext );
/* Check to see if we've already encountered this
* ccl.
*/
if ( (cclval = ccllookup( (Char *) nmstr )) != 0 )
{
if ( input() != ']' )
synerr( _( "bad character class" ) );
yylval = cclval;
++cclreuse;
return PREVCCL;
}
else
{
/* We fudge a bit. We know that this ccl will
* soon be numbered as lastccl + 1 by cclinit.
*/
cclinstal( (Char *) nmstr, lastccl + 1 );
/* Push back everything but the leading bracket
* so the ccl can be rescanned.
*/
yyless( 1 );
BEGIN(FIRSTCCL);
return '[';
}
}
"{"{NAME}"}" {
register Char *nmdefptr;
Char *ndlookup();
strcpy( nmstr, yytext + 1 );
nmstr[yyleng - 2] = '\0'; /* chop trailing brace */
if ( (nmdefptr = ndlookup( nmstr )) == 0 )
format_synerr(
_( "undefined definition {%s}" ),
nmstr );
else
{ /* push back name surrounded by ()'s */
int len = strlen( (char *) nmdefptr );
if ( lex_compat || nmdefptr[0] == '^' ||
(len > 0 && nmdefptr[len - 1] == '$') )
{ /* don't use ()'s after all */
PUT_BACK_STRING((char *) nmdefptr, 0);
if ( nmdefptr[0] == '^' )
BEGIN(CARETISBOL);
}
else
{
unput(')');
PUT_BACK_STRING((char *) nmdefptr, 0);
unput('(');
}
}
}
[/|*+?.(){}] return (unsigned char) yytext[0];
. RETURNCHAR;
}
<SC>{
[,*] return (unsigned char) yytext[0];
">" BEGIN(SECT2); return '>';
">"/^ BEGIN(CARETISBOL); return '>';
{SCNAME} RETURNNAME;
. {
format_synerr( _( "bad <start condition>: %s" ),
yytext );
}
}
<CARETISBOL>"^" BEGIN(SECT2); return '^';
<QUOTE>{
[^"\n] RETURNCHAR;
\" BEGIN(SECT2); return '"';
{NL} {
synerr( _( "missing quote" ) );
BEGIN(SECT2);
++linenum;
return '"';
}
}
<FIRSTCCL>{
"^"/[^-\]\n] BEGIN(CCL); return '^';
"^"/("-"|"]") return '^';
. BEGIN(CCL); RETURNCHAR;
}
<CCL>{
-/[^\]\n] return '-';
[^\]\n] RETURNCHAR;
"]" BEGIN(SECT2); return ']';
.|{NL} {
synerr( _( "bad character class" ) );
BEGIN(SECT2);
return ']';
}
}
<FIRSTCCL,CCL>{
"[:alnum:]" BEGIN(CCL); return CCE_ALNUM;
"[:alpha:]" BEGIN(CCL); return CCE_ALPHA;
"[:blank:]" BEGIN(CCL); return CCE_BLANK;
"[:cntrl:]" BEGIN(CCL); return CCE_CNTRL;
"[:digit:]" BEGIN(CCL); return CCE_DIGIT;
"[:graph:]" BEGIN(CCL); return CCE_GRAPH;
"[:lower:]" BEGIN(CCL); return CCE_LOWER;
"[:print:]" BEGIN(CCL); return CCE_PRINT;
"[:punct:]" BEGIN(CCL); return CCE_PUNCT;
"[:space:]" BEGIN(CCL); return CCE_SPACE;
"[:upper:]" BEGIN(CCL); return CCE_UPPER;
"[:xdigit:]" BEGIN(CCL); return CCE_XDIGIT;
{CCL_EXPR} {
format_synerr(
_( "bad character class expression: %s" ),
yytext );
BEGIN(CCL); return CCE_ALNUM;
}
}
<NUM>{
[[:digit:]]+ {
yylval = myctoi( yytext );
return NUMBER;
}
"," return ',';
"}" BEGIN(SECT2); return '}';
. {
synerr( _( "bad character inside {}'s" ) );
BEGIN(SECT2);
return '}';
}
{NL} {
synerr( _( "missing }" ) );
BEGIN(SECT2);
++linenum;
return '}';
}
}
<PERCENT_BRACE_ACTION>{
{OPTWS}"%}".* bracelevel = 0;
<ACTION>"/*" ACTION_ECHO; yy_push_state( COMMENT );
<CODEBLOCK,ACTION>{
"reject" {
ACTION_ECHO;
CHECK_REJECT(yytext);
}
"yymore" {
ACTION_ECHO;
CHECK_YYMORE(yytext);
}
}
{NAME}|{NOT_NAME}|. ACTION_ECHO;
{NL} {
++linenum;
ACTION_ECHO;
if ( bracelevel == 0 ||
(doing_codeblock && indented_code) )
{
if ( doing_rule_action )
add_action( "\tYY_BREAK\n" );
doing_rule_action = doing_codeblock = false;
BEGIN(SECT2);
}
}
}
/* Reject and YYmore() are checked for above, in PERCENT_BRACE_ACTION */
<ACTION>{
"{" ACTION_ECHO; ++bracelevel;
"}" ACTION_ECHO; --bracelevel;
[^[:alpha:]_{}"'/\n]+ ACTION_ECHO;
{NAME} ACTION_ECHO;
"'"([^'\\\n]|\\.)*"'" ACTION_ECHO; /* character constant */
\" ACTION_ECHO; BEGIN(ACTION_STRING);
{NL} {
++linenum;
ACTION_ECHO;
if ( bracelevel == 0 )
{
if ( doing_rule_action )
add_action( "\tYY_BREAK\n" );
doing_rule_action = false;
BEGIN(SECT2);
}
}
. ACTION_ECHO;
}
<ACTION_STRING>{
[^"\\\n]+ ACTION_ECHO;
\\. ACTION_ECHO;
{NL} ++linenum; ACTION_ECHO;
\" ACTION_ECHO; BEGIN(ACTION);
. ACTION_ECHO;
}
<COMMENT,ACTION,ACTION_STRING><<EOF>> {
synerr( _( "EOF encountered inside an action" ) );
yyterminate();
}
<SECT2,QUOTE,FIRSTCCL,CCL>{ESCSEQ} {
yylval = myesc( (Char *) yytext );
if ( YY_START == FIRSTCCL )
BEGIN(CCL);
return CHAR;
}
<SECT3>{
.*(\n?) ECHO;
<<EOF>> sectnum = 0; yyterminate();
}
<*>.|\n format_synerr( _( "bad character: %s" ), yytext );
%%
int yywrap()
{
if ( --num_input_files > 0 )
{
set_input_file( *++input_files );
return 0;
}
else
return 1;
}
/* set_input_file - open the given file (if NULL, stdin) for scanning */
void set_input_file( file )
char *file;
{
if ( file && strcmp( file, "-" ) )
{
infilename = copy_string( file );
yyin = fopen( infilename, "r" );
if ( yyin == NULL )
lerrsf( _( "can't open %s" ), file );
}
else
{
yyin = stdin;
infilename = copy_string( "<stdin>" );
}
linenum = 1;
}
/* Wrapper routines for accessing the scanner's malloc routines. */
void *flex_alloc( size )
size_t size;
{
return (void *) malloc( size );
}
void *flex_realloc( ptr, size )
void *ptr;
size_t size;
{
return (void *) realloc( ptr, size );
}
void flex_free( ptr )
void *ptr;
{
if ( ptr )
free( ptr );
}

1548
commands/flex-2.5.4/skel.c Normal file

File diff suppressed because it is too large Load diff

262
commands/flex-2.5.4/sym.c Normal file
View file

@ -0,0 +1,262 @@
/* sym - symbol table routines */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
/* declare functions that have forward references */
int hashfunct PROTO((register char[], int));
struct hash_entry *ndtbl[NAME_TABLE_HASH_SIZE];
struct hash_entry *sctbl[START_COND_HASH_SIZE];
struct hash_entry *ccltab[CCL_HASH_SIZE];
struct hash_entry *findsym();
/* addsym - add symbol and definitions to symbol table
*
* -1 is returned if the symbol already exists, and the change not made.
*/
int addsym( sym, str_def, int_def, table, table_size )
register char sym[];
char *str_def;
int int_def;
hash_table table;
int table_size;
{
int hash_val = hashfunct( sym, table_size );
register struct hash_entry *sym_entry = table[hash_val];
register struct hash_entry *new_entry;
register struct hash_entry *successor;
while ( sym_entry )
{
if ( ! strcmp( sym, sym_entry->name ) )
{ /* entry already exists */
return -1;
}
sym_entry = sym_entry->next;
}
/* create new entry */
new_entry = (struct hash_entry *)
flex_alloc( sizeof( struct hash_entry ) );
if ( new_entry == NULL )
flexfatal( _( "symbol table memory allocation failed" ) );
if ( (successor = table[hash_val]) != 0 )
{
new_entry->next = successor;
successor->prev = new_entry;
}
else
new_entry->next = NULL;
new_entry->prev = NULL;
new_entry->name = sym;
new_entry->str_val = str_def;
new_entry->int_val = int_def;
table[hash_val] = new_entry;
return 0;
}
/* cclinstal - save the text of a character class */
void cclinstal( ccltxt, cclnum )
Char ccltxt[];
int cclnum;
{
/* We don't bother checking the return status because we are not
* called unless the symbol is new.
*/
Char *copy_unsigned_string();
(void) addsym( (char *) copy_unsigned_string( ccltxt ),
(char *) 0, cclnum,
ccltab, CCL_HASH_SIZE );
}
/* ccllookup - lookup the number associated with character class text
*
* Returns 0 if there's no CCL associated with the text.
*/
int ccllookup( ccltxt )
Char ccltxt[];
{
return findsym( (char *) ccltxt, ccltab, CCL_HASH_SIZE )->int_val;
}
/* findsym - find symbol in symbol table */
struct hash_entry *findsym( sym, table, table_size )
register char sym[];
hash_table table;
int table_size;
{
static struct hash_entry empty_entry =
{
(struct hash_entry *) 0, (struct hash_entry *) 0,
(char *) 0, (char *) 0, 0,
} ;
register struct hash_entry *sym_entry =
table[hashfunct( sym, table_size )];
while ( sym_entry )
{
if ( ! strcmp( sym, sym_entry->name ) )
return sym_entry;
sym_entry = sym_entry->next;
}
return &empty_entry;
}
/* hashfunct - compute the hash value for "str" and hash size "hash_size" */
int hashfunct( str, hash_size )
register char str[];
int hash_size;
{
register int hashval;
register int locstr;
hashval = 0;
locstr = 0;
while ( str[locstr] )
{
hashval = (hashval << 1) + (unsigned char) str[locstr++];
hashval %= hash_size;
}
return hashval;
}
/* ndinstal - install a name definition */
void ndinstal( name, definition )
char name[];
Char definition[];
{
char *copy_string();
Char *copy_unsigned_string();
if ( addsym( copy_string( name ),
(char *) copy_unsigned_string( definition ), 0,
ndtbl, NAME_TABLE_HASH_SIZE ) )
synerr( _( "name defined twice" ) );
}
/* ndlookup - lookup a name definition
*
* Returns a nil pointer if the name definition does not exist.
*/
Char *ndlookup( nd )
char nd[];
{
return (Char *) findsym( nd, ndtbl, NAME_TABLE_HASH_SIZE )->str_val;
}
/* scextend - increase the maximum number of start conditions */
void scextend()
{
current_max_scs += MAX_SCS_INCREMENT;
++num_reallocs;
scset = reallocate_integer_array( scset, current_max_scs );
scbol = reallocate_integer_array( scbol, current_max_scs );
scxclu = reallocate_integer_array( scxclu, current_max_scs );
sceof = reallocate_integer_array( sceof, current_max_scs );
scname = reallocate_char_ptr_array( scname, current_max_scs );
}
/* scinstal - make a start condition
*
* NOTE
* The start condition is "exclusive" if xcluflg is true.
*/
void scinstal( str, xcluflg )
char str[];
int xcluflg;
{
char *copy_string();
/* Generate start condition definition, for use in BEGIN et al. */
action_define( str, lastsc );
if ( ++lastsc >= current_max_scs )
scextend();
scname[lastsc] = copy_string( str );
if ( addsym( scname[lastsc], (char *) 0, lastsc,
sctbl, START_COND_HASH_SIZE ) )
format_pinpoint_message(
_( "start condition %s declared twice" ),
str );
scset[lastsc] = mkstate( SYM_EPSILON );
scbol[lastsc] = mkstate( SYM_EPSILON );
scxclu[lastsc] = xcluflg;
sceof[lastsc] = false;
}
/* sclookup - lookup the number associated with a start condition
*
* Returns 0 if no such start condition.
*/
int sclookup( str )
char str[];
{
return findsym( str, sctbl, START_COND_HASH_SIZE )->int_val;
}

View file

@ -0,0 +1,887 @@
/* tblcmp - table compression routines */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include "flexdef.h"
/* declarations for functions that have forward references */
void mkentry PROTO((register int*, int, int, int, int));
void mkprot PROTO((int[], int, int));
void mktemplate PROTO((int[], int, int));
void mv2front PROTO((int));
int tbldiff PROTO((int[], int, int[]));
/* bldtbl - build table entries for dfa state
*
* synopsis
* int state[numecs], statenum, totaltrans, comstate, comfreq;
* bldtbl( state, statenum, totaltrans, comstate, comfreq );
*
* State is the statenum'th dfa state. It is indexed by equivalence class and
* gives the number of the state to enter for a given equivalence class.
* totaltrans is the total number of transitions out of the state. Comstate
* is that state which is the destination of the most transitions out of State.
* Comfreq is how many transitions there are out of State to Comstate.
*
* A note on terminology:
* "protos" are transition tables which have a high probability of
* either being redundant (a state processed later will have an identical
* transition table) or nearly redundant (a state processed later will have
* many of the same out-transitions). A "most recently used" queue of
* protos is kept around with the hope that most states will find a proto
* which is similar enough to be usable, and therefore compacting the
* output tables.
* "templates" are a special type of proto. If a transition table is
* homogeneous or nearly homogeneous (all transitions go to the same
* destination) then the odds are good that future states will also go
* to the same destination state on basically the same character set.
* These homogeneous states are so common when dealing with large rule
* sets that they merit special attention. If the transition table were
* simply made into a proto, then (typically) each subsequent, similar
* state will differ from the proto for two out-transitions. One of these
* out-transitions will be that character on which the proto does not go
* to the common destination, and one will be that character on which the
* state does not go to the common destination. Templates, on the other
* hand, go to the common state on EVERY transition character, and therefore
* cost only one difference.
*/
void bldtbl( state, statenum, totaltrans, comstate, comfreq )
int state[], statenum, totaltrans, comstate, comfreq;
{
int extptr, extrct[2][CSIZE + 1];
int mindiff, minprot, i, d;
/* If extptr is 0 then the first array of extrct holds the result
* of the "best difference" to date, which is those transitions
* which occur in "state" but not in the proto which, to date,
* has the fewest differences between itself and "state". If
* extptr is 1 then the second array of extrct hold the best
* difference. The two arrays are toggled between so that the
* best difference to date can be kept around and also a difference
* just created by checking against a candidate "best" proto.
*/
extptr = 0;
/* If the state has too few out-transitions, don't bother trying to
* compact its tables.
*/
if ( (totaltrans * 100) < (numecs * PROTO_SIZE_PERCENTAGE) )
mkentry( state, numecs, statenum, JAMSTATE, totaltrans );
else
{
/* "checkcom" is true if we should only check "state" against
* protos which have the same "comstate" value.
*/
int checkcom =
comfreq * 100 > totaltrans * CHECK_COM_PERCENTAGE;
minprot = firstprot;
mindiff = totaltrans;
if ( checkcom )
{
/* Find first proto which has the same "comstate". */
for ( i = firstprot; i != NIL; i = protnext[i] )
if ( protcomst[i] == comstate )
{
minprot = i;
mindiff = tbldiff( state, minprot,
extrct[extptr] );
break;
}
}
else
{
/* Since we've decided that the most common destination
* out of "state" does not occur with a high enough
* frequency, we set the "comstate" to zero, assuring
* that if this state is entered into the proto list,
* it will not be considered a template.
*/
comstate = 0;
if ( firstprot != NIL )
{
minprot = firstprot;
mindiff = tbldiff( state, minprot,
extrct[extptr] );
}
}
/* We now have the first interesting proto in "minprot". If
* it matches within the tolerances set for the first proto,
* we don't want to bother scanning the rest of the proto list
* to see if we have any other reasonable matches.
*/
if ( mindiff * 100 > totaltrans * FIRST_MATCH_DIFF_PERCENTAGE )
{
/* Not a good enough match. Scan the rest of the
* protos.
*/
for ( i = minprot; i != NIL; i = protnext[i] )
{
d = tbldiff( state, i, extrct[1 - extptr] );
if ( d < mindiff )
{
extptr = 1 - extptr;
mindiff = d;
minprot = i;
}
}
}
/* Check if the proto we've decided on as our best bet is close
* enough to the state we want to match to be usable.
*/
if ( mindiff * 100 > totaltrans * ACCEPTABLE_DIFF_PERCENTAGE )
{
/* No good. If the state is homogeneous enough,
* we make a template out of it. Otherwise, we
* make a proto.
*/
if ( comfreq * 100 >=
totaltrans * TEMPLATE_SAME_PERCENTAGE )
mktemplate( state, statenum, comstate );
else
{
mkprot( state, statenum, comstate );
mkentry( state, numecs, statenum,
JAMSTATE, totaltrans );
}
}
else
{ /* use the proto */
mkentry( extrct[extptr], numecs, statenum,
prottbl[minprot], mindiff );
/* If this state was sufficiently different from the
* proto we built it from, make it, too, a proto.
*/
if ( mindiff * 100 >=
totaltrans * NEW_PROTO_DIFF_PERCENTAGE )
mkprot( state, statenum, comstate );
/* Since mkprot added a new proto to the proto queue,
* it's possible that "minprot" is no longer on the
* proto queue (if it happened to have been the last
* entry, it would have been bumped off). If it's
* not there, then the new proto took its physical
* place (though logically the new proto is at the
* beginning of the queue), so in that case the
* following call will do nothing.
*/
mv2front( minprot );
}
}
}
/* cmptmps - compress template table entries
*
* Template tables are compressed by using the 'template equivalence
* classes', which are collections of transition character equivalence
* classes which always appear together in templates - really meta-equivalence
* classes.
*/
void cmptmps()
{
int tmpstorage[CSIZE + 1];
register int *tmp = tmpstorage, i, j;
int totaltrans, trans;
peakpairs = numtemps * numecs + tblend;
if ( usemecs )
{
/* Create equivalence classes based on data gathered on
* template transitions.
*/
nummecs = cre8ecs( tecfwd, tecbck, numecs );
}
else
nummecs = numecs;
while ( lastdfa + numtemps + 1 >= current_max_dfas )
increase_max_dfas();
/* Loop through each template. */
for ( i = 1; i <= numtemps; ++i )
{
/* Number of non-jam transitions out of this template. */
totaltrans = 0;
for ( j = 1; j <= numecs; ++j )
{
trans = tnxt[numecs * i + j];
if ( usemecs )
{
/* The absolute value of tecbck is the
* meta-equivalence class of a given
* equivalence class, as set up by cre8ecs().
*/
if ( tecbck[j] > 0 )
{
tmp[tecbck[j]] = trans;
if ( trans > 0 )
++totaltrans;
}
}
else
{
tmp[j] = trans;
if ( trans > 0 )
++totaltrans;
}
}
/* It is assumed (in a rather subtle way) in the skeleton
* that if we're using meta-equivalence classes, the def[]
* entry for all templates is the jam template, i.e.,
* templates never default to other non-jam table entries
* (e.g., another template)
*/
/* Leave room for the jam-state after the last real state. */
mkentry( tmp, nummecs, lastdfa + i + 1, JAMSTATE, totaltrans );
}
}
/* expand_nxt_chk - expand the next check arrays */
void expand_nxt_chk()
{
register int old_max = current_max_xpairs;
current_max_xpairs += MAX_XPAIRS_INCREMENT;
++num_reallocs;
nxt = reallocate_integer_array( nxt, current_max_xpairs );
chk = reallocate_integer_array( chk, current_max_xpairs );
zero_out( (char *) (chk + old_max),
(size_t) (MAX_XPAIRS_INCREMENT * sizeof( int )) );
}
/* find_table_space - finds a space in the table for a state to be placed
*
* synopsis
* int *state, numtrans, block_start;
* int find_table_space();
*
* block_start = find_table_space( state, numtrans );
*
* State is the state to be added to the full speed transition table.
* Numtrans is the number of out-transitions for the state.
*
* find_table_space() returns the position of the start of the first block (in
* chk) able to accommodate the state
*
* In determining if a state will or will not fit, find_table_space() must take
* into account the fact that an end-of-buffer state will be added at [0],
* and an action number will be added in [-1].
*/
int find_table_space( state, numtrans )
int *state, numtrans;
{
/* Firstfree is the position of the first possible occurrence of two
* consecutive unused records in the chk and nxt arrays.
*/
register int i;
register int *state_ptr, *chk_ptr;
register int *ptr_to_last_entry_in_state;
/* If there are too many out-transitions, put the state at the end of
* nxt and chk.
*/
if ( numtrans > MAX_XTIONS_FULL_INTERIOR_FIT )
{
/* If table is empty, return the first available spot in
* chk/nxt, which should be 1.
*/
if ( tblend < 2 )
return 1;
/* Start searching for table space near the end of
* chk/nxt arrays.
*/
i = tblend - numecs;
}
else
/* Start searching for table space from the beginning
* (skipping only the elements which will definitely not
* hold the new state).
*/
i = firstfree;
while ( 1 ) /* loops until a space is found */
{
while ( i + numecs >= current_max_xpairs )
expand_nxt_chk();
/* Loops until space for end-of-buffer and action number
* are found.
*/
while ( 1 )
{
/* Check for action number space. */
if ( chk[i - 1] == 0 )
{
/* Check for end-of-buffer space. */
if ( chk[i] == 0 )
break;
else
/* Since i != 0, there is no use
* checking to see if (++i) - 1 == 0,
* because that's the same as i == 0,
* so we skip a space.
*/
i += 2;
}
else
++i;
while ( i + numecs >= current_max_xpairs )
expand_nxt_chk();
}
/* If we started search from the beginning, store the new
* firstfree for the next call of find_table_space().
*/
if ( numtrans <= MAX_XTIONS_FULL_INTERIOR_FIT )
firstfree = i + 1;
/* Check to see if all elements in chk (and therefore nxt)
* that are needed for the new state have not yet been taken.
*/
state_ptr = &state[1];
ptr_to_last_entry_in_state = &chk[i + numecs + 1];
for ( chk_ptr = &chk[i + 1];
chk_ptr != ptr_to_last_entry_in_state; ++chk_ptr )
if ( *(state_ptr++) != 0 && *chk_ptr != 0 )
break;
if ( chk_ptr == ptr_to_last_entry_in_state )
return i;
else
++i;
}
}
/* inittbl - initialize transition tables
*
* Initializes "firstfree" to be one beyond the end of the table. Initializes
* all "chk" entries to be zero.
*/
void inittbl()
{
register int i;
zero_out( (char *) chk, (size_t) (current_max_xpairs * sizeof( int )) );
tblend = 0;
firstfree = tblend + 1;
numtemps = 0;
if ( usemecs )
{
/* Set up doubly-linked meta-equivalence classes; these
* are sets of equivalence classes which all have identical
* transitions out of TEMPLATES.
*/
tecbck[1] = NIL;
for ( i = 2; i <= numecs; ++i )
{
tecbck[i] = i - 1;
tecfwd[i - 1] = i;
}
tecfwd[numecs] = NIL;
}
}
/* mkdeftbl - make the default, "jam" table entries */
void mkdeftbl()
{
int i;
jamstate = lastdfa + 1;
++tblend; /* room for transition on end-of-buffer character */
while ( tblend + numecs >= current_max_xpairs )
expand_nxt_chk();
/* Add in default end-of-buffer transition. */
nxt[tblend] = end_of_buffer_state;
chk[tblend] = jamstate;
for ( i = 1; i <= numecs; ++i )
{
nxt[tblend + i] = 0;
chk[tblend + i] = jamstate;
}
jambase = tblend;
base[jamstate] = jambase;
def[jamstate] = 0;
tblend += numecs;
++numtemps;
}
/* mkentry - create base/def and nxt/chk entries for transition array
*
* synopsis
* int state[numchars + 1], numchars, statenum, deflink, totaltrans;
* mkentry( state, numchars, statenum, deflink, totaltrans );
*
* "state" is a transition array "numchars" characters in size, "statenum"
* is the offset to be used into the base/def tables, and "deflink" is the
* entry to put in the "def" table entry. If "deflink" is equal to
* "JAMSTATE", then no attempt will be made to fit zero entries of "state"
* (i.e., jam entries) into the table. It is assumed that by linking to
* "JAMSTATE" they will be taken care of. In any case, entries in "state"
* marking transitions to "SAME_TRANS" are treated as though they will be
* taken care of by whereever "deflink" points. "totaltrans" is the total
* number of transitions out of the state. If it is below a certain threshold,
* the tables are searched for an interior spot that will accommodate the
* state array.
*/
void mkentry( state, numchars, statenum, deflink, totaltrans )
register int *state;
int numchars, statenum, deflink, totaltrans;
{
register int minec, maxec, i, baseaddr;
int tblbase, tbllast;
if ( totaltrans == 0 )
{ /* there are no out-transitions */
if ( deflink == JAMSTATE )
base[statenum] = JAMSTATE;
else
base[statenum] = 0;
def[statenum] = deflink;
return;
}
for ( minec = 1; minec <= numchars; ++minec )
{
if ( state[minec] != SAME_TRANS )
if ( state[minec] != 0 || deflink != JAMSTATE )
break;
}
if ( totaltrans == 1 )
{
/* There's only one out-transition. Save it for later to fill
* in holes in the tables.
*/
stack1( statenum, minec, state[minec], deflink );
return;
}
for ( maxec = numchars; maxec > 0; --maxec )
{
if ( state[maxec] != SAME_TRANS )
if ( state[maxec] != 0 || deflink != JAMSTATE )
break;
}
/* Whether we try to fit the state table in the middle of the table
* entries we have already generated, or if we just take the state
* table at the end of the nxt/chk tables, we must make sure that we
* have a valid base address (i.e., non-negative). Note that
* negative base addresses dangerous at run-time (because indexing
* the nxt array with one and a low-valued character will access
* memory before the start of the array.
*/
/* Find the first transition of state that we need to worry about. */
if ( totaltrans * 100 <= numchars * INTERIOR_FIT_PERCENTAGE )
{
/* Attempt to squeeze it into the middle of the tables. */
baseaddr = firstfree;
while ( baseaddr < minec )
{
/* Using baseaddr would result in a negative base
* address below; find the next free slot.
*/
for ( ++baseaddr; chk[baseaddr] != 0; ++baseaddr )
;
}
while ( baseaddr + maxec - minec + 1 >= current_max_xpairs )
expand_nxt_chk();
for ( i = minec; i <= maxec; ++i )
if ( state[i] != SAME_TRANS &&
(state[i] != 0 || deflink != JAMSTATE) &&
chk[baseaddr + i - minec] != 0 )
{ /* baseaddr unsuitable - find another */
for ( ++baseaddr;
baseaddr < current_max_xpairs &&
chk[baseaddr] != 0; ++baseaddr )
;
while ( baseaddr + maxec - minec + 1 >=
current_max_xpairs )
expand_nxt_chk();
/* Reset the loop counter so we'll start all
* over again next time it's incremented.
*/
i = minec - 1;
}
}
else
{
/* Ensure that the base address we eventually generate is
* non-negative.
*/
baseaddr = MAX( tblend + 1, minec );
}
tblbase = baseaddr - minec;
tbllast = tblbase + maxec;
while ( tbllast + 1 >= current_max_xpairs )
expand_nxt_chk();
base[statenum] = tblbase;
def[statenum] = deflink;
for ( i = minec; i <= maxec; ++i )
if ( state[i] != SAME_TRANS )
if ( state[i] != 0 || deflink != JAMSTATE )
{
nxt[tblbase + i] = state[i];
chk[tblbase + i] = statenum;
}
if ( baseaddr == firstfree )
/* Find next free slot in tables. */
for ( ++firstfree; chk[firstfree] != 0; ++firstfree )
;
tblend = MAX( tblend, tbllast );
}
/* mk1tbl - create table entries for a state (or state fragment) which
* has only one out-transition
*/
void mk1tbl( state, sym, onenxt, onedef )
int state, sym, onenxt, onedef;
{
if ( firstfree < sym )
firstfree = sym;
while ( chk[firstfree] != 0 )
if ( ++firstfree >= current_max_xpairs )
expand_nxt_chk();
base[state] = firstfree - sym;
def[state] = onedef;
chk[firstfree] = state;
nxt[firstfree] = onenxt;
if ( firstfree > tblend )
{
tblend = firstfree++;
if ( firstfree >= current_max_xpairs )
expand_nxt_chk();
}
}
/* mkprot - create new proto entry */
void mkprot( state, statenum, comstate )
int state[], statenum, comstate;
{
int i, slot, tblbase;
if ( ++numprots >= MSP || numecs * numprots >= PROT_SAVE_SIZE )
{
/* Gotta make room for the new proto by dropping last entry in
* the queue.
*/
slot = lastprot;
lastprot = protprev[lastprot];
protnext[lastprot] = NIL;
}
else
slot = numprots;
protnext[slot] = firstprot;
if ( firstprot != NIL )
protprev[firstprot] = slot;
firstprot = slot;
prottbl[slot] = statenum;
protcomst[slot] = comstate;
/* Copy state into save area so it can be compared with rapidly. */
tblbase = numecs * (slot - 1);
for ( i = 1; i <= numecs; ++i )
protsave[tblbase + i] = state[i];
}
/* mktemplate - create a template entry based on a state, and connect the state
* to it
*/
void mktemplate( state, statenum, comstate )
int state[], statenum, comstate;
{
int i, numdiff, tmpbase, tmp[CSIZE + 1];
Char transset[CSIZE + 1];
int tsptr;
++numtemps;
tsptr = 0;
/* Calculate where we will temporarily store the transition table
* of the template in the tnxt[] array. The final transition table
* gets created by cmptmps().
*/
tmpbase = numtemps * numecs;
if ( tmpbase + numecs >= current_max_template_xpairs )
{
current_max_template_xpairs += MAX_TEMPLATE_XPAIRS_INCREMENT;
++num_reallocs;
tnxt = reallocate_integer_array( tnxt,
current_max_template_xpairs );
}
for ( i = 1; i <= numecs; ++i )
if ( state[i] == 0 )
tnxt[tmpbase + i] = 0;
else
{
transset[tsptr++] = i;
tnxt[tmpbase + i] = comstate;
}
if ( usemecs )
mkeccl( transset, tsptr, tecfwd, tecbck, numecs, 0 );
mkprot( tnxt + tmpbase, -numtemps, comstate );
/* We rely on the fact that mkprot adds things to the beginning
* of the proto queue.
*/
numdiff = tbldiff( state, firstprot, tmp );
mkentry( tmp, numecs, statenum, -numtemps, numdiff );
}
/* mv2front - move proto queue element to front of queue */
void mv2front( qelm )
int qelm;
{
if ( firstprot != qelm )
{
if ( qelm == lastprot )
lastprot = protprev[lastprot];
protnext[protprev[qelm]] = protnext[qelm];
if ( protnext[qelm] != NIL )
protprev[protnext[qelm]] = protprev[qelm];
protprev[qelm] = NIL;
protnext[qelm] = firstprot;
protprev[firstprot] = qelm;
firstprot = qelm;
}
}
/* place_state - place a state into full speed transition table
*
* State is the statenum'th state. It is indexed by equivalence class and
* gives the number of the state to enter for a given equivalence class.
* Transnum is the number of out-transitions for the state.
*/
void place_state( state, statenum, transnum )
int *state, statenum, transnum;
{
register int i;
register int *state_ptr;
int position = find_table_space( state, transnum );
/* "base" is the table of start positions. */
base[statenum] = position;
/* Put in action number marker; this non-zero number makes sure that
* find_table_space() knows that this position in chk/nxt is taken
* and should not be used for another accepting number in another
* state.
*/
chk[position - 1] = 1;
/* Put in end-of-buffer marker; this is for the same purposes as
* above.
*/
chk[position] = 1;
/* Place the state into chk and nxt. */
state_ptr = &state[1];
for ( i = 1; i <= numecs; ++i, ++state_ptr )
if ( *state_ptr != 0 )
{
chk[position + i] = i;
nxt[position + i] = *state_ptr;
}
if ( position + numecs > tblend )
tblend = position + numecs;
}
/* stack1 - save states with only one out-transition to be processed later
*
* If there's room for another state on the "one-transition" stack, the
* state is pushed onto it, to be processed later by mk1tbl. If there's
* no room, we process the sucker right now.
*/
void stack1( statenum, sym, nextstate, deflink )
int statenum, sym, nextstate, deflink;
{
if ( onesp >= ONE_STACK_SIZE - 1 )
mk1tbl( statenum, sym, nextstate, deflink );
else
{
++onesp;
onestate[onesp] = statenum;
onesym[onesp] = sym;
onenext[onesp] = nextstate;
onedef[onesp] = deflink;
}
}
/* tbldiff - compute differences between two state tables
*
* "state" is the state array which is to be extracted from the pr'th
* proto. "pr" is both the number of the proto we are extracting from
* and an index into the save area where we can find the proto's complete
* state table. Each entry in "state" which differs from the corresponding
* entry of "pr" will appear in "ext".
*
* Entries which are the same in both "state" and "pr" will be marked
* as transitions to "SAME_TRANS" in "ext". The total number of differences
* between "state" and "pr" is returned as function value. Note that this
* number is "numecs" minus the number of "SAME_TRANS" entries in "ext".
*/
int tbldiff( state, pr, ext )
int state[], pr, ext[];
{
register int i, *sp = state, *ep = ext, *protp;
register int numdiff = 0;
protp = &protsave[numecs * (pr - 1)];
for ( i = numecs; i > 0; --i )
{
if ( *++protp == *++sp )
*++ep = SAME_TRANS;
else
{
*++ep = *sp;
++numdiff;
}
}
return numdiff;
}

View file

@ -0,0 +1 @@
#define FLEX_VERSION "2.5.4"

216
commands/flex-2.5.4/yylex.c Normal file
View file

@ -0,0 +1,216 @@
/* yylex - scanner front-end for flex */
/*-
* Copyright (c) 1990 The Regents of the University of California.
* All rights reserved.
*
* This code is derived from software contributed to Berkeley by
* Vern Paxson.
*
* The United States Government has rights in this work pursuant
* to contract no. DE-AC03-76SF00098 between the United States
* Department of Energy and the University of California.
*
* Redistribution and use in source and binary forms with or without
* modification are permitted provided that: (1) source distributions retain
* this entire copyright notice and comment, and (2) distributions including
* binaries display the following acknowledgement: ``This product includes
* software developed by the University of California, Berkeley and its
* contributors'' in the documentation or other materials provided with the
* distribution and in all advertising materials mentioning features or use
* of this software. Neither the name of the University nor the names of
* its contributors may be used to endorse or promote products derived from
* this software without specific prior written permission.
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*/
/* $Header$ */
#include <ctype.h>
#include "flexdef.h"
#include "parse.h"
/* yylex - scan for a regular expression token */
int yylex()
{
int toktype;
static int beglin = false;
extern char *yytext;
if ( eofseen )
toktype = EOF;
else
toktype = flexscan();
if ( toktype == EOF || toktype == 0 )
{
eofseen = 1;
if ( sectnum == 1 )
{
synerr( _( "premature EOF" ) );
sectnum = 2;
toktype = SECTEND;
}
else
toktype = 0;
}
if ( trace )
{
if ( beglin )
{
fprintf( stderr, "%d\t", num_rules + 1 );
beglin = 0;
}
switch ( toktype )
{
case '<':
case '>':
case '^':
case '$':
case '"':
case '[':
case ']':
case '{':
case '}':
case '|':
case '(':
case ')':
case '-':
case '/':
case '\\':
case '?':
case '.':
case '*':
case '+':
case ',':
(void) putc( toktype, stderr );
break;
case '\n':
(void) putc( '\n', stderr );
if ( sectnum == 2 )
beglin = 1;
break;
case SCDECL:
fputs( "%s", stderr );
break;
case XSCDECL:
fputs( "%x", stderr );
break;
case SECTEND:
fputs( "%%\n", stderr );
/* We set beglin to be true so we'll start
* writing out numbers as we echo rules.
* flexscan() has already assigned sectnum.
*/
if ( sectnum == 2 )
beglin = 1;
break;
case NAME:
fprintf( stderr, "'%s'", nmstr );
break;
case CHAR:
switch ( yylval )
{
case '<':
case '>':
case '^':
case '$':
case '"':
case '[':
case ']':
case '{':
case '}':
case '|':
case '(':
case ')':
case '-':
case '/':
case '\\':
case '?':
case '.':
case '*':
case '+':
case ',':
fprintf( stderr, "\\%c",
yylval );
break;
default:
if ( ! isascii( yylval ) ||
! isprint( yylval ) )
fprintf( stderr,
"\\%.3o",
(unsigned int) yylval );
else
(void) putc( yylval,
stderr );
break;
}
break;
case NUMBER:
fprintf( stderr, "%d", yylval );
break;
case PREVCCL:
fprintf( stderr, "[%d]", yylval );
break;
case EOF_OP:
fprintf( stderr, "<<EOF>>" );
break;
case OPTION_OP:
fprintf( stderr, "%s ", yytext );
break;
case OPT_OUTFILE:
case OPT_PREFIX:
case CCE_ALNUM:
case CCE_ALPHA:
case CCE_BLANK:
case CCE_CNTRL:
case CCE_DIGIT:
case CCE_GRAPH:
case CCE_LOWER:
case CCE_PRINT:
case CCE_PUNCT:
case CCE_SPACE:
case CCE_UPPER:
case CCE_XDIGIT:
fprintf( stderr, "%s", yytext );
break;
case 0:
fprintf( stderr, _( "End Marker\n" ) );
break;
default:
fprintf( stderr,
_( "*Something Weird* - tok: %d val: %d\n" ),
toktype, yylval );
break;
}
}
return toktype;
}