Changeset 960665c


Ignore:
Timestamp:
Aug 20, 2024, 6:15:01 PM (13 months ago)
Author:
JiadaL <j82liang@…>
Branches:
master
Children:
ad47ec4
Parents:
d1f5054 (diff), df2e00f (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' of plg.uwaterloo.ca:software/cfa/cfa-cc

Files:
12 added
29 edited

Legend:

Unmodified
Added
Removed
  • doc/theses/jiada_liang_MMath/CFAenum.tex

    rd1f5054 r960665c  
    471471        E e;
    472472
    473         for () {
    474                 try {
    475                         @sin | e@;
    476                 } catch( missing_data * ) {
    477                         sout | "missing data";
    478                         continue; // try again
     473        try {
     474                for () {
     475                        try {
     476                                @sin | e@;
     477                        } catch( missing_data * ) {
     478                                sout | "missing data";
     479                                continue; // try again
     480                        }
     481                        sout | e | "= " | value( e );
    479482                }
    480           if ( eof( sin ) ) break;
    481                 sout | e | "= " | value( e );
    482         }
     483        } catch( end_of_file ) {}
    483484}
    484485\end{cfa}
  • doc/theses/mike_brooks_MMath/array.tex

    rd1f5054 r960665c  
    205205Orthogonally, the new @array@ type works with \CFA's generic types, providing argument safety and the associated implicit communication of array length.
    206206Specifically, \CFA allows aggregate types to be generalized with multiple type parameters, including parameterized element types and lengths.
    207 Doing so gives a refinement of C's ``flexible array member'' pattern, allowing nesting structures with array members anywhere within other structures.
     207Doing so gives a refinement of C's ``flexible array member'' pattern, allowing nesting structures with array members anywhere within the structures.
    208208\lstinput{10-15}{hello-accordion.cfa}
    209 This structure's layout has the starting offset of @municipalities@ varying in @NprovTerty@, and the offset of @total_pt@ and @total_mun@ varying in both generic parameters.
    210 For a function that operates on a @CanPop@ structure, the type system handles this variation transparently.
     209This structure's layout has the starting offset of @studentIds@ varying in generic parameter @C@, and the offset of @preferences@ varying in both generic parameters.
     210For a function that operates on a @School@ structure, the type system handles this memory layout transparently.
    211211\lstinput{40-45}{hello-accordion.cfa}
    212 \VRef[Figure]{f:checkHarness} shows the @CanPop@ harness and results with different array sizes, if the municipalities changed after a census.
     212\VRef[Figure]{f:checkHarness} shows the @School@ harness and results with different array sizes, where multidimensional arrays are discussed next.
    213213
    214214\begin{figure}
    215 \lstinput{60-68}{hello-accordion.cfa}
    216 \lstinput{70-75}{hello-accordion.cfa}
    217 \caption{\lstinline{check} Harness}
     215% super hack to get this to line up
     216\begin{tabular}{@{}ll@{\hspace{25pt}}l@{}}
     217\begin{tabular}{@{}p{3.25in}@{}}
     218\lstinput{60-66}{hello-accordion.cfa}
     219\vspace*{-3pt}
     220\lstinput{73-80}{hello-accordion.cfa}
     221\end{tabular}
     222&
     223\raisebox{0.32\totalheight}{%
     224\lstinput{85-93}{hello-accordion.cfa}
     225}%
     226&
     227\lstinput{95-109}{hello-accordion.cfa}
     228\end{tabular}
     229\caption{\lstinline{school} Harness and Output}
    218230\label{f:checkHarness}
    219231\end{figure}
     
    488500From there, @x[all]@ itself is simply a two-dimensional array, in the strict C sense, of these building blocks.
    489501An atom (like the bottommost value, @x[all][3][2]@), is the contained value (in the square box)
    490 and a lie about its size (the wedge above it, growing upward).
     502and a lie about its size (the left diagonal above it, growing upward).
    491503An array of these atoms (like the intermediate @x[all][3]@) is just a contiguous arrangement of them, done according to their size;
    492504call such an array a column.
    493505A column is almost ready to be arranged into a matrix;
    494506it is the \emph{contained value} of the next-level building block, but another lie about size is required.
    495 At first, an atom needs to be arranged as if it were bigger, but now a column needs to be arranged as if it is smaller (the wedge above it, shrinking upward).
     507At first, an atom needs to be arranged as if it were bigger, but now a column needs to be arranged as if it is smaller (the left diagonal above it, shrinking upward).
    496508These lying columns, arranged contiguously according to their size (as announced) form the matrix @x[all]@.
    497509Because @x[all]@ takes indices, first for the fine stride, then for the coarse stride, it achieves the requirement of representing the transpose of @x@.
     
    502514compared with where analogous rows appear when the row-level option is presented for @x@.
    503515
    504 \PAB{I don't understand this paragraph: These size lies create an appearance of overlap.
    505 For example, in \lstinline{x[all]}, the shaded band touches atoms 2.0, 2.1, 2.2, 2.3, 1.4, 1.5 and 1.6.
     516For example, in \lstinline{x[all]}, the shaded band touches atoms 2.0, 2.1, 2.2, 2.3, 1.4, 1.5 and 1.6 (left diagonal).
    506517But only the atom 2.3 is storing its value there.
    507 The rest are lying about (conflicting) claims on this location, but never exercising these alleged claims.}
     518The rest are lying about (conflicting) claims on this location, but never exercising these alleged claims.
    508519
    509520Lying is implemented as casting.
     
    511522This structure uses one type in its internal field declaration and offers a different type as the return of its subscript operator.
    512523The field within is a plain-C array of the fictional type, which is 7 floats long for @x[all][3][2]@ and 1 float long for @x[all][3]@.
    513 The subscript operator presents what is really inside, by casting to the type below the wedge of the lie.
     524The subscript operator presents what is really inside, by casting to the type below the left diagonal of the lie.
    514525
    515526%  Does x[all] have to lie too?  The picture currently glosses over how it it advertises a size of 7 floats.  I'm leaving that as an edge case benignly misrepresented in the picture.  Edge cases only have to be handled right in the code.
  • doc/theses/mike_brooks_MMath/programs/hello-accordion.cfa

    rd1f5054 r960665c  
    88
    99
    10 forall( T, @[NprovTerty]@, @[Nmunicipalities]@ )
    11 struct CanPop {
    12         array( T, @NprovTerty@ ) provTerty; $\C{// nested VLA}$
    13         array( T, @Nmunicipalities@ ) municipalities; $\C{// nested VLA}$
    14         int total_pt, total_mun;
     10forall( [C], [S] ) $\C{// Class size, Students in class}$
     11struct School {
     12        @array( int, C )@ classIds; $\C{// nested VLAs}$
     13        @array( int, S )@ studentIds;
     14        @array( int, C, S )@ preferences; $\C{// multidimensional}$
    1515};
     16
    1617
    1718
    1819// TODO: understand (fix?) why these are needed (autogen seems to be failing ... is typeof as struct member nayok?)
    1920
    20 forall( T, [NprovTerty], [Nmunicipalities] )
    21         void ?{}( T &, CanPop( T, NprovTerty, Nmunicipalities ) & this ) {}
     21forall( [C], [S] )
     22void ?{}( School( C, S ) & this ) {}
    2223
    23 forall( T &, [NprovTerty], [Nmunicipalities] )
    24         void ^?{}( CanPop( T, NprovTerty, Nmunicipalities ) & this ) {}
     24forall( [C], [S] )
     25        void ^?{}( School( C, S ) & this ) {}
    2526
    2627
     
    3738
    3839
    39 
    40 forall( T, [NprovTerty], [Nmunicipalities] )
    41 void check( CanPop( T, NprovTerty, Nmunicipalities ) & pop ) with( pop ) {
    42         total_pt = total_mun = 0;
    43         for ( i; NprovTerty ) total_pt += provTerty[i];
    44         for ( i; Nmunicipalities ) total_mun += municipalities[i];
     40forall( [C], [S] )
     41void init( @School( C, S ) & classes@, int class, int student, int pref ) with( classes ) {
     42        classIds[class] = class; $\C{// handle dynamic offsets of fields within structure}$
     43        studentIds[student] = student;
     44        preferences[class][student] = pref;
    4545}
    4646
     
    5858
    5959
    60 int main( int argc, char * argv[] ) {
    61         const int npt = ato( argv[1] ), nmun = ato( argv[2] );
    62         @CanPop( int, npt, nmun ) pop;@
    63         // read in population numbers
    64         @check( pop );@
    65         sout | setlocale( LC_NUMERIC, getenv( "LANG" ) );
    66         sout | "Total province/territory:" | pop.total_pt;
    67         sout | "Total municipalities:" | pop.total_mun;
     60int main() {
     61        int classes, students;
     62        sin | classes | students;
     63        @School( classes, students ) school;@
     64        int class, student, preference;
     65        // read data into school calling init
     66        // for each student's class/preferences
     67        try {
     68                for ( ) {
     69                        sin | class | student | preference;
     70                        init( school, class, student, preference );
     71                }
     72        } catch( end_of_file * ) {}
     73        for ( s; students ) {
     74                sout | "student" | s | nonl;
     75                for ( c; classes ) {
     76                        sout | school.preferences[c][s] | nonl;
     77                }
     78                sout | nl;
     79        }
    6880}
     81
     82
     83
    6984/*
    70 $\$$ ./a.out  13  3573
    71 Total province/territory: 36,991,981
    72 Total municipalities: 36,991,981
    73 $\$$ ./a.out  13  3654
    74 Total province/territory: 36,991,981
    75 Total municipalities: 36,991,981
     85$\$$ cat school1
     862 2
     870 0 1
     881 0 7
     890 1 12
     901 1 13
     91$\$$ a.out < school1
     92student 0 1 7
     93student 1 12 13
     94
     95$\$$ cat school2
     963 3
     970 0 1
     981 0 7
     992 0 8
     1000 1 12
     1011 1 13
     1022 1 14
     1030 2 26
     1041 2 27
     1052 2 28
     106$\$$ a.out < school2
     107student 0 1 7 8
     108student 1 12 13 14
     109student 2 26 27 28
    76110*/
    77111
  • doc/theses/mike_brooks_MMath/string.tex

    rd1f5054 r960665c  
    11\chapter{String}
    22
    3 
    4 
    5 
    6 
    7 \subsection{Logical overlap}
     3This chapter presents my work on designing and building a modern string type in \CFA.
     4The discussion starts with examples of interesting string problems, followed by examples of how these issues are solved in my design.
     5
     6
     7\section{Logical overlap}
    88
    99\input{sharing-demo.tex}
     
    2020\subsection{RAII limitations}
    2121
    22 Earlier work on \CFA [to cite Schluntz] implemented the feature of constructors and destructors.  A constructor is a user-defined function that runs implicitly, when control passes an object's declaration, while a destructor runs at the exit of the declaration's lexical scope.  The feature allows programmers to assume that, whenever a runtime object of a certain type is accessible, the system called one of the programmer's constuctor functions on that object, and a matching destructor call will happen in the future.  The feature helps programmers know that their programs' invariants obtain.
    23 
    24 The purposes of such invariants go beyond ensuring authentic values for the bits inside the object.   These invariants can track occurrences of the managed objects in other data structures.  Reference counting is a typical application of the latter invariant type.  With a reference-counting smart pointer, the consturctor and destructor \emph{of the pointer type} track the lifecycles of occurrences of these pointers, by incrementing and decrementing a counter (ususally) on the referent object, that is, they maintain a that is state separate from the objects to whose lifecycles they are attached.  Both the \CC and \CFA RAII systems ares powerful enough to achive such reference counting.
    25 
    26 The \CC RAII system supports a more advanced application.  A lifecycle function has access to the object under managamanet, by location; constructors and destuctors receive a @this@ parameter providing its memory address.  A lifecycle-function implementation can then add its objects to a collection upon creation, and remove them at destruction.  A modulue that provides such objects, by using and encapsulating such a collection, can traverse the collection at relevant times, to keep the objects ``good.''  Then, if you are the user of such an module, declaring an object of its type means not only receiving an authentically ``good'' value at initialization, but receiving a subscription to a service that will keep the value ``good'' until you are done with it.
     22Earlier work on \CFA [to cite Schluntz] implemented the feature of constructors and destructors.  A constructor is a user-defined function that runs implicitly, when control passes an object's declaration, while a destructor runs at the exit of the declaration's lexical scope.  The feature allows programmers to assume that, whenever a runtime object of a certain type is accessible, the system called one of the programmer's constructor functions on that object, and a matching destructor call will happen in the future.  The feature helps programmers know that their programs' invariants obtain.
     23
     24The purposes of such invariants go beyond ensuring authentic values for the bits inside the object.   These invariants can track occurrences of the managed objects in other data structures.  Reference counting is a typical application of the latter invariant type.  With a reference-counting smart pointer, the constructor and destructor \emph{of the pointer type} track the life cycles of occurrences of these pointers, by incrementing and decrementing a counter (usually) on the referent object, that is, they maintain a that is state separate from the objects to whose life cycles they are attached.  Both the \CC and \CFA RAII systems ares powerful enough to achieve such reference counting.
     25
     26The \CC RAII system supports a more advanced application.  A life cycle function has access to the object under management, by location; constructors and destuctors receive a @this@ parameter providing its memory address.  A lifecycle-function implementation can then add its objects to a collection upon creation, and remove them at destruction.  A modulue that provides such objects, by using and encapsulating such a collection, can traverse the collection at relevant times, to keep the objects ``good.''  Then, if you are the user of such an module, declaring an object of its type means not only receiving an authentically ``good'' value at initialization, but receiving a subscription to a service that will keep the value ``good'' until you are done with it.
    2727
    2828In many cases, the relationship between memory location and lifecycle is simple.  But with stack-allocated objects being used as parameters and returns, there is a sender version in one stack frame and a receiver version in another.  \CC is able to treat those versions as distinct objects and guarantee a copy-constructor call for communicating the value from one to the other.  This ability has implications on the language's calling convention.  Consider an ordinary function @void f( Vehicle x )@, which receives an aggregate by value.  If the type @Vehicle@ has custom lifecycle functions, then a call to a user-provided copy constructor occurs, after the caller evaluates its argument expression, after the callee's stack frame exists, with room for its variable @x@ (which is the location that the copy-constructor must target), but before the user-provided body of @f@ begins executing.  \CC achieves this ordering by changing the function signature, in the compiled form, to pass-by-reference and having the callee invoke the copy constructor in its preamble.  On the other hand, if @Vehicle@ is a simple structure then the C calling convention is applied as the code originally appeared, that is, the callsite implementation code performs a bitwise copy from the caller's expression result, into the callee's x.
  • doc/user/user.tex

    rd1f5054 r960665c  
    1111%% Created On       : Wed Apr  6 14:53:29 2016
    1212%% Last Modified By : Peter A. Buhr
    13 %% Last Modified On : Fri Jul 26 06:56:11 2024
    14 %% Update Count     : 6955
     13%% Last Modified On : Thu Aug 15 22:23:30 2024
     14%% Update Count     : 6957
    1515%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    1616
     
    46564656\VRef[Figure]{f:CFACommand-LineProcessing} demonstrates the file operations by showing the idiomatic \CFA command-line processing and copying an input file to an output file.
    46574657Note, a stream variable may be copied because it is a reference to an underlying stream data-structures.
    4658 \Textbf{All I/O errors are handled as exceptions}, but end-of-file is not an exception as C programmers are use to explicitly checking for it.
     4658\Textbf{All unusual I/O cases are handled as exceptions, including end-of-file.}
    46594659
    46604660\begin{figure}
     
    46864686        in | nlOn;                                                              §\C{// turn on reading newline}§
    46874687        char ch;
    4688         for () {                                                                §\C{// read/write characters}§
    4689                 in | ch;
    4690           if ( eof( in ) ) break;                               §\C{// eof ?}§
    4691                 out | ch;
    4692         } // for
     4688        try {
     4689                for () {                                                        §\C{// read/write characters}§
     4690                        in | ch;
     4691                        out | ch;
     4692                } // for
     4693        } catch( end_of_file * ) {                              §\C{// end-of-file raised}§
     4694        } // try
    46934695} // main
    46944696\end{cfa}
  • libcfa/src/collections/string_res.cfa

    rd1f5054 r960665c  
    1010// Created On       : Fri Sep 03 11:00:00 2021
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Mon Apr 15 21:56:27 2024
    13 // Update Count     : 85
     12// Last Modified On : Sat Aug 17 14:08:01 2024
     13// Update Count     : 86
    1414//
    1515
     
    251251
    252252ifstream & ?|?( ifstream & is, _Istream_Rquoted f ) with( f.rstr ) {
    253         if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     253        if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    254254        int args;
    255255  fini: {
  • libcfa/src/enum.cfa

    rd1f5054 r960665c  
    4040istype & ?|?( istype & is, E & e ) {
    4141//      fprintf( stderr, "here0\n" );
    42         if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     42        if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    4343
    4444        // Match longest input enumerator string to enumerator labels, where enumerator names are unique.
     
    5959
    6060        fmt( is, " " );                                                                         // skip optional whitespace
     61        if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
     62
    6163        for ( c; max ) {                                                                        // scan columns of the label matix (some columns missing)
    6264                int args = fmt( is, "%c", &ch );                                // read character
  • libcfa/src/heap.cfa

    rd1f5054 r960665c  
    354354};
    355355
    356 static_assert( NoBucketSizes == sizeof(bucketSizes) / sizeof(bucketSizes[0] ), "size of bucket array wrong" );
     356static_assert( sizeof(bucketSizes) == NoBucketSizes * sizeof(unsigned int), "size of bucket array wrong" );
    357357
    358358
  • libcfa/src/iostream.cfa

    rd1f5054 r960665c  
    1010// Created On       : Wed May 27 17:56:53 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Aug  2 07:38:44 2024
    13 // Update Count     : 2021
     12// Last Modified On : Sat Aug 17 12:31:47 2024
     13// Update Count     : 2038
    1414//
    1515
     
    777777forall( istype & | basic_istream( istype ) ) {
    778778        istype & ?|?( istype & is, bool & b ) {
    779                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     779                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    780780                int len = -1;                                                                   // len not set if no match
    781                 // Optional leading whitespace at start of strings.
     781                // remove optional leading whitespace at start of strings.
    782782                fmt( is, " " FALSE "%n", &len );                                // try false
    783783                if ( len != sizeof( FALSE ) - 1 ) {                             // -1 removes null terminate
     
    792792
    793793        istype & ?|?( istype & is, char & c ) {
    794                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     794                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    795795                char temp;
    796796                for () {
    797797                        int args = fmt( is, "%c", &temp );
    798                         if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     798                        if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
     799                        assert( args == 1 );                                            // if not EOF => a single character must be read
    799800                        // do not overwrite parameter with newline unless appropriate
    800801                        if ( temp != '\n' || getANL$( is ) ) { c = temp; break; }
    801                         if ( eof( is ) ) break;
    802802                } // for
    803803                return is;
     
    805805
    806806        istype & ?|?( istype & is, signed char & sc ) {
    807                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
    808                 int args = fmt( is, "%hhi", &sc );
    809                 if ( args != 1 ) throwResume ExceptionInst( missing_data );
     807                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
     808                int args = fmt( is, "%hhi", &sc );                              // can be multiple characters (100)
     809                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
    810810                return is;
    811811        } // ?|?
    812812
    813813        istype & ?|?( istype & is, unsigned char & usc ) {
    814                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
    815                 int args = fmt( is, "%hhi", &usc );
     814                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
     815                int args = fmt( is, "%hhi", &usc );                             // can be multiple characters (-100)
    816816                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
    817817                return is;
     
    819819
    820820        istype & ?|?( istype & is, short int & si ) {
    821                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     821                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    822822                int args = fmt( is, "%hi", &si );
    823823                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    826826
    827827        istype & ?|?( istype & is, unsigned short int & usi ) {
    828                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     828                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    829829                int args = fmt( is, "%hi", &usi );
    830830                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    833833
    834834        istype & ?|?( istype & is, int & i ) {
    835                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     835                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    836836                int args = fmt( is, "%i", &i );
    837837                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    840840
    841841        istype & ?|?( istype & is, unsigned int & ui ) {
    842                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     842                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    843843                int args = fmt( is, "%i", &ui );
    844844                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    847847
    848848        istype & ?|?( istype & is, long int & li ) {
    849                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     849                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    850850                int args = fmt( is, "%li", &li );
    851851                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    854854
    855855        istype & ?|?( istype & is, unsigned long int & ulli ) {
    856                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     856                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    857857                int args = fmt( is, "%li", &ulli );
    858858                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    861861
    862862        istype & ?|?( istype & is, long long int & lli ) {
    863                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     863                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    864864                int args = fmt( is, "%lli", &lli );
    865865                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    868868
    869869        istype & ?|?( istype & is, unsigned long long int & ulli ) {
    870                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     870                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    871871                int args = fmt( is, "%lli", &ulli );
    872872                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    891891                        } // for
    892892                        if ( sign ) ullli = -ullli;
    893                 } else if ( sign ) ungetc( '-', is );                   // return minus when no digits
     893                } // if
    894894                return is;
    895895        } // ?|?
     
    897897
    898898        istype & ?|?( istype & is, float & f ) {
    899                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     899                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    900900                int args = fmt( is, "%f", &f );
    901901                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    904904
    905905        istype & ?|?( istype & is, double & d ) {
    906                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     906                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    907907                int args = fmt( is, "%lf", &d );
    908908                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    911911
    912912        istype & ?|?( istype & is, long double & ld ) {
    913                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     913                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    914914                int args = fmt( is, "%Lf", &ld );
    915915                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
     
    918918
    919919        istype & ?|?( istype & is, float _Complex & fc ) {
    920                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     920                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    921921                float re, im;
    922922                int args = fmt( is, "%f%fi", &re, &im );
     
    927927
    928928        istype & ?|?( istype & is, double _Complex & dc ) {
    929                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     929                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    930930                double re, im;
    931931                int args = fmt( is, "%lf%lfi", &re, &im );
     
    936936
    937937        istype & ?|?( istype & is, long double _Complex & ldc ) {
    938                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     938                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    939939                long double re, im;
    940940                int args = fmt( is, "%Lf%Lfi", &re, &im );
     
    945945
    946946        istype & ?|?( istype & is, const char fmt[] ) {         // match text
    947                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     947                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    948948                size_t len = strlen( fmt );
    949949                char fmtstr[len + 16];
     
    953953                // scanf cursor does not move if no match
    954954                fmt( is, fmtstr, &len );
    955                 if ( ! eof( is ) && len == -1 ) throwResume ExceptionInst( missing_data );
     955                if ( len == -1 ) throwResume ExceptionInst( missing_data );
    956956                return is;
    957957        } // ?|?
     
    987987forall( istype & | basic_istream( istype ) ) {
    988988        istype & ?|?( istype & is, _Istream_Cskip f ) {
    989                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     989                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    990990                if ( f.scanset ) {
    991991                        int nscanset = strlen(f.scanset);
     
    10001000                        for ( f.wd ) {                                                          // skip N characters
    10011001                                int args = fmt( is, "%c", &ch );
    1002                                 if ( args != 1 ) throwResume ExceptionInst( missing_data );
     1002                                if ( ! eof( is ) && args != 1 ) throwResume ExceptionInst( missing_data );
    10031003                        } // for
    10041004                } // if
     
    10071007
    10081008        istype & ?|?( istype & is, _Istream_Cquoted f ) with( f.cstr ) {
    1009                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     1009                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    10101010                int args;
    10111011          fini: {
     
    10321032
    10331033        istype & ?|?( istype & is, _Istream_Cstr f ) with( f.cstr ) {
    1034                 if ( eof( is ) ) throwResume ExceptionInst( missing_data );
     1034                if ( eof( is ) ) throwResume ExceptionInst( end_of_file );
    10351035                const char * scanset;
    10361036                size_t nscanset = 0;
  • libcfa/src/iostream.hfa

    rd1f5054 r960665c  
    1010// Created On       : Wed May 27 17:56:53 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Aug  2 07:37:57 2024
    13 // Update Count     : 760
     12// Last Modified On : Thu Aug 15 18:21:22 2024
     13// Update Count     : 761
    1414//
    1515
     
    374374// *********************************** exceptions ***********************************
    375375
     376ExceptionDecl( end_of_file );                                                   // read encounters end of file
    376377ExceptionDecl( missing_data );                                                  // read finds no appropriate data
    377378ExceptionDecl( cstring_length );                                                // character string size exceeded
  • libcfa/src/parseconfig.cfa

    rd1f5054 r960665c  
    105105
    106106static [ bool ] comments( & ifstream in, size_t size, [] char name ) {
    107         while () {
    108                 in | wdi( size, name );
    109           if ( eof( in ) ) return true;
    110           if ( name[0] != '#' ) return false;
    111                 in | nl;                                                                                // ignore remainder of line
    112         } // while
     107        bool comment = false;
     108        try {
     109                while () {
     110                        in | wdi( size, name );
     111                        if ( name[0] != '#' ) break;
     112                        in | nl;                                                                        // ignore remainder of line
     113                } // while
     114        } catch( end_of_file * ) {
     115                comment = true;
     116        } // try
     117        return comment;
    113118} // comments
    114119
     
    125130                [256] char value;
    126131
    127                 while () {                                                                              // parameter names can appear in any order
    128                         // NOTE: Must add check to see if already read in value for this key,
    129                         // once we switch to using hash table as intermediate storage
    130                   if ( comments( in, 64, key ) ) break;                 // eof ?
    131                         in | wdi( 256, value );
    132 
    133                         add_kv_pair( *kv_pairs, key, value );
    134 
    135                   if ( eof( in ) ) break;
    136                         in | nl;                                                                        // ignore remainder of line
    137                 } // for
     132                try {
     133                        while () {                                                                              // parameter names can appear in any order
     134                                // NOTE: Must add check to see if already read in value for this key,
     135                                // once we switch to using hash table as intermediate storage
     136                                if ( comments( in, 64, key ) ) break;                   // eof ?
     137                                in | wdi( 256, value );
     138
     139                                add_kv_pair( *kv_pairs, key, value );
     140
     141                                in | nl;                                                                        // ignore remainder of line
     142                        } // while
     143                } catch( end_of_file * ) {
     144                } // try
    138145        } catch( open_failure * ex; ex->istream == &in ) {
    139146                delete( kv_pairs );
  • src/GenPoly/GenPoly.cpp

    rd1f5054 r960665c  
    2727#include "AST/Type.hpp"
    2828#include "AST/TypeSubstitution.hpp"
     29#include "Common/Eval.hpp"                // for eval
    2930#include "GenPoly/ErasableScopedMap.hpp"  // for ErasableScopedMap<>::const_...
    3031#include "ResolvExpr/Typeops.hpp"         // for flatten
     
    243244} // namespace
    244245
     246// This function, and its helpers following, have logic duplicated from
     247// unification.  The difference in context is that unification applies where
     248// the types "must" match, while this variation applies to arbitrary type
     249// pairs, when an optimization could apply if they happen to match.  This
     250// variation does not bind type variables.  The helper functions support
     251// the case for matching ArrayType.
     252bool typesPolyCompatible( ast::Type const * lhs, ast::Type const * rhs );
     253
     254static bool exprsPolyCompatibleByStaticValue(
     255                const ast::Expr * e1, const ast::Expr * e2 ) {
     256        Evaluation r1 = eval(e1);
     257        Evaluation r2 = eval(e2);
     258
     259        if ( !r1.hasKnownValue ) return false;
     260        if ( !r2.hasKnownValue ) return false;
     261
     262        if ( r1.knownValue != r2.knownValue ) return false;
     263
     264        return true;
     265}
     266
     267static bool exprsPolyCompatible( ast::Expr const * lhs,
     268                ast::Expr const * rhs ) {
     269        type_index const lid = typeid(*lhs);
     270        type_index const rid = typeid(*rhs);
     271        if ( lid != rid ) return false;
     272
     273        if ( exprsPolyCompatibleByStaticValue( lhs, rhs ) ) return true;
     274
     275        if ( type_index(typeid(ast::CastExpr)) == lid ) {
     276                ast::CastExpr const * l = as<ast::CastExpr>(lhs);
     277                ast::CastExpr const * r = as<ast::CastExpr>(rhs);
     278
     279                // inspect casts' target types
     280                if ( !typesPolyCompatible(
     281                        l->result, r->result ) ) return false;
     282
     283                // inspect casts' inner expressions
     284                return exprsPolyCompatible( l->arg, r->arg );
     285
     286        } else if ( type_index(typeid(ast::VariableExpr)) == lid ) {
     287                ast::VariableExpr const * l = as<ast::VariableExpr>(lhs);
     288                ast::VariableExpr const * r = as<ast::VariableExpr>(rhs);
     289
     290                assert(l->var);
     291                assert(r->var);
     292
     293                // conservative: variable exprs match if their declarations are
     294                // represented by the same C++ AST object
     295                return (l->var == r->var);
     296
     297        } else if ( type_index(typeid(ast::SizeofExpr)) == lid ) {
     298                ast::SizeofExpr const * l = as<ast::SizeofExpr>(lhs);
     299                ast::SizeofExpr const * r = as<ast::SizeofExpr>(rhs);
     300
     301                assert((l->type != nullptr) ^ (l->expr != nullptr));
     302                assert((r->type != nullptr) ^ (r->expr != nullptr));
     303                if ( !(l->type && r->type) ) return false;
     304
     305                // mutual recursion with type poly compatibility
     306                return typesPolyCompatible( l->type, r->type );
     307
     308        } else {
     309                // All other forms compare on static value only, done earlier
     310                return false;
     311        }
     312}
     313
    245314bool typesPolyCompatible( ast::Type const * lhs, ast::Type const * rhs ) {
    246315        type_index const lid = typeid(*lhs);
     
    256325
    257326        // So remaining types can be examined case by case.
    258         // Recurse through type structure (conditions borrowed from Unify.cpp).
     327        // Recurse through type structure (conditions duplicated from Unify.cpp).
    259328
    260329        if ( type_index(typeid(ast::BasicType)) == lid ) {
     
    280349                ast::ArrayType const * r = as<ast::ArrayType>(rhs);
    281350
    282                 if ( l->isVarLen ) {
    283                         if ( !r->isVarLen ) return false;
    284                 } else {
    285                         if ( r->isVarLen ) return false;
    286 
    287                         auto lc = l->dimension.as<ast::ConstantExpr>();
    288                         auto rc = r->dimension.as<ast::ConstantExpr>();
    289                         if ( lc && rc && lc->intValue() != rc->intValue() ) {
     351                if ( l->isVarLen != r->isVarLen ) return false;
     352                if ( (l->dimension != nullptr) != (r->dimension != nullptr) )
     353                        return false;
     354
     355                if ( l->dimension ) {
     356                        assert( r->dimension );
     357                        // mutual recursion with expression poly compatibility
     358                        if ( !exprsPolyCompatible(l->dimension, r->dimension) )
    290359                                return false;
    291                         }
    292360                }
    293361
  • src/Parser/DeclarationNode.cpp

    rd1f5054 r960665c  
    999999        assert( type );
    10001000
     1001        // Some types are parsed as declarations and, syntactically, can have
     1002        // initializers. However, semantically, this is meaningless.
     1003        if ( initializer ) {
     1004                SemanticError( this, "Initializer on type declaration " );
     1005        }
     1006
    10011007        switch ( type->kind ) {
    10021008        case TypeData::Aggregate: {
  • src/ResolvExpr/CandidateFinder.cpp

    rd1f5054 r960665c  
    12411241                Cost minCastCost = Cost::infinity;
    12421242                for ( CandidateRef & cand : finder.candidates ) {
     1243                        ast::ptr< ast::Type > fromType = cand->expr->result;
     1244                        assert( fromType );
     1245                        fromType = resolveTypeof( fromType, context );
     1246                        fromType = adjustExprType( fromType, tenv, symtab );
     1247
    12431248                        ast::AssertionSet need( cand->need.begin(), cand->need.end() ), have;
    12441249                        ast::OpenVarSet open( cand->open );
     
    12501255                        // subexpression results that are cast directly. The candidate is invalid if it
    12511256                        // has fewer results than there are types to cast to.
    1252                         int discardedValues = cand->expr->result->size() - toType->size();
     1257                        int discardedValues = fromType->size() - toType->size();
    12531258                        if ( discardedValues < 0 ) continue;
    12541259
    12551260                        // unification run for side-effects
    1256                         unify( toType, cand->expr->result, cand->env, need, have, open );
     1261                        unify( toType, fromType, cand->env, need, have, open );
    12571262                        Cost thisCost =
    12581263                                (castExpr->isGenerated == ast::GeneratedFlag::GeneratedCast)
    1259                                         ? conversionCost( cand->expr->result, toType, cand->expr->get_lvalue(), symtab, cand->env )
    1260                                         : castCost( cand->expr->result, toType, cand->expr->get_lvalue(), symtab, cand->env );
     1264                                        ? conversionCost( fromType, toType, cand->expr->get_lvalue(), symtab, cand->env )
     1265                                        : castCost( fromType, toType, cand->expr->get_lvalue(), symtab, cand->env );
    12611266                       
    12621267                        // Redefine enum cast
    1263                         auto argAsEnum = cand->expr->result.as<ast::EnumInstType>();
     1268                        auto argAsEnum = fromType.as<ast::EnumInstType>();
    12641269                        auto toAsEnum = toType.as<ast::EnumInstType>();
    12651270                        if ( argAsEnum && toAsEnum && argAsEnum->name != toAsEnum->name ) {
     
    12721277                        PRINT(
    12731278                                std::cerr << "working on cast with result: " << toType << std::endl;
    1274                                 std::cerr << "and expr type: " << cand->expr->result << std::endl;
     1279                                std::cerr << "and expr type: " << fromType << std::endl;
    12751280                                std::cerr << "env: " << cand->env << std::endl;
    12761281                        )
  • tests/.expect/copyfile.txt

    rd1f5054 r960665c  
    1010// Created On       : Fri Jun 19 13:44:05 2020
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Mon Jun  5 21:20:07 2023
    13 // Update Count     : 5
     12// Last Modified On : Sat Aug 17 14:18:47 2024
     13// Update Count     : 11
    1414//
    1515
     
    2222
    2323        try {
    24                 choose ( argc ) {
    25                   case 2, 3:
     24                choose ( argc ) {                                                               // terminate if command-line errors
     25                  case 3, 2:
    2626                        open( in, argv[1] );                                            // open input file first as output creates file
    2727                        if ( argc == 3 ) open( out, argv[2] );          // do not create output unless input opens
    2828                  case 1: ;                                                                             // use default files
    29                   default:
     29                  default:                                                                              // wrong number of options
    3030                        exit | "Usage" | argv[0] | "[ input-file (default stdin) [ output-file (default stdout) ] ]";
    3131                } // choose
     
    4141
    4242        char ch;
    43         for () {                                                                                        // read all characters
    44                 in | ch;
    45           if ( eof( in ) ) break;                                                       // eof ?
    46                 out | ch;
    47         } //for
     43        try {
     44                for () {                                                                                // read all characters
     45                        in | ch;
     46                        out | ch;
     47                } // for
     48        } catch( end_of_file * ) {
     49        } // try
    4850} // main
    49 
    50 // Local Variables: //
    51 // tab-width: 4 //
    52 // compile-command: "cfa copyfile.cfa" //
    53 // End: //
  • tests/.in/copyfile.txt

    rd1f5054 r960665c  
    1010// Created On       : Fri Jun 19 13:44:05 2020
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Mon Jun  5 21:20:07 2023
    13 // Update Count     : 5
     12// Last Modified On : Sat Aug 17 14:18:47 2024
     13// Update Count     : 11
    1414//
    1515
     
    2222
    2323        try {
    24                 choose ( argc ) {
    25                   case 2, 3:
     24                choose ( argc ) {                                                               // terminate if command-line errors
     25                  case 3, 2:
    2626                        open( in, argv[1] );                                            // open input file first as output creates file
    2727                        if ( argc == 3 ) open( out, argv[2] );          // do not create output unless input opens
    2828                  case 1: ;                                                                             // use default files
    29                   default:
     29                  default:                                                                              // wrong number of options
    3030                        exit | "Usage" | argv[0] | "[ input-file (default stdin) [ output-file (default stdout) ] ]";
    3131                } // choose
     
    4141
    4242        char ch;
    43         for () {                                                                                        // read all characters
    44                 in | ch;
    45           if ( eof( in ) ) break;                                                       // eof ?
    46                 out | ch;
    47         } //for
     43        try {
     44                for () {                                                                                // read all characters
     45                        in | ch;
     46                        out | ch;
     47                } // for
     48        } catch( end_of_file * ) {
     49        } // try
    4850} // main
    49 
    50 // Local Variables: //
    51 // tab-width: 4 //
    52 // compile-command: "cfa copyfile.cfa" //
    53 // End: //
  • tests/Makefile.am

    rd1f5054 r960665c  
    210210CFACOMPILE_SYNTAX = ${CFACOMPILETEST} -Wno-unused-variable -Wno-unused-label -c -fsyntax-only -o ${abspath ${@}}
    211211
    212 SYNTAX_ONLY_CODE = expression typedefRedef variableDeclarator switch numericConstants identFuncDeclarator \
    213         init1 limits nested-types cast ctrl-flow/labelledExit array quasiKeyword include/stdincludes include/includes builtins/sync warnings/self-assignment concurrency/waitfor/parse
     212SYNTAX_ONLY_CODE = \
     213        array cast expression identFuncDeclarator init1 limits nested-types numericConstants opt-params quasiKeyword switch typedefRedef variableDeclarator \
     214        builtins/sync concurrency/waitfor/parse ctrl-flow/labelledExit include/stdincludes include/includes warnings/self-assignment
     215
    214216${SYNTAX_ONLY_CODE} : % : %.cfa ${CFACCBIN}
    215217        ${CFACOMPILE_SYNTAX}
  • tests/array-collections/dimexpr-match.hfa

    rd1f5054 r960665c  
    1515//
    1616//      compiler=gcc -x c           # pick one
    17 //      compiler=$fa
     17//      compiler=$cfa
    1818//
    1919//      test=dimexpr-match-c.cfa    # pick one
  • tests/concurrency/examples/quickSort.cfa

    rd1f5054 r960665c  
    1111// Created On       : Wed Dec  6 12:15:52 2017
    1212// Last Modified By : Peter A. Buhr
    13 // Last Modified On : Mon Jan  1 12:07:59 2024
    14 // Update Count     : 188
     13// Last Modified On : Sat Aug 17 13:59:15 2024
     14// Update Count     : 199
    1515//
    1616
     
    145145
    146146        if ( size == -1 ) {                                                                     // generate output ?
    147                 for () {
    148                         unsortedfile | size;                                            // read number of elements in the list
    149                   if ( eof( unsortedfile ) ) break;
    150 
    151                         int * values = aalloc( size );                          // values to be sorted, too large to put on stack
    152                         for ( counter; size ) {                                         // read unsorted numbers
    153                                 unsortedfile | values[counter];
    154                                 if ( counter != 0 && counter % ValuesPerLine == 0 ) sortedfile | nl | "  ";
    155                                 sortedfile | values[counter];
    156                                 if ( counter < size - 1 && (counter + 1) % ValuesPerLine != 0 ) sortedfile | ' ';
     147                int * values = 0p;
     148                try {
     149                        for () {
     150                                unsortedfile | size;                                    // read number of elements in the list
     151                                values = aalloc( size );                                // values to be sorted, too large to put on stack
     152                                for ( counter; size ) {                                 // read unsorted numbers
     153                                        unsortedfile | values[counter];
     154                                        if ( counter != 0 && counter % ValuesPerLine == 0 ) sortedfile | nl | "  ";
     155                                        sortedfile | values[counter];
     156                                        if ( counter < size - 1 && (counter + 1) % ValuesPerLine != 0 ) sortedfile | ' ';
     157                                } // for
     158                                sortedfile | nl;
     159
     160                                if ( size > 0 ) {                                               // values to sort ?
     161                                        Quicksort QS = { values, size - 1, 0 }; // sort values
     162                                } // wait until sort tasks terminate
     163                                for ( counter; size ) {                                 // print sorted list
     164                                        if ( counter != 0 && counter % ValuesPerLine == 0 ) sortedfile | nl | "  ";
     165                                        sortedfile | values[counter];
     166                                        if ( counter < size - 1 && (counter + 1) % ValuesPerLine != 0 ) sortedfile | ' ';
     167                                } // for
     168                                sortedfile | nl | nl;
     169
     170                                delete( values );
     171                                values = 0p;
    157172                        } // for
    158                         sortedfile | nl;
    159 
    160                         if ( size > 0 ) {                                                       // values to sort ?
    161                                 Quicksort QS = { values, size - 1, 0 }; // sort values
    162                         } // wait until sort tasks terminate
    163                         for ( counter; size ) {                                         // print sorted list
    164                                 if ( counter != 0 && counter % ValuesPerLine == 0 ) sortedfile | nl | "  ";
    165                                 sortedfile | values[counter];
    166                                 if ( counter < size - 1 && (counter + 1) % ValuesPerLine != 0 ) sortedfile | ' ';
    167                         } // for
    168                         sortedfile | nl | nl;
    169 
     173                } catch( end_of_file * ) {
    170174                        delete( values );
    171                 } // for
     175                } // try
    172176        } else {                                                                                        // timing
    173177                PRNG prng;                                                                             
  • tests/copyfile.cfa

    rd1f5054 r960665c  
    1010// Created On       : Fri Jun 19 13:44:05 2020
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Mon Jun  5 21:20:19 2023
    13 // Update Count     : 7
     12// Last Modified On : Sat Aug 17 14:18:47 2024
     13// Update Count     : 11
    1414//
    1515
     
    2323        try {
    2424                choose ( argc ) {                                                               // terminate if command-line errors
    25                   case 2, 3:
     25                  case 3, 2:
    2626                        open( in, argv[1] );                                            // open input file first as output creates file
    2727                        if ( argc == 3 ) open( out, argv[2] );          // do not create output unless input opens
     
    4141
    4242        char ch;
    43         for () {                                                                                        // read all characters
    44                 in | ch;
    45           if ( eof( in ) ) break;                                                       // eof ?
    46                 out | ch;
    47         } // for
     43        try {
     44                for () {                                                                                // read all characters
     45                        in | ch;
     46                        out | ch;
     47                } // for
     48        } catch( end_of_file * ) {
     49        } // try
    4850} // main
    49 
    50 // Local Variables: //
    51 // tab-width: 4 //
    52 // compile-command: "cfa copyfile.cfa" //
    53 // End: //
  • tests/coroutine/.expect/fmtLines.txt

    rd1f5054 r960665c  
    99E" d  istr  ibut  ed w  ith   
    1010Cfor  all.  ////   fmt  Line 
    11 s.cc   --/  ///   Auth  or   
    12              : P  eter   A.   
    13 Buhr  // C  reat  ed O  n     
    14       : Su  n Se  p 17   21: 
    15 56:1  5 20  17//   Las  t Mo 
    16 difi  ed B  y :   Pete  r A. 
    17  Buh  r//   Last   Mod  ifie 
    18 d On   : F  ri M  ar 2  2 13 
    19 :41:  03 2  019/  / Up  date 
    20  Cou  nt       :   33/  /#in 
    21 clud  e <f  stre  am.h  fa># 
    22 incl  ude   <cor  outi  ne.h 
    23 fa>c  orou  tine   For  mat   
    24 {       ch  ar c  h;                                                                             
    25         //   used   for   com  muni 
    26 cati  on        i  nt g  , b;                             
    27                                                         /  / gl  obal   bec 
    28 ause   use  d in   des  truc 
    29 tor}  ;voi  d ?{  }( F  orma 
    30 t &   fmt   ) {      r  esum 
    31 e( f  mt )  ;                                                                           / 
    32 / st  art   coro  utin  e}vo 
    33 id ^  ?{}(   For  mat   & fm 
    34 t )   {      if   ( fm  t.g   
    35 != 0   ||   fmt.  b !=   0 ) 
    36  sou  t |   nl;}  void   mai 
    37 n( F  orma  t &   fmt   ) {       
    38 for   ( ;;   ) {                                                                 
    39                 //   for   as   many   cha 
    40 ract  ers               for   ( f  mt.g 
    41  = 0  ; fm  t.g   < 5;   fmt 
    42 .g +  = 1   ) {         //   grou 
     11s.cc   --   form  at c  hara 
     12cter  s in  to b  lock  s of 
     13 4 a  nd g  roup  s of   5 b 
     14lock  s pe  r li  ne//  // A 
     15utho  r                 : Pe 
     16ter   A. B  uhr/  / Cr  eate 
     17d On           :   Sun   Sep 
     18 17   21:5  6:15   201  7//   
     19Last   Mod  ifie  d By   : P 
     20eter   A.   Buhr  // L  ast   
     21Modi  fied   On   : Sa  t Au 
     22g 17   14:  26:0  3 20  24// 
     23 Upd  ate   Coun  t       :   
     2460//  #inc  lude   <fs  trea 
     25m.hf  a>#i  nclu  de <  coro 
     26utin  e.hf  a>co  rout  ine   
     27Form  at {      cha  r ch  ;                     
     28                                                                  // u  sed   for   
     29comm  unic  atio  n     in  t g, 
     30 b;                                                                                     //   glo 
     31bal   beca  use   used   in   
     32dest  ruct  or};  void   mai 
     33n( F  orma  t &   fmt   ) wi 
     34th(   fmt   ) {   for   () { 
     35                                                                                        /  / fo  r as 
     36 man  y ch  arac  ters                  fo 
     37r (   g =   0; g   < 5  ; g   
     38+= 1   ) {                                      //   grou 
    4339ps o  f 5   bloc  ks                    for 
    44  ( f  mt.b   = 0  ; fm  t.b   
    45 < 4;   fmt  .b +  = 1   ) {       
    46 // b  lock  s of   4 c  hara 
    47 cter  s                         for   ( ;  ; )   
    48 {                                                         // f  or n  ewli 
    49 ne c  hara  cter  s                                     su 
    50 spen  d;                                        i  f (   fmt. 
    51 ch !  = '\  n' )   bre  ak;       
    52         //   igno  re n  ewli  ne                 
    53                 }   // f  or                            so  ut | 
    54  fmt  .ch;                                                      /  / pr 
    55 int   char  acte  r                       } // 
    56  for                    s  out   | "    ";       
    57                                                         /  / pr  int   bloc 
    58 k se  para  tor         } /  / fo 
    59 r               s  out   | nl  ;                                                         
    60                 //   pri  nt g  roup   sep 
    61 arat  or        }   //   for}   //   
    62 main  void   prt  ( Fo  rmat 
    63  & f  mt,   char   ch   ) {   
    64    f  mt.c  h =   ch;      r 
    65 esum  e( f  mt )  ;} /  / pr 
    66 tint   mai  n()   {     Fo  rmat 
    67  fmt  ; ch  ar c  h;    f  or ( 
    68  ;;   ) {               sin   | c  h;             
    69                                                                   // r  ead   one   
    70 char  acte  r       if (   eof 
    71 ( si  n )   ) br  eak;                                   
    72                         /  / eo  f ?            prt  ( fm 
    73 t, c  h );      } /  / fo  r} / 
    74 / ma  in//   Loc  al V  aria 
    75 bles  : //  // t  ab-w  idth 
    76 : 4   ////   com  pile  -com 
    77 mand  : "c  fa f  mtLi  nes. 
    78 cfa"   ///  / En  d: /  /
     40 ( b   = 0  ; b   < 4;   b + 
     41= 1   ) {                               /  / bl  ocks 
     42 of   4 ch  arac  ters                                   
     43for   () {                                                                // f 
     44or n  ewli  ne c  hara  cter 
     45s                                       su  spen  d;                               
     46if (   ch   != '  \n'   ) br 
     47eak;                              // i  gnor  e ne 
     48wlin  e                         } /  / fo  r                     
     49        sou  t |   ch;                                                          / 
     50/ pr  int   char  acte  r                         
     51} //   for                      s  out   | "   
     52 ";                                                             /  / pr  int   
     53bloc  k se  para  tor           } / 
     54/ fo  r         s  out   | nl  ;                         
     55                                                        /  / pr  int   grou 
     56p se  para  tor   } //   for 
     57} //   mai  nvoi  d ?{  }( F 
     58orma  t &   fmt   ) {     resu 
     59me(   fmt   );                                                                           
     60// p  rime   (st  art)   cor 
     61outi  ne}v  oid   ^?{}  ( Fo 
     62rmat   & f  mt )   wit  h( f 
     63mt )   {        i  f (   g !=   0 | 
     64| b   != 0   ) s  out   | nl 
     65;}vo  id f  orma  t( F  orma 
     66t &   fmt   ) {   resu  me(   
     67fmt   );}   // f  orma  tint 
     68 mai  n()   {   Fo  rmat   fmt 
     69;       so  ut |   nlO  ff;                                       
     70                                        //   turn   off   aut 
     71o ne  wlin  e   tr  y {         for 
     72 ()   {                                                                         /  / re 
     73ad u  ntil   end   of   file 
     74                        s  in |   fmt  .ch;                               
     75                                  // r  ead   one   char 
     76acte  r                   form  at(   fmt   
     77);                                                              //   pus  h ch 
     78arac  ter   for   form  atti 
     79ng                } //   for    } c  atch 
     80( en  d_of  _fil  e *   ) {       
     81} //   try  } //   mai  n
  • tests/coroutine/.in/fmtLines.txt

    rd1f5054 r960665c  
    55// file "LICENCE" distributed with Cforall.
    66//
    7 // fmtLines.cc --
     7// fmtLines.cc -- format characters into blocks of 4 and groups of 5 blocks per line
    88//
    99// Author           : Peter A. Buhr
    1010// Created On       : Sun Sep 17 21:56:15 2017
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Mar 22 13:41:03 2019
    13 // Update Count     : 33
     12// Last Modified On : Sat Aug 17 14:26:03 2024
     13// Update Count     : 60
    1414//
    1515
     
    2222};
    2323
    24 void ?{}( Format & fmt ) {
    25     resume( fmt );                                                                              // start coroutine
    26 }
    27 
    28 void ^?{}( Format & fmt ) {
    29     if ( fmt.g != 0 || fmt.b != 0 ) sout | nl;
    30 }
    31 
    32 void main( Format & fmt ) {
    33         for ( ;; ) {                                                                            // for as many characters
    34                 for ( fmt.g = 0; fmt.g < 5; fmt.g += 1 ) {              // groups of 5 blocks
    35                         for ( fmt.b = 0; fmt.b < 4; fmt.b += 1 ) {      // blocks of 4 characters
    36                                 for ( ;; ) {                                                    // for newline characters
     24void main( Format & fmt ) with( fmt ) {
     25        for () {                                                                                        // for as many characters
     26                for ( g = 0; g < 5; g += 1 ) {                                  // groups of 5 blocks
     27                        for ( b = 0; b < 4; b += 1 ) {                          // blocks of 4 characters
     28                                for () {                                                                // for newline characters
    3729                                        suspend;
    38                                         if ( fmt.ch != '\n' ) break;            // ignore newline
     30                                  if ( ch != '\n' ) break;                              // ignore newline
    3931                                } // for
    40                                 sout | fmt.ch;                                                  // print character
     32                                sout | ch;                                                              // print character
    4133                        } // for
    4234                        sout | "  ";                                                            // print block separator
    4335                } // for
    44                 sout | nl;                                                                      // print group separator
     36                sout | nl;                                                                              // print group separator
    4537        } // for
    4638} // main
    4739
    48 void prt( Format & fmt, char ch ) {
    49     fmt.ch = ch;
    50     resume( fmt );
    51 } // prt
     40void ?{}( Format & fmt ) {
     41        resume( fmt );                                                                          // prime (start) coroutine
     42}
     43
     44void ^?{}( Format & fmt ) with( fmt ) {
     45        if ( g != 0 || b != 0 ) sout | nl;
     46}
     47
     48void format( Format & fmt ) {
     49        resume( fmt );
     50} // format
    5251
    5352int main() {
    5453        Format fmt;
    55         char ch;
     54        sout | nlOff;                                                                           // turn off auto newline
    5655
    57         for ( ;; ) {
    58                 sin | ch;                                                                               // read one character
    59           if ( eof( sin ) ) break;                                                      // eof ?
    60                 prt( fmt, ch );
    61         } // for
     56        try {
     57                for () {                                                                                // read until end of file
     58                        sin | fmt.ch;                                                           // read one character
     59                        format( fmt );                                                          // push character for formatting
     60                } // for
     61        } catch( end_of_file * ) {
     62        } // try
    6263} // main
    63 
    64 // Local Variables: //
    65 // tab-width: 4 //
    66 // compile-command: "cfa fmtLines.cfa" //
    67 // End: //
  • tests/coroutine/cntparens.cfa

    rd1f5054 r960665c  
    1010// Created On       : Sat Apr 20 11:04:45 2019
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sat Apr 20 11:06:21 2019
    13 // Update Count     : 1
     12// Last Modified On : Thu Aug 15 20:39:34 2024
     13// Update Count     : 2
    1414//
    1515
     
    4646        char ch;
    4747
    48         for () {                                                                                        // read until end of file
    49                 sin | ch;                                                                               // read one character
    50           if ( eof( sin ) ) { sout | "Error"; break; }          // eof ?
    51                 Status ret = next( cpns, ch );                                  // push character for formatting
    52           if ( ret == Match ) { sout | "Match"; break; }
    53           if ( ret == Error ) { sout | "Error"; break; }
    54         } // for
     48        try {
     49                for () {                                                                                        // read until end of file
     50                        sin | ch;                                                                               // read one character
     51                        Status ret = next( cpns, ch );                                  // push character for formatting
     52                        if ( ret == Match ) { sout | "Match"; break; }
     53                        if ( ret == Error ) { sout | "Error"; break; }
     54                } // for
     55        } catch( end_of_file * ) {
     56                sout | "Error";
     57        } // try
    5558} // main
    5659
  • tests/coroutine/devicedriver.cfa

    rd1f5054 r960665c  
    1010// Created On       : Sat Mar 16 15:30:34 2019
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sat Jun 17 09:11:56 2023
    13 // Update Count     : 94
     12// Last Modified On : Thu Aug 15 18:45:45 2024
     13// Update Count     : 96
    1414//
    1515
     
    7171
    7272        sin | nlOn;                                                                                     // read newline (all) characters
    73   eof: for () {                                                                                 // read until end of file
    74                 sin | byte;                                                                             // read one character
    75           if ( eof( sin ) ) break eof;                                          // eof ?
    76                 choose( next( driver, byte ) ) {                                // analyse character
    77                   case CONT: ;
    78                   case MSG: sout | "msg:" | msg;
    79                   case ESTX: sout | "STX in message";
    80                   case ELNTH: sout | "message too long";
    81                   case ECRC: sout | "CRC failure";
    82                 } // choose
    83         } // for
     73        try {
     74                for () {                                                                                // read until end of file
     75                        sin | byte;                                                                     // read one character
     76                        choose( next( driver, byte ) ) {                        // analyse character
     77                          case CONT: ;
     78                          case MSG: sout | "msg:" | msg;
     79                          case ESTX: sout | "STX in message";
     80                          case ELNTH: sout | "message too long";
     81                          case ECRC: sout | "CRC failure";
     82                        } // choose
     83                } // for
     84        } catch( end_of_file * ) {
     85        } // try
    8486} // main
    8587
  • tests/coroutine/fmtLines.cfa

    rd1f5054 r960665c  
    1010// Created On       : Sun Sep 17 21:56:15 2017
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Mar 22 13:41:16 2019
    13 // Update Count     : 58
     12// Last Modified On : Sat Aug 17 14:26:03 2024
     13// Update Count     : 60
    1414//
    1515
     
    5454        sout | nlOff;                                                                           // turn off auto newline
    5555
    56   eof: for () {                                                                                 // read until end of file
    57                 sin | fmt.ch;                                                                   // read one character
    58           if ( eof( sin ) ) break eof;                                          // eof ?
    59                 format( fmt );                                                                  // push character for formatting
    60         } // for
     56        try {
     57                for () {                                                                                // read until end of file
     58                        sin | fmt.ch;                                                           // read one character
     59                        format( fmt );                                                          // push character for formatting
     60                } // for
     61        } catch( end_of_file * ) {
     62        } // try
    6163} // main
    62 
    63 // Local Variables: //
    64 // tab-width: 4 //
    65 // compile-command: "cfa fmtLines.cfa" //
    66 // End: //
  • tests/enum_tests/input.cfa

    rd1f5054 r960665c  
    66        E e;
    77
    8         for () {
    9                 try {
    10                         sin | e;
    11                 } catch( missing_data * ) {
    12                         sout | "missing data";
    13                         continue;                                                                       // try again
    14                 } // try
    15           if ( eof( sin ) ) break;
    16                 sout | e | "= " | value( e );
    17         } // for
    18 }
     8        try {
     9                for () {
     10                        try {
     11                                sin | e;
     12                        } catch( missing_data * ) {
     13                                sout | "missing data";
     14                                continue;                                                               // try again
     15                        } // try
     16                        sout | e | "= " | value( e );
     17                } // for
     18        } catch( end_of_file * ) {
     19        } // try
     20} // main
  • tests/generator/.expect/fmtLines.txt

    rd1f5054 r960665c  
    99E" d  istr  ibut  ed w  ith   
    1010Cfor  all.  ////   fmt  Line 
    11 s.cc   --/  ///   Auth  or   
    12              : P  eter   A.   
    13 Buhr  // C  reat  ed O  n     
    14       : Su  n Se  p 17   21: 
    15 56:1  5 20  17//   Las  t Mo 
    16 difi  ed B  y :   Pete  r A. 
    17  Buh  r//   Last   Mod  ifie 
    18 d On   : F  ri M  ar 2  2 13 
    19 :41:  03 2  019/  / Up  date 
    20  Cou  nt       :   33/  /#in 
    21 clud  e <f  stre  am.h  fa># 
    22 incl  ude   <cor  outi  ne.h 
    23 fa>c  orou  tine   For  mat   
    24 {       ch  ar c  h;                                                                             
    25         //   used   for   com  muni 
    26 cati  on        i  nt g  , b;                             
    27                                                         /  / gl  obal   bec 
    28 ause   use  d in   des  truc 
    29 tor}  ;voi  d ?{  }( F  orma 
    30 t &   fmt   ) {      r  esum 
    31 e( f  mt )  ;                                                                           / 
    32 / st  art   coro  utin  e}vo 
    33 id ^  ?{}(   For  mat   & fm 
    34 t )   {      if   ( fm  t.g   
    35 != 0   ||   fmt.  b !=   0 ) 
    36  sou  t |   nl;}  void   mai 
    37 n( F  orma  t &   fmt   ) {       
    38 for   ( ;;   ) {                                                                 
    39                 //   for   as   many   cha 
    40 ract  ers               for   ( f  mt.g 
    41  = 0  ; fm  t.g   < 5;   fmt 
    42 .g +  = 1   ) {         //   grou 
    43 ps o  f 5   bloc  ks                    for 
    44  ( f  mt.b   = 0  ; fm  t.b   
    45 < 4;   fmt  .b +  = 1   ) {       
    46 // b  lock  s of   4 c  hara 
    47 cter  s                         for   ( ;  ; )   
    48 {                                                         // f  or n  ewli 
    49 ne c  hara  cter  s                                     su 
    50 spen  d;                                        i  f (   fmt. 
    51 ch !  = '\  n' )   bre  ak;       
    52         //   igno  re n  ewli  ne                 
    53                 }   // f  or                            so  ut | 
    54  fmt  .ch;                                                      /  / pr 
    55 int   char  acte  r                       } // 
    56  for                    s  out   | "    ";       
    57                                                         /  / pr  int   bloc 
    58 k se  para  tor         } /  / fo 
    59 r               s  out   | nl  ;                                                         
    60                 //   pri  nt g  roup   sep 
    61 arat  or        }   //   for}   //   
    62 main  void   prt  ( Fo  rmat 
    63  & f  mt,   char   ch   ) {   
    64    f  mt.c  h =   ch;      r 
    65 esum  e( f  mt )  ;} /  / pr 
    66 tint   mai  n()   {     Fo  rmat 
    67  fmt  ; ch  ar c  h;    f  or ( 
    68  ;;   ) {               sin   | c  h;             
    69                                                                   // r  ead   one   
    70 char  acte  r       if (   eof 
    71 ( si  n )   ) br  eak;                                   
    72                         /  / eo  f ?            prt  ( fm 
    73 t, c  h );      } /  / fo  r} / 
    74 / ma  in//   Loc  al V  aria 
    75 bles  : //  // t  ab-w  idth 
    76 : 4   ////   com  pile  -com 
    77 mand  : "c  fa f  mtLi  nes. 
    78 cfa"   ///  / En  d: /  /
     11s.cf  a --   for  mat   char 
     12acte  rs i  nto   bloc  ks o 
     13f 4   and   grou  ps o  f 5   
     14bloc  ks p  er l  ine/  ///   
     15Auth  or                 : T 
     16hier  ry D  elis  le//   Cre 
     17ated   On           :   Thu   
     18Mar    5 1  6:09  :08   2020 
     19// L  ast   Modi  fied   By   
     20: Pe  ter   A. B  uhr/  / La 
     21st M  odif  ied   On :   Sat 
     22 Aug   17   14:2  1:28   202 
     234//   Upda  te C  ount       
     24 : 5  //#i  nclu  de <  fstr 
     25eam.  hfa>  gene  rato  r Fo 
     26rmat   {        c  har   ch;                                     
     27                                                //   use  d fo  r co 
     28mmun  icat  ion   int   g, b 
     29;                                                                                         // g  loba 
     30l be  caus  e us  ed i  n de 
     31stru  ctor  };vo  id m  ain( 
     32 For  mat   & fm  t )   with 
     33( fm  t )   {   fo  r ()   {             
     34                                                                        //   for   as m 
     35any   char  acte  rs              for   
     36( g   = 0;   g <   5;   g += 
     37 1 )   {                                        /  / gr  oups 
     38 of   5 bl  ocks                        f  or ( 
     39 b =   0;   b <   4; b   +=   
     401 )   {                         //   bloc  ks o 
     41f 4   char  acte  rs                            fo 
     42r ()   {                                                                //   for 
     43 new  line   cha  ract  ers       
     44                                  susp  end;                                if 
     45 ( c  h !=   '\n  ' )   brea 
     46k;                              //   ign  ore   newl 
     47ine                             }   //   for                            s 
     48out   | ch  ;                                                           //   
     49prin  t ch  arac  ter                   }   
     50// f  or                        sou  t |   "  " 
     51;                                                               //   prin  t bl 
     52ock   sepa  rato  r             }   //   
     53for             sou  t |   nl;                                   
     54                                        //   prin  t gr  oup   
     55sepa  rato  r   }   // f  or}   
     56// m  ainv  oid   ?{}(   For 
     57mat   & fm  t )   {     re  sume 
     58( fm  t );                                                                              // 
     59 pri  me (  star  t) c  orou 
     60tine  }voi  d ^?  {}(   Form 
     61at &   fmt   ) w  ith(   fmt 
     62 ) {    if   ( g   != 0   ||   
     63b !=   0 )   sou  t |   nl;} 
     64void   for  mat(   For  mat   
     65& fm  t )   {   re  sume  ( fm 
     66t );  } //   for  mati  nt m 
     67ain(  ) {         Form  at f  mt;         
     68sout   | n  lOff  ;                                                       
     69                        /  / tu  rn o  ff a  uto   
     70newl  ine         try   {               f  or ( 
     71) {                                                                             //   read 
     72 unt  il e  nd o  f fi  le               
     73        sin   | f  mt.c  h;                                               
     74                //   rea  d on  e ch  arac 
     75ter                     fo  rmat  ( fm  t ); 
     76                                                                  // p  ush   char 
     77acte  r fo  r fo  rmat  ting 
     78                }   // f  or    }   cat  ch(   
     79end_  of_f  ile   * )   {       }   
     80// t  ry}   // m  ain
  • tests/generator/.in/fmtLines.txt

    rd1f5054 r960665c  
    55// file "LICENCE" distributed with Cforall.
    66//
    7 // fmtLines.cc --
     7// fmtLines.cfa -- format characters into blocks of 4 and groups of 5 blocks per line
    88//
    9 // Author           : Peter A. Buhr
    10 // Created On       : Sun Sep 17 21:56:15 2017
     9// Author           : Thierry Delisle
     10// Created On       : Thu Mar  5 16:09:08 2020
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Mar 22 13:41:03 2019
    13 // Update Count     : 33
     12// Last Modified On : Sat Aug 17 14:21:28 2024
     13// Update Count     : 5
    1414//
    1515
    1616#include <fstream.hfa>
    17 #include <coroutine.hfa>
    1817
    19 coroutine Format {
     18generator Format {
    2019        char ch;                                                                                        // used for communication
    2120        int g, b;                                                                                       // global because used in destructor
    2221};
    2322
    24 void ?{}( Format & fmt ) {
    25     resume( fmt );                                                                              // start coroutine
    26 }
    27 
    28 void ^?{}( Format & fmt ) {
    29     if ( fmt.g != 0 || fmt.b != 0 ) sout | nl;
    30 }
    31 
    32 void main( Format & fmt ) {
    33         for ( ;; ) {                                                                            // for as many characters
    34                 for ( fmt.g = 0; fmt.g < 5; fmt.g += 1 ) {              // groups of 5 blocks
    35                         for ( fmt.b = 0; fmt.b < 4; fmt.b += 1 ) {      // blocks of 4 characters
    36                                 for ( ;; ) {                                                    // for newline characters
     23void main( Format & fmt ) with( fmt ) {
     24        for () {                                                                                        // for as many characters
     25                for ( g = 0; g < 5; g += 1 ) {                                  // groups of 5 blocks
     26                        for ( b = 0; b < 4; b += 1 ) {                          // blocks of 4 characters
     27                                for () {                                                                // for newline characters
    3728                                        suspend;
    38                                         if ( fmt.ch != '\n' ) break;            // ignore newline
     29                                  if ( ch != '\n' ) break;                              // ignore newline
    3930                                } // for
    40                                 sout | fmt.ch;                                                  // print character
     31                                sout | ch;                                                              // print character
    4132                        } // for
    4233                        sout | "  ";                                                            // print block separator
    4334                } // for
    44                 sout | nl;                                                                      // print group separator
     35                sout | nl;                                                                              // print group separator
    4536        } // for
    4637} // main
    4738
    48 void prt( Format & fmt, char ch ) {
    49     fmt.ch = ch;
    50     resume( fmt );
    51 } // prt
     39void ?{}( Format & fmt ) {
     40        resume( fmt );                                                                          // prime (start) coroutine
     41}
     42
     43void ^?{}( Format & fmt ) with( fmt ) {
     44        if ( g != 0 || b != 0 ) sout | nl;
     45}
     46
     47void format( Format & fmt ) {
     48        resume( fmt );
     49} // format
    5250
    5351int main() {
    5452        Format fmt;
    55         char ch;
     53        sout | nlOff;                                                                           // turn off auto newline
    5654
    57         for ( ;; ) {
    58                 sin | ch;                                                                               // read one character
    59           if ( eof( sin ) ) break;                                                      // eof ?
    60                 prt( fmt, ch );
    61         } // for
     55        try {
     56                for () {                                                                                // read until end of file
     57                        sin | fmt.ch;                                                           // read one character
     58                        format( fmt );                                                          // push character for formatting
     59                } // for
     60        } catch( end_of_file * ) {
     61        } // try
    6262} // main
    63 
    64 // Local Variables: //
    65 // tab-width: 4 //
    66 // compile-command: "cfa fmtLines.cfa" //
    67 // End: //
  • tests/generator/fmtLines.cfa

    rd1f5054 r960665c  
    1010// Created On       : Thu Mar  5 16:09:08 2020
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Jun 10 21:56:22 2021
    13 // Update Count     : 2
     12// Last Modified On : Sat Aug 17 14:21:28 2024
     13// Update Count     : 5
    1414//
    1515
     
    5353        sout | nlOff;                                                                           // turn off auto newline
    5454
    55   eof: for () {                                                                                 // read until end of file
    56                 sin | fmt.ch;                                                                   // read one character
    57           if ( eof( sin ) ) break eof;                                          // eof ?
    58                 format( fmt );                                                                  // push character for formatting
    59         } // for
     55        try {
     56                for () {                                                                                // read until end of file
     57                        sin | fmt.ch;                                                           // read one character
     58                        format( fmt );                                                          // push character for formatting
     59                } // for
     60        } catch( end_of_file * ) {
     61        } // try
    6062} // main
    61 
    62 // Local Variables: //
    63 // tab-width: 4 //
    64 // compile-command: "cfa fmtLines.cfa" //
    65 // End: //
Note: See TracChangeset for help on using the changeset viewer.