source: src/SynTree/Type.h @ cf67057

ADTaaron-thesisarm-ehast-experimentalcleanup-dtorsdeferred_resndemanglerenumforall-pointer-decayjacob/cs343-translationjenkins-sandboxnew-astnew-ast-unique-exprnew-envno_listpersistent-indexerpthread-emulationqualifiedEnumresolv-newwith_gc
Last change on this file since cf67057 was 6013bd7, checked in by Peter A. Buhr <pabuhr@…>, 8 years ago

first attempt at named designators

  • Property mode set to 100644
File size: 23.0 KB
Line 
1//
2// Cforall Version 1.0.0 Copyright (C) 2015 University of Waterloo
3//
4// The contents of this file are covered under the licence agreement in the
5// file "LICENCE" distributed with Cforall.
6//
7// Type.h --
8//
9// Author           : Richard C. Bilson
10// Created On       : Mon May 18 07:44:20 2015
11// Last Modified By : Peter A. Buhr
12// Last Modified On : Thu Mar 23 16:16:36 2017
13// Update Count     : 149
14//
15
16#ifndef TYPE_H
17#define TYPE_H
18
19#include "BaseSyntaxNode.h"
20#include "Mutator.h"
21#include "SynTree.h"
22#include "Visitor.h"
23#include <strings.h>                                                                    // ffs
24
25class Type : public BaseSyntaxNode {
26  public:
27        // Simulate inheritance because union does not allow it.
28        // Bug in g++-4.9 prevents static field in union
29        //static const char * Names[];
30        #define BFCommon( BFType, N ) \
31                bool operator[]( unsigned int i ) const { return val & (1 << i); } \
32                bool any() const { return val != 0; } \
33                void reset() { val = 0; } \
34                int ffs() { return ::ffs( val ) - 1; } \
35                BFType operator&=( BFType other ) { \
36                        val &= other.val; return *this; \
37                } \
38                BFType operator&( BFType other ) const { \
39                        BFType q = other; \
40                        q &= *this; \
41                        return q; \
42                } \
43                BFType operator|=( BFType other ) { \
44                        val |= other.val; return *this; \
45                } \
46                BFType operator|( BFType other ) const { \
47                        BFType q = other; \
48                        q |= *this; \
49                        return q; \
50                } \
51                BFType operator-=( BFType other ) { \
52                        val &= ~other.val; return *this; \
53                } \
54                void print( std::ostream & os ) const { \
55                        if ( (*this).any() ) { \
56                                for ( unsigned int i = 0; i < N; i += 1 ) { \
57                                        if ( (*this)[i] ) { \
58                                                os << BFType##Names[i] << ' '; \
59                                        } \
60                                } \
61                        } \
62                }
63
64        // enum must remain in the same order as the corresponding bit fields.
65
66        enum { Inline = 1 << 0, Noreturn = 1 << 1, Fortran = 1 << 2, NumFuncSpecifier = 3 };
67        static const char * FuncSpecifiersNames[];
68        union FuncSpecifiers {
69                unsigned int val;
70                struct {
71                        bool is_inline : 1;
72                        bool is_noreturn : 1;
73                        bool is_fortran : 1;
74                };
75                FuncSpecifiers() : val( 0 ) {}
76                FuncSpecifiers( unsigned int val ) : val( val ) {}
77                // equality (==, !=) works implicitly on first field "val", relational operations are undefined.
78                BFCommon( FuncSpecifiers, NumFuncSpecifier )
79        }; // FuncSpecifiers
80
81        enum { Extern = 1 << 0, Static = 1 << 1, Auto = 1 << 2, Register = 1 << 3, Threadlocal = 1 << 4, NumStorageClass = 5 };
82        static const char * StorageClassesNames[];
83        union StorageClasses {
84                unsigned int val;
85                struct {
86                        bool is_extern : 1;
87                        bool is_static : 1;
88                        bool is_auto : 1;
89                        bool is_register : 1;
90                        bool is_threadlocal : 1;
91                };
92
93                StorageClasses() : val( 0 ) {}
94                StorageClasses( unsigned int val ) : val( val ) {}
95                // equality (==, !=) works implicitly on first field "val", relational operations are undefined.
96                BFCommon( StorageClasses, NumStorageClass )
97        }; // StorageClasses
98
99        enum { Const = 1 << 0, Restrict = 1 << 1, Volatile = 1 << 2, Lvalue = 1 << 3, Mutex = 1 << 4, Atomic = 1 << 5, NumTypeQualifier = 6 };
100        static const char * QualifiersNames[];
101        union Qualifiers {
102                enum { Mask = ~(Restrict | Lvalue) };
103                unsigned int val;
104                struct {
105                        bool is_const : 1;
106                        bool is_restrict : 1;
107                        bool is_volatile : 1;
108                        bool is_lvalue : 1;
109                        bool is_mutex : 1;
110                        bool is_atomic : 1;
111                };
112
113                Qualifiers() : val( 0 ) {}
114                Qualifiers( unsigned int val ) : val( val ) {}
115                // Complex comparisons provide implicit qualifier downcasting, e.g., T downcast to const T.
116                bool operator==( Qualifiers other ) const { return (val & Mask) == (other.val & Mask); }
117                bool operator!=( Qualifiers other ) const { return (val & Mask) != (other.val & Mask); }
118                bool operator<=( Qualifiers other ) const {
119                        return is_const    <= other.is_const        //Any non-const converts to const without cost
120                                        && is_volatile <= other.is_volatile     //Any non-volatile converts to volatile without cost
121                                        && is_mutex    >= other.is_mutex        //Any mutex converts to non-mutex without cost
122                                        && is_atomic   == other.is_atomic;      //No conversion from atomic to non atomic is free
123                }
124                bool operator<( Qualifiers other ) const { return *this != other && *this <= other; }
125                bool operator>=( Qualifiers other ) const { return ! (*this < other); }
126                bool operator>( Qualifiers other ) const { return *this != other && *this >= other; }
127                BFCommon( Qualifiers, NumTypeQualifier )
128        }; // Qualifiers
129
130        Type( const Qualifiers & tq, const std::list< Attribute * > & attributes );
131        Type( const Type & other );
132        virtual ~Type();
133
134        Qualifiers & get_qualifiers() { return tq; }
135        bool get_const() { return tq.is_const; }
136        bool get_volatile() { return tq.is_volatile; }
137        bool get_restrict() { return tq.is_restrict; }
138        bool get_lvalue() { return tq.is_lvalue; }
139        bool get_mutex() { return tq.is_mutex; }
140        bool get_atomic() { return tq.is_atomic; }
141        void set_const( bool newValue ) { tq.is_const = newValue; }
142        void set_volatile( bool newValue ) { tq.is_volatile = newValue; }
143        void set_restrict( bool newValue ) { tq.is_restrict = newValue; }
144        void set_lvalue( bool newValue ) { tq.is_lvalue = newValue; }
145        void set_mutex( bool newValue ) { tq.is_mutex = newValue; }
146        void set_atomic( bool newValue ) { tq.is_atomic = newValue; }
147
148        typedef std::list<TypeDecl *> ForallList;
149        ForallList& get_forall() { return forall; }
150
151        std::list< Attribute * >& get_attributes() { return attributes; }
152        const std::list< Attribute * >& get_attributes() const { return attributes; }
153
154        /// How many elemental types are represented by this type
155        virtual unsigned size() const { return 1; };
156        virtual bool isVoid() const { return size() == 0; }
157        virtual Type * getComponent( unsigned i ) { assertf( size() == 1 && i == 0, "Type::getComponent was called with size %d and index %d\n", size(), i ); return this; }
158
159        /// return type without outer pointers and arrays
160        Type *stripDeclarator();
161
162        virtual bool isComplete() const { return true; }
163
164        virtual Type *clone() const = 0;
165        virtual void accept( Visitor & v ) = 0;
166        virtual Type *acceptMutator( Mutator & m ) = 0;
167        virtual void print( std::ostream & os, int indent = 0 ) const;
168  private:
169        Qualifiers tq;
170        ForallList forall;
171        std::list< Attribute * > attributes;
172};
173
174extern Type::Qualifiers emptyQualifiers;                                // no qualifiers on constants
175
176class VoidType : public Type {
177  public:
178        VoidType( const Type::Qualifiers & tq, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
179
180        virtual unsigned size() const { return 0; };
181        virtual bool isComplete() const { return false; }
182
183        virtual VoidType *clone() const { return new VoidType( *this ); }
184        virtual void accept( Visitor & v ) { v.visit( this ); }
185        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
186        virtual void print( std::ostream & os, int indent = 0 ) const;
187};
188
189class BasicType : public Type {
190  public:
191        enum Kind {
192                Bool,
193                Char,
194                SignedChar,
195                UnsignedChar,
196                ShortSignedInt,
197                ShortUnsignedInt,
198                SignedInt,
199                UnsignedInt,
200                LongSignedInt,
201                LongUnsignedInt,
202                LongLongSignedInt,
203                LongLongUnsignedInt,
204                Float,
205                Double,
206                LongDouble,
207                FloatComplex,
208                DoubleComplex,
209                LongDoubleComplex,
210                FloatImaginary,
211                DoubleImaginary,
212                LongDoubleImaginary,
213                NUMBER_OF_BASIC_TYPES
214        };
215
216        static const char *typeNames[];                                         // string names for basic types, MUST MATCH with Kind
217
218        BasicType( const Type::Qualifiers & tq, Kind bt, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
219
220        Kind get_kind() { return kind; }
221        void set_kind( Kind newValue ) { kind = newValue; }
222
223        virtual BasicType *clone() const { return new BasicType( *this ); }
224        virtual void accept( Visitor & v ) { v.visit( this ); }
225        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
226        virtual void print( std::ostream & os, int indent = 0 ) const;
227
228        bool isInteger() const;
229  private:
230        Kind kind;
231};
232
233class PointerType : public Type {
234  public:
235        PointerType( const Type::Qualifiers & tq, Type *base, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
236        PointerType( const Type::Qualifiers & tq, Type *base, Expression *dimension, bool isVarLen, bool isStatic, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
237        PointerType( const PointerType& );
238        virtual ~PointerType();
239
240        Type *get_base() { return base; }
241        void set_base( Type *newValue ) { base = newValue; }
242        Expression *get_dimension() { return dimension; }
243        void set_dimension( Expression *newValue ) { dimension = newValue; }
244        bool get_isVarLen() { return isVarLen; }
245        void set_isVarLen( bool newValue ) { isVarLen = newValue; }
246        bool get_isStatic() { return isStatic; }
247        void set_isStatic( bool newValue ) { isStatic = newValue; }
248
249        virtual PointerType *clone() const { return new PointerType( *this ); }
250        virtual void accept( Visitor & v ) { v.visit( this ); }
251        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
252        virtual void print( std::ostream & os, int indent = 0 ) const;
253  private:
254        Type *base;
255
256        // In C99, pointer types can be qualified in many ways e.g., int f( int a[ static 3 ] )
257        Expression *dimension;
258        bool isVarLen;
259        bool isStatic;
260};
261
262class ArrayType : public Type {
263  public:
264        ArrayType( const Type::Qualifiers & tq, Type *base, Expression *dimension, bool isVarLen, bool isStatic, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
265        ArrayType( const ArrayType& );
266        virtual ~ArrayType();
267
268        Type *get_base() { return base; }
269        void set_base( Type *newValue ) { base = newValue; }
270        Expression *get_dimension() { return dimension; }
271        void set_dimension( Expression *newValue ) { dimension = newValue; }
272        bool get_isVarLen() { return isVarLen; }
273        void set_isVarLen( bool newValue ) { isVarLen = newValue; }
274        bool get_isStatic() { return isStatic; }
275        void set_isStatic( bool newValue ) { isStatic = newValue; }
276
277        virtual bool isComplete() const { return ! isVarLen; }
278
279        virtual ArrayType *clone() const { return new ArrayType( *this ); }
280        virtual void accept( Visitor & v ) { v.visit( this ); }
281        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
282        virtual void print( std::ostream & os, int indent = 0 ) const;
283  private:
284        Type *base;
285        Expression *dimension;
286        bool isVarLen;
287        bool isStatic;
288};
289
290class FunctionType : public Type {
291  public:
292        FunctionType( const Type::Qualifiers & tq, bool isVarArgs, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
293        FunctionType( const FunctionType& );
294        virtual ~FunctionType();
295
296        std::list<DeclarationWithType*> & get_returnVals() { return returnVals; }
297        std::list<DeclarationWithType*> & get_parameters() { return parameters; }
298        bool get_isVarArgs() const { return isVarArgs; }
299        void set_isVarArgs( bool newValue ) { isVarArgs = newValue; }
300        bool isTtype() const;
301
302        virtual FunctionType *clone() const { return new FunctionType( *this ); }
303        virtual void accept( Visitor & v ) { v.visit( this ); }
304        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
305        virtual void print( std::ostream & os, int indent = 0 ) const;
306  private:
307        std::list<DeclarationWithType*> returnVals;
308        std::list<DeclarationWithType*> parameters;
309
310        // Does the function accept a variable number of arguments following the arguments specified in the parameters list.
311        // This could be because of
312        // - an ellipsis in a prototype declaration
313        // - an unprototyped declaration
314        bool isVarArgs;
315};
316
317class ReferenceToType : public Type {
318  public:
319        ReferenceToType( const Type::Qualifiers & tq, const std::string & name, const std::list< Attribute * > & attributes );
320        ReferenceToType( const ReferenceToType & other );
321        virtual ~ReferenceToType();
322
323        const std::string & get_name() const { return name; }
324        void set_name( std::string newValue ) { name = newValue; }
325        std::list< Expression* >& get_parameters() { return parameters; }
326        bool get_hoistType() const { return hoistType; }
327        void set_hoistType( bool newValue ) { hoistType = newValue; }
328
329        virtual ReferenceToType *clone() const = 0;
330        virtual void accept( Visitor & v ) = 0;
331        virtual Type *acceptMutator( Mutator & m ) = 0;
332        virtual void print( std::ostream & os, int indent = 0 ) const;
333
334        virtual void lookup( const std::string & name, std::list< Declaration* > & foundDecls ) const {}
335  protected:
336        virtual std::string typeString() const = 0;
337        std::list< Expression* > parameters;
338        std::string name;
339  private:
340        bool hoistType;
341};
342
343class StructInstType : public ReferenceToType {
344        typedef ReferenceToType Parent;
345  public:
346        StructInstType( const Type::Qualifiers & tq, const std::string & name, const std::list< Attribute * > & attributes = std::list< Attribute * >()  ) : Parent( tq, name, attributes ), baseStruct( 0 ) {}
347        StructInstType( const Type::Qualifiers & tq, StructDecl * baseStruct, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
348        StructInstType( const StructInstType & other ) : Parent( other ), baseStruct( other.baseStruct ) {}
349
350        StructDecl *get_baseStruct() const { return baseStruct; }
351        void set_baseStruct( StructDecl *newValue ) { baseStruct = newValue; }
352
353        /// Accesses generic parameters of base struct (NULL if none such)
354        std::list<TypeDecl*> * get_baseParameters();
355
356        virtual bool isComplete() const;
357
358        /// Looks up the members of this struct named "name" and places them into "foundDecls".
359        /// Clones declarations into "foundDecls", caller responsible for freeing
360        void lookup( const std::string & name, std::list< Declaration* > & foundDecls ) const;
361
362        virtual StructInstType *clone() const { return new StructInstType( *this ); }
363        virtual void accept( Visitor & v ) { v.visit( this ); }
364        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
365
366        virtual void print( std::ostream & os, int indent = 0 ) const;
367  private:
368        virtual std::string typeString() const;
369
370        // this decl is not "owned" by the struct inst; it is merely a pointer to elsewhere in the tree,
371        // where the structure used in this type is actually defined
372        StructDecl *baseStruct;
373};
374
375class UnionInstType : public ReferenceToType {
376        typedef ReferenceToType Parent;
377  public:
378        UnionInstType( const Type::Qualifiers & tq, const std::string & name, const std::list< Attribute * > & attributes = std::list< Attribute * >()  ) : Parent( tq, name, attributes ), baseUnion( 0 ) {}
379        UnionInstType( const Type::Qualifiers & tq, UnionDecl * baseUnion, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
380        UnionInstType( const UnionInstType & other ) : Parent( other ), baseUnion( other.baseUnion ) {}
381
382        UnionDecl *get_baseUnion() const { return baseUnion; }
383        void set_baseUnion( UnionDecl * newValue ) { baseUnion = newValue; }
384
385        /// Accesses generic parameters of base union (NULL if none such)
386        std::list< TypeDecl * > * get_baseParameters();
387
388        virtual bool isComplete() const;
389
390        /// looks up the members of this union named "name" and places them into "foundDecls"
391        /// Clones declarations into "foundDecls", caller responsible for freeing
392        void lookup( const std::string & name, std::list< Declaration* > & foundDecls ) const;
393
394        virtual UnionInstType *clone() const { return new UnionInstType( *this ); }
395        virtual void accept( Visitor & v ) { v.visit( this ); }
396        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
397
398        virtual void print( std::ostream & os, int indent = 0 ) const;
399  private:
400        virtual std::string typeString() const;
401
402        // this decl is not "owned" by the union inst; it is merely a pointer to elsewhere in the tree,
403        // where the union used in this type is actually defined
404        UnionDecl *baseUnion;
405};
406
407class EnumInstType : public ReferenceToType {
408        typedef ReferenceToType Parent;
409  public:
410        EnumInstType( const Type::Qualifiers & tq, const std::string & name, const std::list< Attribute * > & attributes = std::list< Attribute * >()  ) : Parent( tq, name, attributes ) {}
411        EnumInstType( const Type::Qualifiers & tq, EnumDecl * baseEnum, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
412        EnumInstType( const EnumInstType & other ) : Parent( other ), baseEnum( other.baseEnum ) {}
413
414        EnumDecl *get_baseEnum() const { return baseEnum; }
415        void set_baseEnum( EnumDecl *newValue ) { baseEnum = newValue; }
416
417        virtual bool isComplete() const;
418
419        virtual EnumInstType *clone() const { return new EnumInstType( *this ); }
420        virtual void accept( Visitor & v ) { v.visit( this ); }
421        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
422  private:
423        virtual std::string typeString() const;
424
425        // this decl is not "owned" by the union inst; it is merely a pointer to elsewhere in the tree,
426        // where the union used in this type is actually defined
427        EnumDecl *baseEnum = nullptr;
428};
429
430class TraitInstType : public ReferenceToType {
431        typedef ReferenceToType Parent;
432  public:
433        TraitInstType( const Type::Qualifiers & tq, const std::string & name, const std::list< Attribute * > & attributes = std::list< Attribute * >()  ) : Parent( tq, name, attributes ) {}
434        TraitInstType( const TraitInstType & other );
435        ~TraitInstType();
436
437        std::list< Declaration* >& get_members() { return members; }
438
439        virtual bool isComplete() const;
440
441        virtual TraitInstType *clone() const { return new TraitInstType( *this ); }
442        virtual void accept( Visitor & v ) { v.visit( this ); }
443        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
444  private:
445        virtual std::string typeString() const;
446
447        // this member is filled in by the validate pass, which instantiates the members of the correponding
448        // aggregate with the actual type parameters specified for this use of the context
449        std::list< Declaration* > members;
450};
451
452class TypeInstType : public ReferenceToType {
453        typedef ReferenceToType Parent;
454  public:
455        TypeInstType( const Type::Qualifiers & tq, const std::string & name, TypeDecl *baseType, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
456        TypeInstType( const Type::Qualifiers & tq, const std::string & name, bool isFtype, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
457        TypeInstType( const TypeInstType & other );
458        ~TypeInstType();
459
460        TypeDecl *get_baseType() const { return baseType; }
461        void set_baseType( TypeDecl *newValue );
462        bool get_isFtype() const { return isFtype; }
463        void set_isFtype( bool newValue ) { isFtype = newValue; }
464
465        virtual bool isComplete() const;
466
467        virtual TypeInstType *clone() const { return new TypeInstType( *this ); }
468        virtual void accept( Visitor & v ) { v.visit( this ); }
469        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
470        virtual void print( std::ostream & os, int indent = 0 ) const;
471  private:
472        virtual std::string typeString() const;
473        // this decl is not "owned" by the type inst; it is merely a pointer to elsewhere in the tree,
474        // where the type used here is actually defined
475        TypeDecl *baseType;
476        bool isFtype;
477};
478
479class TupleType : public Type {
480  public:
481        TupleType( const Type::Qualifiers & tq, const std::list< Type * > & types = std::list< Type * >(), const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
482        TupleType( const TupleType& );
483        virtual ~TupleType();
484
485        typedef std::list<Type*> value_type;
486        typedef value_type::iterator iterator;
487
488        std::list<Type*>& get_types() { return types; }
489        virtual unsigned size() const { return types.size(); };
490
491        iterator begin() { return types.begin(); }
492        iterator end() { return types.end(); }
493
494        virtual Type * getComponent( unsigned i ) {
495                assertf( i < size(), "TupleType::getComponent: index %d must be less than size %d", i, size() );
496                return *(begin()+i);
497        }
498
499        // virtual bool isComplete() const { return true; } // xxx - not sure if this is right, might need to recursively check complete-ness
500
501        virtual TupleType *clone() const { return new TupleType( *this ); }
502        virtual void accept( Visitor & v ) { v.visit( this ); }
503        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
504        virtual void print( std::ostream & os, int indent = 0 ) const;
505  private:
506        std::list<Type*> types;
507};
508
509class TypeofType : public Type {
510  public:
511        TypeofType( const Type::Qualifiers & tq, Expression *expr, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
512        TypeofType( const TypeofType& );
513        virtual ~TypeofType();
514
515        Expression *get_expr() const { return expr; }
516        void set_expr( Expression *newValue ) { expr = newValue; }
517
518        virtual bool isComplete() const { assert( false ); return false; }
519
520        virtual TypeofType *clone() const { return new TypeofType( *this ); }
521        virtual void accept( Visitor & v ) { v.visit( this ); }
522        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
523        virtual void print( std::ostream & os, int indent = 0 ) const;
524  private:
525        Expression *expr;
526};
527
528class AttrType : public Type {
529  public:
530        AttrType( const Type::Qualifiers & tq, const std::string & name, Expression *expr, const std::list< Attribute * > & attributes = std::list< Attribute * >() );
531        AttrType( const Type::Qualifiers & tq, const std::string & name, Type *type, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
532        AttrType( const AttrType& );
533        virtual ~AttrType();
534
535        const std::string & get_name() const { return name; }
536        void set_name( const std::string & newValue ) { name = newValue; }
537        Expression *get_expr() const { return expr; }
538        void set_expr( Expression *newValue ) { expr = newValue; }
539        Type *get_type() const { return type; }
540        void set_type( Type *newValue ) { type = newValue; }
541        bool get_isType() const { return isType; }
542        void set_isType( bool newValue ) { isType = newValue; }
543
544        virtual bool isComplete() const { assert( false ); } // xxx - not sure what to do here
545
546        virtual AttrType *clone() const { return new AttrType( *this ); }
547        virtual void accept( Visitor & v ) { v.visit( this ); }
548        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
549        virtual void print( std::ostream & os, int indent = 0 ) const;
550  private:
551        std::string name;
552        Expression *expr;
553        Type *type;
554        bool isType;
555};
556
557/// Represents the GCC built-in varargs type
558class VarArgsType : public Type {
559  public:
560        VarArgsType();
561        VarArgsType( Type::Qualifiers tq, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
562
563        virtual bool isComplete() const{ return true; } // xxx - is this right?
564
565        virtual VarArgsType *clone() const { return new VarArgsType( *this ); }
566        virtual void accept( Visitor & v ) { v.visit( this ); }
567        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
568        virtual void print( std::ostream & os, int indent = 0 ) const;
569};
570
571/// Represents a zero constant
572class ZeroType : public Type {
573  public:
574        ZeroType();
575        ZeroType( Type::Qualifiers tq, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
576
577        virtual ZeroType *clone() const { return new ZeroType( *this ); }
578        virtual void accept( Visitor & v ) { v.visit( this ); }
579        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
580        virtual void print( std::ostream & os, int indent = 0 ) const;
581};
582
583/// Represents a one constant
584class OneType : public Type {
585  public:
586        OneType();
587        OneType( Type::Qualifiers tq, const std::list< Attribute * > & attributes = std::list< Attribute * >()  );
588
589        virtual OneType *clone() const { return new OneType( *this ); }
590        virtual void accept( Visitor & v ) { v.visit( this ); }
591        virtual Type *acceptMutator( Mutator & m ) { return m.mutate( this ); }
592        virtual void print( std::ostream & os, int indent = 0 ) const;
593};
594
595std::ostream & operator<<( std::ostream & out, const Type * type );
596
597#endif // TYPE_H
598
599// Local Variables: //
600// tab-width: 4 //
601// mode: c++ //
602// compile-command: "make install" //
603// End: //
Note: See TracBrowser for help on using the repository browser.