]> thyrsus.com Git - cupl.git/commitdiff
Ready to release 1.2.
authorEric S. Raymond <esr@thyrsus.com>
Fri, 28 Jun 1996 13:12:04 +0000 (13:12 +0000)
committerEric S. Raymond <esr@thyrsus.com>
Fri, 28 Jun 1996 13:12:04 +0000 (13:12 +0000)
Makefile
READ.ME
cupl.l
cupl.xml

index cd58bf005f9b6dd3c23dab8d0faddee2c253998a..45e53763b05a80aca919ab0b182799cfaea971ef 100644 (file)
--- a/Makefile
+++ b/Makefile
@@ -5,7 +5,7 @@
 # Note: When the version changes, you also have to change
 #  * the name of the containing directory
 #  * the RPM spec file
-V=1.1
+V=1.2
 
 CDEBUG = -g    # use -O for production, -g for debugging
 YFLAGS = -vt   # use -l for production, -vt for debugging
diff --git a/READ.ME b/READ.ME
index a726ebc147ab62f06653c96144cc7ac6668379ff..cc438cecf5c80e14b3823d6b371841944d8ef546 100644 (file)
--- a/READ.ME
+++ b/READ.ME
@@ -31,7 +31,6 @@ READ.ME                       -- this file
 cupl.doc               -- transcription of the original CUPL documentation
 corc.doc               -- transcription of the original CORC documentation
 cupl.mm                        -- description and discussion of the language
-tour.doc               -- a tour of the compiler internals
 
                        Source files
 
@@ -100,6 +99,10 @@ Send comments, bug reports, and fixes to esr@snark.thyrsus.com.  Also see
 my home page at http://www.ccil.org/~esr/home.html for updates and other
 related resources.
 ---------------------------------------------------------------------------
+Version 1.2:
+       * Fixed off-by-one bug in TITLE processing.
+       * Merged tour.doc into cupl.mm.
+       * Added "Hello World" program.
 Version 1.1:
        * Added CORC support.
        * Fixed a core-dump bug in the prettyprinter.
diff --git a/cupl.l b/cupl.l
index 65622ace59efa7307d059ad2fbabb435b1b028b9..c455096a3c4b4a8733dbaeff8ec496dd321a2251 100644 (file)
--- a/cupl.l
+++ b/cupl.l
@@ -85,7 +85,7 @@ SQRT          {return(SQRT);}
 STOP           {return(STOP);}
 THEN           {return(THEN);}
 TIMES          {return(TIMES);}
-TITLE.*\n      {corc = TRUE; yylval.node = intern_string(yytext + 6); return(TITLE);}
+TITLE.*\n      {corc = TRUE; yylval.node = intern_string(yytext + 5); return(TITLE);}
 TO             {return(TO);}
 TRC            {return(TRC);}
 TRN            {return(TRN);}
index 19e832c31e24409500d42d86f3958b7803038edb..9762aa196b5a0b3d143ddff967812e1d8c382b21 100644 (file)
--- a/cupl.xml
+++ b/cupl.xml
@@ -25,8 +25,8 @@ The purpose of this implementation, and this paper, is to preserve a
 CUPL/CORC implementation for the edification of historians and
 students of programming-language design.  CUPL and CORC were
 representative of a significant class of teaching languages in its
-period, and study of the design casts a clear light on the
-preoccupations of its time.
+period, and study of their design casts a clear light on the
+preoccupations of their time.
 .P
 .H 1 "The CUPL and CORC Languages"
 .P
@@ -135,6 +135,54 @@ variable and label are printed after each run.  At level 3, an
 execution trace is displayed as the parse tree is printed.  At level
 4, each token intern and cons-cell allocation during parsing is also
 dumped.
+.P
+.H 1 "Unix Implementation Notes."
+.P
+The CUPL/CORC implementation is built around YACC and LEX.  The rest is
+ANSI and POSIX-conformant C.
+.P
+The YACC grammar just builds a parse tree, which is passed to
+interpret() for interpretation.  This method requires that all
+programs are always small enough that the entire tree can be held
+in memory, but it has the advantage that front and back end are very
+well separated.  It is a winning strategy on virtual-memory systems.
+.P
+One hack that greatly simplifies the grammar productions is that the
+lexer actually returns parse tree nodes, even for atoms like
+identifiers, strings, and numbers.  In fact, the lexical analyzer even
+does label and variable name resolution with the same simple piece of
+code; each IDENTIFIER token is looked up in the identifier list when
+it's recognized, so the parse tree early becomes a DAG.  (The -v1 option
+causes the compiler to dump its parse tree for inspection.)
+.P
+Most of the smarts are in interpret() and its sub-functions.  Because
+array variables can be re-allocated, the internals have to use a
+dynamic vector/array type with its own indexing machinery.  The code
+to manipulate this type lives in monitor.c.
+.P
+Note that much of this machinery is quite generic and could be re-used
+for other languages with little change.
+.P
+The implementation trades away some possible efficiencies for
+simplicity.  Most importantly, each value has an attached malloc
+object to hold its elements, even when there is only one such element
+(as for scalars) which could reasonably be represented by a static
+field.
+.P
+There are some comments in the code which discuss the possibility of
+a back end that would emit C.   This would be easy to do if there were
+any serious corpus of CUPL/CORC code demanding to be translated.  The
+compiler back end would emit code shaped like the parse tree, which
+would then link monitor.c as runtime support.
+.P
+The only nontrivial difference between CUPL and CORC is the interpretation
+of GO TO <label> when <label> is associated with a block.  In CUPL, this
+is a go to beginning of block; in CORC, it's go to end of block (which in
+CUPL is GO TO <block> END.  The interpreter sets a flag when it sees any
+of the appropriate CORC-specific keywords (NOTE, BEGIN, DEC, DECREASE, EQL,
+GEQ, GTR, INC, INCREASE, INT, LEQ, LSS, NEQ, REPEAT, TITLE, UNTIL, $) during
+lexing, and execute() modifies its behavior appropriately.
+