Changes in / [6cbc25a:7ff30d07]


Ignore:
Files:
36 edited

Legend:

Unmodified
Added
Removed
  • doc/LaTeXmacros/common.tex

    r6cbc25a r7ff30d07  
    1111%% Created On       : Sat Apr  9 10:06:17 2016
    1212%% Last Modified By : Peter A. Buhr
    13 %% Last Modified On : Fri Jun  3 09:32:19 2016
    14 %% Update Count     : 62
     13%% Last Modified On : Fri Jun 10 16:35:25 2016
     14%% Update Count     : 101
    1515%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    1616
     
    5656%   \belowdisplayskip \abovedisplayskip
    5757%}
     58
     59\usepackage{pslatex}                                                                    % reduce size of san serif font
    5860\usepackage{relsize}                                    % must be after change to small or selects old size
    5961
     
    7981    \vskip 50\p@
    8082  }}
    81 \renewcommand\section{\@startsection{section}{1}{\z@}{-3.5ex \@plus -1ex \@minus -.2ex}{2.3ex \@plus .2ex}{\normalfont\large\bfseries}}
     83\renewcommand\section{\@startsection{section}{1}{\z@}{-3.5ex \@plus -1ex \@minus -.2ex}{1.75ex \@plus .2ex}{\normalfont\large\bfseries}}
    8284\renewcommand\subsection{\@startsection{subsection}{2}{\z@}{-3.25ex \@plus -1ex \@minus -.2ex}{1.5ex \@plus .2ex}{\normalfont\normalsize\bfseries}}
    8385\renewcommand\subsubsection{\@startsection{subsubsection}{3}{\z@}{-2.5ex \@plus -1ex \@minus -.2ex}{1.0ex \@plus .2ex}{\normalfont\normalsize\bfseries}}
     
    132134
    133135\newenvironment{quote2}{%
    134         \list{}{\lstset{resetmargins=true}\leftmargin=\parindent\rightmargin\leftmargin}%
     136        \list{}{\lstset{resetmargins=true,aboveskip=0pt,belowskip=0pt}\topsep=4pt\parsep=0pt\leftmargin=\parindent\rightmargin\leftmargin}%
    135137        \item\relax
    136138}{%
     
    199201language=CFA,
    200202columns=flexible,
    201 basicstyle=\sf,
     203basicstyle=\linespread{0.9}\sf,
    202204stringstyle=\tt,
    203205tabsize=4,
     
    210212showlines=true,
    211213aboveskip=4pt,
    212 belowskip=2pt,
     214belowskip=3pt,
    213215moredelim=**[is][\color{red}]{®}{®}, % red highlighting
    214 % moredelim=**[is][\color{blue}]{¢}{¢}, % blue highlighting
     216moredelim=**[is][\color{blue}]{ß}{ß}, % blue highlighting
     217moredelim=**[is][\color{OliveGreen}]{¢}{¢}, % green highlighting
    215218moredelim=[is][\lstset{keywords={}}]{¶}{¶}, % temporarily turn off keywords
    216 % literate={\\`}{\raisebox{0.3ex}{\ttfamily\upshape \hspace*{-2pt}`}}1, % escape \`, otherwise used for red highlighting
    217 literate={...}{{$\dots$}}1 {<-}{{$\leftarrow$}}1 {=>}{{$\Rightarrow$}}1,
     219% replace/adjust listing characters that look bad in sanserif
     220literate={-}{\raisebox{-0.15ex}{\texttt{-}}}1 {^}{\raisebox{0.6ex}{$\scriptscriptstyle\land\,$}}1
     221        {~}{\raisebox{0.3ex}{$\scriptstyle\sim\,$}}1 {_}{\makebox[1.2ex][c]{\rule{1ex}{0.1ex}}}1 {`}{\ttfamily\upshape\hspace*{-0.1ex}`}1
     222        {<-}{$\leftarrow$}2 {=>}{$\Rightarrow$}2 {...}{$\dots$}2,
    218223}%
    219224
    220225\lstMakeShortInline©    % single-character for \lstinline
    221 
    222 \makeatletter
    223 % replace/adjust listings characters that look bad in sanserif
    224 \lst@CCPutMacro
    225 \lst@ProcessOther{"22}{\lst@ttfamily{"}{\raisebox{0.3ex}{\ttfamily\upshape "}}} % replace double quote
    226 \lst@ProcessOther{"27}{\lst@ttfamily{'}{\raisebox{0.3ex}{\ttfamily\upshape '\hspace*{-2pt}}}} % replace single quote
    227 \lst@ProcessOther{"2D}{\lst@ttfamily{-}{\textbf{\texttt{-}}}} % replace minus
    228 \lst@ProcessOther{"3C}{\lst@ttfamily{<}{\textbf{\texttt{<}}}} % replace less than
    229 \lst@ProcessOther{"3E}{\lst@ttfamily{>}{\textbf{\texttt{>}}}} % replace greater than
    230 \lst@ProcessOther{"5E}{\raisebox{0.4ex}{$\scriptstyle\land\,$}} % replace circumflex
    231 \lst@ProcessOther{"5F}{\lst@ttfamily{\char95}{{\makebox[1.2ex][c]{\rule{1ex}{0.1ex}}}}} % replace underscore
    232 \lst@ProcessOther{"60}{\lst@ttfamily{`}{\raisebox{0.3ex}{\ttfamily\upshape \hspace*{-2pt}`}}} % replace backquote
    233 \lst@ProcessOther{"7E}{\raisebox{0.3ex}{$\scriptstyle\sim\,$}} % replace tilde
    234 %\lst@ProcessOther{"7E}{\raisebox{-.4ex}[1ex][0pt]{\textasciitilde}} % lower tilde
    235 \@empty\z@\@empty % NECESSARY DO NOT REMOVE
    236 \makeatother
    237226
    238227% Local Variables: %
  • doc/user/Cdecl.fig

    r6cbc25a r7ff30d07  
    3434        1 1 1.00 45.00 90.00
    3535         1950 1275 1950 1500
    36 4 1 0 50 -1 4 9 0.0000 2 105 90 1350 1650 0\001
    37 4 1 0 50 -1 4 9 0.0000 2 105 90 1500 1650 1\001
    38 4 1 0 50 -1 4 9 0.0000 2 105 90 1650 1650 2\001
    39 4 1 0 50 -1 4 9 0.0000 2 105 90 1800 1650 3\001
    40 4 1 0 50 -1 4 9 0.0000 2 105 90 1950 1650 4\001
    41 4 1 0 50 -1 4 9 0.0000 2 75 75 1200 1325 x\001
     364 1 0 50 -1 4 10 0.0000 2 105 90 1350 1650 0\001
     374 1 0 50 -1 4 10 0.0000 2 105 90 1500 1650 1\001
     384 1 0 50 -1 4 10 0.0000 2 105 90 1650 1650 2\001
     394 1 0 50 -1 4 10 0.0000 2 105 90 1800 1650 3\001
     404 1 0 50 -1 4 10 0.0000 2 105 90 1950 1650 4\001
     414 1 0 50 -1 4 10 0.0000 2 75 75 1200 1325 x\001
    4242-6
    43436 2325 1200 3600 1350
     
    54542 2 0 1 0 7 50 -1 -1 0.000 0 0 -1 0 0 5
    5555         2850 1200 3600 1200 3600 1350 2850 1350 2850 1200
    56 4 1 0 50 -1 4 9 0.0000 2 105 90 2925 1325 0\001
    57 4 1 0 50 -1 4 9 0.0000 2 105 90 3075 1325 1\001
    58 4 1 0 50 -1 4 9 0.0000 2 105 90 3225 1325 2\001
    59 4 1 0 50 -1 4 9 0.0000 2 105 90 3375 1325 3\001
    60 4 1 0 50 -1 4 9 0.0000 2 105 90 3525 1325 4\001
     564 1 0 50 -1 4 10 0.0000 2 105 90 2925 1325 0\001
     574 1 0 50 -1 4 10 0.0000 2 105 90 3075 1325 1\001
     584 1 0 50 -1 4 10 0.0000 2 105 90 3225 1325 2\001
     594 1 0 50 -1 4 10 0.0000 2 105 90 3375 1325 3\001
     604 1 0 50 -1 4 10 0.0000 2 105 90 3525 1325 4\001
    6161-6
    62622 2 0 1 0 7 50 -1 -1 0.000 0 0 -1 0 0 5
     
    6666         2550 1275 2850 1275
    6767-6
    68 4 1 0 50 -1 4 9 0.0000 2 75 75 2400 1325 x\001
     684 1 0 50 -1 4 10 0.0000 2 75 75 2400 1325 x\001
    6969-6
  • doc/user/user.tex

    r6cbc25a r7ff30d07  
    1111%% Created On       : Wed Apr  6 14:53:29 2016
    1212%% Last Modified By : Peter A. Buhr
    13 %% Last Modified On : Fri Jun  3 09:49:31 2016
    14 %% Update Count     : 281
     13%% Last Modified On : Fri Jun 10 16:38:22 2016
     14%% Update Count     : 394
    1515%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    1616
     
    1818
    1919% inline code ©...© (copyright symbol) emacs: C-q M-)
    20 % red highlighting ®...® (registered trademark sumbol) emacs: C-q M-.
    21 % latex escape §...§ (section symbol) emacs: C-q M-'
     20% red highlighting ®...® (registered trademark symbol) emacs: C-q M-.
     21% blue highlighting ß...ß (sharp s symbol) emacs: C-q M-_
     22% green highlighting ¢...¢ (cent symbol) emacs: C-q M-"
     23% Latex escape §...§ (section symbol) emacs: C-q M-'
    2224% keyword escape ¶...¶ (pilcrow symbol) emacs: C-q M-^
    2325% math escape $...$ (dollar symbol)
    2426
    25 \documentclass[openright,twoside]{article}
     27\documentclass[twoside,11pt]{article}
    2628%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    2729
     
    3234\usepackage{fullpage,times,comment}
    3335\usepackage{epic,eepic}
    34 \usepackage{upquote}                                                                    % switch curled `' to straight `'
     36\usepackage{upquote}                                                                    % switch curled `'" to straight `'"
    3537\usepackage{xspace}
    3638\usepackage{varioref}                                                                   % extended references
    3739\usepackage{listings}                                                                   % format program code
    38 \usepackage{footmisc}                                                                   % support label/reference in footnote
     40\usepackage[flushmargin]{footmisc}                                              % support label/reference in footnote
    3941\usepackage{latexsym}                                   % \Box glyph
    4042\usepackage{mathptmx}                                   % better math font with "times"
     43\usepackage[usenames]{color}
    4144\usepackage[pagewise]{lineno}
    4245\renewcommand{\linenumberfont}{\scriptsize\sffamily}
     46\input{common}                                          % bespoke macros used in the document
    4347\usepackage[dvips,plainpages=false,pdfpagelabels,pdfpagemode=UseNone,colorlinks=true,pagebackref=true,linkcolor=blue,citecolor=blue,urlcolor=blue,pagebackref=true,breaklinks=true]{hyperref}
    4448\usepackage{breakurl}
    4549\renewcommand{\UrlFont}{\small\sf}
    4650
    47 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    48 
    49 % Bespoke macros used in the document.
    50 \input{common}
    51 
    52 %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    53 
    5451% Names used in the document.
    5552
    5653\newcommand{\Version}{1.0.0}
    5754\newcommand{\CS}{C\raisebox{-0.9ex}{\large$^\sharp$}\xspace}
     55
     56\newcommand{\Textbf}[2][red]{{\color{#1}{\textbf{#2}}}}
     57\newcommand{\Emph}[2][red]{{\color{#1}\textbf{\emph{#2}}}}
     58\newcommand{\R}[1]{\Textbf{#1}}
     59\newcommand{\B}[1]{{\Textbf[blue]{#1}}}
     60\newcommand{\G}[1]{{\Textbf[OliveGreen]{#1}}}
    5861
    5962%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
     
    110113
    111114\CFA\footnote{Pronounced ``C-for-all'', and written \CFA, CFA, or \CFL.} is a modern general-purpose programming-language, designed an as evolutionary step forward from the C programming language.
    112 The syntax of the \CFA language builds from C, and should look immediately familiar to C programmers.
     115The syntax of the \CFA language builds from C, and should look immediately familiar to C/\CC programmers.
    113116% Any language feature that is not described here can be assumed to be using the standard C11 syntax.
    114 \CFA adds many modern programming-language features that directly leads to increased \emph{safety} and \emph{productivity}, while maintaining interoperability with existing C programs and achieving C performance.
     117\CFA adds many modern programming-language features that directly lead to increased \emph{safety} and \emph{productivity}, while maintaining interoperability with existing C programs and achieving C performance.
    115118Like C, \CFA is a statically typed, procedural language with a low-overhead runtime, meaning there is no global garbage-collection.
    116119The primary new features include parametric-polymorphism routines and types, exceptions, concurrency, and modules.
     
    123126New programs can be written in \CFA using a combination of C and \CFA features.
    124127\CC had a similar goal 30 years ago, but has struggled over the intervening time to incorporate modern programming-language features because of early design choices.
    125 \CFA has 30 years of hindsight and clean starting point.
     128\CFA has 30 years of hindsight and a clean starting point.
    126129
    127130Like \CC, there may be both an old and new ways to achieve the same effect.
    128131For example, the following programs compare the \CFA and C I/O mechanisms.
    129132\begin{quote2}
    130 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    131 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
     133\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     134\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
    132135\begin{lstlisting}
    133136#include <fstream>
    134137int main( void ) {
    135138        int x = 0, y = 1, z = 2;
    136         sout | x | y | z | endl;
     139        ®sout | x | y | z | endl;®
    137140}
    138141\end{lstlisting}
     
    142145int main( void ) {
    143146        int x = 0, y = 1, z = 2;
    144         printf( "%d %d %d\n", x, y, z );
     147        ®printf( "%d %d %d\n", x, y, z );®
    145148}
    146149\end{lstlisting}
     
    148151\end{quote2}
    149152Both programs output the same result.
    150 While the \CFA I/O looks similar to the \CC output style, there are several important differences, such as automatic spacing between variables as in Python (see also~\VRef{s:IOLibrary}).
    151 
    152 This document is a reference manual for the \CFA programming language, targeted at \CFA programmers.
     153While the \CFA I/O looks similar to the \CC output style, there are important differences, such as automatic spacing between variables as in Python (see also~\VRef{s:IOLibrary}).
     154
     155This document is a user manual for the \CFA programming language, targeted at \CFA programmers.
    153156Implementers may refer to the \CFA Programming Language Specification for details about the language syntax and semantics.
    154157In its current state, this document covers the intended core features of the language.
     
    159162\section{History}
    160163
    161 The \CFA project started with K-W C~\cite{Till89,Buhr94a}, which extended C with new declaration syntax, multiple return values from routines, and extended assignment capabilities using the notion of tuples.
     164The \CFA project started with K-W C~\cite{Buhr94a,Till89}, which extended C with new declaration syntax, multiple return values from routines, and extended assignment capabilities using the notion of tuples.
    162165(See~\cite{Werther96} for some similar work, but for \CC.)
    163166The original \CFA project~\cite{Ditchfield92} extended the C type system with parametric polymorphism and overloading, as opposed to the \CC approach of object-oriented extensions to the C type-system.
    164167A first implementation of the core Cforall language was created~\cite{Bilson03,Esteves04}, but at the time there was little interesting in extending C, so work did not continue.
    165 As the saying goes, ``What goes around, comes around'', and there is now renewed interest in the C programming language because of legacy code-bases, so the \CFA project has been restarted.
     168As the saying goes, ``What goes around, comes around.'', and there is now renewed interest in the C programming language because of legacy code-bases, so the \CFA project has been restarted.
    166169
    167170
     
    169172
    170173Even with all its problems, C is a very popular programming language because it allows writing software at virtually any level in a computer system without restriction.
    171 For systems programming, where direct access to hardware and dealing with real-time issues is a requirement, C is usually the language of choice.
     174For system programming, where direct access to hardware and dealing with real-time issues is a requirement, C is usually the language of choice.
    172175As well, there are millions of lines of C legacy code, forming the base for many software development projects (especially on UNIX systems).
    173176The TIOBE index (\url{http://www.tiobe.com/tiobe_index}) for March 2016 shows programming-language popularity, with Java 20.5\%, C 14.5\%, \CC 6.7\%, \CS 4.3\%, Python 4.3\%, and all other programming languages below 3\%.
     177As well, for 30 years, C has been the number 1 and 2 most popular programming language:
     178\begin{center}
     179\setlength{\tabcolsep}{1.5ex}
     180\begin{tabular}{@{}r|c|c|c|c|c|c|c@{}}
     181Ranking & 2016  & 2011  & 2006  & 2001  & 1996  & 1991  & 1986          \\
     182\hline
     183Java    & 1             & 1             & 1             & 3             & 29    & -             & -                     \\
     184\hline
     185\R{C}   & \R{2} & \R{2} & \R{2} & \R{1} & \R{1} & \R{1} & \R{1}         \\
     186\hline
     187\CC             & 3             & 3             & 3             & 2             & 2             & 2             & 7                     \\
     188\end{tabular}
     189\end{center}
    174190Hence, C is still an extremely important programming language, with double the usage of \CC, where \CC itself is largely C code.
    175191Finally, love it or hate it, C has been an important and influential part of computer science for 40 years and it appears it will continue to be for many more years.
     
    178194The goal of this project is to engineer modern language features into C in an evolutionary rather than revolutionary way.
    179195\CC~\cite{c++,ANSI14:C++} is an example of a similar project;
    180 however, it largely extended the language, and did not address existing problems.\footnote{%
     196however, it largely extended the language, and did not address many existing problems.\footnote{%
    181197Two important existing problems addressed were changing the type of character literals from ©int© to ©char© and enumerator from ©int© to the type of its enumerators.}
    182 Fortran~\cite{Fortran08}, Ada~\cite{Ada12}, and Cobol~\cite{Cobol14} are examples of programming languages that took an evolutionary approach, where modern language features are added and problems fixed within the framework of the existing language.
     198Fortran~\cite{Fortran08}, Ada~\cite{Ada12}, and Cobol~\cite{Cobol14} are examples of programming languages that took an evolutionary approach, where modern language features (e.g., objects, concurrency) are added and problems fixed within the framework of the existing language.
    183199Java~\cite{Java8}, Go~\cite{Go}, Rust~\cite{Rust} and D~\cite{D} are examples of the revolutionary approach for modernizing C/\CC, resulting in a new language rather than an extension of the descendent.
    184200These languages have different syntax and semantics from C, and do not interoperate directly with C, largely because of garbage collection.
    185201As a result, there is a significant learning curve to move to these languages, and C legacy-code must be rewritten.
    186 These costs can be prohibitive for many companies with a large software base in C/\CC, and many programmers that require retraining to a new programming language.
    187 
    188 The result of this project is a language that is largely backwards compatible with C11~\cite{C11}, but containing many modern language features and fixing some of the well known C problems.
    189 Without significant extension to the C programming language, C will be unable to cope with the needs of modern programming problems and programmers;
     202These costs can be prohibitive for many companies with a large software base in C/\CC, and a significant number of programmers requiring retraining to a new programming language.
     203
     204The result of this project is a language that is largely backwards compatible with C11~\cite{C11}, but fixing some of the well known C problems and containing many modern language features.
     205Without significant extension to the C programming language, it is becoming unable to cope with the needs of modern programming problems and programmers;
    190206as a result, it will fade into disuse.
    191207Considering the large body of existing C code and programmers, there is significant impetus to ensure C is transformed into a modern programming language.
     
    200216This feature allows users of \CFA to take advantage of the existing panoply of C libraries from inside their \CFA code.
    201217In fact, one of the biggest issues for any new programming language is establishing a minimum level of library code to support a large body of activities.
    202 Programming-language developers often state that adequate library support takes more work than designing and implementing the language itself.
     218Language developers often state that adequate library support takes more work than designing and implementing the language itself.
    203219Like \CC, \CFA starts with immediate access to all exiting C libraries, and in many cases, can easily wrap library routines with simpler and safer interfaces, at very low cost.
     220Hence, \CFA begins by leveraging the large repository of C libraries with little cost.
    204221
    205222However, it is necessary to differentiate between C and \CFA code because of name overloading, as for \CC.
    206 For example, the C math-library provides the following routines for computing the absolute value of the basic type: ©abs©, ©labs©, ©llabs©, ©fabs©, ©fabsf©, ©fabsl©, ©cabsf©, ©cabs©, and ©cabsl©.
    207 Whereas, \CFA wraps each of these routines into one with the common name ©abs©.
     223For example, the C math-library provides the following routines for computing the absolute value of the basic types: ©abs©, ©labs©, ©llabs©, ©fabs©, ©fabsf©, ©fabsl©, ©cabsf©, ©cabs©, and ©cabsl©.
     224Whereas, \CFA wraps each of these routines into ones with the common name ©abs©:
    208225\begin{lstlisting}
    209226char abs( char );
    210227extern "C" {
    211 int abs( int );                         // use default C routine for int
     228int abs( int );                                 // use default C routine for int
    212229} // extern "C"
    213230long int abs( long int );
     
    233250\section[Compiling CFA Program]{Compiling \CFA Program}
    234251
    235 The command ©cfa© is used to compile \CFA program(s).
    236 This command works like the GNU ©gcc©\index{gcc} command, e.g.:
     252The command ©cfa© is used to compile \CFA program(s), and is based on the GNU ©gcc©\index{gcc} command, e.g.:
    237253\begin{lstlisting}
    238254cfa§\indexc{cfa}\index{compilation!cfa@©cfa©}§ [ gcc-options ] C/§\CFA§-files [ assembler/loader-files ]
     
    240256By default, \CFA programs having the following ©gcc© flags turned on:
    241257\begin{description}
    242 \item\hspace*{-4pt}\Indexc{-std=gnu99}\index{compilation option!-std=gnu99@{©-std=gnu99©}}
     258\item\hspace*{-0.6ex}\Indexc{-std=gnu99}\index{compilation option!-std=gnu99@{©-std=gnu99©}}
    243259The 1999 C standard plus GNU extensions.
    244 \item\hspace*{-4pt}\Indexc{-fgnu89-¶inline¶}\index{compilation option!-fgnu89-inline@{©-fgnu89-¶inline¶©}}
     260\item\hspace*{-0.6ex}\Indexc{-fgnu89-¶inline¶}\index{compilation option!-fgnu89-inline@{©-fgnu89-¶inline¶©}}
    245261Use the traditional GNU semantics for inline routines in C99 mode, which allows inline routines in header files.
    246262\end{description}
    247263The following new \CFA option is available:
    248264\begin{description}
    249 \item\hspace*{-4pt}\Indexc{-CFA}\index{compilation option!-CFA@{©-CFA©}}
     265\item\hspace*{-0.6ex}\Indexc{-CFA}\index{compilation option!-CFA@{©-CFA©}}
    250266Only the C preprocessor and the \CFA translator steps are performed and the transformed program is written to standard output, which makes it possible to examine the code generated by the \CFA translator.
    251267\end{description}
     
    253269The following preprocessor variables are available:
    254270\begin{description}
    255 \item\hspace*{-4pt}\Indexc{__CFA__}\index{preprocessor variables!__CFA__@{©__CFA__©}}
     271\item\hspace*{-0.6ex}\Indexc{__CFA__}\index{preprocessor variables!__CFA__@{©__CFA__©}}
    256272is always available during preprocessing and its value is the current major \Index{version number} of \CFA.\footnote{
    257273The C preprocessor allows only integer values in a preprocessor variable so a value like ``\Version'' is not allowed.
    258274Hence, the need to have three variables for the major, minor and patch version number.}
    259275
    260 \item\hspace*{-4pt}\Indexc{__CFA_MINOR__}\index{preprocessor variables!__CFA_MINOR__@{©__CFA_MINOR__©}}
     276\item\hspace*{-0.6ex}\Indexc{__CFA_MINOR__}\index{preprocessor variables!__CFA_MINOR__@{©__CFA_MINOR__©}}
    261277is always available during preprocessing and its value is the current minor \Index{version number} of \CFA.
    262278
    263 \item\hspace*{-4pt}\Indexc{__CFA_PATCH__}\index{preprocessor variables!__CFA_PATCH__@©__CFA_PATCH__©}
     279\item\hspace*{-0.6ex}\Indexc{__CFA_PATCH__}\index{preprocessor variables!__CFA_PATCH__@©__CFA_PATCH__©}
    264280is always available during preprocessing and its value is the current patch \Index{version number} of \CFA.
    265281
    266 \item\hspace*{-4pt}\Indexc{__CFORALL__}\index{preprocessor variables!__CFORALL__@©__CFORALL__©}
    267 is always available during preprocessing and it has no value.
     282\item\hspace*{-0.6ex}\Indexc{__CFA__}\index{preprocessor variables!__CFA__@©__CFA__©} and \Indexc{__CFORALL__}\index{preprocessor variables!__CFORALL__@©__CFORALL__©}
     283are always available during preprocessing and have no value.
    268284\end{description}
    269285
     
    272288\begin{lstlisting}
    273289#ifndef __CFORALL__
    274 #include <stdio.h>                      // C header file
     290#include <stdio.h>                              // C header file
    275291#else
    276 #include <fstream>                      // §\CFA{}§ header file
     292#include <fstream>                              // §\CFA{}§ header file
    277293#endif
    278294\end{lstlisting}
     
    284300Numeric constants are extended to allow \Index{underscore}s within constants\index{constant!underscore}, e.g.:
    285301\begin{lstlisting}
    286 2®_®147®_®483®_®648;                            // decimal constant
    287 56_ul;                                          // decimal unsigned long constant
    288 0_377;                                          // octal constant
    289 0x_ff_ff;                                       // hexadecimal constant
    290 0x_ef3d_aa5c;                           // hexadecimal constant
    291 3.141_592_654;                          // floating point constant
    292 10_e_+1_00;                                     // floating point constant
    293 0x_ff_ff_p_3;                           // hexadecimal floating point
    294 0x_1.ffff_ffff_p_128_l;         // hexadecimal floating point long constant
    295 L_"\x_ff_ee";                           // wide character constant
     3022®_®147®_®483®_®648;                                    // decimal constant
     30356_ul;                                                  // decimal unsigned long constant
     3040_377;                                                  // octal constant
     3050x_ff_ff;                                               // hexadecimal constant
     3060x_ef3d_aa5c;                                   // hexadecimal constant
     3073.141_592_654;                                  // floating point constant
     30810_e_+1_00;                                             // floating point constant
     3090x_ff_ff_p_3;                                   // hexadecimal floating point
     3100x_1.ffff_ffff_p_128_l;                 // hexadecimal floating point long constant
     311L_"\x_ff_ee";                                   // wide character constant
    296312\end{lstlisting}
    297313The rules for placement of underscores is as follows:
     
    311327\end{enumerate}
    312328It is significantly easier to read and enter long constants when they are broken up into smaller groupings (most cultures use comma or period among digits for the same purpose).
    313 This extension is backwards compatible, matches with the use of underscore in variable names, and appears in Ada and Java.
     329This extension is backwards compatible, matches with the use of underscore in variable names, and appears in Ada and Java 8.
    314330
    315331
     
    321337\begin{quote2}
    322338\begin{tabular}{@{}ll@{}}
    323 \begin{lstlisting}[aboveskip=0pt,belowskip=0pt]
    324 int *x[ 5 ]
     339\begin{lstlisting}
     340int *x[5]
    325341\end{lstlisting}
    326342&
     
    332348For example, a routine returning a pointer to an array of integers is defined and used in the following way:
    333349\begin{lstlisting}
    334 int (*f())[ 5 ] {...};  // definition mimics usage
    335 ... (*f())[ 3 ] += 1;
     350int (*f())[5] {...};                    // definition mimics usage
     351... (*f())[3] += 1;
    336352\end{lstlisting}
    337353Essentially, the return type is wrapped around the routine name in successive layers (like an onion).
    338354While attempting to make the two contexts consistent was a laudable goal, it has not worked out in practice.
    339355
    340 \CFA provides its own type, variable and routine declarations, using a slightly different syntax.
    341 The new declarations place modifiers to the left of the base type, while C declarations place modifiers to the right of the base type.
     356\CFA provides its own type, variable and routine declarations, using a different syntax.
     357The new declarations place qualifiers to the left of the base type, while C declarations place qualifiers to the right of the base type.
     358In the following example, \R{red} is for the base type and \B{blue} is for the qualifiers.
     359The \CFA declarations move the qualifiers to the left of the base type, i.e., blue to the left of the red, while the qualifiers have the same meaning but are ordered left to left to right to specify the variable's type.
     360\begin{quote2}
     361\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     362\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
     363\begin{lstlisting}
     364ß[5] *ß ®int® x1;
     365ß* [5]ß ®int® x2;
     366ß[* [5] int]ß f®( int p )®;
     367\end{lstlisting}
     368&
     369\begin{lstlisting}
     370®int® ß*ß x1 ß[5]ß;
     371®int® ß(*ßx2ß)[5]ß;
     372ßint (*ßf®( int p )®ß)[5]ß;
     373\end{lstlisting}
     374\end{tabular}
     375\end{quote2}
    342376The only exception is bit field specification, which always appear to the right of the base type.
    343 C and the new \CFA declarations may appear together in the same program block, but cannot be mixed within a specific declaration.
    344 
    345 In \CFA declarations, the same tokens are used as in C: the character ©*© is used to indicate a pointer, square brackets ©[©\,©]© are used to represent an array, and parentheses ©()© are used to indicate a routine parameter.
    346 However, unlike C, \CFA type declaration tokens are specified from left to right and the entire type specification is distributed across all variables in the declaration list.
     377% Specifically, the character ©*© is used to indicate a pointer, square brackets ©[©\,©]© are used to represent an array or function return value, and parentheses ©()© are used to indicate a routine parameter.
     378However, unlike C, \CFA type declaration tokens are distributed across all variables in the declaration list.
    347379For instance, variables ©x© and ©y© of type pointer to integer are defined in \CFA as follows:
    348380\begin{quote2}
    349 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    350 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
    351 \begin{lstlisting}
    352 ®* int x, y;®
     381\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     382\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
     383\begin{lstlisting}
     384®*® int x, y;
    353385\end{lstlisting}
    354386&
    355387\begin{lstlisting}
    356 int *x, *y;
     388int ®*®x, ®*®y;
    357389\end{lstlisting}
    358390\end{tabular}
     
    360392Other examples are:
    361393\begin{quote2}
    362 \begin{tabular}{@{}l@{\hspace{30pt}}l@{\hspace{20pt}}l@{}}
    363 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c@{\hspace{20pt}}}{\textbf{C}}        \\
     394\begin{tabular}{@{}l@{\hspace{3em}}l@{\hspace{2em}}l@{}}
     395\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c@{\hspace{2em}}}{\textbf{C}} \\
    364396\begin{lstlisting}
    365397[ 5 ] int z;
     
    397429\end{quote2}
    398430
    399 All type qualifiers, i.e., ©const© and ©volatile©, are used in the normal way with the new declarations but appear left to right, e.g.:
     431All type qualifiers, e.g., ©const©, ©volatile©, etc., are used in the normal way with the new declarations and also appear left to right, e.g.:
    400432\begin{quote2}
    401 \begin{tabular}{@{}l@{\hspace{30pt}}l@{\hspace{20pt}}l@{}}
    402 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c@{\hspace{20pt}}}{\textbf{C}}        \\
     433\begin{tabular}{@{}l@{\hspace{1em}}l@{\hspace{1em}}l@{}}
     434\multicolumn{1}{c@{\hspace{1em}}}{\textbf{\CFA}}        & \multicolumn{1}{c@{\hspace{1em}}}{\textbf{C}} \\
    403435\begin{lstlisting}
    404436const * const int x;
     
    417449\end{tabular}
    418450\end{quote2}
    419 All declaration qualifiers, i.e., ©extern©, ©static©, etc., are used in the normal way with the new declarations but can only appear at the start of a \CFA routine declaration,\footnote{\label{StorageClassSpecifier}
     451All declaration qualifiers, e.g., ©extern©, ©static©, etc., are used in the normal way with the new declarations but can only appear at the start of a \CFA routine declaration,\footnote{\label{StorageClassSpecifier}
    420452The placement of a storage-class specifier other than at the beginning of the declaration specifiers in a declaration is an obsolescent feature.~\cite[\S~6.11.5(1)]{C11}} e.g.:
    421453\begin{quote2}
    422 \begin{tabular}{@{}l@{\hspace{30pt}}l@{\hspace{20pt}}l@{}}
    423 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c@{\hspace{20pt}}}{\textbf{C}}        \\
     454\begin{tabular}{@{}l@{\hspace{3em}}l@{\hspace{2em}}l@{}}
     455\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c@{\hspace{2em}}}{\textbf{C}} \\
    424456\begin{lstlisting}
    425457extern [ 5 ] int x;
     
    443475e.g.:
    444476\begin{lstlisting}
    445 x;                                              // int x
    446 *y;                                             // int *y
    447 f( p1, p2 );                    // int f( int p1, int p2 );
    448 f( p1, p2 ) {}                  // int f( int p1, int p2 ) {}
    449 \end{lstlisting}
    450 
    451 As stated above, the two styles of declaration may appear together in the same block.
     477x;                                                              // int x
     478*y;                                                             // int *y
     479f( p1, p2 );                                    // int f( int p1, int p2 );
     480f( p1, p2 ) {}                                  // int f( int p1, int p2 ) {}
     481\end{lstlisting}
     482
     483Finally, new \CFA declarations may appear together with C declarations in the same program block, but cannot be mixed within a specific declaration.
    452484Therefore, a programmer has the option of either continuing to use traditional C declarations or take advantage of the new style.
    453485Clearly, both styles need to be supported for some time due to existing C-style header-files, particularly for UNIX systems.
     
    458490The new declaration syntax can be used in other contexts where types are required, e.g., casts and the pseudo-routine ©sizeof©:
    459491\begin{quote2}
    460 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    461 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
    462 \begin{lstlisting}
    463 y = (* int)x;
    464 i = sizeof([ 5 ] * int);
     492\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     493\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
     494\begin{lstlisting}
     495y = (®* int®)x;
     496i = sizeof(®[ 5 ] * int®);
    465497\end{lstlisting}
    466498&
    467499\begin{lstlisting}
    468 y = (int *)x;
    469 i = sizeof(int *[ 5 ]);
     500y = (®int *®)x;
     501i = sizeof(®int *[ 5 ]®);
    470502\end{lstlisting}
    471503\end{tabular}
     
    476508
    477509\CFA also supports a new syntax for routine definition, as well as ISO C and K\&R routine syntax.
    478 The point of the new syntax is to allow returning multiple values from a routine~\cite{CLU,Galletly96}, e.g.:
     510The point of the new syntax is to allow returning multiple values from a routine~\cite{Galletly96,CLU}, e.g.:
    479511\begin{lstlisting}
    480512®[ int o1, int o2, char o3 ]® f( int i1, char i2, char i3 ) {
     
    490522Declaration qualifiers can only appear at the start of a routine definition, e.g.:
    491523\begin{lstlisting}
    492 extern [ int x ] g( int y ) {§\,§}
     524®extern® [ int x ] g( int y ) {§\,§}
    493525\end{lstlisting}
    494526Lastly, if there are no output parameters or input parameters, the brackets and/or parentheses must still be specified;
    495527in both cases the type is assumed to be void as opposed to old style C defaults of int return type and unknown parameter types, respectively, as in:
    496528\begin{lstlisting}
    497 [§\,§] g();                                             // no input or output parameters
    498 [ void ] g( void );                     // no input or output parameters
     529[§\,§] g();                                                     // no input or output parameters
     530[ void ] g( void );                             // no input or output parameters
    499531\end{lstlisting}
    500532
     
    503535[ i, j, ch ] = f( 3, 'a', ch );
    504536\end{lstlisting}
    505 The list of return values from f and the grouping on the left-hand side of the assignment is called a tuple and discussed in Section 12.
     537The list of return values from f and the grouping on the left-hand side of the assignment is called a \newterm{return list} and discussed in Section 12.
    506538
    507539\CFA style declarations cannot be used to declare parameters for K\&R style routine definitions because of the following ambiguity:
     
    514546\begin{lstlisting}
    515547typedef int foo;
    516 int f( int (* foo) );           // foo is redefined as a parameter name
     548int f( int (* foo) );                   // foo is redefined as a parameter name
    517549\end{lstlisting}
    518550The string ``©int (* foo)©'' declares a C-style named-parameter of type pointer to an integer (the parenthesis are superfluous), while the same string declares a \CFA style unnamed parameter of type routine returning integer with unnamed parameter of type pointer to foo.
    519 The redefinition of a type name in a parameter list is the only context in C where the character ©*© can appear to the left of a type name, and \CFA relies on all type modifier characters appearing to the right of the type name.
     551The redefinition of a type name in a parameter list is the only context in C where the character ©*© can appear to the left of a type name, and \CFA relies on all type qualifier characters appearing to the right of the type name.
    520552The inability to use \CFA declarations in these two contexts is probably a blessing because it precludes programmers from arbitrarily switching between declarations forms within a declaration contexts.
    521553
    522554C-style declarations can be used to declare parameters for \CFA style routine definitions, e.g.:
    523555\begin{lstlisting}
    524 [ int ] f( * int, int * );      // returns an integer, accepts 2 pointers to integers
    525 [ * int, int * ] f( int );      // returns 2 pointers to integers, accepts an integer
     556[ int ] f( * int, int * );              // returns an integer, accepts 2 pointers to integers
     557[ * int, int * ] f( int );              // returns 2 pointers to integers, accepts an integer
    526558\end{lstlisting}
    527559The reason for allowing both declaration styles in the new context is for backwards compatibility with existing preprocessor macros that generate C-style declaration-syntax, as in:
    528560\begin{lstlisting}
    529561#define ptoa( n, d ) int (*n)[ d ]
    530 int f( ptoa(p,5) ) ...          // expands to int f( int (*p)[ 5 ] )
    531 [ int ] f( ptoa(p,5) ) ...      // expands to [ int ] f( int (*p)[ 5 ] )
     562int f( ptoa( p, 5 ) ) ...               // expands to int f( int (*p)[ 5 ] )
     563[ int ] f( ptoa( p, 5 ) ) ...   // expands to [ int ] f( int (*p)[ 5 ] )
    532564\end{lstlisting}
    533565Again, programmers are highly encouraged to use one declaration form or the other, rather than mixing the forms.
    534566
    535567
    536 \subsection{Returning Values}
    537 
    538 Named return values handle the case where it is necessary to define a local variable whose value is then returned in a ©return© statement, as in:
     568\subsection{Named Return Values}
     569
     570\Index{Named return values} handle the case where it is necessary to define a local variable whose value is then returned in a ©return© statement, as in:
    539571\begin{lstlisting}
    540572int f() {
     
    545577\end{lstlisting}
    546578Because the value in the return variable is automatically returned when a \CFA routine terminates, the ©return© statement \emph{does not} contain an expression, as in:
    547 \begin{lstlisting}
    548 ®[ int x ]® f() {
    549         ... x = 0; ... x = y; ...
    550         ®return;® // implicitly return x
    551 }
    552 \end{lstlisting}
    553 When the return is encountered, the current value of ©x© is returned to the calling routine.
     579\newline
     580\begin{minipage}{\linewidth}
     581\begin{lstlisting}
     582®[ int x, int y ]® f() {
     583        int z;
     584        ... x = 0; ... y = z; ...
     585        ®return;® // implicitly return x, y
     586}
     587\end{lstlisting}
     588\end{minipage}
     589\newline
     590When the return is encountered, the current values of ©x© and ©y© are returned to the calling routine.
    554591As well, ``falling off the end'' of a routine without a ©return© statement is permitted, as in:
    555592\begin{lstlisting}
    556 [ int x ] f() {
    557         ... x = 0; ... x = y; ...
    558 } // implicitly return x
    559 \end{lstlisting}
    560 In this case, the current value of ©x© is returned to the calling routine just as if a ©return© had been encountered.
     593[ int x, int y ] f() {
     594        ...
     595} // implicitly return x, y
     596\end{lstlisting}
     597In this case, the current values of ©x© and ©y© are returned to the calling routine just as if a ©return© had been encountered.
    561598
    562599
     
    566603as well, parameter names are optional, e.g.:
    567604\begin{lstlisting}
    568 [ int x ] f ();                         // returning int with no parameters
    569 [ * int ] g (int y);            // returning pointer to int with int parameter
    570 [ ] h (int,char);                       // returning no result with int and char parameters
    571 [ * int,int ] j (int);          // returning pointer to int and int, with int parameter
     605[ int x ] f ();                                 // returning int with no parameters
     606[ * int ] g (int y);                    // returning pointer to int with int parameter
     607[ ] h (int,char);                               // returning no result with int and char parameters
     608[ * int,int ] j (int);                  // returning pointer to int and int, with int parameter
    572609\end{lstlisting}
    573610This syntax allows a prototype declaration to be created by cutting and pasting source text from the routine definition header (or vice versa).
    574611It is possible to declare multiple routine-prototypes in a single declaration, but the entire type specification is distributed across \emph{all} routine names in the declaration list (see~\VRef{s:Declarations}), e.g.:
    575612\begin{quote2}
    576 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    577 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
     613\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     614\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
    578615\begin{lstlisting}
    579616[ int ] f(int), g;
     
    604641for example, the following is incorrect:
    605642\begin{lstlisting}
    606 * [ int x ] f () fp;            // routine name "f" is not allowed
     643* [ int x ] f () fp;                    // routine name "f" is not allowed
    607644\end{lstlisting}
    608645
     
    737774While in theory default arguments can be simulated with overloading, as in:
    738775\begin{quote2}
    739 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    740 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{default arguments}}  & \multicolumn{1}{c}{\textbf{overloading}}      \\
     776\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     777\multicolumn{1}{c@{\hspace{3em}}}{\textbf{default arguments}}   & \multicolumn{1}{c}{\textbf{overloading}}      \\
    741778\begin{lstlisting}
    742779void p( int x, int y = 2, int z = 3 ) {...}
     
    773810\CFA allows \Index{type nesting}, and type qualification of the nested types, where as C hoists\index{type hoisting} (refactors) nested types into the enclosing scope and has no type qualification.
    774811\begin{quote2}
    775 \begin{tabular}{@{}l@{\hspace{30pt}}l|l@{}}
    776 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{C Type Nesting}}     & \multicolumn{1}{c}{\textbf{C Implicit Hoisting}}      & \multicolumn{1}{|c}{\textbf{\CFA}}    \\
     812\begin{tabular}{@{}l@{\hspace{3em}}l|l@{}}
     813\multicolumn{1}{c@{\hspace{3em}}}{\textbf{C Type Nesting}}      & \multicolumn{1}{c}{\textbf{C Implicit Hoisting}}      & \multicolumn{1}{|c}{\textbf{\CFA}}    \\
    777814\hline
    778815\begin{lstlisting}
     
    880917
    881918
    882 \section{Tuples}
     919\section{Lexical List}
    883920
    884921In C and \CFA, lists of elements appear in several contexts, such as the parameter list for a routine call.
    885922(More contexts are added shortly.)
    886 A list of such elements is called a tuple.
    887 The general syntax of a tuple is:
     923A list of such elements is called a \newterm{lexical list}.
     924The general syntax of a lexical list is:
    888925\begin{lstlisting}
    889926[ §\emph{exprlist}§ ]
    890927\end{lstlisting}
    891928where ©$\emph{exprlist}$© is a list of one or more expressions separated by commas.
    892 The brackets, ©[]©, allow differentiating between tuples and expressions containing the C comma operator.
    893 The following are examples of tuples:
     929The brackets, ©[]©, allow differentiating between lexical lists and expressions containing the C comma operator.
     930The following are examples of lexical lists:
    894931\begin{lstlisting}
    895932[ x, y, z ]
     
    11801217\begin{figure}
    11811218\centering
    1182 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    1183 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
     1219\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     1220\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
    11841221\begin{lstlisting}
    11851222®L1:® for ( ... ) {
     
    12111248\vspace*{0.25in}
    12121249
    1213 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    1214 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{C}}        \\
     1250\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     1251\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{C}}        \\
    12151252\begin{lstlisting}
    12161253®L1®: for ( ... ) {
     
    14531490Therefore, the ©case© clause is extended with a list of values, as in:
    14541491\begin{quote2}
    1455 \begin{tabular}{@{}l@{\hspace{30pt}}l@{\hspace{20pt}}l@{}}
    1456 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c@{\hspace{20pt}}}{\textbf{C}}        \\
     1492\begin{tabular}{@{}l@{\hspace{3em}}l@{\hspace{2em}}l@{}}
     1493\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c@{\hspace{2em}}}{\textbf{C}} \\
    14571494\begin{lstlisting}
    14581495switch ( i ) {
     
    14851522In addition, two forms of subranges are allowed to specify case values: the GNU C form and a new \CFA form.
    14861523\begin{quote2}
    1487 \begin{tabular}{@{}l@{\hspace{30pt}}l@{\hspace{20pt}}l@{}}
    1488 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c@{\hspace{20pt}}}{\textbf{GNU C}}    \\
     1524\begin{tabular}{@{}l@{\hspace{3em}}l@{\hspace{2em}}l@{}}
     1525\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c@{\hspace{2em}}}{\textbf{GNU C}}     \\
    14891526\begin{lstlisting}
    14901527switch ( i ) {
     
    20072044Auto type-inferencing occurs in a declaration where a variable's type is inferred from its initialization expression type.
    20082045\begin{quote2}
    2009 \begin{tabular}{@{}l@{\hspace{30pt}}ll@{}}
    2010 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CC}}        & \multicolumn{1}{c}{©gcc©}\index{gcc} \\
     2046\begin{tabular}{@{}l@{\hspace{3em}}ll@{}}
     2047\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CC}} & \multicolumn{1}{c}{©gcc©}\index{gcc} \\
    20112048\begin{lstlisting}
    20122049
     
    41104147The general case is printing out a sequence of variables separated by whitespace.
    41114148\begin{quote2}
    4112 \begin{tabular}{@{}l@{\hspace{30pt}}l@{}}
    4113 \multicolumn{1}{c@{\hspace{30pt}}}{\textbf{\CFA}}       & \multicolumn{1}{c}{\textbf{\CC}}      \\
     4149\begin{tabular}{@{}l@{\hspace{3em}}l@{}}
     4150\multicolumn{1}{c@{\hspace{3em}}}{\textbf{\CFA}}        & \multicolumn{1}{c}{\textbf{\CC}}      \\
    41144151\begin{lstlisting}
    41154152int x = 0, y = 1, z = 2;
  • doc/working/resolver_design.md

    r6cbc25a r7ff30d07  
    8181
    8282## Conversion Costs ##
    83 Each possible resolution of an expression has a _cost_ consisting of four
    84 integer components: _unsafe_ conversion cost, _polymorphic_ specialization
    85 cost, _safe_ conversion cost, and a _count_ of conversions.
    86 These components form a lexically-ordered tuple which can be summed
    87 element-wise; summation starts at `(0, 0, 0, 0)`.
     83Each possible resolution of an expression has a _cost_ tuple consisting of
     84the following components: _unsafe_ conversion cost, _polymorphic_
     85specialization cost, _safe_ conversion cost, a count of _explicit_
     86conversions, and _qualifier_ conversion cost.
     87These components are lexically-ordered and can be summed element-wise;
     88summation starts at `(0, 0, 0, 0, 0)`.
    8889
    8990### Lvalue and Qualifier Conversions ###
     
    12241225programmers.
    12251226
     1227## Resolver Architecture ##
     1228
     1229### Function Application Resolution ###
     1230Our resolution algorithm for function application expressions is based on
     1231Baker's[3] single-pass bottom-up algorithm, with Cormack's[4] single-pass
     1232top-down algorithm applied where appropriate as an optimization.
     1233Broadly speaking, the cost of this resolution per expression will be
     1234proportional to `i^d`, where `i` is the number of interpretations of each
     1235program symbol, and `d` is the maximum depth of the expression DAG.
     1236Since `d` is determined by the user programmer (in general, bounded by a small
     1237constant), opportunities for resolver optimization primarily revolve around
     1238minimizing `i`, the number of interpretations of each symbol that are
     1239considered.
     1240
     1241[3] Baker, Theodore P. A one-pass algorithm for overload resolution in Ada.
     1242ACM Transactions on Programming Languages and Systems (1982) 4:4 p.601-614
     1243
     1244[4] Cormack, Gordon V. An algorithm for the selection of overloaded functions
     1245in Ada. SIGPLAN Notices (1981) 16:2 p.48-52
     1246
     1247Unlike Baker, our system allows implicit type conversions for function
     1248arguments and return types; the problem then becomes to find the valid
     1249interpretation for an expression that has the unique minimal conversion cost,
     1250if such exists.
     1251Interpretations can be produced both by overloaded names and implicit
     1252conversions applied to existing interpretations; we have proposals to reduce
     1253the number of interpretations considered from both sources.
     1254To simplify the problem for this discussion, we will consider application
     1255resolution restricted to a domain of functions applied to variables, possibly
     1256in a nested manner (e.g. `f( g( x ), y )`, where `x` and `y` are variables and
     1257`f` and `g` are functions), and possibly in a typed context such as a variable
     1258initialization (e.g. `int i = f( x );`); the other aspects of Cforall type
     1259resolution should be able to be straightforwardly mapped into this model.
     1260The types of the symbol tables used for variable and function declarations
     1261look somewhat like the following:
     1262
     1263        variable_table = name_map( variable_name, variable_map )
     1264       
     1265        function_table = name_map( function_name, function_map )
     1266       
     1267        variable_map = multi_index( by_type( variable_type ),
     1268                                    variable_decl_set )
     1269
     1270        function_map = multi_index( by_int( n_params ),
     1271                                                                by_type( return_type ),
     1272                                                                function_decl_set )
     1273
     1274`variable_name` and `function_name` are likely simple strings, with `name_map`
     1275a hash table (or perhaps trie) mapping string keys to values.
     1276`variable_decl_set` and `function_decl_set` can be thought of for the moment
     1277as simple bags of typed declarations, where the declaration types are linked
     1278to the graph of available conversions for that type.
     1279In a typed context both the `variable_decl_set` and the `function_decl_set`
     1280should be able to be selected upon by type; this is accomplished by the
     1281`by_type` index of both `variable_map` and `function_map`.
     1282The `by_int` index of `function_map` also provides a way to select functions
     1283by their number of parameters; this index may be used to swiftly discard any
     1284function declaration which does not have the appropriate number of parameters
     1285for the argument interpretations being passed to it; given the likely small
     1286number of entries in this map, it is possible that a binary search of a sorted
     1287vector or even a linear search of an unsorted vector would be more efficient
     1288than the usual hash-based index.
     1289
     1290Given these data structures, the general outline of our algorithm follows
     1291Baker, with Cormack's algorithm used as a heuristic filter in typed contexts.
     1292
     1293In an untyped context, we use a variant of Baker's bottom-up algorithm.
     1294The leaves of the interpretation DAG are drawn from the variable symbol table,
     1295with entries in the table each producing zero-cost interpretations, and each
     1296implicit conversion available to be applied to the type of an existing entry
     1297producing a further interpretation with the same cost as the conversion.
     1298As in Baker, if two or more interpretations have the same type, only the
     1299minimum cost interpretation with that type is produced; if there is no unique
     1300minimum cost interpretation than resolution with that type is ambiguous, and
     1301not permitted.
     1302It should be relatively simple to produce the list of interpretations sorted
     1303by cost by producing the interpretations via a breadth-first search of the
     1304conversion graph from the initial interpretations provided in the variable
     1305symbol table.
     1306
     1307To match a function at one of the internal nodes of the DAG, we first look up
     1308the function's name in the function symbol table, the appropriate number of
     1309parameters for the arguments that are provided through the `by_int` index of
     1310the returned `function_map`, then go through the resulting `function_decl_set`
     1311searching for functions where the parameter types can unify with the provided
     1312argument lists; any such matching function produces an interpretation with a
     1313cost that is the sum of its argument costs.
     1314Though this is not included in our simplified model, this unification step may
     1315include binding of polymorphic variables, which introduces a cost for the
     1316function binding itself which must be added to the argument costs.
     1317Also, checking of function assertions would likely be done at this step as
     1318well, possibly eliminating some possible matching functions (if no suitable
     1319assertions can be satisfied), or adding further conversion costs for the
     1320assertion satisfaction.
     1321Once the set of valid function interpretations is produced, these may also be
     1322expanded by the graph of implicit conversions on their return types, as the
     1323variable interpretations were.
     1324
     1325This implicit conversion-based expansion of interpretations should be skipped
     1326for the top-level expression if used in an untyped (void) context, e.g. for
     1327`f` in `f( g ( x ) );` or `x` in `x;`.
     1328On the other hand, if the top-level expression specifies a type, e.g. in
     1329`int i = f( x );`, only top level expressions that return that type are
     1330relevant to the search, so the candidates for `f` can be filtered first by
     1331those that return `int` (or a type convertable to it); this can be
     1332accomplished by performing a top-down filter of the interpretations of `f` by
     1333the `by_type` index of the `function_map` in a manner similar to Cormack's[4]
     1334algorithm.
     1335
     1336In a typed context, such as an initialization expression
     1337`T x = f( g( y ), z );`, only interpretations of `f( g( y ), z )` which have
     1338type `T` are valid; since there are likely to be valid interpretations of
     1339`f( g( y ), z )` which cannot be used to initialize a variable of type `T`, we
     1340can use this information to reduce the number of interpretations considered.
     1341Drawing from Cormack[4], we first search for interpretations of `f` where the
     1342return type is `T`; by breadth-first-search of the conversion graph, it should
     1343be straightforward to order the interpretations of `f` by the cost to convert
     1344their return type to `T`.
     1345We can also filter out interpretations of `f` with less than two parameters,
     1346since both `g( y )` and `z` must produce at least one parameter; we may not,
     1347however, rule out interpretations of `f` with more than two parameters, as
     1348there may be a valid interpretation of `g( y )` as a function returning more
     1349than one parameter (if the expression was `f( y, z )` instead, we could use an
     1350exact parameter count, assuming that variables of tuple type don't exist).
     1351For each compatible interpretation of `f`, we can add the type of the first
     1352parameter of that interpretation of `f` to a set `S`, and recursively search
     1353for interpretations of `g( y )` that return some type `Si` in `S`, and
     1354similarly for interpretations of `z` that match the type of any of the second
     1355parameters of some `f`.
     1356Naturally, if no matching interpretation of `g( y )` can be found for the
     1357first parameter of some `f`, the type of the second parameter of that `f` will
     1358not be added to the set of valid types for `z`.
     1359Each node in this interpretation DAG is given a cost the same way it would be
     1360in the bottom-up approach, with the exception that when going top-down there
     1361must be a final bottom-up pass to sum the interpretation costs and sort them
     1362as appropriate.
     1363
     1364If a parameter type for some `f` is a polymorphic type variable that is left
     1365unbound by the return type (e.g. `forall(otype S) int f(S x, int y)`), the
     1366matching arguments should be found using the bottom-up algorithm above for
     1367untyped contexts, because the polymorphic type variable does not sufficiently
     1368constrain the available interpretations of the argument expression.
     1369Similarly, it would likely be an advantage to use top-down resolution for
     1370cast expressions (e.g. `(int)x`), even when those cast expressions are
     1371subexpressions of an otherwise untyped expression.
     1372It may also be fruitful to switch between the bottom-up and top-down
     1373algorithms if the number of valid interpretations for a subexpression or valid
     1374types for an argument exceeds some heuristic threshold, but finding such
     1375a threshold (if any exists) will require experimental data.
     1376This hybrid top-down/bottom-up search provides more opportunities for pruning
     1377interpretations than either a bottom-up or top-down approach alone, and thus
     1378may be more efficient than either.
     1379A top-down-only approach, however, devolves to linear search through every
     1380possible interpretation in the solution space in an untyped context, and is
     1381thus likely to be inferior to a strictly bottom-up approach, though this
     1382hypothesis needs to be empirically validated.
     1383
     1384Both Baker and Cormack explicitly generate all possible interpretations of a
     1385given expression; thinking of the set of interpretations of an expression as a
     1386list sorted by cost, this is an eager evaluation of the list.
     1387However, since we generally expect that user programmers will not often use
     1388high-cost implicit conversions, one potentially effective way to prune the
     1389search space would be to first find the minimal-cost interpretations of any
     1390given subexpression, then to save the resolution progress of the
     1391subexpressions and attempt to resolve the superexpression using only those
     1392subexpression interpretations.
     1393If no valid interpretation of the superexpression can be found, the resolver
     1394would then repeatedly find the next-most-minimal cost interpretations of the
     1395subexpressions and attempt to produce the minimal cost interpretation of the
     1396superexpression.
     1397This process would proceed until all possible subexpression interpretations
     1398have been found and considered.
     1399
     1400A middle ground between the eager and lazy approaches can be taken by
     1401considering the lexical order on the cost tuple; essentially, every
     1402interpretation in each of the classes below will be strictly cheaper than any
     1403interpretation in the class after it, so if a min-cost valid interpretation
     1404can be found while only generating interpretations in a given class, that
     1405interpretation is guaranteed to be the best possible one:
     1406
     14071. Interpretations without polymorphic functions or implicit conversions
     14082. Interpretations without polymorphic functions using only safe conversions
     14093. Interpretations using polymorphic functions without unsafe conversions
     14104. Interpretations using unsafe conversions
     1411
     1412In this lazy-eager approach, all the interpretations in one class would be
     1413eagerly generated, while the interpretations in the next class would only be
     1414considered if no match was found in the previous class.
     1415
    12261416## Appendix A: Partial and Total Orders ##
    12271417The `<=` relation on integers is a commonly known _total order_, and
  • src/CodeGen/CodeGenerator.cc

    r6cbc25a r7ff30d07  
    99// Author           : Richard C. Bilson
    1010// Created On       : Mon May 18 07:44:20 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Fri May 06 16:01:00 2016
    13 // Update Count     : 255
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Thu Jun  9 13:21:00 2016
     13// Update Count     : 256
    1414//
    1515
     
    251251        //*** Expressions
    252252        void CodeGenerator::visit( ApplicationExpr *applicationExpr ) {
     253                extension( applicationExpr );
    253254                if ( VariableExpr *varExpr = dynamic_cast< VariableExpr* >( applicationExpr->get_function() ) ) {
    254255                        OperatorInfo opInfo;
     
    366367
    367368        void CodeGenerator::visit( UntypedExpr *untypedExpr ) {
     369                extension( untypedExpr );
    368370                if ( NameExpr *nameExpr = dynamic_cast< NameExpr* >( untypedExpr->get_function() ) ) {
    369371                        OperatorInfo opInfo;
     
    450452
    451453        void CodeGenerator::visit( NameExpr *nameExpr ) {
     454                extension( nameExpr );
    452455                OperatorInfo opInfo;
    453456                if ( operatorLookup( nameExpr->get_name(), opInfo ) ) {
     
    460463
    461464        void CodeGenerator::visit( AddressExpr *addressExpr ) {
     465                extension( addressExpr );
    462466                output << "(&";
    463467                // this hack makes sure that we don't convert "constant_zero" to "0" if we're taking its address
     
    471475
    472476        void CodeGenerator::visit( CastExpr *castExpr ) {
     477                extension( castExpr );
    473478                output << "(";
    474479                if ( castExpr->get_results().empty() ) {
     
    493498
    494499        void CodeGenerator::visit( MemberExpr *memberExpr ) {
     500                extension( memberExpr );
    495501                memberExpr->get_aggregate()->accept( *this );
    496502                output << "." << mangleName( memberExpr->get_member() );
     
    498504
    499505        void CodeGenerator::visit( VariableExpr *variableExpr ) {
     506                extension( variableExpr );
    500507                OperatorInfo opInfo;
    501508                if ( variableExpr->get_var()->get_linkage() == LinkageSpec::Intrinsic && operatorLookup( variableExpr->get_var()->get_name(), opInfo ) && opInfo.type == OT_CONSTANT ) {
     
    508515        void CodeGenerator::visit( ConstantExpr *constantExpr ) {
    509516                assert( constantExpr->get_constant() );
     517                extension( constantExpr );
    510518                constantExpr->get_constant()->accept( *this );
    511519        }
    512520
    513521        void CodeGenerator::visit( SizeofExpr *sizeofExpr ) {
     522                extension( sizeofExpr );
    514523                output << "sizeof(";
    515524                if ( sizeofExpr->get_isType() ) {
     
    522531
    523532        void CodeGenerator::visit( AlignofExpr *alignofExpr ) {
     533                extension( alignofExpr );
    524534                // use GCC extension to avoid bumping std to C11
    525535                output << "__alignof__(";
     
    537547
    538548        void CodeGenerator::visit( OffsetofExpr *offsetofExpr ) {
     549                extension( offsetofExpr );
    539550                // use GCC builtin
    540551                output << "__builtin_offsetof(";
     
    549560
    550561        void CodeGenerator::visit( LogicalExpr *logicalExpr ) {
     562                extension( logicalExpr );
    551563                output << "(";
    552564                logicalExpr->get_arg1()->accept( *this );
     
    561573
    562574        void CodeGenerator::visit( ConditionalExpr *conditionalExpr ) {
     575                extension( conditionalExpr );
    563576                output << "(";
    564577                conditionalExpr->get_arg1()->accept( *this );
     
    571584
    572585        void CodeGenerator::visit( CommaExpr *commaExpr ) {
     586                extension( commaExpr );
    573587                output << "(";
    574588                commaExpr->get_arg1()->accept( *this );
     
    583597
    584598        void CodeGenerator::visit( AsmExpr *asmExpr ) {
     599                extension( asmExpr );
    585600                if ( asmExpr->get_inout() ) {
    586601                        output << "[ ";
  • src/CodeGen/CodeGenerator.h

    r6cbc25a r7ff30d07  
    1010// Created On       : Mon May 18 07:44:20 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Wed Mar  2 17:32:24 2016
    13 // Update Count     : 28
     12// Last Modified On : Thu Jun  9 13:15:58 2016
     13// Update Count     : 29
    1414//
    1515
     
    9696                        std::ostream& operator()(std::ostream & os);
    9797                };
     98
     99                void extension( Expression *expr ) {
     100                        if ( expr->get_extension() ) {
     101                                output << "__extension__ ";
     102                        } // if
     103                } // extension
    98104          private:
    99105
  • src/Common/utility.h

    r6cbc25a r7ff30d07  
    99// Author           : Richard C. Bilson
    1010// Created On       : Mon May 18 07:44:20 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Thu Apr 28 13:18:24 2016
    13 // Update Count     : 16
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jun  8 17:33:59 2016
     13// Update Count     : 22
    1414//
    1515
     
    3333}
    3434
     35template<typename T, typename U>
     36struct maybeBuild_t {
     37        static T * doit( const U *orig ) {
     38                if ( orig ) {
     39                        return orig->build();
     40                } else {
     41                        return 0;
     42                } // if
     43        }
     44};
     45
    3546template< typename T, typename U >
    3647static inline T * maybeBuild( const U *orig ) {
    37         if ( orig ) {
    38                 return orig->build();
    39         } else {
    40                 return 0;
    41         } // if
     48        return maybeBuild_t<T,U>::doit(orig);
    4249}
    4350
  • src/Parser/ExpressionNode.cc

    r6cbc25a r7ff30d07  
    1010// Created On       : Sat May 16 13:17:07 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Apr  8 15:43:05 2016
    13 // Update Count     : 296
     12// Last Modified On : Mon Jun 13 14:46:17 2016
     13// Update Count     : 307
    1414//
    1515
     
    3232using namespace std;
    3333
    34 ExpressionNode::ExpressionNode() : ParseNode(), argName( 0 ) {}
    35 
    36 ExpressionNode::ExpressionNode( const string *name ) : ParseNode( name ), argName( 0 ) {}
    37 
    38 ExpressionNode::ExpressionNode( const ExpressionNode &other ) : ParseNode( other.name ) {
     34ExpressionNode::ExpressionNode() : ParseNode() {}
     35
     36ExpressionNode::ExpressionNode( const string *name ) : ParseNode( name ) {}
     37
     38ExpressionNode::ExpressionNode( const ExpressionNode &other ) : ParseNode( other.name ), extension( other.extension ) {
    3939        if ( other.argName ) {
    4040                argName = other.argName->clone();
     
    344344
    345345Expression *DesignatorNode::build() const {
    346         Expression * ret = get_argName()->build();
     346        Expression * ret = maybeBuild<Expression>(get_argName());
    347347
    348348        if ( isArrayIndex ) {
     
    389389        "Cond", "NCond",
    390390        // diadic
    391         "SizeOf", "AlignOf", "OffsetOf", "Attr", "CompLit", "?+?", "?-?", "?*?", "?/?", "?%?", "||", "&&",
     391        "SizeOf", "AlignOf", "OffsetOf", "Attr", "?+?", "?-?", "?*?", "?/?", "?%?", "||", "&&",
    392392        "?|?", "?&?", "?^?", "Cast", "?<<?", "?>>?", "?<?", "?>?", "?<=?", "?>=?", "?==?", "?!=?",
    393393        "?=?", "?*=?", "?/=?", "?%=?", "?+=?", "?-=?", "?<<=?", "?>>=?", "?&=?", "?^=?", "?|=?",
     
    466466
    467467        if ( ! ( op = dynamic_cast<OperatorNode *>( function ) ) ) { // function as opposed to operator
    468                 return new UntypedExpr( function->build(), args, maybeBuild< Expression >( get_argName() ));
     468                return new UntypedExpr( maybeBuild<Expression>(function), args, maybeBuild< Expression >( get_argName() ));
    469469        } // if
    470470
     
    550550                        if ( dynamic_cast< VoidType* >( targetType ) ) {
    551551                                delete targetType;
    552                                 return new CastExpr( expr_node->build(), maybeBuild< Expression >( get_argName() ) );
     552                                return new CastExpr( maybeBuild<Expression>(expr_node), maybeBuild< Expression >( get_argName() ) );
    553553                        } else {
    554                                 return new CastExpr( expr_node->build(),targetType, maybeBuild< Expression >( get_argName() ) );
     554                                return new CastExpr( maybeBuild<Expression>(expr_node),targetType, maybeBuild< Expression >( get_argName() ) );
    555555                        } // if
    556556                }
     
    621621                        assert( var );
    622622                        if ( ! get_args()->get_link() ) {
    623                                 return new AttrExpr( var->build(), ( Expression*)0);
     623                                return new AttrExpr( maybeBuild<Expression>(var), ( Expression*)0);
    624624                        } else if ( TypeValueNode * arg = dynamic_cast<TypeValueNode *>( get_args()->get_link()) ) {
    625                                 return new AttrExpr( var->build(), arg->get_decl()->buildType());
     625                                return new AttrExpr( maybeBuild<Expression>(var), arg->get_decl()->buildType());
    626626                        } else {
    627                                 return new AttrExpr( var->build(), args.back());
    628                         } // if
    629                 }
    630           case OperatorNode::CompLit:
    631                 throw UnimplementedError( "C99 compound literals" );
    632                 // the short-circuited operators
     627                                return new AttrExpr( maybeBuild<Expression>(var), args.back());
     628                        } // if
     629                }
    633630          case OperatorNode::Or:
    634631          case OperatorNode::And:
     
    719716
    720717Expression *AsmExprNode::build() const {
    721         return new AsmExpr( maybeBuild< Expression >( inout ), (ConstantExpr *)constraint->build(), operand->build() );
     718        return new AsmExpr( maybeBuild< Expression >( inout ), (ConstantExpr *)maybeBuild<Expression>(constraint), maybeBuild<Expression>(operand) );
    722719}
    723720
     
    796793
    797794Expression *ValofExprNode::build() const {
    798         return new UntypedValofExpr ( get_body()->build(), maybeBuild< Expression >( get_argName() ) );
     795        return new UntypedValofExpr ( maybeBuild<Statement>(get_body()), maybeBuild< Expression >( get_argName() ) );
    799796}
    800797
     
    908905
    909906Expression *CompoundLiteralNode::build() const {
    910         Declaration * newDecl = type->build();                          // compound literal type
     907        Declaration * newDecl = maybeBuild<Declaration>(type); // compound literal type
    911908        if ( DeclarationWithType * newDeclWithType = dynamic_cast< DeclarationWithType * >( newDecl ) ) { // non-sue compound-literal type
    912                 return new CompoundLiteralExpr( newDeclWithType->get_type(), kids->build() );
     909                return new CompoundLiteralExpr( newDeclWithType->get_type(), maybeBuild<Initializer>(kids) );
    913910        // these types do not have associated type information
    914911        } else if ( StructDecl * newDeclStructDecl = dynamic_cast< StructDecl * >( newDecl )  ) {
    915                 return new CompoundLiteralExpr( new StructInstType( Type::Qualifiers(), newDeclStructDecl->get_name() ), kids->build() );
     912                return new CompoundLiteralExpr( new StructInstType( Type::Qualifiers(), newDeclStructDecl->get_name() ), maybeBuild<Initializer>(kids) );
    916913        } else if ( UnionDecl * newDeclUnionDecl = dynamic_cast< UnionDecl * >( newDecl )  ) {
    917                 return new CompoundLiteralExpr( new UnionInstType( Type::Qualifiers(), newDeclUnionDecl->get_name() ), kids->build() );
     914                return new CompoundLiteralExpr( new UnionInstType( Type::Qualifiers(), newDeclUnionDecl->get_name() ), maybeBuild<Initializer>(kids) );
    918915        } else if ( EnumDecl * newDeclEnumDecl = dynamic_cast< EnumDecl * >( newDecl )  ) {
    919                 return new CompoundLiteralExpr( new EnumInstType( Type::Qualifiers(), newDeclEnumDecl->get_name() ), kids->build() );
     916                return new CompoundLiteralExpr( new EnumInstType( Type::Qualifiers(), newDeclEnumDecl->get_name() ), maybeBuild<Initializer>(kids) );
    920917        } else {
    921918                assert( false );
  • src/Parser/ParseNode.h

    r6cbc25a r7ff30d07  
    99// Author           : Rodolfo G. Esteves
    1010// Created On       : Sat May 16 13:28:16 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Thu Apr 14 15:37:52 2016
    13 // Update Count     : 205
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Mon Jun 13 16:04:47 2016
     13// Update Count     : 240
    1414//
    1515
     
    2020#include <list>
    2121#include <iterator>
     22#include <memory>
    2223
    2324#include "Common/utility.h"
    2425#include "Parser/LinkageSpec.h"
    2526#include "SynTree/Type.h"
     27#include "SynTree/Expression.h"
    2628//#include "SynTree/Declaration.h"
    2729#include "Common/UniqueName.h"
     
    7981        ExpressionNode *set_argName( const std::string *aName );
    8082        ExpressionNode *set_argName( ExpressionNode *aDesignator );
     83        bool get_extension() const { return extension; }
     84        ExpressionNode *set_extension( bool exten ) { extension = exten; return this; }
    8185
    8286        virtual void print( std::ostream &, int indent = 0) const = 0;
     
    8791        void printDesignation ( std::ostream &, int indent = 0) const;
    8892  private:
    89         ExpressionNode *argName;
     93        ExpressionNode *argName = 0;
     94        bool extension = false;
     95};
     96
     97template< typename T >
     98struct maybeBuild_t<Expression, T> {
     99        static inline Expression * doit( const T *orig ) {
     100                if ( orig ) {
     101                        Expression *p = orig->build();
     102                        p->set_extension( orig->get_extension() );
     103                        return p;
     104                } else {
     105                        return 0;
     106                } // if
     107        }
    90108};
    91109
     
    179197                                Cond, NCond,
    180198                                // diadic
    181                                 SizeOf, AlignOf, OffsetOf, Attr, CompLit, Plus, Minus, Mul, Div, Mod, Or, And,
     199                                SizeOf, AlignOf, OffsetOf, Attr, Plus, Minus, Mul, Div, Mod, Or, And,
    182200                                BitOr, BitAnd, Xor, Cast, LShift, RShift, LThan, GThan, LEThan, GEThan, Eq, Neq,
    183201                                Assign, MulAssn, DivAssn, ModAssn, PlusAssn, MinusAssn, LSAssn, RSAssn, AndAssn, ERAssn, OrAssn,
     
    574592        while ( cur ) {
    575593                try {
    576                         SynTreeType *result = dynamic_cast< SynTreeType *>( cur->build() );
     594//                      SynTreeType *result = dynamic_cast< SynTreeType *>( maybeBuild<typename std::result_of<decltype(&NodeType::build)(NodeType)>::type>( cur ) );
     595                        SynTreeType *result = dynamic_cast< SynTreeType *>( maybeBuild<typename std::pointer_traits<decltype(cur->build())>::element_type>( cur ) );
    577596                        if ( result ) {
    578597                                *out++ = result;
  • src/Parser/StatementNode.cc

    r6cbc25a r7ff30d07  
    1010// Created On       : Sat May 16 14:59:41 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Jul 30 14:39:39 2015
    13 // Update Count     : 130
     12// Last Modified On : Thu Jun  9 14:18:46 2016
     13// Update Count     : 132
    1414//
    1515
     
    222222                                branches.pop_front();
    223223                        } // if
    224                         return new IfStmt( labs, notZeroExpr( get_control()->build() ), thenb, elseb );
     224                        return new IfStmt( labs, notZeroExpr( maybeBuild<Expression>(get_control()) ), thenb, elseb );
    225225                }
    226226          case While:
    227227                assert( branches.size() == 1 );
    228                 return new WhileStmt( labs, notZeroExpr( get_control()->build() ), branches.front() );
     228                return new WhileStmt( labs, notZeroExpr( maybeBuild<Expression>(get_control()) ), branches.front() );
    229229          case Do:
    230230                assert( branches.size() == 1 );
    231                 return new WhileStmt( labs, notZeroExpr( get_control()->build() ), branches.front(), true );
     231                return new WhileStmt( labs, notZeroExpr( maybeBuild<Expression>(get_control()) ), branches.front(), true );
    232232          case For:
    233233                {
     
    244244                        Expression *cond = 0;
    245245                        if ( ctl->get_condition() != 0 )
    246                                 cond = notZeroExpr( ctl->get_condition()->build() );
     246                                cond = notZeroExpr( maybeBuild<Expression>(ctl->get_condition()) );
    247247
    248248                        Expression *incr = 0;
    249249                        if ( ctl->get_change() != 0 )
    250                                 incr = ctl->get_change()->build();
     250                                incr = maybeBuild<Expression>(ctl->get_change());
    251251
    252252                        return new ForStmt( labs, init, cond, incr, branches.front() );
    253253                }
    254254          case Switch:
    255                 return new SwitchStmt( labs, get_control()->build(), branches );
     255                return new SwitchStmt( labs, maybeBuild<Expression>(get_control()), branches );
    256256          case Choose:
    257                 return new ChooseStmt( labs, get_control()->build(), branches );
     257                return new ChooseStmt( labs, maybeBuild<Expression>(get_control()), branches );
    258258          case Fallthru:
    259259                return new FallthruStmt( labs );
    260260          case Case:
    261                 return new CaseStmt( labs, get_control()->build(), branches );
     261                return new CaseStmt( labs, maybeBuild<Expression>(get_control()), branches );
    262262          case Default:
    263263                return new CaseStmt( labs, 0, branches, true );
     
    266266                        if ( get_target() == "" ) {                                     // computed goto
    267267                                assert( get_control() != 0 );
    268                                 return new BranchStmt( labs, get_control()->build(), BranchStmt::Goto );
     268                                return new BranchStmt( labs, maybeBuild<Expression>(get_control()), BranchStmt::Goto );
    269269                        } // if
    270270
  • src/Parser/parser.cc

    r6cbc25a r7ff30d07  
    52995299/* Line 1806 of yacc.c  */
    53005300#line 432 "parser.yy"
    5301     { (yyval.en) = (yyvsp[(2) - (2)].en); }
     5301    { (yyval.en) = (yyvsp[(2) - (2)].en)->set_extension( true ); }
    53025302    break;
    53035303
     
    58095809/* Line 1806 of yacc.c  */
    58105810#line 685 "parser.yy"
    5811     { (yyval.sn) = new StatementNode( (yyvsp[(2) - (2)].decl) ); }
     5811    { (yyval.sn) = new StatementNode( (yyvsp[(2) - (2)].decl) )/*->set_extension( true )*/; }
    58125812    break;
    58135813
     
    71227122/* Line 1806 of yacc.c  */
    71237123#line 1475 "parser.yy"
    7124     { (yyval.decl) = (yyvsp[(2) - (3)].decl); }
     7124    { (yyval.decl) = (yyvsp[(2) - (3)].decl)/*->set_extension( true )*/; }
    71257125    break;
    71267126
     
    71297129/* Line 1806 of yacc.c  */
    71307130#line 1478 "parser.yy"
    7131     { (yyval.decl) = (yyvsp[(2) - (3)].decl); }
     7131    { (yyval.decl) = (yyvsp[(2) - (3)].decl)/*->set_extension( true )*/; }
    71327132    break;
    71337133
     
    79137913/* Line 1806 of yacc.c  */
    79147914#line 1994 "parser.yy"
    7915     { (yyval.decl) = (yyvsp[(2) - (2)].decl); }
     7915    { (yyval.decl) = (yyvsp[(2) - (2)].decl)/*->set_extension( true )*/; }
    79167916    break;
    79177917
  • src/Parser/parser.yy

    r6cbc25a r7ff30d07  
    1010// Created On       : Sat Sep  1 20:22:55 2001
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Tue Jun  7 08:08:31 2016
    13 // Update Count     : 1560
     12// Last Modified On : Mon Jun 13 15:00:23 2016
     13// Update Count     : 1578
    1414//
    1515
     
    430430                { $$ = $1; }
    431431        | EXTENSION cast_expression                                                     // GCC
    432                 { $$ = $2; }
     432                { $$ = $2->set_extension( true ); }
    433433        | ptrref_operator cast_expression                                       // CFA
    434434                { $$ = new CompositeExprNode( $1, $2 ); }
     
    683683                { $$ = new StatementNode( $1 ); }
    684684        | EXTENSION declaration                                                         // GCC
    685                 { $$ = new StatementNode( $2 ); }
     685                { $$ = new StatementNode( $2 )/*->set_extension( true )*/; }
    686686        | function_definition
    687687                { $$ = new StatementNode( $1 ); }
     
    14731473        new_field_declaring_list ';'                                            // CFA, new style field declaration
    14741474        | EXTENSION new_field_declaring_list ';'                        // GCC
    1475                 { $$ = $2; }
     1475                { $$ = $2/*->set_extension( true )*/; }
    14761476        | field_declaring_list ';'
    14771477        | EXTENSION field_declaring_list ';'                            // GCC
    1478                 { $$ = $2; }
     1478                { $$ = $2/*->set_extension( true )*/; }
    14791479        ;
    14801480
     
    19921992                }
    19931993        | EXTENSION external_definition
    1994                 { $$ = $2; }
     1994                { $$ = $2/*->set_extension( true )*/; }
    19951995        ;
    19961996
  • src/ResolvExpr/AlternativeFinder.cc

    r6cbc25a r7ff30d07  
    99// Author           : Richard C. Bilson
    1010// Created On       : Sat May 16 23:52:08 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Wed Apr 20 14:24:03 2016
    13 // Update Count     : 24
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Mon Jun 13 16:13:54 2016
     13// Update Count     : 25
    1414//
    1515
     
    757757                for ( std::list< DeclarationWithType* >::iterator i = declList.begin(); i != declList.end(); ++i ) {
    758758                        VariableExpr newExpr( *i, nameExpr->get_argName() );
     759                        newExpr.set_extension( nameExpr->get_extension() );
    759760                        alternatives.push_back( Alternative( newExpr.clone(), env, Cost() ) );
    760761                        PRINT(
  • src/SynTree/Expression.cc

    r6cbc25a r7ff30d07  
    99// Author           : Richard C. Bilson
    1010// Created On       : Mon May 18 07:44:20 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Fri May 13 13:23:11 2016
    13 // Update Count     : 40
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Mon Jun 13 16:03:39 2016
     13// Update Count     : 42
    1414//
    1515
     
    3232Expression::Expression( Expression *_aname ) : env( 0 ), argName( _aname ) {}
    3333
    34 Expression::Expression( const Expression &other ) : env( maybeClone( other.env ) ), argName( maybeClone( other.get_argName() ) ) {
     34Expression::Expression( const Expression &other ) : env( maybeClone( other.env ) ), argName( maybeClone( other.get_argName() ) ), extension( other.extension ) {
    3535        cloneAll( other.results, results );
    3636}
     
    5959                os << std::string( indent, ' ' ) << "with designator:";
    6060                argName->print( os, indent+2 );
     61        } // if
     62
     63        if ( extension ) {
     64                os << std::string( indent, ' ' ) << "with extension:";
    6165        } // if
    6266}
  • src/SynTree/Expression.h

    r6cbc25a r7ff30d07  
    99// Author           : Richard C. Bilson
    1010// Created On       : Mon May 18 07:44:20 2015
    11 // Last Modified By : Rob Schluntz
    12 // Last Modified On : Wed Apr 27 17:06:49 2016
    13 // Update Count     : 21
     11// Last Modified By : Peter A. Buhr
     12// Last Modified On : Wed Jun  8 17:05:30 2016
     13// Update Count     : 22
    1414//
    1515
     
    3838        Expression *get_argName() const { return argName; }
    3939        void set_argName( Expression *name ) { argName = name; }
     40        bool get_extension() const { return extension; }
     41        void set_extension( bool exten ) { extension = exten; }
    4042
    4143        virtual Expression *clone() const = 0;
     
    4749        TypeSubstitution *env;
    4850        Expression* argName; // if expression is used as an argument, it can be "designated" by this name
     51        bool extension = false;
    4952};
    5053
  • src/Tests/Abstype.c

    r6cbc25a r7ff30d07  
    1 type T | { T x( T ); };
     1otype T | { T x( T ); };
    22
    33T y( T t ) {
     
    66}
    77
    8 forall( type T ) lvalue T *?( T * );
     8forall( otype T ) lvalue T *?( T * );
    99int ?++( int * );
    1010int ?=?( int *, int );
    1111forall( dtype DT ) DT * ?=?( DT **, DT * );
    1212
    13 type U = int *;
     13otype U = int *;
    1414
    1515U x( U u ) {
  • src/Tests/Attributes.c

    r6cbc25a r7ff30d07  
    66//    @max
    77//
    8 // 2. a direct application to a manifest type
     8// 2. a direct application to a manifest otype
    99//
    1010//    @max( int )
    1111//
    12 // 3. constraining a type variable; the application is implicitly performed at the call site as in (2)
     12// 3. constraining a otype variable; the application is implicitly performed at the call site as in (2)
    1313//
    14 //    forall( type T | { T @max( T ); } ) T x( T t );
     14//    forall( otype T | { T @max( T ); } ) T x( T t );
    1515//
    1616//
     
    2323//    x = (*attr_var);
    2424//
    25 // 2. an indirect application to a manifest type
     25// 2. an indirect application to a manifest otype
    2626//
    2727//    (*attr_var)( int )
    2828//
    29 // 3. a direct application to a type variable
     29// 3. a direct application to a otype variable
    3030//
    3131//    @max( T )
     
    4747// 3. polymorphic
    4848//
    49 //    forall( type T | constraint( T ) ) int @attr( T );
     49//    forall( otype T | constraint( T ) ) int @attr( T );
    5050
    5151int @max = 3;
     
    5353int main() {
    5454    int x;
    55     type @type(type t);                                                                 // compiler intrinsic
    56     type @widest(type t);
    57     @type(x) *y;                                                                                // gcc: typeof(x) *y;
    58     const @widest(double) *w;                                                   // gcc: const typeof(x) *w;
    59     * @type(3 + 4) z;                                                                   // cfa declaration syntax
     55    otype @otype(otype t);                                                                      // compiler intrinsic
     56    otype @widest(otype t);
     57    @otype(x) *y;                                                                               // gcc: otypeof(x) *y;
     58    const @widest(double) *w;                                                   // gcc: const otypeof(x) *w;
     59    * @otype(3 + 4) z;                                                                  // cfa declaration syntax
    6060    y = @max;           
    6161    z = @max(x) + @size(int);
  • src/Tests/InferParam.c

    r6cbc25a r7ff30d07  
    33double ?=?( double*, double );
    44
    5 forall( type T, type U | { U f(T); } ) U g(T);
     5forall( otype T, otype U | { U f(T); } ) U g(T);
    66float f( int );
    77double f( int );
     
    1313}
    1414
    15 context has_f_and_j( type T, type U ) {
     15context has_f_and_j( otype T, otype U ) {
    1616        U f( T );
    1717        U j( T, U );
     
    1919
    2020float j( int, float );
    21 forall( type T, type U | has_f_and_j( T, U ) ) U k( T );
     21forall( otype T, otype U | has_f_and_j( T, U ) ) U k( T );
    2222
    2323void l() {
  • src/Tests/Makefile

    r6cbc25a r7ff30d07  
    1 CFA ?= ../cfa-cpp
     1CFA ?= ../driver/cfa-cpp
    22CFAOPT ?= -a
    33OUTPUT ?= Output
     
    3232
    3333${OUTPUTDIR} :
    34         mkdir $@
     34        mkdir -p $@
    3535
    3636# remove the expected results directories to generate new ones from the current output
  • src/Tests/Members.c

    r6cbc25a r7ff30d07  
    33float ?=?( float*, float );
    44forall( dtype DT ) DT * ?=?( DT**, DT* );
    5 forall(type T) lvalue T *?( T* );
     5forall(otype T) lvalue T *?( T* );
    66char *__builtin_memcpy();
    77
  • src/Tests/OccursError.c

    r6cbc25a r7ff30d07  
    1 forall( type T ) void f( void (*)( T, T* ) );
    2 forall( type U ) void g( U*, U );
     1forall( otype T ) void f( void (*)( T, T* ) );
     2forall( otype U ) void g( U*, U );
    33
    44void test() {
  • src/Tests/Quad.c

    r6cbc25a r7ff30d07  
    22int ?*?( int, int );
    33
    4 forall( type T | { T ?*?( T, T ); } )
     4forall( otype T | { T ?*?( T, T ); } )
    55T square( T t ) {
    66        return t * t;
    77}
    88
    9 forall( type U | { U square( U ); } )
     9forall( otype U | { U square( U ); } )
    1010U quad( U u ) {
    1111        return square( square( u ) );
  • src/Tests/Rank2.c

    r6cbc25a r7ff30d07  
    33
    44void a() {
    5         forall( type T ) void f( T );
    6         void g( forall( type U ) void p( U ) );
     5        forall( otype T ) void f( T );
     6        void g( forall( otype U ) void p( U ) );
    77        g( f );
    88}
     
    1010void g() {
    1111        void h( int *null );
    12         forall( type T ) T id( T );
     12        forall( otype T ) T id( T );
    1313        forall( dtype T ) T *0;
    1414        int 0;
  • src/driver/cc1.cc

    r6cbc25a r7ff30d07  
    1010// Created On       : Fri Aug 26 14:23:51 2005
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Jun  2 17:24:26 2016
    13 // Update Count     : 79
     12// Last Modified On : Fri Jun 10 09:27:37 2016
     13// Update Count     : 80
    1414//
    1515
     
    151151                                i += 1;                                                                 // and the argument
    152152                                cpp_flag = true;
    153                         } else if ( arg == "-D__CFA__" ) {
     153                        } else if ( arg == "-D__CFA_PREPROCESS__" ) {
    154154                                CFA_flag = true;
    155                         } else if ( arg == "-D" && string( argv[i + 1] ) == "__CFA__" ) {
     155                        } else if ( arg == "-D" && string( argv[i + 1] ) == "__CFA_PREPROCESS__" ) {
    156156                                i += 1;                                                                 // and the argument
    157157                                CFA_flag = true;
  • src/driver/cfa.cc

    r6cbc25a r7ff30d07  
    1010// Created On       : Tue Aug 20 13:44:49 2002
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Jun  2 17:24:25 2016
    13 // Update Count     : 137
     12// Last Modified On : Fri Jun 10 09:26:19 2016
     13// Update Count     : 138
    1414//
    1515
     
    263263        args[nargs] = ( *new string( string("-D__CFA_PATCHLEVEL__=") + Patch ) ).c_str();
    264264        nargs += 1;
    265         args[nargs] = "-D__CFORALL__=1";
     265        args[nargs] = "-D__CFA__";
     266        nargs += 1;
     267        args[nargs] = "-D__CFORALL__";
    266268        nargs += 1;
    267269
     
    272274
    273275        if ( CFA_flag ) {
    274                 args[nargs] = "-D__CFA__";
     276                args[nargs] = "-D__CFA_PREPROCESS_";
    275277                nargs += 1;
    276278        } // if
  • src/libcfa/Makefile.am

    r6cbc25a r7ff30d07  
    1111## Created On       : Sun May 31 08:54:01 2015
    1212## Last Modified By : Peter A. Buhr
    13 ## Last Modified On : Wed Jun  8 14:20:34 2016
    14 ## Update Count     : 165
     13## Last Modified On : Mon Jun 13 14:27:22 2016
     14## Update Count     : 166
    1515###############################################################################
    1616
     
    5050        @BACKEND_CC@ -c -o $@ $<
    5151
    52 CFLAGS = -g -Wall -Wno-unused-function -B${abs_top_srcdir}/src/driver -XCFA -t  # TEMPORARY: does not build with -O2
     52CFLAGS = -quiet -g -Wall -Wno-unused-function -B${abs_top_srcdir}/src/driver -XCFA -t  # TEMPORARY: does not build with -O2
    5353CC = ${abs_top_srcdir}/src/driver/cfa
    5454
  • src/tests/Array.c

    r6cbc25a r7ff30d07  
    11//Testing array declarations
    22int a1[];
    3 int a2[*];
    4 double a4[3.0];
     3//int a2[*];
     4//double a4[3.0];
    55
    66int m1[][3];
    7 int m2[*][*];
     7//int m2[*][*];
    88int m4[3][3];
    99
     
    1111
    1212int fred() {
    13         int a1[];
    14         int a2[*];
     13//      int a1[];
     14//      int a2[*];
    1515        int a4[3];
    1616        int T[3];
  • src/tests/Forall.c

    r6cbc25a r7ff30d07  
    77
    88void g1() {
    9         forall( type T ) T f( T );
     9        forall( otype T ) T f( T );
    1010        void f( int );
    1111        void h( void (*p)(void) );
     
    2424
    2525void g2() {
    26         forall( type T ) void f( T, T );
    27         forall( type T, type U ) void f( T, U );
     26        forall( otype T ) void f( T, T );
     27        forall( otype T, otype U ) void f( T, U );
    2828 
    2929        int x;
     
    3737}
    3838
    39 typedef forall ( type T ) int (*f)( int );
     39typedef forall ( otype T ) int (*f)( int );
    4040
    41 forall( type T )
     41forall( otype T )
    4242void swap( T left, T right ) {
    4343        T temp = left;
     
    4646}
    4747
    48 context sumable( type T ) {
     48context sumable( otype T ) {
    4949        const T 0;
    5050        T ?+?(T, T);
     
    5353};
    5454
    55 type T1 | { const T1 0; T1 ?+?(T1, T1); T1 ?++(T1); [T1] ?+=?(T1,T1); },
    56         T2(type P1, type P2 ),
     55otype T1 | { const T1 0; T1 ?+?(T1, T1); T1 ?++(T1); [T1] ?+=?(T1,T1); },
     56        T2(otype P1, otype P2 ),
    5757        T3 | sumable(T3);
    5858
    59 type T2(type P1, type P2) | sumable(T2(P1,P2)) = struct { P1 i; P2 j; };
     59otype T2(otype P1, otype P2) | sumable(T2(P1,P2)) = struct { P1 i; P2 j; };
    6060
    6161T2(int, int) w1;
    6262typedef T2(int, int) w2;
    6363w2 g2;
    64 type w3 = T2(int, int);
     64otype w3 = T2(int, int);
    6565w3 g3;
    6666
    67 forall( type T | sumable( T ) )
     67forall( otype T | sumable( T ) )
    6868T sum( int n, T a[] ) {
    6969        T total = 0;
     
    7474}
    7575
    76 forall( type T | { const T 0; T ?+?(T, T); T ?++(T); [T] ?+=?(T,T); } )
     76forall( otype T | { const T 0; T ?+?(T, T); T ?++(T); [T] ?+=?(T,T); } )
    7777T twice( T t ) {
    7878        return t + t;
    7979}
    8080
    81 forall( type T | { const T 0; int ?!=?(T, T); int ?<?(T, T); } )
     81forall( otype T | { const T 0; int ?!=?(T, T); int ?<?(T, T); } )
    8282T min( T t1, T t2 ) {
    8383        return t1 < t2 ? t1 : t2;
  • src/tests/Functions.c

    r6cbc25a r7ff30d07  
    2828int ((*f12())[])[3] {}
    2929
    30 // "implicit int" type specifier (not ANSI)
     30// "implicit int" otype specifier (not ANSI)
    3131
    3232fII1( int i ) {}
  • src/tests/GccExtensions.c

    r6cbc25a r7ff30d07  
    1919    __signed s2;
    2020
    21     __typeof(s1) t1;
    22     __typeof__(s1) t2;
     21    __otypeof(s1) t1;
     22    __otypeof__(s1) t2;
    2323
    2424    __volatile int v1;
  • src/tests/Scope.c

    r6cbc25a r7ff30d07  
    33typedef float t;
    44y z;
    5 type u = struct { int a; double b; };
     5otype u = struct { int a; double b; };
    66int f( int y );
    77y q;
    88
    99y w( y y, u v ) {
    10         type x | { x t(u); };
     10        otype x | { x t(u); };
    1111        u u = y;
    1212        x z = t(u);
     
    1515y p;
    1616
    17 context has_u( type z ) {
     17context has_u( otype z ) {
    1818        z u(z);
    1919};
    2020
    21 forall( type t | has_u( t ) )
     21forall( otype t | has_u( t ) )
    2222y q( t the_t ) {
    2323        t y = u( the_t );
  • src/tests/Subrange.c

    r6cbc25a r7ff30d07  
    1 // A small context defining the notion of an ordered type.  (The standard
     1// A small context defining the notion of an ordered otype.  (The standard
    22// library should probably contain a context for this purpose.)
    3 context ordered(type T) {
     3context ordered(otype T) {
    44    int ?<?(T, T), ?<=?(T, T);
    55};
    66
    7 // A subrange type resembling an Ada subtype with a base type and a range
     7// A subrange otype resembling an Ada subotype with a base otype and a range
    88// constraint.
    9 type subrange(type base_t | ordered(base_t), base_t low = 0, base_t high = 8) = base_t;
     9otype subrange(otype base_t | ordered(base_t), base_t low = 0, base_t high = 8) = base_t;
    1010
    11 // Note that subrange() can be applied to floating-point and pointer types, not
    12 // just integral types.
    13 //   This requires a "type generator" extension to Cforall.  Type generators
    14 // must accept type and non-type parameters, which is beyond what we discussed
     11// Note that subrange() can be applied to floating-point and pointer otypes, not
     12// just integral otypes.
     13//   This requires a "otype generator" extension to Cforall.  Type generators
     14// must accept otype and non-otype parameters, which is beyond what we discussed
    1515// previously.  Type parameters must be usable in the declaration of
    1616// subsequent parameters: parameter T is used to declare parameters "low"
     
    2222subrange(int, 0, (rand() & 0xF) ) foo;
    2323
    24 // What sorts of expressions can be used as arguments of type generators?  Is
     24// What sorts of expressions can be used as arguments of otype generators?  Is
    2525// "subrange(int, 0, rand() & 0xF)" legal?  Probably.  The nearest C equivalent
    2626// to the "low" and "high" arguments is the array size in a variable-length
     
    2828
    2929// Convenient access to subrange bounds, for instance for iteration:
    30 forall (type T, T low, T high)
     30forall (otype T, T low, T high)
    3131T lbound( subrange(T, low, high) v) {
    3232    return low;
    3333}
    3434
    35 forall (type T, T low, T high)
     35forall (otype T, T low, T high)
    3636T hbound( subrange(T, low, high) v) {
    3737    return high;
     
    4141unsigned lday = lbound(day_of_month);
    4242
    43 // Assignment from the base type, with bounds checking.  I'll ignore the issue
     43// Assignment from the base otype, with bounds checking.  I'll ignore the issue
    4444// of exception handling here.  Inlining allows the compiler to eliminate
    4545// bounds checks.
    46 forall (type T | ordered(T), T low, T high)
     46forall (otype T | ordered(T), T low, T high)
    4747inline subrange(T, low, high) ?=?(subrange(T, low, high)* target, T source) {
    4848    if (low <= source && source <= high) *((T*)target) = source;
     
    5151}
    5252
    53 // Assignment between subranges with a common base type.  The bounds check
     53// Assignment between subranges with a common base otype.  The bounds check
    5454// compares range bounds so that the compiler can optimize checks away when the
    5555// ranges are known to overlap.
    56 forall (type T | ordered(T), T t_low, T t_high, T s_low, T s_high)
     56forall (otype T | ordered(T), T t_low, T t_high, T s_low, T s_high)
    5757inline subrange(T, t_low, t_high) ?=?(subrange(T, t_low, t_high)* target,
    5858                                      subrange(T, s_low, s_high) source) {
  • src/tests/TypeGenerator.c

    r6cbc25a r7ff30d07  
    1 context addable( type T ) {
     1context addable( otype T ) {
    22        T ?+?( T,T );
    33        T ?=?( T*, T);
    44};
    55
    6 type List1( type T | addable( T ) ) = struct { T data; List1( T ) *next; } *;
     6otype List1( otype T | addable( T ) ) = struct { T data; List1( T ) *next; } *;
    77typedef List1( int ) ListOfIntegers;
    88//List1( int ) li;
     
    1111[int] h( * List1( int ) p );                                                    // new declaration syntax
    1212
    13 struct( type T ) S2 { T i; };                                                   // actual definition
     13struct( otype T ) S2 { T i; };                                                  // actual definition
    1414struct( int ) S3 v1, *p;                                                                // expansion and instantiation
    15 struct( type T )( int ) S24 { T i; } v2;                                // actual definition, expansion and instantiation
    16 struct( type T )( int ) { T i; } v2;                                    // anonymous actual definition, expansion and instantiation
     15struct( otype T )( int ) S24 { T i; } v2;                               // actual definition, expansion and instantiation
     16struct( otype T )( int ) { T i; } v2;                                   // anonymous actual definition, expansion and instantiation
    1717
    18 struct( type T | addable( T ) ) node { T data; struct( T ) node *next; };
    19 type List( type T ) = struct( T ) node *;
     18struct( otype T | addable( T ) ) node { T data; struct( T ) node *next; };
     19otype List( otype T ) = struct( T ) node *;
    2020List( int ) my_list;
    2121
    22 type Complex | addable( Complex );
     22otype Complex | addable( Complex );
    2323
    2424int main() {
  • src/tests/Typedef.c

    r6cbc25a r7ff30d07  
    1818a c;
    1919
    20 typedef typeof(3) x, y;  // GCC
     20typedef otypeof(3) x, y;  // GCC
    2121
    2222x p;
     
    2424
    2525int main() {
    26     typedef typeof(3) z, p;
     26    typedef otypeof(3) z, p;
    2727    z w;
    2828    p x;
  • src/tests/Typeof.c

    r6cbc25a r7ff30d07  
    11int main() {
    22    int *v1;
    3     typeof(v1) v2;
    4     typeof(*v1) v3[4];
     3    otypeof(v1) v2;
     4    otypeof(*v1) v3[4];
    55    char *v4[4];
    6     typeof(typeof(char *)[4]) v5;
    7     typeof (int *) v6;
    8     typeof( int ( int, int p ) ) *v7;
    9     typeof( [int] ( int, int p ) ) *v8;
     6    otypeof(otypeof(char *)[4]) v5;
     7    otypeof (int *) v6;
     8    otypeof( int ( int, int p ) ) *v7;
     9    otypeof( [int] ( int, int p ) ) *v8;
    1010}
  • src/tests/io.c

    r6cbc25a r7ff30d07  
    1111// Created On       : Wed Mar  2 16:56:02 2016
    1212// Last Modified By : Peter A. Buhr
    13 // Last Modified On : Thu May 26 10:06:00 2016
    14 // Update Count     : 28
     13// Last Modified On : Wed Jun  8 22:52:04 2016
     14// Update Count     : 30
    1515//
    1616
     
    3434        long double _Complex ldc;
    3535        char s1[10], s2[10];
     36
     37        int x = 3, y = 5, z = 7;
     38        sout | x * 3 | y + 1 | z << 2 | x == y | (x | y) | (x || y) | (x > z ? 1 : 2) | endl;
     39        sout | 1 | 2 | 3 | endl;
     40        sout | '1' | '2' | '3' | endl;
     41        sout | 1 | "" | 2 | "" | 3 | endl;
     42        sout | endl;
    3643
    3744        ifstream in;                                                                                            // create / open file
Note: See TracChangeset for help on using the changeset viewer.