source: src/Parser/TypeData.cc@ e0ff3e6

ADT aaron-thesis arm-eh ast-experimental cleanup-dtors ctor deferred_resn demangler enum forall-pointer-decay gc_noraii jacob/cs343-translation jenkins-sandbox memory new-ast new-ast-unique-expr new-env no_list persistent-indexer pthread-emulation qualifiedEnum resolv-new string with_gc
Last change on this file since e0ff3e6 was de62360d, checked in by Peter A. Buhr <pabuhr@…>, 10 years ago

fix computed goto, fixed -std=, implicit typedefs for enum and aggregates, add _Noreturn _Thread_local

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