source: src/Parser/TypeData.cc @ 4e2b9710

aaron-thesisarm-ehcleanup-dtorsctordeferred_resndemanglerenumforall-pointer-decayjacob/cs343-translationjenkins-sandboxnew-astnew-ast-unique-exprnew-envno_listpersistent-indexerpthread-emulationqualifiedEnumresolv-newwith_gc
Last change on this file since 4e2b9710 was 4e2b9710, checked in by Peter A. Buhr <pabuhr@…>, 6 years ago

Merge branch 'master' of plg2:software/cfa/cfa-cc

  • Property mode set to 100644
File size: 28.9 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// TypeData.cc --
8//
9// Author           : Rodolfo G. Esteves
10// Created On       : Sat May 16 15:12:51 2015
11// Last Modified By : Peter A. Buhr
12// Last Modified On : Wed Aug 24 13:46:55 2016
13// Update Count     : 69
14//
15
16#include <cassert>
17#include <algorithm>
18#include <iterator>
19#include "Common/utility.h"
20#include "TypeData.h"
21#include "SynTree/Type.h"
22#include "SynTree/Declaration.h"
23#include "SynTree/Expression.h"
24#include "SynTree/Statement.h"
25#include "SynTree/Initializer.h"
26
27TypeData::TypeData( Kind k ) : kind( k ), base( 0 ), forall( 0 ) {
28        switch ( kind ) {
29          case Unknown:
30          case Pointer:
31          case EnumConstant:
32                // nothing else to initialize
33                break;
34          case Basic:
35                basic = new Basic_t;
36                break;
37          case Array:
38                array = new Array_t;
39                array->dimension = 0;
40                array->isVarLen = false;
41                array->isStatic = false;
42                break;
43          case Function:
44                function = new Function_t;
45                function->params = 0;
46                function->idList = 0;
47                function->oldDeclList = 0;
48                function->body = 0;
49                function->hasBody = false;
50                function->newStyle = false;
51                break;
52          case Aggregate:
53                aggregate = new Aggregate_t;
54                aggregate->params = 0;
55                aggregate->actuals = 0;
56                aggregate->fields = 0;
57                break;
58          case AggregateInst:
59                aggInst = new AggInst_t;
60                aggInst->aggregate = 0;
61                aggInst->params = 0;
62                break;
63          case Enum:
64                enumeration = new Enumeration_t;
65                enumeration->constants = 0;
66                break;
67          case Symbolic:
68          case SymbolicInst:
69                symbolic = new Symbolic_t;
70                symbolic->params = 0;
71                symbolic->actuals = 0;
72                symbolic->assertions = 0;
73                break;
74          case Variable:
75                variable = new Variable_t;
76                variable->tyClass = DeclarationNode::Type;
77                variable->assertions = 0;
78                break;
79          case Tuple:
80                tuple = new Tuple_t;
81                tuple->members = 0;
82                break;
83          case Typeof:
84                typeexpr = new Typeof_t;
85                typeexpr->expr = 0;
86                break;
87          case Builtin:
88                builtin = new Builtin_t;
89                break;
90          case Attr:
91                attr = new Attr_t;
92                attr->expr = 0;
93                attr->type = 0;
94                break;
95        } // switch
96}
97
98TypeData::~TypeData() {
99        delete base;
100        delete forall;
101
102        switch ( kind ) {
103          case Unknown:
104          case Pointer:
105          case EnumConstant:
106                // nothing to destroy
107                break;
108          case Basic:
109                delete basic;
110                break;
111          case Array:
112                delete array->dimension;
113                delete array;
114                break;
115          case Function:
116                delete function->params;
117                delete function->idList;
118                delete function->oldDeclList;
119                delete function->body;
120                delete function;
121                break;
122          case Aggregate:
123                delete aggregate->params;
124                delete aggregate->actuals;
125                delete aggregate->fields;
126                delete aggregate;
127                break;
128          case AggregateInst:
129                delete aggInst->aggregate;
130                delete aggInst->params;
131                delete aggInst;
132                break;
133          case Enum:
134                delete enumeration->constants;
135                delete enumeration;
136                break;
137          case Symbolic:
138          case SymbolicInst:
139                delete symbolic->params;
140                delete symbolic->actuals;
141                delete symbolic->assertions;
142                delete symbolic;
143                break;
144          case Variable:
145                delete variable->assertions;
146                delete variable;
147                break;
148          case Tuple:
149                delete tuple->members;
150                delete tuple;
151                break;
152          case Typeof:
153                delete typeexpr->expr;
154                delete typeexpr;
155                break;
156          case Builtin:
157                delete builtin;
158                break;
159          case Attr:
160                delete attr->expr;
161                delete attr->type;
162                delete attr;
163                break;
164        } // switch
165}
166
167TypeData *TypeData::clone() const {
168        TypeData *newtype = new TypeData( kind );
169        newtype->qualifiers = qualifiers;
170        newtype->base = maybeClone( base );
171        newtype->forall = maybeClone( forall );
172
173        switch ( kind ) {
174          case Unknown:
175          case EnumConstant:
176          case Pointer:
177                // nothing else to copy
178                break;
179          case Basic:
180                newtype->basic->typeSpec = basic->typeSpec;
181                newtype->basic->modifiers = basic->modifiers;
182                break;
183          case Array:
184                newtype->array->dimension = maybeClone( array->dimension );
185                newtype->array->isVarLen = array->isVarLen;
186                newtype->array->isStatic = array->isStatic;
187                break;
188          case Function:
189                newtype->function->params = maybeClone( function->params );
190                newtype->function->idList = maybeClone( function->idList );
191                newtype->function->oldDeclList = maybeClone( function->oldDeclList );
192                newtype->function->body = maybeClone( function->body );
193                newtype->function->hasBody = function->hasBody;
194                newtype->function->newStyle = function->newStyle;
195                break;
196          case Aggregate:
197                newtype->aggregate->params = maybeClone( aggregate->params );
198                newtype->aggregate->actuals = maybeClone( aggregate->actuals );
199                newtype->aggregate->fields = maybeClone( aggregate->fields );
200                newtype->aggregate->name = aggregate->name;
201                newtype->aggregate->kind = aggregate->kind;
202                newtype->aggregate->body = aggregate->body;
203                break;
204          case AggregateInst:
205                newtype->aggInst->aggregate = maybeClone( aggInst->aggregate );
206                newtype->aggInst->params = maybeClone( aggInst->params );
207                break;
208          case Enum:
209                newtype->enumeration->name = enumeration->name;
210                newtype->enumeration->constants = maybeClone( enumeration->constants );
211                break;
212          case Symbolic:
213          case SymbolicInst:
214                newtype->symbolic->params = maybeClone( symbolic->params );
215                newtype->symbolic->actuals = maybeClone( symbolic->actuals );
216                newtype->symbolic->assertions = maybeClone( symbolic->assertions );
217                newtype->symbolic->isTypedef = symbolic->isTypedef;
218                newtype->symbolic->name = symbolic->name;
219                break;
220          case Variable:
221                newtype->variable->assertions = maybeClone( variable->assertions );
222                newtype->variable->name = variable->name;
223                newtype->variable->tyClass = variable->tyClass;
224                break;
225          case Tuple:
226                newtype->tuple->members = maybeClone( tuple->members );
227                break;
228          case Typeof:
229                newtype->typeexpr->expr = maybeClone( typeexpr->expr );
230                break;
231          case Builtin:
232                newtype->builtin->type = builtin->type;
233                break;
234          case Attr:
235                newtype->attr->expr = maybeClone( attr->expr );
236                newtype->attr->type = maybeClone( attr->type );
237                break;
238        } // switch
239        return newtype;
240}
241
242void TypeData::print( std::ostream &os, int indent ) const {
243        using std::endl;
244        using std::string;
245
246        for ( int i = 0; i < DeclarationNode::NoOfQualifier; i += 1 ) {
247                if ( qualifiers[i] ) os << DeclarationNode::qualifierName[ i ] << ' ';
248        } // for
249
250        if ( forall ) {
251                os << "forall " << endl;
252                forall->printList( os, indent + 4 );
253        } // if
254
255        switch ( kind ) {
256          case Unknown:
257                os << "entity of unknown type ";
258                break;
259          case Pointer:
260                os << "pointer ";
261                if ( base ) {
262                        os << "to ";
263                        base->print( os, indent );
264                } // if
265                break;
266          case EnumConstant:
267                os << "enumeration constant ";
268                break;
269          case Basic:
270                printEnums( basic->modifiers.begin(), basic->modifiers.end(), DeclarationNode::modifierName, os );
271                printEnums( basic->typeSpec.begin(), basic->typeSpec.end(), DeclarationNode::basicTypeName, os );
272                break;
273          case Array:
274                if ( array->isStatic ) {
275                        os << "static ";
276                } // if
277                if ( array->dimension ) {
278                        os << "array of ";
279                        array->dimension->printOneLine( os, indent );
280                } else if ( array->isVarLen ) {
281                        os << "variable-length array of ";
282                } else {
283                        os << "open array of ";
284                } // if
285                if ( base ) {
286                        base->print( os, indent );
287                } // if
288                break;
289          case Function:
290                os << "function" << endl;
291                if ( function->params ) {
292                        os << string( indent + 2, ' ' ) << "with parameters " << endl;
293                        function->params->printList( os, indent + 4 );
294                } else {
295                        os << string( indent + 2, ' ' ) << "with no parameters " << endl;
296                } // if
297                if ( function->idList ) {
298                        os << string( indent + 2, ' ' ) << "with old-style identifier list " << endl;
299                        function->idList->printList( os, indent + 4 );
300                } // if
301                if ( function->oldDeclList ) {
302                        os << string( indent + 2, ' ' ) << "with old-style declaration list " << endl;
303                        function->oldDeclList->printList( os, indent + 4 );
304                } // if
305                os << string( indent + 2, ' ' ) << "returning ";
306                if ( base ) {
307                        base->print( os, indent + 4 );
308                } else {
309                        os << "nothing ";
310                } // if
311                os << endl;
312                if ( function->hasBody ) {
313                        os << string( indent + 2, ' ' ) << "with body " << endl;
314                } // if
315                if ( function->body ) {
316                        function->body->printList( os, indent + 2 );
317                } // if
318                break;
319          case Aggregate:
320                os << DeclarationNode::aggregateName[ aggregate->kind ] << ' ' << aggregate->name << endl;
321                if ( aggregate->params ) {
322                        os << string( indent + 2, ' ' ) << "with type parameters " << endl;
323                        aggregate->params->printList( os, indent + 4 );
324                } // if
325                if ( aggregate->actuals ) {
326                        os << string( indent + 2, ' ' ) << "instantiated with actual parameters " << endl;
327                        aggregate->actuals->printList( os, indent + 4 );
328                } // if
329                if ( aggregate->fields ) {
330                        os << string( indent + 2, ' ' ) << "with members " << endl;
331                        aggregate->fields->printList( os, indent + 4 );
332                } // if
333                if ( aggregate->body ) {
334                        os << string( indent + 2, ' ' ) << " with body " << endl;
335                } // if
336                break;
337          case AggregateInst:
338                if ( aggInst->aggregate ) {
339                        os << "instance of " ;
340                        aggInst->aggregate->print( os, indent );
341                } else {
342                        os << "instance of an unspecified aggregate ";
343                } // if
344                if ( aggInst->params ) {
345                        os << string( indent + 2, ' ' ) << "with parameters " << endl;
346                        aggInst->params->printList( os, indent + 2 );
347                } // if
348                break;
349          case Enum:
350                os << "enumeration ";
351                if ( enumeration->constants ) {
352                        os << "with constants" << endl;
353                        enumeration->constants->printList( os, indent + 2 );
354                } // if
355                break;
356          case SymbolicInst:
357                os << "instance of type " << symbolic->name;
358                if ( symbolic->actuals ) {
359                        os << " with parameters" << endl;
360                        symbolic->actuals->printList( os, indent + 2 );
361                } // if
362                break;
363          case Symbolic:
364                if ( symbolic->isTypedef ) {
365                        os << "typedef definition ";
366                } else {
367                        os << "type definition ";
368                } // if
369                if ( symbolic->params ) {
370                        os << endl << string( indent + 2, ' ' ) << "with parameters" << endl;
371                        symbolic->params->printList( os, indent + 2 );
372                } // if
373                if ( symbolic->assertions ) {
374                        os << endl << string( indent + 2, ' ' ) << "with assertions" << endl;
375                        symbolic->assertions->printList( os, indent + 4 );
376                        os << string( indent + 2, ' ' );
377                } // if
378                if ( base ) {
379                        os << "for ";
380                        base->print( os, indent + 2 );
381                } // if
382                break;
383          case Variable:
384                os << DeclarationNode::typeClassName[ variable->tyClass ] << " variable ";
385                if ( variable->assertions ) {
386                        os << endl << string( indent + 2, ' ' ) << "with assertions" << endl;
387                        variable->assertions->printList( os, indent + 4 );
388                        os << string( indent + 2, ' ' );
389                } // if
390                break;
391          case Tuple:
392                os << "tuple ";
393                if ( tuple->members ) {
394                        os << "with members " << endl;
395                        tuple->members->printList( os, indent + 2 );
396                } // if
397                break;
398          case Typeof:
399                os << "type-of expression ";
400                if ( typeexpr->expr ) {
401                        typeexpr->expr->print( os, indent + 2 );
402                } // if
403                break;
404          case Attr:
405                os << "attribute type decl " << attr->name << " applied to ";
406                if ( attr->expr ) {
407                        attr->expr->print( os, indent + 2 );
408                } // if
409                if ( attr->type ) {
410                        attr->type->print( os, indent + 2 );
411                } // if
412                break;
413          case Builtin:
414                os << "gcc builtin type";
415                break;
416          default:
417                os << "internal error: TypeData::print " << kind  << endl;
418                assert( false );
419        } // switch
420}
421
422TypeData *TypeData::extractAggregate( bool toplevel ) const {
423        TypeData *ret = 0;
424
425        switch ( kind ) {
426          case Aggregate:
427                if ( ! toplevel && aggregate->fields ) {
428                        ret = clone();
429//                      ret->qualifiers.reset();
430                } // if
431                break;
432          case Enum:
433                if ( ! toplevel && enumeration->constants ) {
434                        ret = clone();
435//                      ret->qualifiers.reset();
436                } // if
437                break;
438          case AggregateInst:
439                if ( aggInst->aggregate ) {
440                        ret = aggInst->aggregate->extractAggregate( false );
441                } // if
442                break;
443          default:
444                if ( base ) {
445                        ret = base->extractAggregate( false );
446                } // if
447        } // switch
448        return ret;
449}
450
451void buildForall( const DeclarationNode *firstNode, std::list< TypeDecl* > &outputList ) {
452        buildList( firstNode, outputList );
453        for ( std::list< TypeDecl* >::iterator i = outputList.begin(); i != outputList.end(); ++i ) {
454                if ( (*i)->get_kind() == TypeDecl::Any ) {
455                        // add assertion parameters to `type' tyvars in reverse order
456                        // add dtor:  void ^?{}(T *)
457                        FunctionType *dtorType = new FunctionType( Type::Qualifiers(), false );
458                        dtorType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new PointerType( Type::Qualifiers(), new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ) ), 0 ) );
459                        (*i)->get_assertions().push_front( new FunctionDecl( "^?{}", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, dtorType, 0, false, false ) );
460
461                        // add copy ctor:  void ?{}(T *, T)
462                        FunctionType *copyCtorType = new FunctionType( Type::Qualifiers(), false );
463                        copyCtorType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new PointerType( Type::Qualifiers(), new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ) ), 0 ) );
464                        copyCtorType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ), 0 ) );
465                        (*i)->get_assertions().push_front( new FunctionDecl( "?{}", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, copyCtorType, 0, false, false ) );
466
467                        // add default ctor:  void ?{}(T *)
468                        FunctionType *ctorType = new FunctionType( Type::Qualifiers(), false );
469                        ctorType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new PointerType( Type::Qualifiers(), new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ) ), 0 ) );
470                        (*i)->get_assertions().push_front( new FunctionDecl( "?{}", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, ctorType, 0, false, false ) );
471
472                        // add assignment operator:  T * ?=?(T *, T)
473                        FunctionType *assignType = new FunctionType( Type::Qualifiers(), false );
474                        assignType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new PointerType( Type::Qualifiers(), new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ) ), 0 ) );
475                        assignType->get_parameters().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ), 0 ) );
476                        assignType->get_returnVals().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new TypeInstType( Type::Qualifiers(), (*i)->get_name(), *i ), 0 ) );
477                        (*i)->get_assertions().push_front( new FunctionDecl( "?=?", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, assignType, 0, false, false ) );
478                } // if
479        } // for
480}
481
482Declaration *TypeData::buildDecl( std::string name, DeclarationNode::StorageClass sc, Expression *bitfieldWidth, bool isInline, bool isNoreturn, LinkageSpec::Spec linkage, Initializer *init ) const {
483        if ( kind == TypeData::Function ) {
484                FunctionDecl *decl;
485                if ( function->hasBody ) {
486                        if ( function->body ) {
487                                Statement *stmt = function->body->build();
488                                CompoundStmt *body = dynamic_cast< CompoundStmt* >( stmt );
489                                assert( body );
490                                decl = new FunctionDecl( name, sc, linkage, buildFunction(), body, isInline, isNoreturn );
491                        } else {
492                                // std::list< Label > ls;
493                                decl = new FunctionDecl( name, sc, linkage, buildFunction(), new CompoundStmt( std::list< Label >() ), isInline, isNoreturn );
494                        } // if
495                } else {
496                        decl = new FunctionDecl( name, sc, linkage, buildFunction(), 0, isInline, isNoreturn );
497                } // if
498                for ( DeclarationNode *cur = function->idList; cur != 0; cur = dynamic_cast< DeclarationNode* >( cur->get_next() ) ) {
499                        if ( cur->get_name() != "" ) {
500                                decl->get_oldIdents().insert( decl->get_oldIdents().end(), cur->get_name() );
501                        } // if
502                } // for
503                buildList( function->oldDeclList, decl->get_oldDecls() );
504                return decl;
505        } else if ( kind == TypeData::Aggregate ) {
506                return buildAggregate();
507        } else if ( kind == TypeData::Enum ) {
508                return buildEnum();
509        } else if ( kind == TypeData::Symbolic ) {
510                return buildSymbolic( name, sc );
511        } else if ( kind == TypeData::Variable ) {
512                return buildVariable();
513        } else {
514                return new ObjectDecl( name, sc, linkage, bitfieldWidth, build(), init, std::list< Attribute * >(),  isInline, isNoreturn );
515        } // if
516        return 0;
517}
518
519Type *TypeData::build() const {
520        switch ( kind ) {
521          case Unknown:
522                // fill in implicit int
523                return new BasicType( buildQualifiers(), BasicType::SignedInt );
524          case Basic:
525                return buildBasicType();
526          case Pointer:
527                return buildPointer();
528          case Array:
529                return buildArray();
530          case Function:
531                return buildFunction();
532          case AggregateInst:
533                return buildAggInst();
534          case EnumConstant:
535                // the name gets filled in later -- by SymTab::Validate
536                return new EnumInstType( buildQualifiers(), "" );
537          case SymbolicInst:
538                return buildSymbolicInst();;
539          case Tuple:
540                return buildTuple();
541          case Typeof:
542                return buildTypeof();
543          case Builtin:
544                return new VarArgsType( buildQualifiers() );
545          case Attr:
546                return buildAttr();
547          case Symbolic:
548          case Enum:
549          case Aggregate:
550          case Variable:
551                assert( false );
552        } // switch
553        return 0;
554}
555
556Type::Qualifiers TypeData::buildQualifiers() const {
557        Type::Qualifiers q;
558        q.isConst = qualifiers[ DeclarationNode::Const ];
559        q.isVolatile = qualifiers[ DeclarationNode::Volatile ];
560        q.isRestrict = qualifiers[ DeclarationNode::Restrict ];
561        q.isLvalue = qualifiers[ DeclarationNode::Lvalue ];
562        q.isAtomic = qualifiers[ DeclarationNode::Atomic ];;
563        return q;
564}
565
566Type *TypeData::buildBasicType() const {
567        static const BasicType::Kind kindMap[] = { BasicType::Char, BasicType::SignedInt, BasicType::Float, BasicType::Double,
568                                                                                           BasicType::Char /* void */, BasicType::Bool, BasicType::DoubleComplex,
569                                                                                           BasicType::DoubleImaginary };
570        bool init = false;
571        bool sawDouble = false;
572        bool sawSigned = false;
573        BasicType::Kind ret;
574
575        for ( std::list< DeclarationNode::BasicType >::const_iterator i = basic->typeSpec.begin(); i != basic->typeSpec.end(); ++i ) {
576                if ( ! init ) {
577                        init = true;
578                        if ( *i == DeclarationNode::Void ) {
579                                if ( basic->typeSpec.size() != 1 || ! basic->modifiers.empty() ) {
580                                        throw SemanticError( "invalid type specifier \"void\" in type: ", this );
581                                } else {
582                                        return new VoidType( buildQualifiers() );
583                                } // if
584                        } else {
585                                ret = kindMap[ *i ];
586                        } // if
587                } else {
588                        switch ( *i ) {
589                          case DeclarationNode::Float:
590                                if ( sawDouble ) {
591                                        throw SemanticError( "invalid type specifier \"float\" in type: ", this );
592                                } else {
593                                        switch ( ret ) {
594                                          case BasicType::DoubleComplex:
595                                                ret = BasicType::FloatComplex;
596                                                break;
597                                          case BasicType::DoubleImaginary:
598                                                ret = BasicType::FloatImaginary;
599                                                break;
600                                          default:
601                                                throw SemanticError( "invalid type specifier \"float\" in type: ", this );
602                                        } // switch
603                                } // if
604                                break;
605                          case DeclarationNode::Double:
606                                if ( sawDouble ) {
607                                        throw SemanticError( "duplicate type specifier \"double\" in type: ", this );
608                                } else {
609                                        switch ( ret ) {
610                                          case BasicType::DoubleComplex:
611                                          case BasicType::DoubleImaginary:
612                                                break;
613                                          default:
614                                                throw SemanticError( "invalid type specifier \"double\" in type: ", this );
615                                        } // switch
616                                } // if
617                                break;
618                          case DeclarationNode::Complex:
619                                switch ( ret ) {
620                                  case BasicType::Float:
621                                        ret = BasicType::FloatComplex;
622                                        break;
623                                  case BasicType::Double:
624                                        ret = BasicType::DoubleComplex;
625                                        break;
626                                  default:
627                                        throw SemanticError( "invalid type specifier \"_Complex\" in type: ", this );
628                                } // switch
629                                break;
630                          case DeclarationNode::Imaginary:
631                                switch ( ret ) {
632                                  case BasicType::Float:
633                                        ret = BasicType::FloatImaginary;
634                                        break;
635                                  case BasicType::Double:
636                                        ret = BasicType::DoubleImaginary;
637                                        break;
638                                  default:
639                                        throw SemanticError( "invalid type specifier \"_Imaginary\" in type: ", this );
640                                } // switch
641                                break;
642                          default:
643                                throw SemanticError( std::string( "invalid type specifier \"" ) + DeclarationNode::basicTypeName[ *i ] + "\" in type: ", this );
644                        } // switch
645                } // if
646                if ( *i == DeclarationNode::Double ) {
647                        sawDouble = true;
648                } // if
649        } // for
650
651        for ( std::list< DeclarationNode::Modifier >::const_iterator i = basic->modifiers.begin(); i != basic->modifiers.end(); ++i ) {
652                switch ( *i ) {
653                  case DeclarationNode::Long:
654                        if ( ! init ) {
655                                init = true;
656                                ret = BasicType::LongSignedInt;
657                        } else {
658                                switch ( ret ) {
659                                  case BasicType::SignedInt:
660                                        ret = BasicType::LongSignedInt;
661                                        break;
662                                  case BasicType::UnsignedInt:
663                                        ret = BasicType::LongUnsignedInt;
664                                        break;
665                                  case BasicType::LongSignedInt:
666                                        ret = BasicType::LongLongSignedInt;
667                                        break;
668                                  case BasicType::LongUnsignedInt:
669                                        ret = BasicType::LongLongUnsignedInt;
670                                        break;
671                                  case BasicType::Double:
672                                        ret = BasicType::LongDouble;
673                                        break;
674                                  case BasicType::DoubleComplex:
675                                        ret = BasicType::LongDoubleComplex;
676                                        break;
677                                  case BasicType::DoubleImaginary:
678                                        ret = BasicType::LongDoubleImaginary;
679                                        break;
680                                  default:
681                                        throw SemanticError( "invalid type modifier \"long\" in type: ", this );
682                                } // switch
683                        } // if
684                        break;
685                  case DeclarationNode::Short:
686                        if ( ! init ) {
687                                init = true;
688                                ret = BasicType::ShortSignedInt;
689                        } else {
690                                switch ( ret ) {
691                                  case BasicType::SignedInt:
692                                        ret = BasicType::ShortSignedInt;
693                                        break;
694                                  case BasicType::UnsignedInt:
695                                        ret = BasicType::ShortUnsignedInt;
696                                        break;
697                                  default:
698                                        throw SemanticError( "invalid type modifier \"short\" in type: ", this );
699                                } // switch
700                        } // if
701                        break;
702                  case DeclarationNode::Signed:
703                        if ( ! init ) {
704                                init = true;
705                                ret = BasicType::SignedInt;
706                        } else if ( sawSigned ) {
707                                throw SemanticError( "duplicate type modifer \"signed\" in type: ", this );
708                        } else {
709                                switch ( ret ) {
710                                  case BasicType::LongLongSignedInt:
711                                        ret = BasicType::LongLongUnsignedInt;
712                                        break;
713                                  case BasicType::LongSignedInt:
714                                        ret = BasicType::LongUnsignedInt;
715                                        break;
716                                  case BasicType::SignedInt:
717                                  case BasicType::ShortSignedInt:
718                                        break;
719                                  case BasicType::Char:
720                                        ret = BasicType::SignedChar;
721                                        break;
722                                  default:
723                                        throw SemanticError( "invalid type modifer \"signed\" in type: ", this );
724                                } // switch
725                        } // if
726                        break;
727                  case DeclarationNode::Unsigned:
728                        if ( ! init ) {
729                                init = true;
730                                ret = BasicType::UnsignedInt;
731                        } else if ( sawSigned ) {
732                                throw SemanticError( "invalid type modifer \"unsigned\" in type: ", this );
733                        } else {
734                                switch ( ret ) {
735                                  case BasicType::LongLongSignedInt:
736                                        ret = BasicType::LongLongUnsignedInt;
737                                        break;
738                                  case BasicType::LongSignedInt:
739                                        ret = BasicType::LongUnsignedInt;
740                                        break;
741                                  case BasicType::SignedInt:
742                                        ret = BasicType::UnsignedInt;
743                                        break;
744                                  case BasicType::ShortSignedInt:
745                                        ret = BasicType::ShortUnsignedInt;
746                                        break;
747                                  case BasicType::Char:
748                                        ret = BasicType::UnsignedChar;
749                                        break;
750                                  default:
751                                        throw SemanticError( "invalid type modifer \"unsigned\" in type: ", this );
752                                } // switch
753                        } // if
754                        break;
755                } // switch
756
757                if ( *i == DeclarationNode::Signed ) {
758                        sawSigned = true;
759                } // if
760        } // for
761
762        BasicType *bt;
763        if ( ! init ) {
764                bt = new BasicType( buildQualifiers(), BasicType::SignedInt );
765        } else {
766                bt = new BasicType( buildQualifiers(), ret );
767        } // if
768        buildForall( forall, bt->get_forall() );
769        return bt;
770}
771
772
773PointerType *TypeData::buildPointer() const {
774        PointerType *pt;
775        if ( base ) {
776                pt = new PointerType( buildQualifiers(), base->build() );
777        } else {
778                pt = new PointerType( buildQualifiers(), new BasicType( Type::Qualifiers(), BasicType::SignedInt ) );
779        } // if
780        buildForall( forall, pt->get_forall() );
781        return pt;
782}
783
784ArrayType *TypeData::buildArray() const {
785        ArrayType *at;
786        if ( base ) {
787                at = new ArrayType( buildQualifiers(), base->build(), maybeBuild< Expression >( array->dimension ),
788                                                        array->isVarLen, array->isStatic );
789        } else {
790                at = new ArrayType( buildQualifiers(), new BasicType( Type::Qualifiers(), BasicType::SignedInt ),
791                                                        maybeBuild< Expression >( array->dimension ), array->isVarLen, array->isStatic );
792        } // if
793        buildForall( forall, at->get_forall() );
794        return at;
795}
796
797FunctionType *TypeData::buildFunction() const {
798        assert( kind == Function );
799        bool hasEllipsis = function->params ? function->params->get_hasEllipsis() : true;
800        if ( ! function->params ) hasEllipsis = ! function->newStyle;
801        FunctionType *ft = new FunctionType( buildQualifiers(), hasEllipsis );
802        buildList( function->params, ft->get_parameters() );
803        buildForall( forall, ft->get_forall() );
804        if ( base ) {
805                switch ( base->kind ) {
806                  case Tuple:
807                        buildList( base->tuple->members, ft->get_returnVals() );
808                        break;
809                  default:
810                        ft->get_returnVals().push_back( dynamic_cast< DeclarationWithType* >( base->buildDecl( "", DeclarationNode::NoStorageClass, 0, false, false, LinkageSpec::Cforall ) ) );
811                } // switch
812        } else {
813                ft->get_returnVals().push_back( new ObjectDecl( "", DeclarationNode::NoStorageClass, LinkageSpec::Cforall, 0, new BasicType( Type::Qualifiers(), BasicType::SignedInt ), 0 ) );
814        } // if
815        return ft;
816}
817
818AggregateDecl *TypeData::buildAggregate() const {
819        assert( kind == Aggregate );
820        AggregateDecl *at;
821        switch ( aggregate->kind ) {
822          case DeclarationNode::Struct:
823                at = new StructDecl( aggregate->name );
824                buildForall( aggregate->params, at->get_parameters() );
825                break;
826          case DeclarationNode::Union:
827                at = new UnionDecl( aggregate->name );
828                buildForall( aggregate->params, at->get_parameters() );
829                break;
830          case DeclarationNode::Trait:
831                at = new TraitDecl( aggregate->name );
832                buildList( aggregate->params, at->get_parameters() );
833                break;
834          default:
835                assert( false );
836        } // switch
837
838        buildList( aggregate->fields, at->get_members() );
839        at->set_body( aggregate->body );
840
841        return at;
842}
843
844ReferenceToType *TypeData::buildAggInst() const {
845        assert( kind == AggregateInst );
846
847        ReferenceToType *ret;
848        if ( aggInst->aggregate->kind == Enum ) {
849                ret = new EnumInstType( buildQualifiers(), aggInst->aggregate->enumeration->name );
850        } else {
851                assert( aggInst->aggregate->kind == Aggregate );
852                switch ( aggInst->aggregate->aggregate->kind ) {
853                  case DeclarationNode::Struct:
854                        ret = new StructInstType( buildQualifiers(), aggInst->aggregate->aggregate->name );
855                        break;
856                  case DeclarationNode::Union:
857                        ret = new UnionInstType( buildQualifiers(), aggInst->aggregate->aggregate->name );
858                        break;
859                  case DeclarationNode::Trait:
860                        ret = new TraitInstType( buildQualifiers(), aggInst->aggregate->aggregate->name );
861                        break;
862                  default:
863                        assert( false );
864                } // switch
865        } // if
866        buildList( aggInst->params, ret->get_parameters() );
867        buildForall( forall, ret->get_forall() );
868        return ret;
869}
870
871NamedTypeDecl *TypeData::buildSymbolic( const std::string &name, DeclarationNode::StorageClass sc ) const {
872        assert( kind == Symbolic );
873        NamedTypeDecl *ret;
874        if ( symbolic->isTypedef ) {
875                ret = new TypedefDecl( name, sc, maybeBuild< Type >( base ) );
876        } else {
877                ret = new TypeDecl( name, sc, maybeBuild< Type >( base ), TypeDecl::Any );
878        } // if
879        buildList( symbolic->params, ret->get_parameters() );
880        buildList( symbolic->assertions, ret->get_assertions() );
881        return ret;
882}
883
884TypeDecl *TypeData::buildVariable() const {
885        assert( kind == Variable );
886        static const TypeDecl::Kind kindMap[] = { TypeDecl::Any, TypeDecl::Ftype, TypeDecl::Dtype };
887
888        TypeDecl *ret = new TypeDecl( variable->name, DeclarationNode::NoStorageClass, 0, kindMap[ variable->tyClass ] );
889        buildList( variable->assertions, ret->get_assertions() );
890        return ret;
891}
892
893EnumDecl *TypeData::buildEnum() const {
894        assert( kind == Enum );
895        EnumDecl *ret = new EnumDecl( enumeration->name );
896        buildList( enumeration->constants, ret->get_members() );
897        std::list< Declaration * >::iterator members = ret->get_members().begin();
898        for ( const DeclarationNode *cur = enumeration->constants; cur != nullptr; cur = dynamic_cast< DeclarationNode * >( cur->get_next() ), ++members ) {
899                if ( cur->has_enumeratorValue() ) {
900                        ObjectDecl *member = dynamic_cast< ObjectDecl * >(*members);
901                        member->set_init( new SingleInit( maybeMoveBuild< Expression >( cur->consume_enumeratorValue() ), std::list< Expression * >() ) );
902                } // if
903        } // for
904        return ret;
905}
906
907TypeInstType *TypeData::buildSymbolicInst() const {
908        assert( kind == SymbolicInst );
909        TypeInstType *ret = new TypeInstType( buildQualifiers(), symbolic->name, false );
910        buildList( symbolic->actuals, ret->get_parameters() );
911        buildForall( forall, ret->get_forall() );
912        return ret;
913}
914
915TupleType *TypeData::buildTuple() const {
916        assert( kind == Tuple );
917        TupleType *ret = new TupleType( buildQualifiers() );
918        buildTypeList( tuple->members, ret->get_types() );
919        buildForall( forall, ret->get_forall() );
920        return ret;
921}
922
923TypeofType *TypeData::buildTypeof() const {
924        assert( kind == Typeof );
925        assert( typeexpr );
926        assert( typeexpr->expr );
927        TypeofType *ret = new TypeofType( buildQualifiers(), typeexpr->expr->build() );
928        return ret;
929}
930
931AttrType *TypeData::buildAttr() const {
932        assert( kind == Attr );
933        assert( attr );
934        AttrType *ret;
935        if ( attr->expr ) {
936                ret = new AttrType( buildQualifiers(), attr->name, attr->expr->build() );
937        } else {
938                assert( attr->type );
939                ret = new AttrType( buildQualifiers(), attr->name, attr->type->buildType() );
940        } // if
941        return ret;
942}
943
944// Local Variables: //
945// tab-width: 4 //
946// mode: c++ //
947// compile-command: "make install" //
948// End: //
Note: See TracBrowser for help on using the repository browser.