Changeset 779a4a3


Ignore:
Timestamp:
May 3, 2018, 4:33:19 PM (3 years ago)
Author:
Rob Schluntz <rschlunt@…>
Branches:
aaron-thesis, arm-eh, cleanup-dtors, deferred_resn, demangler, jacob/cs343-translation, jenkins-sandbox, master, new-ast, new-ast-unique-expr, new-env, no_list, persistent-indexer, with_gc
Children:
f3152ab
Parents:
f465f0e (diff), c9d5c4f (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
Message:

Merge branch 'master' into fix-reference-overloading

Files:
2 added
48 edited

Legend:

Unmodified
Added
Removed
  • doc/papers/concurrency/Makefile

    rf465f0e r779a4a3  
    7575        mkdir -p ${Build}
    7676
    77 ${BASE}.out.ps:
    78         ln -fs build/Paper.out.ps .
     77${BASE}.out.ps: ${Build}
     78        ln -fs ${Build}/Paper.out.ps .
    7979
    8080WileyNJD-AMA.bst:
    8181        ln -fs ../AMA/AMA-stix/ama/WileyNJD-AMA.bst .
    8282
    83 %.tex : %.fig
     83%.tex : %.fig ${Build}
    8484        fig2dev -L eepic $< > ${Build}/$@
    8585
    86 %.ps : %.fig
     86%.ps : %.fig ${Build}
    8787        fig2dev -L ps $< > ${Build}/$@
    8888
    89 %.pstex : %.fig
     89%.pstex : %.fig ${Build}
    9090        fig2dev -L pstex $< > ${Build}/$@
    9191        fig2dev -L pstex_t -p ${Build}/$@ $< > ${Build}/$@_t
  • doc/papers/general/Makefile

    rf465f0e r779a4a3  
    6969        mkdir -p ${Build}
    7070
    71 ${BASE}.out.ps:
    72         ln -fs build/Paper.out.ps .
     71${BASE}.out.ps: ${Build}
     72        ln -fs ${Build}/Paper.out.ps .
    7373
    7474WileyNJD-AMA.bst:
    7575        ln -fs ../AMA/AMA-stix/ama/WileyNJD-AMA.bst .
    7676
    77 ${GRAPHS} : timing.gp timing.dat
     77${GRAPHS} : ${Build} timing.gp timing.dat
    7878        gnuplot -e Build="'${Build}/'" evaluation/timing.gp
    7979
    80 %.tex : %.fig
     80%.tex : %.fig ${Build}
    8181        fig2dev -L eepic $< > ${Build}/$@
    8282
    83 %.ps : %.fig
     83%.ps : %.fig ${Build}
    8484        fig2dev -L ps $< > ${Build}/$@
    8585
    86 %.pstex : %.fig
     86%.pstex : %.fig ${Build}
    8787        fig2dev -L pstex $< > ${Build}/$@
    8888        fig2dev -L pstex_t -p ${Build}/$@ $< > ${Build}/$@_t
  • doc/papers/general/Paper.tex

    rf465f0e r779a4a3  
    228228Nevertheless, C, first standardized over thirty years ago, lacks many features that make programming in more modern languages safer and more productive.
    229229
    230 \CFA (pronounced ``C-for-all'', and written \CFA or Cforall) is an evolutionary extension of the C programming language that aims to add modern language features to C, while maintaining both source and runtime compatibility with C and a familiar programming model for programmers.
     230\CFA (pronounced ``C-for-all'', and written \CFA or Cforall) is an evolutionary extension of the C programming language that adds modern language-features to C, while maintaining both source and runtime compatibility with C and a familiar programming model for programmers.
    231231The four key design goals for \CFA~\cite{Bilson03} are:
    232232(1) The behaviour of standard C code must remain the same when translated by a \CFA compiler as when translated by a C compiler;
     
    237237\CC is used similarly, but has the disadvantages of multiple legacy design-choices that cannot be updated and active divergence of the language model from C, requiring significant effort and training to incrementally add \CC to a C-based project.
    238238
     239All languages features discussed in this paper are working, except some advanced exception-handling features.
     240Not discussed in this paper are the integrated concurrency-constructs and user-level threading-library~\cite{Delisle18}.
    239241\CFA is an \emph{open-source} project implemented as an source-to-source translator from \CFA to the gcc-dialect of C~\cite{GCCExtensions}, allowing it to leverage the portability and code optimizations provided by gcc, meeting goals (1)--(3).
    240242Ultimately, a compiler is necessary for advanced features and optimal performance.
    241 All features discussed in this paper are working, unless otherwise stated as under construction.
     243% @plg2[9]% cd cfa-cc/src; cloc ArgTweak CodeGen CodeTools Common Concurrency ControlStruct Designators GenPoly InitTweak MakeLibCfa.cc MakeLibCfa.h Parser ResolvExpr SymTab SynTree Tuples driver prelude main.cc
     244% -------------------------------------------------------------------------------
     245% Language                     files          blank        comment           code
     246% -------------------------------------------------------------------------------
     247% C++                            108           5420           5232          34961
     248% C/C++ Header                    86           2379           2450           8464
     249% Teamcenter def                   2            115             65           1387
     250% make                             5            168             87           1052
     251% C                               20            109            403            488
     252% awk                              1             12             26            121
     253% sed                              1              0              0              6
     254% -------------------------------------------------------------------------------
     255% SUM:                           223           8203           8263          46479
     256% -------------------------------------------------------------------------------
     257The \CFA translator is 200+ files and 46,000+ lines of code written in C/\CC.
     258Starting with a translator versus a compiler makes it easier and faster to generate and debug C object-code rather than intermediate, assembler or machine code.
     259The translator design is based on the \emph{visitor pattern}, allowing multiple passes over the abstract code-tree, which works well for incrementally adding new feature through additional visitor passes.
     260At the heart of the translator is the type resolver, which handles the polymorphic routine/type overload-resolution.
     261% @plg2[8]% cd cfa-cc/src; cloc libcfa
     262% -------------------------------------------------------------------------------
     263% Language                     files          blank        comment           code
     264% -------------------------------------------------------------------------------
     265% C                               35           1256           1240           9116
     266% C/C++ Header                    54            358           1106           1198
     267% make                             2            201            325           1167
     268% C++                              3             18             17            124
     269% Assembly                         3             56             97            111
     270% Bourne Shell                     2              2              0             25
     271% awk                              1              4              0             22
     272% -------------------------------------------------------------------------------
     273% SUM:                           100           1895           2785          11763
     274% -------------------------------------------------------------------------------
     275The \CFA runtime system is 100+ files and 11,000+ lines of code, written in \CFA.
     276Currently, the \CFA runtime is the largest \emph{user} of \CFA providing a vehicle to test the language features and implementation.
     277% @plg2[6]% cd cfa-cc/src; cloc tests examples benchmark
     278% -------------------------------------------------------------------------------
     279% Language                     files          blank        comment           code
     280% -------------------------------------------------------------------------------
     281% C                              237          12260           2869          23286
     282% make                             8            464            245           2838
     283% C/C++ Header                    22            225            175            785
     284% Python                           5            131             93            420
     285% C++                             10             48              5            201
     286% Lua                              2             31              4            126
     287% Java                             4              5              0             80
     288% Go                               2             11              9             40
     289% -------------------------------------------------------------------------------
     290% SUM:                           290          13175           3400          27776
     291% -------------------------------------------------------------------------------
     292The \CFA tests are 290+ files and 27,000+ lines of code.
     293The tests illustrate syntactic and semantic features in \CFA, plus a growing number of runtime benchmarks.
     294The tests check for correctness and are used for daily regression testing of commits (3800+).
    242295
    243296Finally, it is impossible to describe a programming language without usages before definitions.
     
    260313There are only two hard things in Computer Science: cache invalidation and \emph{naming things} -- Phil Karlton
    261314\end{quote}
     315\vspace{-10pt}
    262316C already has a limited form of ad-hoc polymorphism in the form of its basic arithmetic operators, which apply to a variety of different types using identical syntax.
    263317\CFA extends the built-in operator overloading by allowing users to define overloads for any function, not just operators, and even any variable;
     
    354408
    355409\CFA has replacement libraries condensing hundreds of existing C functions into tens of \CFA overloaded functions, all without rewriting the actual computations (see Section~\ref{sec:libraries}).
    356 For example, it is possible to write a type-safe \CFA wrapper @malloc@ based on the C @malloc@:
     410For example, it is possible to write a type-safe \CFA wrapper @malloc@ based on the C @malloc@, where the return type supplies the type/size of the allocation, which is impossible in most type systems.
    357411\begin{cfa}
    358412forall( dtype T | sized(T) ) T * malloc( void ) { return (T *)malloc( sizeof(T) ); }
    359 int * ip = malloc();                                            $\C{// select type and size from left-hand side}$
    360 double * dp = malloc();
    361 struct S {...} * sp = malloc();
    362 \end{cfa}
    363 where the return type supplies the type/size of the allocation, which is impossible in most type systems.
     413// select type and size from left-hand side
     414int * ip = malloc();  double * dp = malloc();  struct S {...} * sp = malloc();
     415\end{cfa}
    364416
    365417Call-site inferencing and nested functions provide a localized form of inheritance.
     
    373425}
    374426\end{cfa}
    375 Within the block, the nested version of @?<?@ performs @?>?@ and this local version overrides the built-in @?<?@ so it is passed to @qsort@.
     427The local version of @?<?@ performs @?>?@ overriding the built-in @?<?@ so it is passed to @qsort@.
    376428Hence, programmers can easily form local environments, adding and modifying appropriate functions, to maximize reuse of other existing functions and types.
    377429
     
    382434        inline {                                                                        $\C{// nested distribution block, add forall/inline to declarations}$
    383435                void push( stack(`T`) & s, `T` value ) ...      $\C{// generic operations}$
    384                 T pop( stack(`T`) & s ) ...
    385436        }
    386437}
     
    388439
    389440
     441\vspace*{-2pt}
    390442\subsection{Traits}
    391443
    392444\CFA provides \newterm{traits} to name a group of type assertions, where the trait name allows specifying the same set of assertions in multiple locations, preventing repetition mistakes at each function declaration:
     445
    393446\begin{cquote}
    394447\lstDeleteShortInline@%
     
    462515
    463516
     517\vspace*{-2pt}
    464518\section{Generic Types}
    465519
     
    474528
    475529\CC, Java, and other languages use \newterm{generic types} to produce type-safe abstract data-types.
    476 \CFA also implements generic types that integrate efficiently and naturally with the existing polymorphic functions, while retaining backwards compatibility with C and providing separate compilation.
     530\CFA generic types integrate efficiently and naturally with the existing polymorphic functions, while retaining backwards compatibility with C and providing separate compilation.
    477531However, for known concrete parameters, the generic-type definition can be inlined, like \CC templates.
    478532
     
    480534\begin{cquote}
    481535\lstDeleteShortInline@%
    482 \begin{tabular}{@{}l@{\hspace{2\parindentlnth}}l@{}}
     536\begin{tabular}{@{}l|@{\hspace{2\parindentlnth}}l@{}}
    483537\begin{cfa}
    484538forall( otype R, otype S ) struct pair {
     
    13731427resume( $\emph{alternate-stack}$ )
    13741428\end{cfa}
    1375 These overloads of @resume@ raise the specified exception or the currently propagating exception (reresume) at another \CFA coroutine or task\footnote{\CFA coroutine and concurrency features are discussed in a separately submitted paper.}~\cite{Delisle18}.
     1429These overloads of @resume@ raise the specified exception or the currently propagating exception (reresume) at another \CFA coroutine or task~\cite{Delisle18}.
    13761430Nonlocal raise is restricted to resumption to provide the exception handler the greatest flexibility because processing the exception does not unwind its stack, allowing it to continue after the handler returns.
    13771431
     
    20402094
    20412095
     2096\begin{comment}
    20422097\subsection{Integral Suffixes}
    20432098
     
    20732128\lstMakeShortInline@%
    20742129\end{cquote}
     2130\end{comment}
    20752131
    20762132
     
    26442700Figure~\ref{fig:eval} and Table~\ref{tab:eval} show the results of running the benchmark in Figure~\ref{fig:BenchmarkTest} and its C, \CC, and \CCV equivalents.
    26452701The graph plots the median of 5 consecutive runs of each program, with an initial warm-up run omitted.
    2646 All code is compiled at \texttt{-O2} by gcc or g++ 6.3.0, with all \CC code compiled as \CCfourteen.
     2702All code is compiled at \texttt{-O2} by gcc or g++ 6.4.0, with all \CC code compiled as \CCfourteen.
    26472703The benchmarks are run on an Ubuntu 16.04 workstation with 16 GB of RAM and a 6-core AMD FX-6300 CPU with 3.5 GHz maximum clock frequency.
    26482704
     
    26622718                                                                        & \CT{C}        & \CT{\CFA}     & \CT{\CC}      & \CT{\CCV}             \\ \hline
    26632719maximum memory usage (MB)                       & 10,001        & 2,502         & 2,503         & 11,253                \\
    2664 source code size (lines)                        & 196           & 186           & 125           & 290                   \\
     2720source code size (lines)                        & 201           & 191           & 125           & 294                   \\
    26652721redundant type annotations (lines)      & 27            & 0                     & 2                     & 16                    \\
    26662722binary size (KB)                                        & 14            & 257           & 14            & 37                    \\
     
    27652821data-parallel features have not yet been added to \CFA, but are easily incorporated within its design, while concurrency primitives similar to those in $\mu$\CC have already been added~\cite{Delisle18}.
    27662822Finally, CCured~\cite{Necula02} and Ironclad \CC~\cite{DeLozier13} attempt to provide a more memory-safe C by annotating pointer types with garbage collection information; type-checked polymorphism in \CFA covers several of C's memory-safety issues, but more aggressive approaches such as annotating all pointer types with their nullability or requiring runtime garbage collection are contradictory to \CFA's backwards compatibility goals.
    2767 
    2768 
    2769 \begin{comment}
    2770 \subsection{Control Structures / Declarations / Literals}
    2771 
    2772 Java has default fall through like C/\CC.
    2773 Pascal/Ada/Go/Rust do not have default fall through.
    2774 \Csharp does not have fall through but still requires a break.
    2775 Python uses dictionary mapping. \\
    2776 \CFA choose is like Rust match.
    2777 
    2778 Java has labelled break/continue. \\
    2779 Languages with and without exception handling.
    2780 
    2781 Alternative C declarations. \\
    2782 Different references \\
    2783 Constructors/destructors
    2784 
    2785 0/1 Literals \\
    2786 user defined: D, Objective-C
    2787 \end{comment}
    27882823
    27892824
     
    28752910}
    28762911_Bool stack_empty( const stack * s ) {
    2877          return s->head == NULL;
     2912        return s->head == NULL;
    28782913}
    28792914void push_stack( stack * s, void * v ) {
    2880         node * n = malloc(sizeof(node)); /***/
     2915        node * n = malloc( sizeof(node) ); /***/
    28812916        *n = (node){ v, s->head }; /***/
    28822917        s->head = n;
     
    29082943        };
    29092944        struct stack { node(T) * head; };
    2910         void ?{}( stack(T) & s ) { (s.head){ 0 }; }
    2911         void ?{}( stack(T) & s, stack(T) t ) {
     2945        void ?{}( stack(T) & s, stack(T) t ) { // copy
    29122946                node(T) ** cr = &s.head;
    29132947                for ( node(T) * nx = t.head; nx; nx = nx->next ) {
     
    29232957                        nx = cr->next;
    29242958                        ^(*cr){};
    2925                         free(cr);
     2959                        free( cr );
    29262960                }
    29272961                head = 0;
    29282962        }
     2963
    29292964\end{cfa}
    29302965&
    29312966\begin{cfa}[xleftmargin=0pt,aboveskip=0pt,belowskip=0pt]
     2967        void ?{}( stack(T) & s ) { (s.head){ 0 }; }
    29322968        void ^?{}( stack(T) & s) { clear( s ); }
    29332969        stack(T) ?=?( stack(T) & s, stack(T) t ) {
     
    29542990        }
    29552991}
    2956 
    29572992\end{cfa}
    29582993\end{tabular}
     
    30033038                return *this;
    30043039        }
    3005         bool empty() const { return head == nullptr; }
     3040        bool empty() const {
     3041                return head == nullptr;
     3042        }
    30063043        void push( const T & value ) {
    30073044                head = new node{ value, head };  /***/
     
    30153052        }
    30163053};
    3017 
    3018 
    30193054
    30203055\end{cfa}
     
    30663101                return *this;
    30673102        }
    3068         bool empty() const { return head == nullptr; }
     3103        bool empty() const {
     3104                return head == nullptr;
     3105        }
    30693106        void push( const object & value ) {
    30703107                head = new node{ value, head }; /***/
     
    30793116};
    30803117
    3081 
    3082 
    30833118\end{cfa}
    30843119\end{tabular}
  • doc/papers/general/evaluation/c-stack.c

    rf465f0e r779a4a3  
    2727}
    2828
    29 stack new_stack() { return (stack){ NULL }; /***/ }
     29stack new_stack() {
     30        return (stack){ NULL }; /***/
     31}
    3032
    3133stack * assign_stack( stack * s, const stack * t,
     
    3739}
    3840
    39 _Bool stack_empty( const stack * s ) { return s->head == NULL; }
     41_Bool stack_empty( const stack * s ) {
     42        return s->head == NULL;
     43}
    4044
    4145void push_stack( stack * s, void * v ) {
  • doc/papers/general/evaluation/c-stack.h

    rf465f0e r779a4a3  
    66} stack;
    77
     8void copy_stack(stack * dst, const stack * src, void * (* copy)(const void *));
     9void clear_stack(stack * s, void (*free_el)(void *));
    810stack new_stack();
    9 void copy_stack(stack * dst, const stack * src, void * (* copy)(const void *));
    1011stack * assign_stack( stack * dst, const stack * src,
    1112        void * (* copy_el)(const void *), void (* free_el)(void *));
    12 void clear_stack(stack * s, void (*free_el)(void *));
    1313
    1414_Bool stack_empty( const stack * s );
  • doc/papers/general/evaluation/cfa-stack.c

    rf465f0e r779a4a3  
    88        };
    99
    10         void ?{}( stack(T) & s ) { (s.head){ 0 }; }
    11 
    12         void ?{}( stack(T) & s, stack(T) t ) {
     10        void ?{}( stack(T) & s, stack(T) t ) {          // copy
    1311                node(T) ** cr = &s.head;
    1412                for ( node(T) * nx = t.head; nx; nx = nx->next ) {
     
    2018        }
    2119
    22         void ^?{}( stack(T) & s) { clear( s ); }
    23 
    24     void clear( stack(T) & s ) with( s ) {
     20        void clear( stack(T) & s ) with( s ) {
    2521                for ( node(T) * nx = head; nx; ) {
    2622                        node(T) * cr = nx;
    2723                        nx = cr->next;
    2824                        ^(*cr){};
    29                         free(cr);
     25                        free( cr );
    3026                }
    3127                head = 0;
    3228        }
     29
     30        void ?{}( stack(T) & s ) { (s.head){ 0 }; }
     31        void ^?{}( stack(T) & s) { clear( s ); }
    3332
    3433        stack(T) ?=?( stack(T) & s, stack(T) t ) {
     
    3938        }
    4039
    41         _Bool empty( const stack(T) & s ) { return s.head == 0; }
     40        _Bool empty( const stack(T) & s ) {
     41                return s.head == 0;
     42        }
    4243
    4344        void push( stack(T) & s, T value ) with( s ) {
  • doc/papers/general/evaluation/cfa-stack.h

    rf465f0e r779a4a3  
    77        };
    88
     9        void ?{}( stack(T) & s, stack(T) t );
     10        void clear( stack(T) & s );
    911        void ?{}( stack(T) & s );
    10         void ?{}( stack(T) & s, stack(T) t );
    1112        void ^?{}( stack(T) & s);
    12         void clear( stack(T) & s );
    1313
    1414        stack(T) ?=?( stack(T) & s, stack(T) t );
  • doc/papers/general/evaluation/cpp-stack.hpp

    rf465f0e r779a4a3  
    1010        node * head;
    1111
    12         stack() : head( nullptr ) {}
    13         stack( const stack<T> & o ) { copy( o ); }
     12        void copy( const stack<T> & o ) {
     13                node ** cr = &head;
     14                for ( node * nx = o.head; nx; nx = nx->next ) {
     15                        *cr = new node{ nx->value }; /***/
     16                        cr = &(*cr)->next;
     17                }
     18                *cr = nullptr;
     19        }
    1420
    1521        void clear() {
     
    2228        }
    2329
    24         void copy( const stack<T> & o ) {
    25                 node ** cr = &head;
    26                 for ( node * nx = o.head; nx; nx = nx->next ) {
    27                         *cr = new node{ nx->value }; /***/
    28                         cr = &(*cr)->next;
    29                 }
    30                 *cr = nullptr;
    31         }
    32 
     30        stack() : head( nullptr ) {}
     31        stack( const stack<T> & o ) { copy( o ); }
    3332        ~stack() { clear(); }
    3433
    35         stack & operator= ( const stack<T> & o ) {
     34        stack & operator=( const stack<T> & o ) {
    3635                if ( this == &o ) return *this;
    3736                clear();
     
    4039        }
    4140
    42         bool empty() const { return head == nullptr; }
     41        bool empty() const {
     42                return head == nullptr;
     43        }
    4344
    44         void push( const T & value ) { head = new node{ value, head };  /***/ }
     45        void push( const T & value ) {
     46                head = new node{ value, head };  /***/
     47        }
    4548
    4649        T pop() {
  • doc/papers/general/evaluation/cpp-vstack.cpp

    rf465f0e r779a4a3  
    33
    44stack::node::node( const object & v, node * n ) : value( v.new_copy() ), next( n ) {}
     5
     6void stack::copy( const stack & o ) {
     7        node ** cr = &head;
     8        for ( node * nx = o.head; nx; nx = nx->next ) {
     9                *cr = new node{ *nx->value }; /***/
     10                cr = &(*cr)->next;
     11        }
     12        *cr = nullptr;
     13}
    514
    615void stack::clear() {
     
    1120        }
    1221        head = nullptr;
    13 }
    14 
    15 void stack::copy( const stack & o ) {
    16         node ** cr = &head;
    17         for ( node * nx = o.head; nx; nx = nx->next ) {
    18                 *cr = new node{ *nx->value }; /***/
    19                 cr = &(*cr)->next;
    20         }
    21         *cr = nullptr;
    2222}
    2323
     
    3333}
    3434
    35 bool stack::empty() const { return head == nullptr; }
     35bool stack::empty() const {
     36        return head == nullptr;
     37}
    3638
    37 void stack::push( const object & value ) { head = new node{ value, head }; /***/ }
     39void stack::push( const object & value ) {
     40        head = new node{ value, head }; /***/
     41}
    3842
    3943ptr<object> stack::pop() {
  • doc/papers/general/evaluation/cpp-vstack.hpp

    rf465f0e r779a4a3  
    1010        node * head;
    1111
     12        void copy( const stack & o );
    1213        void clear();
    13         void copy( const stack & o );
    1414
    1515        stack();
  • doc/papers/general/evaluation/timing.dat

    rf465f0e r779a4a3  
    11"400 million repetitions"       "C"     "\\CFA{}"       "\\CC{}"        "\\CC{obj}"
    2 "push\nint"     3002    2459    1542    3269
    3 "copy\nint"     2985    2057    1539    3083
    4 "clear\nint"    1374    827     756     1469
    5 "pop\nint"      1416    1221    760     5098
    6 "push\npair"    4214    2752    950     6873
    7 "copy\npair"    6127    2105    987     7293
    8 "clear\npair"   2881    885     751     3460
    9 "pop\npair"     3046    5434    822     24962
     2"push\nint"     2911    2034    1504    3246
     3"copy\nint"     2953    1622    1526    3075
     4"clear\nint"    1397    754     753     1452
     5"pop\nint"      1446    1203    760     5016
     6"push\npair"    3673    2297    955     6971
     7"copy\npair"    6027    1183    998     7204
     8"clear\npair"   2840    773     748     3511
     9"pop\npair"     3025    5414    813     23867
     10
  • doc/papers/general/evaluation/timing.gp

    rf465f0e r779a4a3  
    2424set yrange [0:10]
    2525
    26 set label "25.0" at 7.125,10.5
     26set label "23.9" at 7.125,10.5
    2727
    2828# set datafile separator ","
  • doc/refrat/Makefile

    rf465f0e r779a4a3  
    3434
    3535DOCUMENT = refrat.pdf
     36BASE = ${basename ${DOCUMENT}}
    3637
    3738# Directives #
     
    4243
    4344clean :
    44         @rm -frv ${DOCUMENT} ${basename ${DOCUMENT}}.ps ${Build}
     45        @rm -frv ${DOCUMENT} ${BASE}.ps ${Build}
    4546
    4647# File Dependencies #
    4748
    48 ${DOCUMENT} : ${basename ${DOCUMENT}}.ps
     49${DOCUMENT} : ${BASE}.ps
    4950        ps2pdf $<
    5051
    51 ${basename ${DOCUMENT}}.ps : ${basename ${DOCUMENT}}.dvi
     52${BASE}.ps : ${BASE}.dvi
    5253        dvips ${Build}/$< -o $@
    5354
    54 ${basename ${DOCUMENT}}.dvi : Makefile ${Build} ${GRAPHS} ${PROGRAMS} ${PICTURES} ${FIGURES} ${SOURCES} \
     55${BASE}.dvi : Makefile ${Build} ${GRAPHS} ${PROGRAMS} ${PICTURES} ${FIGURES} ${SOURCES} \
    5556                ${Macros}/common.tex ${Macros}/lstlang.sty ${Macros}/indexstyle ../bibliography/pl.bib
    5657        # Conditionally create an empty *.ind (index) file for inclusion until makeindex is run.
     
    7071
    7172predefined :
    72         sed -f predefined.sed ${basename ${DOCUMENT}}.tex > ${basename $@}.cf
     73        sed -f predefined.sed ${BASE}.tex > ${basename $@}.cf
    7374
    7475## Define the default recipes.
     
    7778        mkdir -p ${Build}
    7879
    79 %.tex : %.fig
     80%.tex : %.fig ${Build}
    8081        fig2dev -L eepic $< > ${Build}/$@
    8182
    82 %.ps : %.fig
     83%.ps : %.fig ${Build}
    8384        fig2dev -L ps $< > ${Build}/$@
    8485
    85 %.pstex : %.fig
     86%.pstex : %.fig ${Build}
    8687        fig2dev -L pstex $< > ${Build}/$@
    8788        fig2dev -L pstex_t -p ${Build}/$@ $< > ${Build}/$@_t
  • doc/user/Makefile

    rf465f0e r779a4a3  
    3838
    3939DOCUMENT = user.pdf
     40BASE = ${basename ${DOCUMENT}}
    4041
    4142# Directives #
     
    4647
    4748clean :
    48         @rm -frv ${DOCUMENT} ${basename ${DOCUMENT}}.ps ${Build}
     49        @rm -frv ${DOCUMENT} ${BASE}.ps ${Build}
    4950
    5051# File Dependencies #
    5152
    52 ${DOCUMENT} : ${basename ${DOCUMENT}}.ps
     53${DOCUMENT} : ${BASE}.ps
    5354        ps2pdf $<
    5455
    55 ${basename ${DOCUMENT}}.ps : ${basename ${DOCUMENT}}.dvi
     56${BASE}.ps : ${BASE}.dvi
    5657        dvips ${Build}/$< -o $@
    5758
    58 ${basename ${DOCUMENT}}.dvi : Makefile ${Build} ${GRAPHS} ${PROGRAMS} ${PICTURES} ${FIGURES} ${SOURCES} \
     59${BASE}.dvi : Makefile ${Build} ${GRAPHS} ${PROGRAMS} ${PICTURES} ${FIGURES} ${SOURCES} \
    5960                ${Macros}/common.tex ${Macros}/lstlang.sty ${Macros}/indexstyle ../bibliography/pl.bib
    6061        # Conditionally create an empty *.ind (index) file for inclusion until makeindex is run.
     
    7879        mkdir -p ${Build}
    7980
    80 %.tex : %.fig
     81%.tex : %.fig ${Build}
    8182        fig2dev -L eepic $< > ${Build}/$@
    8283
    83 %.ps : %.fig
     84%.ps : %.fig ${Build}
    8485        fig2dev -L ps $< > ${Build}/$@
    8586
    86 %.pstex : %.fig
     87%.pstex : %.fig ${Build}
    8788        fig2dev -L pstex $< > ${Build}/$@
    8889        fig2dev -L pstex_t -p ${Build}/$@ $< > ${Build}/$@_t
  • src/CodeGen/CodeGenerator.cc

    rf465f0e r779a4a3  
    887887                if ( asmStmt->get_instruction() ) asmStmt->get_instruction()->accept( *visitor );
    888888                output << " )" ;
     889        }
     890
     891        void CodeGenerator::postvisit( DirectiveStmt * dirStmt ) {
     892                output << dirStmt->directive;
    889893        }
    890894
  • src/CodeGen/CodeGenerator.h

    rf465f0e r779a4a3  
    9999                void postvisit( ExprStmt * );
    100100                void postvisit( AsmStmt * );
     101                void postvisit( DirectiveStmt * );
    101102                void postvisit( AsmDecl * );                            // special: statement in declaration context
    102103                void postvisit( IfStmt * );
  • src/Common/PassVisitor.h

    rf465f0e r779a4a3  
    7171        virtual void visit( ExprStmt * exprStmt ) override final;
    7272        virtual void visit( AsmStmt * asmStmt ) override final;
     73        virtual void visit( DirectiveStmt * dirStmt ) override final;
    7374        virtual void visit( IfStmt * ifStmt ) override final;
    7475        virtual void visit( WhileStmt * whileStmt ) override final;
     
    168169        virtual Statement * mutate( ExprStmt * exprStmt ) override final;
    169170        virtual Statement * mutate( AsmStmt * asmStmt ) override final;
     171        virtual Statement * mutate( DirectiveStmt * dirStmt ) override final;
    170172        virtual Statement * mutate( IfStmt * ifStmt ) override final;
    171173        virtual Statement * mutate( WhileStmt * whileStmt ) override final;
  • src/Common/PassVisitor.impl.h

    rf465f0e r779a4a3  
    777777
    778778//--------------------------------------------------------------------------
     779// AsmStmt
     780template< typename pass_type >
     781void PassVisitor< pass_type >::visit( DirectiveStmt * node ) {
     782        VISIT_START( node )
     783
     784        VISIT_END( node );
     785}
     786
     787template< typename pass_type >
     788Statement * PassVisitor< pass_type >::mutate( DirectiveStmt * node ) {
     789        MUTATE_START( node );
     790
     791        MUTATE_END( Statement, node );
     792}
     793
     794//--------------------------------------------------------------------------
    779795// IfStmt
    780796template< typename pass_type >
  • src/Common/SemanticError.cc

    rf465f0e r779a4a3  
    77// SemanticError.cc --
    88//
    9 // Author           : Richard C. Bilson
     9// Author           : Thierry Delisle
    1010// Created On       : Mon May 18 07:44:20 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Tue Aug 29 18:17:35 2017
    13 // Update Count     : 3
     12// Last Modified On : Wed May  2 18:13:37 2018
     13// Update Count     : 8
    1414//
    1515
    1616#include <cstdarg>
    1717#include <cstdio>                                                                               // for fileno, stderr
     18#include <cstring>
    1819#include <unistd.h>                                                                             // for isatty
    1920#include <iostream>                                                                             // for basic_ostream, operator<<, ostream
    2021#include <list>                                                                                 // for list, _List_iterator
    2122#include <string>                                                                               // for string, operator<<, operator+, to_string
     23#include <vector>
    2224
    2325#include "Common/utility.h"                                                             // for to_string, CodeLocation (ptr only)
    2426#include "SemanticError.h"
    2527
     28//-----------------------------------------------------------------------------
     29// Severity Handling
     30std::vector<Severity> & get_severities() {
     31        static std::vector<Severity> severities;
     32        if(severities.empty()) {
     33                severities.reserve((size_t)Warning::NUMBER_OF_WARNINGS);
     34                for ( const auto w : WarningFormats ) {
     35                        severities.push_back( w.default_severity );
     36                } // for
     37        }
     38        return severities;
     39}
     40
     41void SemanticWarning_SuppressAll() {
     42        for( auto & s : get_severities() ) {
     43                s = Severity::Suppress;
     44        }
     45}
     46
     47void SemanticWarning_EnableAll() {
     48        for( auto & s : get_severities() ) {
     49                s = Severity::Warn;
     50        }
     51}
     52
     53void SemanticWarning_WarningAsError() {
     54        for( auto & s : get_severities() ) {
     55                if(s == Severity::Warn) s = Severity::Error;
     56        }
     57}
     58
     59void SemanticWarning_Set(const char * const name, Severity s) {
     60        size_t idx = 0;
     61        for ( const auto & w : WarningFormats ) {
     62                if ( std::strcmp( name, w.name ) == 0 ) {
     63                        get_severities()[idx] = s;
     64                        break;
     65                }
     66                idx++;
     67        }
     68}
     69
     70//-----------------------------------------------------------------------------
     71// Semantic Error
    2672SemanticErrorException::SemanticErrorException( CodeLocation location, std::string error ) {
    2773        append( location, error );
     
    69115
    70116void SemanticWarningImpl( CodeLocation location, Warning warning, const char * const fmt, ... ) {
    71         Severity severity = WarningFormats[(int)warning].severity;
     117        Severity severity = get_severities()[(int)warning];
    72118        switch(severity) {
    73119        case Severity::Suppress :
  • src/Common/SemanticError.h

    rf465f0e r779a4a3  
    77// SemanticError.h --
    88//
    9 // Author           : Richard C. Bilson
     9// Author           : Thierry Delisle
    1010// Created On       : Mon May 18 07:44:20 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Apr 19 17:52:03 2018
    13 // Update Count     : 19
     12// Last Modified On : Wed May  2 18:13:15 2018
     13// Update Count     : 29
    1414//
    1515
     
    1717
    1818#include "ErrorObjects.h"
     19#include <cstring>
    1920
    2021//-----------------------------------------------------------------------------
     
    4647        const char * const name;
    4748        const char * const message;
    48         mutable Severity severity;
     49        const Severity default_severity;
    4950};
    5051
    51 constexpr const WarningData WarningFormats[] = {
    52         {"self-assign"         , "self assignment of expression: %s"           , Severity::Warn},
    53         {"reference-conversion", "rvalue to reference conversion of rvalue: %s", Severity::Warn},
     52constexpr WarningData WarningFormats[] = {
     53        {"self-assign"            , "self assignment of expression: %s"            , Severity::Warn},
     54        {"reference-conversion"   , "rvalue to reference conversion of rvalue: %s" , Severity::Warn},
    5455        {"qualifiers-zero_t-one_t", "questionable use of type qualifier %s with %s", Severity::Warn},
    5556};
     
    7172void SemanticWarningImpl (CodeLocation loc, Warning warn, const char * const fmt, ...) __attribute__((format(printf, 3, 4)));
    7273
     74void SemanticWarning_SuppressAll   ();
     75void SemanticWarning_EnableAll     ();
     76void SemanticWarning_WarningAsError();
     77void SemanticWarning_Set           (const char * const name, Severity s);
     78
     79// SKULLDUGGERY: cfa.cc is built before SemanticError.cc but needs this routine.
     80static inline bool SemanticWarning_Exist(const char * const name) {
     81        for ( const auto & w : WarningFormats ) {
     82                if ( std::strcmp( name, w.name ) == 0 ) return true;
     83        }
     84        return false;
     85}
    7386
    7487//-----------------------------------------------------------------------------
  • src/Common/module.mk

    rf465f0e r779a4a3  
    66## file "LICENCE" distributed with Cforall.
    77##
    8 ## module.mk -- 
     8## module.mk --
    99##
    1010## Author           : Richard C. Bilson
     
    1818       Common/UniqueName.cc \
    1919       Common/DebugMalloc.cc \
    20        Common/Assert.cc
     20       Common/Assert.cc \
     21       Common/Heap.cc
  • src/Common/utility.h

    rf465f0e r779a4a3  
    1010// Created On       : Mon May 18 07:44:20 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Fri Apr 20 22:35:33 2018
    13 // Update Count     : 38
     12// Last Modified On : Thu May  3 12:18:31 2018
     13// Update Count     : 39
    1414//
    1515
     
    441441
    442442template<typename T>
    443 inline constexpr T ilog2(const T & t) {
    444         if ( std::is_integral<T>::value ) {
     443inline
     444#if __GNUC__ > 4
     445constexpr
     446#endif
     447T ilog2(const T & t) {
     448        if(std::is_integral<T>::value) {
    445449                const constexpr int r = sizeof(t) * __CHAR_BIT__ - 1;
    446                 if ( sizeof(T) == sizeof(unsigned int ) ) return r - __builtin_clz( t );
    447                 if ( sizeof(T) == sizeof(unsigned long) ) return r - __builtin_clzl( t );
    448                 if ( sizeof(T) == sizeof(unsigned long long) ) return r - __builtin_clzll( t );
    449         } // if
     450                if( sizeof(T) == sizeof(unsigned       int) ) return r - __builtin_clz  ( t );
     451                if( sizeof(T) == sizeof(unsigned      long) ) return r - __builtin_clzl ( t );
     452                if( sizeof(T) == sizeof(unsigned long long) ) return r - __builtin_clzll( t );
     453        }
     454        assert(false);
    450455        return -1;
    451 } // ilong2
     456} // ilog2
    452457
    453458
  • src/Makefile.in

    rf465f0e r779a4a3  
    164164        Common/driver_cfa_cpp-DebugMalloc.$(OBJEXT) \
    165165        Common/driver_cfa_cpp-Assert.$(OBJEXT) \
     166        Common/driver_cfa_cpp-Heap.$(OBJEXT) \
    166167        ControlStruct/driver_cfa_cpp-LabelGenerator.$(OBJEXT) \
    167168        ControlStruct/driver_cfa_cpp-LabelFixer.$(OBJEXT) \
     
    486487        Concurrency/Waitfor.cc Common/SemanticError.cc \
    487488        Common/UniqueName.cc Common/DebugMalloc.cc Common/Assert.cc \
    488         ControlStruct/LabelGenerator.cc ControlStruct/LabelFixer.cc \
    489         ControlStruct/MLEMutator.cc ControlStruct/Mutate.cc \
    490         ControlStruct/ForExprMutator.cc \
     489        Common/Heap.cc ControlStruct/LabelGenerator.cc \
     490        ControlStruct/LabelFixer.cc ControlStruct/MLEMutator.cc \
     491        ControlStruct/Mutate.cc ControlStruct/ForExprMutator.cc \
    491492        ControlStruct/ExceptTranslate.cc GenPoly/Box.cc \
    492493        GenPoly/GenPoly.cc GenPoly/ScrubTyVars.cc GenPoly/Lvalue.cc \
     
    672673        Common/$(DEPDIR)/$(am__dirstamp)
    673674Common/driver_cfa_cpp-Assert.$(OBJEXT): Common/$(am__dirstamp) \
     675        Common/$(DEPDIR)/$(am__dirstamp)
     676Common/driver_cfa_cpp-Heap.$(OBJEXT): Common/$(am__dirstamp) \
    674677        Common/$(DEPDIR)/$(am__dirstamp)
    675678ControlStruct/$(am__dirstamp):
     
    973976@AMDEP_TRUE@@am__include@ @am__quote@Common/$(DEPDIR)/driver_cfa_cpp-Assert.Po@am__quote@
    974977@AMDEP_TRUE@@am__include@ @am__quote@Common/$(DEPDIR)/driver_cfa_cpp-DebugMalloc.Po@am__quote@
     978@AMDEP_TRUE@@am__include@ @am__quote@Common/$(DEPDIR)/driver_cfa_cpp-Heap.Po@am__quote@
    975979@AMDEP_TRUE@@am__include@ @am__quote@Common/$(DEPDIR)/driver_cfa_cpp-SemanticError.Po@am__quote@
    976980@AMDEP_TRUE@@am__include@ @am__quote@Common/$(DEPDIR)/driver_cfa_cpp-UniqueName.Po@am__quote@
     
    13081312@am__fastdepCXX_FALSE@  $(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -c -o Common/driver_cfa_cpp-Assert.obj `if test -f 'Common/Assert.cc'; then $(CYGPATH_W) 'Common/Assert.cc'; else $(CYGPATH_W) '$(srcdir)/Common/Assert.cc'; fi`
    13091313
     1314Common/driver_cfa_cpp-Heap.o: Common/Heap.cc
     1315@am__fastdepCXX_TRUE@   $(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -MT Common/driver_cfa_cpp-Heap.o -MD -MP -MF Common/$(DEPDIR)/driver_cfa_cpp-Heap.Tpo -c -o Common/driver_cfa_cpp-Heap.o `test -f 'Common/Heap.cc' || echo '$(srcdir)/'`Common/Heap.cc
     1316@am__fastdepCXX_TRUE@   $(AM_V_at)$(am__mv) Common/$(DEPDIR)/driver_cfa_cpp-Heap.Tpo Common/$(DEPDIR)/driver_cfa_cpp-Heap.Po
     1317@AMDEP_TRUE@@am__fastdepCXX_FALSE@      $(AM_V_CXX)source='Common/Heap.cc' object='Common/driver_cfa_cpp-Heap.o' libtool=no @AMDEPBACKSLASH@
     1318@AMDEP_TRUE@@am__fastdepCXX_FALSE@      DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
     1319@am__fastdepCXX_FALSE@  $(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -c -o Common/driver_cfa_cpp-Heap.o `test -f 'Common/Heap.cc' || echo '$(srcdir)/'`Common/Heap.cc
     1320
     1321Common/driver_cfa_cpp-Heap.obj: Common/Heap.cc
     1322@am__fastdepCXX_TRUE@   $(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -MT Common/driver_cfa_cpp-Heap.obj -MD -MP -MF Common/$(DEPDIR)/driver_cfa_cpp-Heap.Tpo -c -o Common/driver_cfa_cpp-Heap.obj `if test -f 'Common/Heap.cc'; then $(CYGPATH_W) 'Common/Heap.cc'; else $(CYGPATH_W) '$(srcdir)/Common/Heap.cc'; fi`
     1323@am__fastdepCXX_TRUE@   $(AM_V_at)$(am__mv) Common/$(DEPDIR)/driver_cfa_cpp-Heap.Tpo Common/$(DEPDIR)/driver_cfa_cpp-Heap.Po
     1324@AMDEP_TRUE@@am__fastdepCXX_FALSE@      $(AM_V_CXX)source='Common/Heap.cc' object='Common/driver_cfa_cpp-Heap.obj' libtool=no @AMDEPBACKSLASH@
     1325@AMDEP_TRUE@@am__fastdepCXX_FALSE@      DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@
     1326@am__fastdepCXX_FALSE@  $(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -c -o Common/driver_cfa_cpp-Heap.obj `if test -f 'Common/Heap.cc'; then $(CYGPATH_W) 'Common/Heap.cc'; else $(CYGPATH_W) '$(srcdir)/Common/Heap.cc'; fi`
     1327
    13101328ControlStruct/driver_cfa_cpp-LabelGenerator.o: ControlStruct/LabelGenerator.cc
    13111329@am__fastdepCXX_TRUE@   $(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) $(driver_cfa_cpp_CXXFLAGS) $(CXXFLAGS) -MT ControlStruct/driver_cfa_cpp-LabelGenerator.o -MD -MP -MF ControlStruct/$(DEPDIR)/driver_cfa_cpp-LabelGenerator.Tpo -c -o ControlStruct/driver_cfa_cpp-LabelGenerator.o `test -f 'ControlStruct/LabelGenerator.cc' || echo '$(srcdir)/'`ControlStruct/LabelGenerator.cc
  • src/Parser/ParseNode.h

    rf465f0e r779a4a3  
    1010// Created On       : Sat May 16 13:28:16 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sun Apr 29 14:04:05 2018
    13 // Update Count     : 830
     12// Last Modified On : Mon Apr 30 09:19:17 2018
     13// Update Count     : 831
    1414//
    1515
     
    416416Statement * build_finally( StatementNode * stmt );
    417417Statement * build_compound( StatementNode * first );
    418 Statement * build_asmstmt( bool voltile, Expression * instruction, ExpressionNode * output = nullptr, ExpressionNode * input = nullptr, ExpressionNode * clobber = nullptr, LabelNode * gotolabels = nullptr );
    419 Statement * build_dirstmt( std::string * directive );
     418Statement * build_asm( bool voltile, Expression * instruction, ExpressionNode * output = nullptr, ExpressionNode * input = nullptr, ExpressionNode * clobber = nullptr, LabelNode * gotolabels = nullptr );
     419Statement * build_directive( std::string * directive );
    420420WaitForStmt * build_waitfor( ExpressionNode * target, StatementNode * stmt, ExpressionNode * when );
    421421WaitForStmt * build_waitfor( ExpressionNode * target, StatementNode * stmt, ExpressionNode * when, WaitForStmt * existing );
  • src/Parser/StatementNode.cc

    rf465f0e r779a4a3  
    1010// Created On       : Sat May 16 14:59:41 2015
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sun Apr 29 14:21:45 2018
    13 // Update Count     : 353
     12// Last Modified On : Mon Apr 30 09:21:16 2018
     13// Update Count     : 354
    1414//
    1515
     
    310310}
    311311
    312 Statement * build_asmstmt( bool voltile, Expression * instruction, ExpressionNode * output, ExpressionNode * input, ExpressionNode * clobber, LabelNode * gotolabels ) {
     312Statement * build_asm( bool voltile, Expression * instruction, ExpressionNode * output, ExpressionNode * input, ExpressionNode * clobber, LabelNode * gotolabels ) {
    313313        std::list< Expression * > out, in;
    314314        std::list< ConstantExpr * > clob;
     
    320320}
    321321
    322 Statement * build_dirstmt( string * directive ) {
    323         cout << *directive << endl;
    324         return nullptr;
     322Statement * build_directive( string * directive ) {
     323        return new DirectiveStmt( *directive );
    325324}
    326325
  • src/Parser/lex.ll

    rf465f0e r779a4a3  
    1010 * Created On       : Sat Sep 22 08:58:10 2001
    1111 * Last Modified By : Peter A. Buhr
    12  * Last Modified On : Sun Apr 29 14:10:49 2018
    13  * Update Count     : 675
     12 * Last Modified On : Thu May  3 13:42:40 2018
     13 * Update Count     : 676
    1414 */
    1515
     
    174174}
    175175
    176                                 /* ignore preprocessor-style directives (for now) */
     176                                /* preprocessor-style directives */
    177177^{h_white}*"#"[^\n]*"\n" { RETURN_VAL( DIRECTIVE ); }
    178178
  • src/Parser/parser.yy

    rf465f0e r779a4a3  
    1010// Created On       : Sat Sep  1 20:22:55 2001
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Sun Apr 29 14:20:17 2018
    13 // Update Count     : 3206
     12// Last Modified On : Thu May  3 08:20:09 2018
     13// Update Count     : 3225
    1414//
    1515
     
    877877        | asm_statement
    878878        | DIRECTIVE
    879                 { $$ = new StatementNode( build_dirstmt( $1 ) ); }
     879                { $$ = new StatementNode( build_directive( $1 ) ); }
    880880        ;
    881881
     
    12071207asm_statement:
    12081208        ASM asm_volatile_opt '(' string_literal ')' ';'
    1209                 { $$ = new StatementNode( build_asmstmt( $2, $4, 0 ) ); }
     1209                { $$ = new StatementNode( build_asm( $2, $4, 0 ) ); }
    12101210        | ASM asm_volatile_opt '(' string_literal ':' asm_operands_opt ')' ';' // remaining GCC
    1211                 { $$ = new StatementNode( build_asmstmt( $2, $4, $6 ) ); }
     1211                { $$ = new StatementNode( build_asm( $2, $4, $6 ) ); }
    12121212        | ASM asm_volatile_opt '(' string_literal ':' asm_operands_opt ':' asm_operands_opt ')' ';'
    1213                 { $$ = new StatementNode( build_asmstmt( $2, $4, $6, $8 ) ); }
     1213                { $$ = new StatementNode( build_asm( $2, $4, $6, $8 ) ); }
    12141214        | ASM asm_volatile_opt '(' string_literal ':' asm_operands_opt ':' asm_operands_opt ':' asm_clobbers_list_opt ')' ';'
    1215                 { $$ = new StatementNode( build_asmstmt( $2, $4, $6, $8, $10 ) ); }
     1215                { $$ = new StatementNode( build_asm( $2, $4, $6, $8, $10 ) ); }
    12161216        | ASM asm_volatile_opt GOTO '(' string_literal ':' ':' asm_operands_opt ':' asm_clobbers_list_opt ':' label_list ')' ';'
    1217                 { $$ = new StatementNode( build_asmstmt( $2, $5, 0, $8, $10, $12 ) ); }
     1217                { $$ = new StatementNode( build_asm( $2, $5, 0, $8, $10, $12 ) ); }
    12181218        ;
    12191219
     
    24052405        | ASM '(' string_literal ')' ';'                                        // GCC, global assembler statement
    24062406                {
    2407                         $$ = DeclarationNode::newAsmStmt( new StatementNode( build_asmstmt( false, $3, 0 ) ) );
     2407                        $$ = DeclarationNode::newAsmStmt( new StatementNode( build_asm( false, $3, 0 ) ) );
    24082408                }
    24092409        | EXTERN STRINGliteral                                                          // C++-style linkage specifier
     
    24512451        | declaration_qualifier_list type_qualifier_list
    24522452                {
    2453                         if ( $1->type->forall ) xxx = forall = true; // remember generic type
     2453                        // forall must be in the type_qualifier_list
     2454                        if ( $2->type->forall ) xxx = forall = true; // remember generic type
    24542455                }
    24552456          push '{' external_definition_list '}'                         // CFA, namespace
  • src/ResolvExpr/AlternativeFinder.cc

    rf465f0e r779a4a3  
    459459        /// Adds type variables to the open variable set and marks their assertions
    460460        void makeUnifiableVars( Type *type, OpenVarSet &unifiableVars, AssertionSet &needAssertions ) {
    461                 for ( Type::ForallList::const_iterator tyvar = type->get_forall().begin(); tyvar != type->get_forall().end(); ++tyvar ) {
     461                for ( Type::ForallList::const_iterator tyvar = type->forall.begin(); tyvar != type->forall.end(); ++tyvar ) {
    462462                        unifiableVars[ (*tyvar)->get_name() ] = TypeDecl::Data{ *tyvar };
    463                         for ( std::list< DeclarationWithType* >::iterator assert = (*tyvar)->get_assertions().begin(); assert != (*tyvar)->get_assertions().end(); ++assert ) {
     463                        for ( std::list< DeclarationWithType* >::iterator assert = (*tyvar)->assertions.begin(); assert != (*tyvar)->assertions.end(); ++assert ) {
    464464                                needAssertions[ *assert ].isUsed = true;
    465465                        }
  • src/ResolvExpr/AlternativeFinder.h

    rf465f0e r779a4a3  
    126126        void printAlts( const AltList &list, std::ostream &os, unsigned int indentAmt = 0 );
    127127
     128        /// Adds type variables to the open variable set and marks their assertions
     129        void makeUnifiableVars( Type *type, OpenVarSet &unifiableVars, AssertionSet &needAssertions );
     130
    128131        template< typename InputIterator >
    129132        void simpleCombineEnvironments( InputIterator begin, InputIterator end, TypeEnvironment &result ) {
  • src/ResolvExpr/Resolver.cc

    rf465f0e r779a4a3  
    544544                                                        OpenVarSet openVars;
    545545                                                        AssertionSet resultNeed, resultHave;
    546                                                         TypeEnvironment resultEnv;
     546                                                        TypeEnvironment resultEnv( func.env );
     547                                                        makeUnifiableVars( function, openVars, resultNeed );
     548                                                        // add all type variables as open variables now so that those not used in the parameter
     549                                                        // list are still considered open.
     550                                                        resultEnv.add( function->forall );
    547551
    548552                                                        // Load type variables from arguemnts into one shared space
     
    583587                                                                        ss << "' to '";
    584588                                                                        arg.expr->get_result()->print( ss );
     589                                                                        ss << "' with env '";
     590                                                                        resultEnv.print(ss);
    585591                                                                        ss << "'\n";
    586592                                                                        SemanticError( function, ss.str() );
  • src/SynTree/Mutator.h

    rf465f0e r779a4a3  
    3939        virtual Statement * mutate( ExprStmt * exprStmt ) = 0;
    4040        virtual Statement * mutate( AsmStmt * asmStmt ) = 0;
     41        virtual Statement * mutate( DirectiveStmt * dirStmt ) = 0;
    4142        virtual Statement * mutate( IfStmt * ifStmt ) = 0;
    4243        virtual Statement * mutate( WhileStmt * whileStmt ) = 0;
  • src/SynTree/Statement.cc

    rf465f0e r779a4a3  
    9494
    9595
     96DirectiveStmt::DirectiveStmt( const std::string & directive ) : Statement(), directive( directive ) {}
     97
     98void DirectiveStmt::print( std::ostream &os, Indenter ) const {
     99        os << "GCC Directive:" << directive << endl;
     100}
     101
     102
    96103const char *BranchStmt::brType[] = { "Goto", "Break", "Continue" };
    97104
  • src/SynTree/Statement.h

    rf465f0e r779a4a3  
    126126};
    127127
     128class DirectiveStmt : public Statement {
     129        public:
     130        std::string directive;
     131
     132        DirectiveStmt( const std::string & );
     133        virtual ~DirectiveStmt(){}
     134
     135        virtual DirectiveStmt * clone() const { return new DirectiveStmt( *this ); }
     136        virtual void accept( Visitor & v ) { v.visit( this ); }
     137        virtual Statement * acceptMutator( Mutator & m ) { return m.mutate( this ); }
     138        virtual void print( std::ostream & os, Indenter indent = {} ) const;
     139};
     140
    128141class IfStmt : public Statement {
    129142  public:
  • src/SynTree/SynTree.h

    rf465f0e r779a4a3  
    4444class ExprStmt;
    4545class AsmStmt;
     46class DirectiveStmt;
    4647class IfStmt;
    4748class WhileStmt;
  • src/SynTree/Visitor.h

    rf465f0e r779a4a3  
    4141        virtual void visit( ExprStmt * exprStmt ) = 0;
    4242        virtual void visit( AsmStmt * asmStmt ) = 0;
     43        virtual void visit( DirectiveStmt * directiveStmt ) = 0;
    4344        virtual void visit( IfStmt * ifStmt ) = 0;
    4445        virtual void visit( WhileStmt * whileStmt ) = 0;
  • src/benchmark/bench.h

    rf465f0e r779a4a3  
    66        #include <stdlib.h>
    77        #include <unistd.h>                                     // sysconf
    8         #include <sys/times.h>                                  // times
     8#if ! defined(__cforall)
    99        #include <time.h>
    10 #if defined(__cforall)
     10        #include <sys/time.h>
     11#else
    1112}
    12 //#include <bits/cfatime.h>
     13#include <time>
    1314#endif
    1415
    1516
    16 static inline unsigned long long int Time() {
     17static inline unsigned long long int bench_time() {
    1718    struct timespec ts;
    1819    clock_gettime(
     
    4142        }                                               \
    4243        long long int StartTime, EndTime;       \
    43         StartTime = Time();                     \
     44        StartTime = bench_time();               \
    4445        statement;                                      \
    45         EndTime = Time();                               \
     46        EndTime = bench_time();                 \
    4647        unsigned long long int output =         \
    4748        ( EndTime - StartTime ) / n;
    4849
    49 __cfa_time_t default_preemption() {
     50#if defined(__cforall)
     51Duration default_preemption() {
    5052        return 0;
    5153}
     54#endif
  • src/benchmark/ctxswitch/cfa_cor.c

    rf465f0e r779a4a3  
    11#include <stdio.h>
     2#include <kernel>
    23#include <thread>
    34
  • src/driver/Makefile.am

    rf465f0e r779a4a3  
    1111## Created On       : Sun May 31 08:49:31 2015
    1212## Last Modified By : Peter A. Buhr
    13 ## Last Modified On : Fri Oct 28 13:46:06 2016
    14 ## Update Count     : 10
     13## Last Modified On : Mon Apr 30 17:44:17 2018
     14## Update Count     : 11
    1515###############################################################################
    1616
    1717# applies to both programs
    18 AM_CXXFLAGS = -Wall -O2 -g -std=c++14
     18AM_CXXFLAGS = -Wall -O2 -g -std=c++14 -I${abs_top_srcdir}/src
    1919if BUILD_NO_LIB
    2020else
  • src/driver/Makefile.in

    rf465f0e r779a4a3  
    294294
    295295# applies to both programs
    296 AM_CXXFLAGS = -Wall -O2 -g -std=c++14 $(am__append_1) $(am__append_2) \
    297         $(am__append_3)
     296AM_CXXFLAGS = -Wall -O2 -g -std=c++14 -I${abs_top_srcdir}/src \
     297        $(am__append_1) $(am__append_2) $(am__append_3)
    298298cfa_SOURCES = cfa.cc
    299299
  • src/driver/cfa.cc

    rf465f0e r779a4a3  
    1010// Created On       : Tue Aug 20 13:44:49 2002
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Mon Feb  5 22:05:28 2018
    13 // Update Count     : 166
     12// Last Modified On : Wed May  2 17:57:43 2018
     13// Update Count     : 224
    1414//
    1515
     
    1919#include <unistd.h>                                                                             // execvp
    2020#include <string>                                                                               // STL version
    21 
     21#include <string.h>                                                                             // strcmp
     22
     23#include "Common/SemanticError.h"
    2224#include "config.h"                                                                             // configure info
    2325
     
    160162                                args[nargs] = argv[i];                                  // pass the argument along
    161163                                nargs += 1;
     164                        } else if ( arg == "-w" ) {
     165                                args[nargs] = argv[i];                                  // pass the argument along
     166                                nargs += 1;
     167                                args[nargs] = ( *new string( string("-D__CFA_FLAG__=") + arg ) ).c_str(); // add the argument for cfa-cpp
     168                                nargs += 1;
     169                        } else if ( prefix( arg, "-W" ) ) {                     // check before next tests
     170                                if ( arg == "-Werror" || arg == "-Wall" ) {
     171                                        args[nargs] = argv[i];                          // pass the argument along
     172                                        nargs += 1;
     173                                        args[nargs] = ( *new string( string("-D__CFA_FLAG__=") + arg ) ).c_str(); // add the argument for cfa-cpp
     174                                        nargs += 1;
     175                                } else {
     176                                        unsigned int adv = prefix( arg, "-Wno-" ) ? 5 : 2;
     177                                        args[nargs] = argv[i];                          // conditionally pass the argument along
     178                                        const char * warning = argv[i] + adv;     // extract warning
     179                                        if ( SemanticWarning_Exist( warning ) ) { // replace the argument for cfa-cpp
     180                                                args[nargs] = ( *new string( string("-D__CFA_FLAG__=") + arg ) ).c_str();
     181                                        } // if
     182                                        nargs += 1;
     183                                } // if
    162184                        } else if ( prefix( arg, "-B" ) ) {
    163185                                Bprefix = arg.substr(2);                                // strip the -B flag
     
    247269                #if ! defined(HAVE_LIBCFA_RELEASE)
    248270                        if( !debug ) {
    249                                 cerr << "error: Option -nodebug is not available, libcfa was not installed." << endl;
     271                                cerr << "error: Option -nodebug is unavailable, libcfa was not installed." << endl;
    250272                                exit( EXIT_FAILURE );
    251273                                }
     
    253275                #if ! defined(HAVE_LIBCFA_DEBUG)
    254276                        if( debug ) {
    255                                 cerr << "error: Option -debug is not available, libcfa-d was not installed." << endl;
     277                                cerr << "error: Option -debug is unavailable, libcfa-d was not installed." << endl;
    256278                                exit( EXIT_FAILURE );
    257279                                }
  • src/libcfa/concurrency/preemption.c

    rf465f0e r779a4a3  
    404404}
    405405
     406//=============================================================================================
     407// Kernel Signal Debug
     408//=============================================================================================
     409
     410void __cfaabi_check_preemption() {
     411        bool ready = TL_GET( preemption_state ).enabled;
     412        if(!ready) { abort("Preemption should be ready"); }
     413
     414        sigset_t oldset;
     415        int ret;
     416        ret = sigprocmask(0, NULL, &oldset);
     417        if(ret != 0) { abort("ERROR sigprocmask returned %d", ret); }
     418
     419        ret = sigismember(&oldset, SIGUSR1);
     420        if(ret <  0) { abort("ERROR sigismember returned %d", ret); }
     421
     422        if(ret == 1) { abort("ERROR SIGUSR1 is disabled"); }
     423}
     424
    406425// Local Variables: //
    407426// mode: c //
  • src/libcfa/concurrency/thread

    rf465f0e r779a4a3  
    2020
    2121#include "coroutine"
     22#include "kernel"
    2223#include "monitor"
    2324
  • src/libcfa/interpose.c

    rf465f0e r779a4a3  
    1010// Created On       : Wed Mar 29 16:10:31 2017
    1111// Last Modified By : Peter A. Buhr
    12 // Last Modified On : Thu Feb  8 16:18:09 2018
    13 // Update Count     : 75
     12// Last Modified On : Tue May  1 15:05:35 2018
     13// Update Count     : 83
    1414//
    1515
     
    9595void sigHandler_fpe  ( __CFA_SIGPARMS__ );
    9696void sigHandler_abort( __CFA_SIGPARMS__ );
     97void sigHandler_term ( __CFA_SIGPARMS__ );
    9798
    9899struct {
     
    114115                __cfaabi_sigaction( SIGFPE , sigHandler_fpe  , SA_SIGINFO ); // Failure handler
    115116                __cfaabi_sigaction( SIGABRT, sigHandler_abort, SA_SIGINFO ); // Failure handler
     117                __cfaabi_sigaction( SIGTERM, sigHandler_term , SA_SIGINFO ); // Failure handler
     118                __cfaabi_sigaction( SIGINT , sigHandler_term , SA_SIGINFO ); // Failure handler
    116119        }
    117120}
     
    268271}
    269272
     273void sigHandler_term( __CFA_SIGPARMS__ ) {
     274        abort( "Application stopped by %s signal.", sig == SIGINT ? "an interrupt (SIGINT)" : "a terminate (SIGTERM)" );
     275}
     276
    270277// Local Variables: //
    271278// mode: c //
  • src/main.cc

    rf465f0e r779a4a3  
    1 
    21//
    32// Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo
     
    1110// Created On       : Fri May 15 23:12:02 2015
    1211// Last Modified By : Peter A. Buhr
    13 // Last Modified On : Tue Oct 31 12:22:40 2017
    14 // Update Count     : 445
     12// Last Modified On : Wed May  2 14:59:02 2018
     13// Update Count     : 490
    1514//
    1615
     
    3534#include "CodeTools/DeclStats.h"            // for printDeclStats
    3635#include "CodeTools/TrackLoc.h"             // for fillLocations
     36#include "Common/CompilerError.h"           // for CompilerError
     37#include "Common/Heap.h"
    3738#include "Common/PassVisitor.h"
    38 #include "Common/CompilerError.h"           // for CompilerError
    3939#include "Common/SemanticError.h"           // for SemanticError
    4040#include "Common/UnimplementedError.h"      // for UnimplementedError
     
    175175        signal( SIGABRT, sigAbortHandler );
    176176
     177        // std::cout << "main" << std::endl;
     178        // for ( int i = 0; i < argc; i += 1 ) {
     179        //      std::cout << '\t' << argv[i] << std::endl;
     180        // } // for
     181
    177182        parse_cmdline( argc, argv, filename );                          // process command-line arguments
    178183        CodeGen::FixMain::setReplaceMain( !nomainp );
     
    354359                OPTPRINT( "end" )
    355360
     361
    356362                if ( output != &cout ) {
    357363                        delete output;
     
    384390
    385391        deleteAll( translationUnit );
     392        HeapStats::printStats();
    386393        return 0;
    387394} // main
     
    416423        opterr = 0;                                                                                     // (global) prevent getopt from printing error messages
    417424
     425        bool Werror = false;
    418426        int c;
    419         while ( (c = getopt_long( argc, argv, "abBcCdefgGlLmnNpqrstTvyzZD:F:", long_opts, &long_index )) != -1 ) {
     427        while ( (c = getopt_long( argc, argv, "abBcCdefgGlLmnNpqrstTvwW:yzZD:F:", long_opts, &long_index )) != -1 ) {
    420428                switch ( c ) {
    421429                  case Ast:
     
    453461                        yydebug = true;
    454462                        break;
    455                   case 'G':                   // dump AST after instantiate generics
     463                  case 'G':                                                                             // dump AST after instantiate generics
    456464                        genericsp = true;
    457465                        break;
     
    501509                  case 'v':                                                                             // dump AST after decl validation pass
    502510                        validp = true;
     511                        break;
     512                  case 'w':
     513                        SemanticWarning_SuppressAll();
     514                        break;
     515                  case 'W':
     516                        if ( strcmp( optarg, "all" ) == 0 ) {
     517                                SemanticWarning_EnableAll();
     518                        } else if ( strcmp( optarg, "error" ) == 0 ) {
     519                                Werror = true;
     520                        } else {
     521                                char * warning = optarg;
     522                                Severity s;
     523                                if ( strncmp( optarg, "no-", 3 ) == 0 ) {
     524                                        warning += 3;
     525                                        s = Severity::Suppress;
     526                                } else {
     527                                        s = Severity::Warn;
     528                                } // if
     529                                SemanticWarning_Set( warning, s );
     530                        } // if
    503531                        break;
    504532                  case 'y':                                                                             // dump AST on error
     
    530558                } // switch
    531559        } // while
     560
     561        if ( Werror ) {
     562                SemanticWarning_WarningAsError();
     563        } // if
     564        // for ( const auto w : WarningFormats ) {
     565        //      cout << w.name << ' ' << (int)w.severity << endl;
     566        // } // for
    532567} // parse_cmdline
    533568
  • src/tests/concurrent/examples/boundedBufferEXT.c

    rf465f0e r779a4a3  
    88// Created On       : Wed Apr 18 22:52:12 2018
    99// Last Modified By : Peter A. Buhr
    10 // Last Modified On : Fri Apr 20 22:25:14 2018
    11 // Update Count     : 6
     10// Last Modified On : Wed May  2 16:12:58 2018
     11// Update Count     : 7
    1212//
    1313
     
    2222enum { BufferSize = 50 };
    2323
    24 forall( otype T )
    25 monitor Buffer {
    26         int front, back, count;
    27         T elements[BufferSize];
    28 };
     24forall( otype T ) {
     25        monitor Buffer {
     26                int front, back, count;
     27                T elements[BufferSize];
     28        }; // Buffer
    2929
    30 forall( otype T )
    31 void ?{}( Buffer(T) & buffer ) with( buffer ) { [front, back, count] = 0; }
     30        void ?{}( Buffer(T) & buffer ) with( buffer ) { [front, back, count] = 0; }
    3231
    33 forall( otype T )
    34 int query( Buffer(T) & buffer ) { return buffer.count; }
     32        int query( Buffer(T) & buffer ) { return buffer.count; } // read-only, no mutual exclusion
    3533
    36 forall( otype T )                                                                               // forward
    37 T remove( Buffer(T) & mutex buffer );
     34        T remove( Buffer(T) & mutex buffer );                           // forward
    3835
    39 forall( otype T )
    40 void insert( Buffer(T) & mutex buffer, T elem ) with( buffer ) {
    41         if ( count == BufferSize ) waitfor( remove, buffer );
    42         elements[back] = elem;
    43         back = ( back + 1 ) % BufferSize;
    44         count += 1;
    45 }
     36        void insert( Buffer(T) & mutex buffer, T elem ) with( buffer ) {
     37                if ( count == BufferSize ) waitfor( remove, buffer );
     38                elements[back] = elem;
     39                back = ( back + 1 ) % BufferSize;
     40                count += 1;
     41        } // insert
    4642
    47 forall( otype T )
    48 T remove( Buffer(T) & mutex buffer ) with( buffer ) {
    49         if ( count == 0 ) waitfor( insert, buffer );
    50         T elem = elements[front];
    51         front = ( front + 1 ) % BufferSize;
    52         count -= 1;
    53         return elem;
     43        T remove( Buffer(T) & mutex buffer ) with( buffer ) {
     44                if ( count == 0 ) waitfor( insert, buffer );
     45                T elem = elements[front];
     46                front = ( front + 1 ) % BufferSize;
     47                count -= 1;
     48                return elem;
     49        } // remove
    5450}
    5551
  • src/tests/concurrent/examples/boundedBufferINT.c

    rf465f0e r779a4a3  
    88// Created On       : Mon Oct 30 12:45:13 2017
    99// Last Modified By : Peter A. Buhr
    10 // Last Modified On : Fri Apr 20 22:18:18 2018
    11 // Update Count     : 78
     10// Last Modified On : Thu Apr 26 23:08:17 2018
     11// Update Count     : 82
    1212//
    1313
     
    2222enum { BufferSize = 50 };
    2323
    24 forall( otype T )
    25 monitor Buffer {
    26         condition full, empty;
    27         int front, back, count;
    28         T elements[BufferSize];
    29 };
     24forall( otype T ) {
     25        monitor Buffer {
     26                condition full, empty;
     27                int front, back, count;
     28                T elements[BufferSize];
     29        }; // Buffer
    3030
    31 forall( otype T )
    32 void ?{}( Buffer(T) & buffer ) with( buffer ) { [front, back, count] = 0; }
     31        void ?{}( Buffer(T) & buffer ) with( buffer ) { [front, back, count] = 0; }
    3332
    34 forall( otype T )
    35 int query( Buffer(T) & buffer ) { return buffer.count; }
     33        int query( Buffer(T) & buffer ) { return buffer.count; } // read-only, no mutual exclusion
    3634
    37 forall( otype T )
    38 void insert( Buffer(T) & mutex buffer, T elem ) with( buffer ) {
    39         if ( count == BufferSize ) wait( empty );
    40         elements[back] = elem;
    41         back = ( back + 1 ) % BufferSize;
    42         count += 1;
    43         signal( full );
    44 }
     35        void insert( Buffer(T) & mutex buffer, T elem ) with( buffer ) {
     36                if ( count == BufferSize ) wait( empty );
     37                elements[back] = elem;
     38                back = ( back + 1 ) % BufferSize;
     39                count += 1;
     40                signal( full );
     41        } // insert
    4542
    46 forall( otype T )
    47 T remove( Buffer(T) & mutex buffer ) with( buffer ) {
    48         if ( count == 0 ) wait( full );
    49         T elem = elements[front];
    50         front = ( front + 1 ) % BufferSize;
    51         count -= 1;
    52         signal( empty );
    53         return elem;
     43        T remove( Buffer(T) & mutex buffer ) with( buffer ) {
     44                if ( count == 0 ) wait( full );
     45                T elem = elements[front];
     46                front = ( front + 1 ) % BufferSize;
     47                count -= 1;
     48                signal( empty );
     49                return elem;
     50        } // remove
    5451}
    5552
  • src/tests/concurrent/preempt.c

    rf465f0e r779a4a3  
    1717#endif
    1818
     19extern void __cfaabi_check_preemption();
     20
    1921static volatile int counter = 0;
    2022
     
    2931void main(worker_t & this) {
    3032        while(counter < N) {
     33                __cfaabi_check_preemption();
    3134                if( (counter % 7) == this.value ) {
     35                        __cfaabi_check_preemption();
    3236                        int next = __atomic_add_fetch_4(&counter, 1, __ATOMIC_SEQ_CST);
     37                        __cfaabi_check_preemption();
    3338                        if( (next % 100) == 0 ) printf("%d\n", (int)next);
     39                        __cfaabi_check_preemption();
    3440                }
     41                __cfaabi_check_preemption();
    3542        }
    3643}
Note: See TracChangeset for help on using the changeset viewer.